Tomcat8源码分析3--Bootstrap启动过程

1. 执行Bootstrap类的static代码块, 初始化Bootstrap的catalinaHomeFile属性和catalinaBaseFile属性, 默认情况下值都为tomcat的安装目录. 关于这两个属性, 说明如下.

==================================================
Advanced Configuration - Multiple Tomcat Instances
==================================================

In many circumstances, it is desirable to have a single copy of a Tomcat
binary distribution shared among multiple users on the same server.  To make
this possible, you can set the CATALINA_BASE environment variable to the
directory that contains the files for your ‘personal‘ Tomcat instance.

When running with a separate CATALINA_HOME and CATALINA_BASE, the files
and directories are split as following:

In CATALINA_BASE:

 * bin  - Only the following files:

           * setenv.sh (*nix) or setenv.bat (Windows),
           * tomcat-juli.jar

          The setenv scripts were described above. The tomcat-juli library
          is documented in the Logging chapter in the User Guide.

 * conf - Server configuration files (including server.xml)

 * lib  - Libraries and classes, as explained below

 * logs - Log and output files

 * webapps - Automatically loaded web applications

 * work - Temporary working directories for web applications

 * temp - Directory used by the JVM for temporary files (java.io.tmpdir)

In CATALINA_HOME:

 * bin  - Startup and shutdown scripts

          The following files will be used only if they are absent in
          CATALINA_BASE/bin:

          setenv.sh (*nix), setenv.bat (Windows), tomcat-juli.jar

 * lib  - Libraries and classes, as explained below

 * endorsed - Libraries that override standard "Endorsed Standards"
              libraries provided by JRE. See Classloading documentation
              in the User Guide for details.

              By default this "endorsed" directory is absent.

In the default configuration the JAR libraries and classes both in
CATALINA_BASE/lib and in CATALINA_HOME/lib will be added to the common
classpath, but the ones in CATALINA_BASE will be added first and thus will
be searched first.

The idea is that you may leave the standard Tomcat libraries in
CATALINA_HOME/lib and add other ones such as database drivers into
CATALINA_BASE/lib.

In general it is advised to never share libraries between web applications,
but put them into WEB-INF/lib directories inside the applications. See
Classloading documentation in the User Guide for details.

It might be useful to note that the values of CATALINA_HOME and
CATALINA_BASE can be referenced in the XML configuration files processed
by Tomcat as ${catalina.home} and ${catalina.base} respectively.

For example, the standard manager web application can be kept in
CATALINA_HOME/webapps/manager and loaded into CATALINA_BASE by using
the following trick:

 * Copy the CATALINA_HOME/webapps/manager/META-INF/context.xml
   file as CATALINA_BASE/conf/Catalina/localhost/manager.xml

 * Add docBase attribute as shown below.

The file will look like the following:

  <?xml version="1.0" encoding="UTF-8"?>
  <Context docBase="${catalina.home}/webapps/manager"
    antiResourceLocking="false" privileged="true" >
    <Valve className="org.apache.catalina.valves.RemoteAddrValve"
         allow="127\.0\.0\.1" />
  </Context>

See Deployer chapter in User Guide and Context and Host chapters in the
Configuration Reference for more information on contexts and web
application deployment.

区分这两个属性主要是为了支持Tomcat的多实例功能.

home属性主要包含:  bin(主要包含启动停止脚本), lib(公用jar包), endorsed(要覆盖JRE的jar).

base属性主要包含 :  bin(只能包含setevn(设置JRE_HOME等环境变量),  tomcat-juli.jar(日志相关)文件), conf, logs, webapps, work, temp, lib(该tomcat实例下所有web应用共享的jar,tomcat加载时,会先加载这里的jar再加载home/lib下的jar).

2. 如果daemon属性为null, 就创建一个Bootstrap实例,并调用Bootstrap.init()方法初始化, 否则设置当前线程类加载器为daemon.catalinaLoader(另外线程调用Bootstrap.main(‘stop‘)方法).

3. Bootstrap.init()方法逻辑, 首先初始化三个类加载器initClassLoaders().

commonLoader: 根据common.loader属性的配置(catalina.properties), 创建对应的类加载器, 默认情况下顺序加载 ${catalina.base}/lib, ${catalina.base}/lib/*.jar, ${catalina.home}/lib, ${catalina.home}/lib/*.jar 四个目录下的class和jar.

catalinaLoader:  根据server.loader属性的配置, 创建对应的类加载器,其父类加载其为commonLoader, 默认server.loader属性为空, 则直接使用commonLoader.

sharedLoader:根据shared.loader属性配置,创建对应的类加载器,其父类加载其为commonLoader, 默认shared.loader属性为空, 则直接使用commonLoader.

4. 初始化完类加载器后, 设置当前线程上下文类加载器为 catalinaLoader 类加载器, 既commonLoader类加载器. Thread.currentThread().setContextClassLoader(catalinaLoader)

5. 如果当前有SecurityManager, 则提前加载一些类, 防止出现AccessControlException异常. SecurityClassLoad.securityClassLoad(catalinaLoader)

6. 使用catalinaLoader加载org.apache.catalina.startup.Catalina类, 创建实例(Catalina构造方法会配置安全属性,如果有安全管理器), 并反射调用setParentClassLoader(sharedLoader), 设置Catalina实例的parentClassLoader属性为sharedLoader类加载器.

7. 设置daemon为新创建的实例.

8. 进入start命令逻辑. 反射调用Catalina.setAwait(true), 主要是为了启动完成后, 阻塞main线程, 监听某一端口, 等待shutdown命令到来(Catalina.start(), Catalina.await()). 如果不设置, 则main线程执行完, 直接退出.

9. 反射调用Catalina.load(arg[])方法, 可以通过启动参数设置server.xml文件位置, 设置是否启用naming, 然后调用Catalina.load().

10. Catalina.load()逻辑, 首先初始化temp目录, 然后初始化naming需要的一些系统属性(org.apache.naming.java.javaURLContextFactory),  然后获取server.xml配置文件, 创建Digester实例, 开始解析server.xml配置文件.

11. Digester具体的解析方式见 xxxxxxxxxxxxxxxxxxxxxxxxx.

12. 双休关联StandardServer和Catalina实例, 并设置server的catalinaHome和catalinaBase属性.

13. 包装System.out和in流为SystemLogHandler.

14. 启动server, getServer().init().

时间: 2024-10-12 15:14:57

Tomcat8源码分析3--Bootstrap启动过程的相关文章

Netty源码分析之客户端启动过程

一.先来看一下客户端示例代码. 1 public class NettyClientTest { 2 public void connect(int port, String host) throws Exception { 3 EventLoopGroup group = new NioEventLoopGroup();//与服务端不同,客户端只需要一个IO线程组 4 5 try { 6 Bootstrap b = new Bootstrap(); 7 b.group(group) 8 .op

wxWidgets源码分析(1) - App启动过程

目录 APP启动过程 wxApp入口定义 wxApp实例化准备 wxApp的实例化 wxApp运行 总结 APP启动过程 本文主要介绍wxWidgets应用程序的启动过程,从app.cpp入手. wxApp入口定义 wxApp通过IMPLEMENT_APP宏注册App类,这个宏同时定义了入口,实现在wx/app.h文件中. // wx/app.h 文件中定义 #define IMPLEMENT_APP(app) wxIMPLEMENT_APP(app); // 可以忽略 wxIMPLEMENT_

Tomcat源码分析之—具体启动流程分析

从Tomcat启动调用栈可知,Bootstrap类的main方法为整个Tomcat的入口,在init初始化Bootstrap类的时候为设置Catalina的工作路径也就是Catalina_HOME信息.Catalina.base信息,在initClassLoaders方法中初始化类加载器,然后通过反射初始化org.apache.catalina.startup.Catalina作为catalina守护进程: 一.load Bootstrap中load流程: 反射调用Catalina的load方法

spark源码分析之Executor启动与任务提交篇

任务提交流程 概述 在阐明了Spark的Master的启动流程与Worker启动流程.接下继续执行的就是Worker上的Executor进程了,本文继续分析整个Executor的启动与任务提交流程 Spark-submit 提交一个任务到集群通过的是Spark-submit 通过启动脚本的方式启动它的主类,这里以WordCount为例子 spark-submit --class cn.itcast.spark.WordCount bin/spark-clas -> org.apache.spar

手机自动化测试:appium源码分析之bootstrap一

手机自动化测试:appium源码分析之bootstrap一 前言: poptest是国内唯一一家培养测试开发工程师的培训机构,以学员能胜任自动化测试,性能测试,测试工具开发等工作为目标.poptest推出手机自动化测试的课程,讲解appuim的实际应用,培训全程用商业项目,   大家可以加qq群进行交流:195983133 开源的项目最大的好处是可以获得源代码,我们可以在源代码的基础上进行修改代码,编译,开发出符合我们要求的项目.如果想要做到可以修改源代码,首先要读懂代码了解代码.国内的一些公司

手机自动化测试:appium源码分析之bootstrap十一

手机自动化测试:appium源码分析之bootstrap十一 poptest是国内唯一一家培养测试开发工程师的培训机构,以学员能胜任自动化测试,性能测试,测试工具开发等工作为目标.如果对课程感兴趣,请大家咨询qq:908821478. GetName package io.appium.android.bootstrap.handler; import com.android.uiautomator.core.UiObjectNotFoundException; import io.appium

手机自动化测试:appium源码分析之bootstrap九

手机自动化测试:appium源码分析之bootstrap九 poptest是国内唯一一家培养测试开发工程师的培训机构,以学员能胜任自动化测试,性能测试,测试工具开发等工作为目标.如果对课程感兴趣,请大家咨询qq:908821478. TouchLongClick package io.appium.android.bootstrap.handler; import android.os.SystemClock; import com.android.uiautomator.common.Refl

手机自动化测试:appium源码分析之bootstrap十

手机自动化测试:appium源码分析之bootstrap十 poptest是国内唯一一家培养测试开发工程师的培训机构,以学员能胜任自动化测试,性能测试,测试工具开发等工作为目标.如果对课程感兴趣,请大家咨询qq:908821478. setText package io.appium.android.bootstrap.handler; import com.android.uiautomator.core.UiDevice; import com.android.uiautomator.cor

手机自动化测试:appium源码分析之bootstrap十二

手机自动化测试:appium源码分析之bootstrap十二 poptest是国内唯一一家培养测试开发工程师的培训机构,以学员能胜任自动化测试,性能测试,测试工具开发等工作为目标.如果对课程感兴趣,请大家咨询qq:908821478. ScrollTo package io.appium.android.bootstrap.handler; import com.android.uiautomator.core.UiObject; import com.android.uiautomator.c

手机自动化测试:appium源码分析之bootstrap四

手机自动化测试:appium源码分析之bootstrap四 Orientation是调整屏幕方向的操作 package io.appium.android.bootstrap.handler; import android.os.RemoteException;import com.android.uiautomator.core.UiDevice;import io.appium.android.bootstrap.*;import org.json.JSONException; import