persistence@glassfish.java.net

RE: Need for a releaseTemporaryClassLoader method

From: Mike Keith <michael.keith_at_oracle.com>
Date: Fri, 10 Mar 2006 14:39:37 -0500

Hi Sahoo,

Sorry, I am just catching up on email that has been been in my "need to clarify" bin :-)

The temp loader should only be used in the createContainerEMF call and be closable afterwards.
I think that the way it is defined now is probably a little looser than what it needs to be and we can
tighten this up a little.

-Mike
  -----Original Message-----
  From: Sanjeeb.Sahoo_at_Sun.COM [mailto:Sanjeeb.Sahoo_at_Sun.COM]On Behalf Of Sanjeeb Kumar Sahoo
  Sent: Thursday, March 02, 2006 1:14 PM
  To: Mike Keith
  Cc: persistence_at_glassfish.dev.java.net; Marina Vatkina
  Subject: Need for a releaseTemporaryClassLoader method


  Hi Mike,

  By default Sun JDK use some kind of URL caching(http://java.sun.com/j2se/1.5.0/docs/api/java/net/URLConnection.html#getDefaultUseCaches()). On Windows platform this leads to jar file locking. What we have observed is that once a URLClassLoader loads a resource from a jar file, even after the class loader is garbage collected, the jar file can not be deleted. It can only be deleted after JVM exits. This affects redeployment of applications on Windows platform.
  In our app server, we use a special ClassLoader which uses some work around to avoid this issue. We create special URLStreamHandler which by passes this caching and we also have a special clean up method in our custom ClassLoader class that closes all the streams etc. We rely on container to call this clean up method.

  The temporary class loader introduced in persistence spec is causing some problems. There is only a getNewTemporaryClassLoader() method (https://glassfish.dev.java.net/source/browse/*checkout*/glassfish/persistence-api/src/java/javax/persistence/spi/PersistenceUnitInfo.java?rev=1.3) which returns a java.lang.ClassLoader to the provider. There is no release method which provider can use to signal the container to release the class loader. So even if we give out a special class loader as temporary class loader, in the absence of such a release method, container is not able to call the clean up method.

  There are ways to work around this, but we are of the opinion that a simple change in the spec can lead to simpler implementation. There are at least a couple of ways to do this:

  1. Change the scope of temporary class loader. Make it such that the temporary class loader is only usable inside PersistenceProvider.createContainerEntityManagerFactory() call (I don't see any reason why a provider would be using temporary class loader after EMF creation). Allow container to hold a strong reference to the class loader. That way after PersistenceProvider.createContainerEntityManagerFactory() returns, container can call appropriate clean up method of class loader.
  OR
  2. Add a method in PersistenceUnitInfo (say) releaseTemporaryClassLoader(ClassLoader cl) which provider is must call for every getNewTemporaryClassLoader() call.

  I would be interested in knowing your opinion on this.

  Thanks,
  Sahoo