Timothy Bennett wrote:

Here's something that I discovered yesterday about the classloader that
kinda surprised me.  Maybe some of you merlin contributors can comment on
it...

I have a container that deploys the Jetty-Phoenix block.  The classloader
for this container includes the jasper-compiler.jar, jasper-runtime.jar, and
the javax-servlet.jar in order to support JSPs.  The Jetty-Phoenix block
supports deployment of web applications.  I deployed a WAR in my
Jetty-Phoenix yesterday that included some JSP.  The JSP compiled fine, but
when the JSP was attempted to execute, it could not resolve classes in the
jasper-runtime or the servlet.jar.


Looking at the error message here it appears the the context classloader is not being supplied as the parent classloader to the jetty http context. I don't know much about jetty but based on a browse though the javadocs my guess is that you need to do something like:


 // create the web app context (using whatever approach your
 // currently using - the following is only illustrative)

WebApplicationContext context = new WebApplicationContext();

 // this is the important bit
 // set the parent classloader using the classloader merlin
 // has assigned to the container thread

context.setParentClassLoader( Thread.currentThread().getContextClassLoader() );

This should ensure that the classloader assigned to the container is established as the parent classloader for the jetty HTTPContext.


I finally got it working by deploying the jasper-runtime.jar and servlet.jar in the WEB-INF/lib directory of my web app WAR. It seems that the jasper-runtime and servlet jars weren't visible to the web application from the merlin container classloader, although the jasper-compiler jar was when the Jetty-Phoenix initially compiled the JSP to Java code.


Something to keep in mind is that the phoenix variant does not have a notion of cascading containers and as such it does not make sence to pass classloaders around. In the current servak variant a classpath reference is created that points to a local lib directory. In Merlin you don't want to do this because you want to be able to take control of the classloading in order to be able to reuse the services provided by the block.




Thinking I might need a more "global" classloader than the container's, I
tried moving the jasper-runtime and servlet jars to the merlin/ext
directory, but that help either.  Only including them in the web apps
WEB-INF/lib directory makes them visible to the executing JSP code.  I think
that is strange.


The /ext directory is only for bootstrap to deal with variations of JVMs (yes - I know - more documetation is needed on this).



If I run Jetty or Tomcat as standalone servers, I don't have to put those jars in the webapps classloader, as they distributed as part of the server's own common lib. I might have to go back and test this, but I think by including those jars in the SAR file when I deploy the Jetty-Phoenix block in a Phoenix container, I don't have to include them in the webapps classloader either.


Correct - because the http context is being provided with the classes via (a) a path or (b) a parent classloader. As mentioned above - I fugure that your have not assigned the classloader to the context but as soon as you do everything should start to work.


Cheers, Steve.

--

Stephen J. McConnell
mailto:[EMAIL PROTECTED]




--------------------------------------------------------------------- To unsubscribe, e-mail: [EMAIL PROTECTED] For additional commands, e-mail: [EMAIL PROTECTED]



Reply via email to