5

Implementing a web service using Hiberate for persistence layer. Works great, with no errors. However, when I write a unit test to access the Dao an encounter this error when getting an instance of the ServiceRegistry:

ServiceRegistry sr = new ServiceRegistryBuilder().applySettings(
                    configuration.getProperties()).buildServiceRegistry();

Full stack trace:

java.util.ServiceConfigurationError: org.hibernate.integrator.spi.Integrator: Provider org.jadira.usertype.dateandtime.joda.integrator.UserTypeJodaTimeHibernateIntegrator could not be instantiated: java.lang.NoClassDefFoundError: org/jadira/usertype/dateandtime/shared/spi/AbstractVersionableUserType
    at java.util.ServiceLoader.fail(ServiceLoader.java:224)
    at java.util.ServiceLoader.access$100(ServiceLoader.java:181)
    at java.util.ServiceLoader$LazyIterator.next(ServiceLoader.java:377)
    at java.util.ServiceLoader$1.next(ServiceLoader.java:445)
    at org.hibernate.service.classloading.internal.ClassLoaderServiceImpl.loadJavaServices(ClassLoaderServiceImpl.java:236)
    at org.hibernate.integrator.internal.IntegratorServiceImpl.<init>(IntegratorServiceImpl.java:53)
    at org.hibernate.service.internal.BootstrapServiceRegistryImpl.<init>(BootstrapServiceRegistryImpl.java:80)
    at org.hibernate.service.internal.BootstrapServiceRegistryImpl.<init>(BootstrapServiceRegistryImpl.java:57)
    at org.hibernate.service.ServiceRegistryBuilder.<init>(ServiceRegistryBuilder.java:76)
    at com.dg.dao.SessionConfig.getSession(SessionConfig.java:26)
    at com.dg.dao.CustomerHibernate.doGetSingleById(CustomerHibernate.java:210)
    at com.dg.dao.CustomerHibernate.getCustomerByID(CustomerHibernate.java:44)
    at com.dg.dao.test.CustomerDaoTest.testCustomerDao(CustomerDaoTest.java:27)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:601)
    at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:47)
    at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:12)
    at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:44)
    at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:17)
    at org.junit.internal.runners.statements.RunBefores.evaluate(RunBefores.java:26)
    at org.springframework.test.context.junit4.statements.RunBeforeTestMethodCallbacks.evaluate(RunBeforeTestMethodCallbacks.java:74)
    at org.springframework.test.context.junit4.statements.RunAfterTestMethodCallbacks.evaluate(RunAfterTestMethodCallbacks.java:82)
    at org.springframework.test.context.junit4.statements.SpringRepeat.evaluate(SpringRepeat.java:72)
    at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.runChild(SpringJUnit4ClassRunner.java:231)
    at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:50)
    at org.junit.runners.ParentRunner$3.run(ParentRunner.java:238)
    at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:63)
    at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:236)
    at org.junit.runners.ParentRunner.access$000(ParentRunner.java:53)
    at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:229)
    at org.springframework.test.context.junit4.statements.RunBeforeTestClassCallbacks.evaluate(RunBeforeTestClassCallbacks.java:61)
    at org.springframework.test.context.junit4.statements.RunAfterTestClassCallbacks.evaluate(RunAfterTestClassCallbacks.java:70)
    at org.junit.runners.ParentRunner.run(ParentRunner.java:309)
    at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.run(SpringJUnit4ClassRunner.java:174)
    at org.eclipse.jdt.internal.junit4.runner.JUnit4TestReference.run(JUnit4TestReference.java:50)
    at org.eclipse.jdt.internal.junit.runner.TestExecution.run(TestExecution.java:38)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:467)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:683)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.run(RemoteTestRunner.java:390)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.main(RemoteTestRunner.java:197)
Caused by: java.lang.NoClassDefFoundError: org/jadira/usertype/dateandtime/shared/spi/AbstractVersionableUserType

I have verified that the class does not exist in the classpath. To correct that I need to get an older version of usertype.spi.

Question is, why would it try to utilize an older class file when unit testing but work absolutely fine when running the service in a container? Has anyone seen this issue before?

1 Answer 1

6

I figured out that this issue is caused by a clash among the following dependencies:

<dependency>
   <groupId>org.jadira.usertype</groupId>
   <artifactId>usertype.jodatime</artifactId>
   <version>2.0.1</version>
</dependency>

And

<dependency>
   <groupId>org.jadira.usertype</groupId>
   <artifactId>usertype.core</artifactId>
   <version>3.1.0.CR6</version>
</dependency>

The issue comes about in particular because both packages contain the PersistentDateTime class (although there are many other duplicate classes). Both instances of PersistentDateTime extend a class called AbstractVersionableUserType. The only thing is, the base classes here both reside in different packages. So, hibernate loads these types dynamically using reflection when creating the ServiceRegistry. The reason it bombs for junit is that hibernate is trying to load the PersistentDateTime class from the usertype.jodatime package and the actual class that needs to be loaded comes from the usertype.core package. It works in the container simply because there is a different classloader being used.

Anyway, when removing the usertype.jodatime dependency, everything works well.

Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.