现在的位置: 首页 > 综合 > 正文

How Tomcat Works 17

2018年05月22日 ⁄ 综合 ⁄ 共 3746字 ⁄ 字号 评论关闭

tomcat的启动

 

一,catalina里的start方法,用15章介绍的digester,把server.xml解析,建立起一些列对象,设置初始属性,建立对象间联系,最后把server设给catalina。

 

二,bat文件。设置一些初始值,classpath,最后启动BootStrap类,传递命令参数。

 

三,这是重点,classloader系统。

第八章说过WebappLoader,每个app都会有自己的WebappLoader,在WebappLoader的start方法里,会建立一个webappclassloader,这个才是真正的classloader。

这个webappclassloader和从前的委派模式不同,在第八章已经说过了:

  1. All previously loaded classes are cached, so first check the local cache.(检查webappclassloader里的缓存中是否有)
  2. If not found in the local cache, check in the cache, i.e. by calling the findLoadedClass of the java.lang.ClassLoader class.(检查ClassLoader里的缓存中是否有)
  3. If not found in both caches, use the system's class loader to prevent the web application from overriding J2EE class.(用systemclassloader找,这是为了防止用户类覆盖j2se的基础类或classpath下的类)
  4. If SecurityManager is used, check if the class is allowed to be
    loaded. If the class is not allowed, throw a ClassNotFoundException.(如果用了SecurityManager
    ,则检查要载入的类是否允许,默认似乎是没有使用SecurityManager )
  5. If the delegate flag is on or if the class to be loaded belongs to
    the package name in the package trigger, use the parent class loader to
    load the class. If the parent class loader is null, use the system
    class loader.(delegate
    为true,或者将要载入的类的包属于package trigger,就用parent class loader,如果parentclassloader是null,则用systemclassloader。在这里parentclassloader是sharedclassloader。deleget默认是false,是从webapploader的start方法中设的)
  6. Load the class from the current repositories.(自己载入)
  7. If the class is not found in the current repositories, and if the
    delegate flag is not on, use the parent class loader. If the parent
    class loader is null, use the system class loader.(没找到,并且delegate是false,就用parent class loader,如果parentclassloader是null,则用systemclassloader)
  8. If the class is still not found, throw a ClassNotFoundException.

在第5条里,提到了sharedclassloader,下面就说一下tomcat的classloader体系:

      
+---------------------------+

      
|        
Bootstrap        
|

      
|            
|            
|

      
|         
System          
|

      
|            
|            
|

      
|         
Common          
|

      
|        
/     
/         
|

      
|    
Catalina 
Shared     
|

      
+---------------------------+

在BootStrap类里,会init三个classloader,他们的作用域不同,具体的load类的路径看
http://blog.csdn.net/chen77716/archive/2004/07/05/34790.aspx

 

这里边,catalina是负责读tomcat容器需要加载的类的;shared是读shared目录下的类的,并且shared是webappclassloader的parent,所以catalina和shared是互相不可见的。

在Bootstrap类的init方法中:(参考http://gotothework.javaeye.com/blog/219299)

这样本thread就用catalina来load类了。

 

再看

 

按照上述的道理,每个context都有一个webapploader,这是在context的start方法里:

 

然后在webappclassloader类的start方法里:

 

这样,所有的classloader机制建立完毕。

 

 

ps:

写到这时曾经有个疑问,就是在context里,对loader的设置是否必须在fire START_EVENT之前。因为,一旦fire START_EVENT,则contextConfig就会读取web.xml并解析,这样在解析时生成的对象是不是要用webappclassloader加载?

后来想明白了,contextConfig里生成的对象,是wrapper,并不是servlet。具体的servlet对象的加载,要等到调用时再standardwrappervalve里。

 


抱歉!评论已关闭.