导入 idea
ant ide-intellij 会下载点依赖在 %userprofile%\tomcat-build-libs
科学上网可以加 -Dproxy.use=true -Dproxy.host=127.0.0.1 -Dproxy.port=10808
关键代码逻辑
作为入口,通过反射调用 Catalina 的 setAwait、load、start
-
创建 ClassLoader(如 CommonClassLoader),加载 catalina.jar 等内部 JAR
-
使用
Thread.currentThread().setContextClassLoader()设置该加载器 -
通过反射调用
org.apache.catalina.startup.Catalina.start(),确保 Catalina 类由 CommonClassLoader 加载,而非系统类加载器
三个自定义类加载器,commonLoader、catalinaLoader、sharedLoader
加载类的路径不同,每种类加载都有自己的职责范围,配置默认在conf/catalina.properties
Thread.currentThread().setContextClassLoader(daemon.catalinaLoader);破坏双亲委派的一贯做法
catalina.home和catalina.base
catalina.home是Tomcat安装目录,包含bin和lib
catalina.base是实例目录,包含conf、logs、webapps等,不指定则和catalina.home相同
一个Tomcat可以通过配置CATALINA_BASE来增加多个工作目录,也就是增加多个实例。多个实例各自可以有自己的conf,logs,temp,webapps
代码
org.apache.catalina.startup.Bootstrap
main()
Bootstrap bootstrap = new Bootstrap();
bootstrap.init();
String command = "start";
if (command.equals("startd")) {
daemon.load(args);
daemon.start();
} else if (command.equals("stopd")) {
args[args.length - 1] = "stop";
daemon.stop();
} else if (command.equals("start")) {
daemon.setAwait(true);
daemon.load(args);
daemon.start();
if (null == daemon.getServer()) {
System.exit(1);
}
} else if (command.equals("stop")) {
daemon.stopServer(args);
...创建 Bootstrap 对象,调用 init ()初始化,根据启动参数,分别调用 Bootstrap 对象的不同方法
static 块
private static final File catalinaBaseFile;
private static final File catalinaHomeFile;
System.setProperty("catalina.base");
System.setProperty("catalina.home");getCanonicalFile 可以根据操作系统,解析得到规范的唯一路径名,如../ ./等,getCanonicalFile可以正确解析,而getAbsoluteFile不会
start()
daemon.setAwait(true);
daemon.load(args);
daemon.start();通过反射去调用 init 方法里初始化过的 Catalina 对象的同名的方法
setAwait
调用Server的await()开启线程,监听默认8005端口SHUTDOWN指令后,调用Server的stop和destroy,停止并销毁Server下的所有子容器和组件
时序
%%{init: {"sequence": {"rightAngles":true,"width":300}}}%%
sequenceDiagram
participant startup.bat
participant BootStrap
participant Catalina
participant Server
participant Service
participant Executor
participant Engine
participant Host
participant Context
participant Connector
participant ProtocolHandler
startup.bat ->> BootStrap: main()
activate startup.bat
deactivate startup.bat
activate BootStrap
BootStrap ->> BootStrap: init
BootStrap ->> BootStrap: load
BootStrap ->> Catalina: load
activate BootStrap
deactivate BootStrap
activate Catalina
Catalina ->> Server: init
deactivate Catalina
activate Server
Server ->> Service: init
deactivate Server
activate Service
Service ->> Executor: init
activate Executor
deactivate Executor
Service ->> Engine: init
activate Engine
Engine ->> Host: init
deactivate Engine
activate Host
Host ->> Context: init
deactivate Host
activate Context
deactivate Context
Service ->> Connector: init
activate Connector
deactivate Service
Connector ->> ProtocolHandler: init
activate ProtocolHandler
deactivate ProtocolHandler
deactivate Connector
BootStrap ->> Catalina: start
activate BootStrap
deactivate BootStrap
activate Catalina
Catalina ->> Server: start
deactivate Catalina
activate Server
Server ->> Service: start
deactivate Server
activate Service
Service ->> Executor: start
activate Executor
deactivate Executor
Service ->> Engine: start
activate Engine
Engine ->> Host: start
deactivate Engine
activate Host
Host ->> Context: start
deactivate Host
activate Context
deactivate Context
Service ->> Connector: start
deactivate Service
activate Connector
Connector ->> ProtocolHandler: start
activate ProtocolHandler
deactivate ProtocolHandler
deactivate Connector
deactivate BootStrap
深入
server.xml解析,Server一键初始化,一键启停涉及到Tomcat的生命周期管理