diff --git a/src/main/java/org/springframework/data/jpa/provider/JpaClassUtils.java b/src/main/java/org/springframework/data/jpa/provider/JpaClassUtils.java index 7b2ac83ce..54e023b4c 100644 --- a/src/main/java/org/springframework/data/jpa/provider/JpaClassUtils.java +++ b/src/main/java/org/springframework/data/jpa/provider/JpaClassUtils.java @@ -43,7 +43,11 @@ abstract class JpaClassUtils { * @return */ public static boolean isEntityManagerOfType(EntityManager em, String type) { - return isOfType(em, type, em.getDelegate().getClass().getClassLoader()); + Object delegate = em.getDelegate(); + if (delegate instanceof EntityManager) { + em = (EntityManager) delegate; + } + return isOfType(em, type, delegate.getClass().getClassLoader()); } public static boolean isMetamodelOfType(Metamodel metamodel, String type) { diff --git a/src/main/java/org/springframework/data/jpa/provider/PersistenceProvider.java b/src/main/java/org/springframework/data/jpa/provider/PersistenceProvider.java index ee4f6d19a..9bb7f00e3 100644 --- a/src/main/java/org/springframework/data/jpa/provider/PersistenceProvider.java +++ b/src/main/java/org/springframework/data/jpa/provider/PersistenceProvider.java @@ -44,6 +44,7 @@ import org.springframework.util.ConcurrentReferenceHashMap; * @author Oliver Gierke * @author Thomas Darimont * @author Mark Paluch + * @author Jens Schauder */ public enum PersistenceProvider implements QueryExtractor, ProxyIdAccessor { @@ -224,7 +225,7 @@ public enum PersistenceProvider implements QueryExtractor, ProxyIdAccessor { String OPENJPA_JPA_METAMODEL_TYPE = "org.apache.openjpa.persistence.meta.MetamodelImpl"; } - private static ConcurrentReferenceHashMap, PersistenceProvider> CACHE = new ConcurrentReferenceHashMap, PersistenceProvider>(); + static ConcurrentReferenceHashMap, PersistenceProvider> CACHE = new ConcurrentReferenceHashMap, PersistenceProvider>(); private final Iterable entityManagerClassNames; private final Iterable metamodelClassNames; diff --git a/src/test/java/org/springframework/data/jpa/provider/PersistenceProviderUnitTests.java b/src/test/java/org/springframework/data/jpa/provider/PersistenceProviderUnitTests.java index 78fcdfb58..62b4419f9 100644 --- a/src/test/java/org/springframework/data/jpa/provider/PersistenceProviderUnitTests.java +++ b/src/test/java/org/springframework/data/jpa/provider/PersistenceProviderUnitTests.java @@ -40,6 +40,7 @@ import org.springframework.util.ClassUtils; * * @author Thomas Darimont * @author Oliver Gierke + * @author Jens Schauder */ public class PersistenceProviderUnitTests { @@ -47,6 +48,9 @@ public class PersistenceProviderUnitTests { @Before public void setup() { + + PersistenceProvider.CACHE.clear(); + this.shadowingClassLoader = new ShadowingClassLoader(getClass().getClassLoader()); } @@ -80,12 +84,25 @@ public class PersistenceProviderUnitTests { assertThat(fromEntityManager(em), is(HIBERNATE)); } + @Test // DATAJPA-1379 + public void detectsProviderFromProxiedEntityManager() throws Exception { + + shadowingClassLoader.excludePackage("org.eclipse.persistence.jpa"); + + EntityManager em = mockProviderSpecificEntityManagerInterface(ECLIPSELINK_ENTITY_MANAGER_INTERFACE); + + EntityManager emProxy = Mockito.mock(EntityManager.class); + Mockito.when(emProxy.getDelegate()).thenReturn(em); + + assertThat(fromEntityManager(emProxy), is(ECLIPSELINK)); + } + private EntityManager mockProviderSpecificEntityManagerInterface(String interfaceName) throws ClassNotFoundException { Class providerSpecificEntityManagerInterface = InterfaceGenerator.generate(interfaceName, shadowingClassLoader, EntityManager.class); - EntityManager em = EntityManager.class.cast(Mockito.mock(providerSpecificEntityManagerInterface)); + EntityManager em = (EntityManager) Mockito.mock(providerSpecificEntityManagerInterface); Mockito.when(em.getDelegate()).thenReturn(em); // delegate is used to determine the classloader of the provider // specific interface, therefore we return the proxied // EntityManager.