Http://seanhe.iteye.com/blog/841723
Since JBoss 4.2.x is used in projects, the analysis on this version here is not necessarily applicable to other JBoss versions.
Let's get down to the truth.
To share classes, JBoss introduces the class loader repository concept, and designs org. jboss. mx. loading. unigiedclassloader3 (UCL) to complete sharing classes.
UCL and UnifiedLoaderRepository3 have a one-to-multiple relationship. By default, only one uniiedloaderrepository3 instance is in the jboss instance. This uniform loaderrepository instance is associated with all UCL instances.
NoAnnotationClassLoader is the UCL parent classloader used to load the jar under $ JBOSS_HOME/lib. system class loader is the parent classloader of NoAnnotationClassLoader.
For the relationships between these objects, see
By default, all UCL instances share a Repository, which enables class sharing. In the UnifiedLoaderRepository3 instance, two containers are maintained. One is class cache. This container obviously caches some classes, which improves the execution efficiency of the loadClass method. The other is packagesMap: this map maintains the package name of the class and the mapping relationship of UCL. For details about the logic of UCL to load class, see the following activity diagram:
Shows the inheritance structure of UnifiedClassLoader3. The RepositoryClassLoader parent class of UnifiedClassLoader3 overrides the loadClass method of URLClassLoader and implements the logic.
See the following code:
RepositoryClassLoader. java
Java code
- Public Class loadClass (String name, boolean resolve)
- Throws ClassNotFoundException
- {
- Boolean trace = log. isTraceEnabled ();
- If (trace)
- Log. trace ("loadClass" + this + "name =" + name + ", loadClassDepth =" + loadClassDepth );
- Class clazz = null;
- Try
- {
- If (repository! = Null)
- {
- Clazz = repository. getCachedClass (name); // load class from the cache first
- If (clazz! = Null)
- {
- If (log. isTraceEnabled ())
- {
- StringBuffer buffer = new StringBuffer ("Loaded class from cache ,");
- ClassToStringAction. toString (clazz, buffer );
- Log. trace (buffer. toString ());
- }
- Return clazz;
- }
- }
- // Some LoadMgr3 methods will be called in loadClassImpl to implement the logic of the flowchart above. The specific code implementation is lengthy and will not be posted here
- Clazz = loadClassImpl (name, resolve, Integer. MAX_VALUE );
- Return clazz;
- }
- Finally
- {
- If (trace)
- {
- If (clazz! = Null)
- Log. trace ("loadClass" + this + "name =" + name + "class =" + clazz + "cl =" + clazz. getClassLoader ());
- Else
- Log. trace ("loadClass" + this + "name =" + name + "not found ");
- }
- }
- }
There are several conclusions that can help to deepen your impression:
- As the Application Server, JBoss can deploy the ear package or the war package. However, by default, jboss processes the ear and war class load mechanisms.
- When deploying the ear, JBOSS uses the class load mechanism I mentioned earlier by default. All the jar files in an ear package are uniformly loaded and managed by a UCL.
- Note that the war deployment in the ear is a bit special. It just adds itself to the classpath domain of ucl, while the WEB-INF/lib/*. jar under war is loaded by WebAppClassloader
Due to the shared mechanism of jboss to all UCL, some class version conflicts may occur, and some applications cannot load the class required by their own applications. JBOSS provides some solutions to this problem: http://community.jboss.org/wiki/classloadingconfiguration. I will sort out the cases and solutions for a class conflict that I have encountered before.
Tomcat6/7 class loader Mechanism
Tomcat class loader hierarchy
Tomcat's class load mechanism is simpler than Jboss.
When a web application needs to load a class, it first calls the loadClass method of WebAppClassloader. The internal logic of loadClass is as follows:
- Call findLoadedClass (String) to check whether the class has been loaded. If the class is loaded, it will be returned directly. If not, continue to the next step.
- Call the loadClass method of system class loader to load it to the JDK core class. If no matching class is found, continue to the next step.
- If the delegate attribute of WebAppClassloader is true or the class being processed is in the filter list, classes are first loaded from the parent class loader. If not, proceed to the next step. This step is generally not executed.
- WebAppClassloader looks for classes in its own class libraries (WEB-INF/classes and WEB-INF/lib. If not, proceed to the next step.
- If the previous step 3rd has been skipped, the execution will continue. If the previous step has been executed, this step will not be executed. The execution logic of this step is the same as that of step 1.
For specific code, see WebAppClassloader. loadClass (..)
Reference:
Http://community.jboss.org/wiki/JBossClassLoadingUseCases
Http://community.jboss.org/wiki/ClassLoadingConfiguration
Http://community.jboss.org/wiki/EnableClassloaderLogging
Http://agapple.iteye.com/blog/791940
Http://www.iteye.com/topic/826661