users@glassfish.java.net

Re: web app classloader not following spec, or...?

From: Jan Luehe <Jan.Luehe_at_Sun.COM>
Date: Thu, 20 Apr 2006 14:37:53 -0700

Hi Joseph,

Jan Luehe wrote On 04/20/06 11:46,:
> Hi Joseph,
>
> Joseph B. Ottinger wrote On 04/20/06 05:13,:
>
>> Okay, another silly question, focused on deployment on Glassfish B44.
>>
>> i have an ear structured something like this:
>>
>> ear1.ear
>> /META-INF/application.xml
>> /ejb1.jar
>> /util1.jar
>> /sitemesh-2.2.1.jar
>> /web1.war
>> /web2.war
>>
>> Now, each .war uses a .tld and a filter that's located in
>> sitemesh-2.2.1.jar. The META-INF/MANIFEST.MF for each .war refers to
>> sitemesh-2.2.1.jar via the Class-Path entry, which is supposed to be
>> supported when a .war is deployed in an .ear (see J2EE.8.2,
>> specifically J2EE.8.2.1, from the Java EE spec referred to from jcp.org.)
>>
>> However, the filter isn't loaded from the jar; deployment gives an
>> exception, saying that the class for the filter isn't found. In fact,
>> I have DWR installed up there too, and the DWR servlet isn't found
>> either - even though I've checked the logs and the logs show both
>> sitemesh and DWR in the classpath for the .wars. I haven't a clue
>> whether the TLD is going to be resolved - but if the filter can't
>> start and the web app doesn't deploy, that doesn't matter much.
>>
>> Again, according to J2EE.8.2, my understanding is that the web app
>> should be able to load filters/servlets/TLDs from libraries referred
>> to in the MANIFEST.MF file; perhaps I'm misunderstanding, and the
>> manifest entry only applies to NON-servlets/filters/TLDs, as perhaps
>> they need resources available to web-apps rather than being able to
>> stand alone.
>>
>> Can anyone clarify this for me?
>
>
> This should work.
>
> I just deployed a very simple EAR with this layout:
>
> 123.jar
> 123.war
> META-INF/application.xml
>
> where META-INF/application.xml lists the contained WAR as follows:
>
> <application ...>
> ...
> <module>
> <web>
> <web-uri>123.war</web-uri>
> <context-root>/123</context-root>
> </web>
> </module>
> </application>
>
> 123.war has this layout:
>
> META-INF/MANIFEST.MF
> WEB-INF/web.xml
>
> where WEB-INF/web.xml declares a servlet ("TestServlet") whose class
> file is contained inside 123.jar, which is referenced from 123.war's
> META-INF/MANIFEST.MF, as follows:
>
> Class-Path: 123.jar
>
> The EAR deploys fine, and when I access the servlet, the
> WebappClassLoader delegates to its EJBClassLoader parent, which contains
> 123.jar as one of its URL entries and therefore manages to resolve the
> "TestServlet" class (I get the following log entries when setting the
> "classloader" log level in my domain.xml to FINEST):

OK, here's an interesting twist:

When I

- add a taglib JAR ("mytaglib.jar") to my EAR,
- add to 123.war a JSP that references a TLD bundled in "mytaglib.jar",
- add "mytaglib.jar" to the Class-Path attribute in the
   META-INF/MANIFEST.MF of 123.war, and
- deploy the EAR and access the JSP in 123.war,

the TLD won't be found!

Here's the reason why:

The JAR files referenced in the Class-Path attribute of a WAR's
META-INF/MANIFEST.MF are loaded by the parent classloader of the WAR's
WebappClassLoader. That classloader is an instance of EJBClassLoader.

When the web container determines the TLDs accessible by a webapp, it
also walks up the delegation chain of the webapp's WebappClassLoader.
In doing so, it considers only classloaders that are instances of
URLClassLoader, and then calls those classloaders' getURLs() method
and examines the returned URLs for TLDs.

Unfortunately, EJBClassLoader is *not* an instance of URLClassLoader!
This means that in my example, the "123.jar" and "mytaglib.jar" files
loaded by the EJBClassLoader will not be searched for TLDs!

Loading any other resources (such as class files) from those JAR files
works just fine (as I was able to verify with my "TestServlet"), it is
only TLD resources that will not be found.

Can you please file an issue on GlassFish?

Thanks,


Jan


>
> [#|2006-04-21T02:26:09.413+0800|FINEST|sun-appserver-pe9.0|org.apache.catalina.loader.WebappClassLoader|
>
> _ThreadID=18;_ThreadName=httpWorkerThread-1024-0;ClassName=org.apache.catalina.loader.WebappClassLoader;
>
> MethodName=loadClass;_RequestID=6ecd3a3c-b782-482c-8c7e-35105a4cfe59;|loadClass(TestServlet,false)|#]
>
>
> [#|2006-04-21T02:26:09.414+0800|FINEST|sun-appserver-pe9.0|org.apache.catalina.loader.WebappClassLoader|
>
> _ThreadID=18;_ThreadName=httpWorkerThread-1024-0;ClassName=org.apache.catalina.loader.WebappClassLoader;
>
> MethodName=loadClass;_RequestID=6ecd3a3c-b782-482c-8c7e-35105a4cfe59;|
> Delegating to parent classloader1 EJBClassLoader :
> urlSet = [URLEntry :
> file:/space/luehe/ws/sjsas90/publish/glassfish/domains/domain1/applications/j2ee-apps/123/123.jar,
>
> URLEntry :
> file:/space/luehe/ws/sjsas90/publish/glassfish/domains/domain1/generated/ejb/j2ee-apps/123/]
>
>
> doneCalled = false
> Parent -> EJBClassLoader :
> urlSet = []
> doneCalled = false
> Parent -> java.net.URLClassLoader_at_dda25b
>
>
> Jan
>
>
>>
>> -----------------------------------------------------------------------
>> Joseph B. Ottinger http://enigmastation.com
>> Editor, http://www.TheServerSide.com joeo@enigmastation.com
>>
>> ---------------------------------------------------------------------
>> To unsubscribe, e-mail: users-unsubscribe_at_glassfish.dev.java.net
>> For additional commands, e-mail: users-help_at_glassfish.dev.java.net
>>
>
> ---------------------------------------------------------------------
> To unsubscribe, e-mail: users-unsubscribe_at_glassfish.dev.java.net
> For additional commands, e-mail: users-help_at_glassfish.dev.java.net
>