dev@glassfish.java.net

strange classloading issue with jersey and jaxb on glassfish v3

From: Jakub Podlesak <Jakub.Podlesak_at_Sun.COM>
Date: Fri, 25 Sep 2009 11:29:16 +0200

Hi all,

i am experiencing a strange classloading issue when trying to utilize
JAXB2.2 provided as GFv3 module in Jersey. It seems, that classes bundled
in a war file can without any issues access JAXB2.2 implementation classes from
the bundled module, but it does not apply for the underlying Jersey classes,
which are also bundled in a module withing GFv3.

I have attached a simple test case, where if you unzip and mvn package it, could be
deployed onto GFv3 (using the latest promoted GFv3 b65 from [1].

Then accesing resource [2] with your browser should give you st. like:

<p>FIND: javax.ws.rs.core.Application javax/ws/rs/core/Application.class
 <br> Class loader of class
    bundle://115.0:1/javax/ws/rs/core/Application.class
 <br> Context class loader
    bundle://115.0:1/javax/ws/rs/core/Application.class
<p>FIND: com.sun.jersey.api.container.ContainerFactory com/sun/jersey/api/container/ContainerFactory.class
 <br> Class loader of class
    bundle://91.0:1/com/sun/jersey/api/container/ContainerFactory.class
 <br> Context class loader
    bundle://91.0:1/com/sun/jersey/api/container/ContainerFactory.class
<p>FIND: com.sun.xml.bind.annotation.OverrideAnnotationOf com/sun/xml/bind/annotation/OverrideAnnotationOf.class
 <br> Class loader of class
    bundle://151.0:1/com/sun/xml/bind/annotation/OverrideAnnotationOf.class
 <br> Context class loader
    bundle://151.0:1/com/sun/xml/bind/annotation/OverrideAnnotationOf.class
<p>FIND: com.sun.xml.bind.v2.runtime.unmarshaller.UnmarshallerImpl com/sun/xml/bind/v2/runtime/unmarshaller/UnmarshallerImpl.class
 <br> Class loader of class
    bundle://151.0:1/com/sun/xml/bind/v2/runtime/unmarshaller/UnmarshallerImpl.class
 <br> Context class loader
    bundle://151.0:1/com/sun/xml/bind/v2/runtime/unmarshaller/UnmarshallerImpl.class
classforname succeeded

where the last line comes from:

        try {
            Class.forName("com.sun.xml.bind.annotation.OverrideAnnotationOf");

            out.println("classforname succeeded");
        } catch (ClassNotFoundException ex) {
            ex.printStackTrace(out);
        }

in Gaga.java source file.


Now the very same Class.forName statement is used also in Jersey code in JSONConfiguration.java:

    public static NaturalBuilder natural() {
        // this is to make sure people trying to use NATURAL notation will get clear message what is missing, when an old JAXB RI version is used
        try {
            Class.forName("com.sun.xml.bind.annotation.OverrideAnnotationOf");
        } catch (ClassNotFoundException ex) {
            Logger.getLogger(JSONConfiguration.class.getName()).log(Level.SEVERE, ImplMessages.ERROR_JAXB_RI_2_1_10_MISSING());
            throw new RuntimeException(ImplMessages.ERROR_JAXB_RI_2_1_10_MISSING());
        }
        return new NaturalBuilder(Notation.NATURAL);
    }

,
but there when starting the app, it ends up with the following in the server.log:

#|2009-09-25T10:53:14.423+0200|SEVERE|glassfish|com.sun.jersey.core.spi.component.ProviderFactory|_ThreadID=22;_ThreadName=Thread-3;|The provider class, class com.mycompany.JSONTrials.providers.JAXBContextResolver, could not be instantiated. Processing will continue but the class will not be utilized
java.lang.RuntimeException: [failed to localize] error.jaxb.ri.2.1.10.missing()
  at com.sun.jersey.api.json.JSONConfiguration.natural(JSONConfiguration.java:351)
  at com.mycompany.JSONTrials.providers.JAXBContextResolver.<init>(JAXBContextResolver.java:103)
  at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
  at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:39)
  at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:27)
  at java.lang.reflect.Constructor.newInstance(Constructor.java:513)
  at java.lang.Class.newInstance0(Class.java:355)
  at java.lang.Class.newInstance(Class.java:308)
  at com.sun.jersey.core.spi.component.ComponentConstructor._getInstance(ComponentConstructor.java:152)
  at com.sun.jersey.core.spi.component.ComponentConstructor.getInstance(ComponentConstructor.java:140)
  at com.sun.jersey.core.spi.component.ProviderFactory.__getComponentProvider(ProviderFactory.java:159)
  at com.sun.jersey.core.spi.component.ProviderFactory._getComponentProvider(ProviderFactory.java:152)
  at com.sun.jersey.core.spi.component.ioc.IoCProviderFactory._getComponentProvider(IoCProviderFactory.java:87)
  at com.sun.jersey.core.spi.component.ProviderFactory.getComponentProvider(ProviderFactory.java:146)
  at com.sun.jersey.core.spi.component.ProviderServices.getComponent(ProviderServices.java:185)
  at com.sun.jersey.core.spi.component.ProviderServices.getProviders(ProviderServices.java:95)
  at com.sun.jersey.core.spi.factory.ContextResolverFactory.<init>(ContextResolverFactory.java:78)
  at com.sun.jersey.server.impl.application.WebApplicationImpl.initiate(WebApplicationImpl.java:560)
  at com.sun.jersey.server.impl.application.WebApplicationImpl.initiate(WebApplicationImpl.java:420)
  at com.sun.jersey.spi.container.servlet.ServletContainer.initiate(ServletContainer.java:377)
  at com.sun.jersey.spi.container.servlet.ServletContainer$InternalWebComponent.initiate(ServletContainer.java:242)
  at com.sun.jersey.spi.container.servlet.WebComponent.load(WebComponent.java:466)
  at com.sun.jersey.spi.container.servlet.WebComponent.init(WebComponent.java:182)
  at com.sun.jersey.spi.container.servlet.ServletContainer.init(ServletContainer.java:281)
  at com.sun.jersey.spi.container.servlet.ServletContainer.init(ServletContainer.java:442)
  at javax.servlet.GenericServlet.init(GenericServlet.java:242)
  at org.apache.catalina.core.StandardWrapper.initServlet(StandardWrapper.java:1427)
  at org.apache.catalina.core.StandardWrapper.load(StandardWrapper.java:1230)
  at org.apache.catalina.core.StandardContext.loadOnStartup(StandardContext.java:5046)
  at org.apache.catalina.core.StandardContext.start(StandardContext.java:5319)
  at com.sun.enterprise.web.WebModule.start(WebModule.java:483)
  at org.apache.catalina.core.ContainerBase.addChildInternal(ContainerBase.java:928)
  at org.apache.catalina.core.ContainerBase.addChild(ContainerBase.java:912)
  at org.apache.catalina.core.StandardHost.addChild(StandardHost.java:694)
  at com.sun.enterprise.web.WebContainer.loadWebModule(WebContainer.java:1816)
  at com.sun.enterprise.web.WebContainer.loadWebModule(WebContainer.java:1520)
  at com.sun.enterprise.web.WebApplication.start(WebApplication.java:93)
  at org.glassfish.internal.data.EngineRef.start(EngineRef.java:126)
  at org.glassfish.internal.data.ModuleInfo.start(ModuleInfo.java:229)
  at org.glassfish.internal.data.ApplicationInfo.start(ApplicationInfo.java:214)
  at com.sun.enterprise.v3.server.ApplicationLifecycle.deploy(ApplicationLifecycle.java:307)
  at com.sun.enterprise.v3.server.ApplicationLifecycle.deploy(ApplicationLifecycle.java:172)
  at org.glassfish.deployment.admin.DeployCommand.execute(DeployCommand.java:270)
  at com.sun.enterprise.v3.admin.CommandRunnerImpl$4.execute(CommandRunnerImpl.java:403)
  at com.sun.enterprise.v3.admin.CommandRunnerImpl.doCommand(CommandRunnerImpl.java:418)
  at com.sun.enterprise.v3.admin.CommandRunnerImpl.doCommand(CommandRunnerImpl.java:505)
  at com.sun.enterprise.v3.admin.CommandRunnerImpl.doCommand(CommandRunnerImpl.java:138)
  at com.sun.enterprise.v3.admin.AdminAdapter.doCommand(AdminAdapter.java:355)
  at com.sun.enterprise.v3.admin.AdminAdapter.service(AdminAdapter.java:195)
  at com.sun.grizzly.tcp.http11.GrizzlyAdapter.service(GrizzlyAdapter.java:166)
  at com.sun.enterprise.v3.server.HK2Dispatcher.dispath(HK2Dispatcher.java:100)
  at com.sun.enterprise.v3.services.impl.ContainerMapper.service(ContainerMapper.java:217)
  at com.sun.grizzly.http.ProcessorTask.invokeAdapter(ProcessorTask.java:753)
  at com.sun.grizzly.http.ProcessorTask.doProcess(ProcessorTask.java:661)
  at com.sun.grizzly.http.ProcessorTask.process(ProcessorTask.java:914)
  at com.sun.grizzly.http.DefaultProtocolFilter.execute(DefaultProtocolFilter.java:166)
  at com.sun.grizzly.DefaultProtocolChain.executeProtocolFilter(DefaultProtocolChain.java:135)
  at com.sun.grizzly.DefaultProtocolChain.execute(DefaultProtocolChain.java:102)
  at com.sun.grizzly.DefaultProtocolChain.execute(DefaultProtocolChain.java:88)
  at com.sun.grizzly.http.HttpProtocolChain.execute(HttpProtocolChain.java:76)
  at com.sun.grizzly.ProtocolChainContextTask.doCall(ProtocolChainContextTask.java:53)
  at com.sun.grizzly.SelectionKeyContextTask.call(SelectionKeyContextTask.java:57)
  at com.sun.grizzly.ContextTask.run(ContextTask.java:69)
  at com.sun.grizzly.util.FixedThreadPool$BasicWorker.dowork(FixedThreadPool.java:379)
  at com.sun.grizzly.util.FixedThreadPool$BasicWorker.run(FixedThreadPool.java:360)
  at java.lang.Thread.run(Thread.java:619)
|#]


Could please someone explain, why the very same statement

Class.forName("com.sun.xml.bind.annotation.OverrideAnnotationOf")

has different results, and how to make Jersey bundle see the JAXB 2.2 classes?

Please note, that if i remove Jersey from GlassFish, and bundle the Jersey
jars with the war file, the proper JAXB 2.2 is resolved all right.

Thanks,

~Jakub


[1]http://download.java.net/glassfish/v3/promoted/
[2]http://localhost:8080/JSONTrials/webresources/gaga



-- 
Jakub Podlešák, Software Engineer                                                             
Web Services and Technologies, SUN Microsystems                                               
http://blogs.sun.com/japod