Tomcat顶层结构及启动过程

Tomcat的顶层结构及启动过程

1.Tomcat的顶层结构

Tomcat中最顶层的容器叫Server,代表整个服务器。
Server中包含至少一个Service,用于具体提供服务
Service主要包含两部分:Connector和Container
Connector用于处理连接相关的事情,并提供Socket与request、response的转换
Container用于封装和管理Servlet,以及具体处理request请求。

一个Tomcat中只有一个Server,一个Server可以有多个Service,一个Service只有一个Container,但可以有多个Connector(因为一个服务可以有多个连接,如同时提供http和https连接,也可以提供相同协议不同端口的连接)

Tomcat里的Server由org.apache.catalina.startup.Catalina来管理,Catalina是整个Tomcat的管理类,它里面的三个方法load、start、stop分别用来管理整个服务器的生命周期
load方法用于根据conf/server.xml文件创建Server并调用Server的init方法进行初始化
start方法用于启动服务器
stop方法用于停止服务器
start和stop方法在内部分别调用了Server的start和stop方法,load方法内部调用了Server的init方法,这三个方法会按容器的结构逐层调用相应的方法,比如Server的start方法中会调用所有的Service中的start方法,Service中的start方法又会调用所有包含的Container和Connectors的start方法,这样整个服务器就启动了,init和stop方法也一样
这就是Tomcat生命周期的管理方式
Catalina中的await方法直接调用了Server的await方法,这个方法的作用是进入一个循环,让主线程不会退出
不过Tomcat的入口main方法并不在Catalina类里,而是在org.apache.catalina.startup.Bootstrap中,Bootstrap的作用类似一个CatalinaAdaptor,
具体处理过程还是使用Catalina来完成的,这么做的好处是可以把启动的入口和具体的管理类分开,从而可以很方便地创建出多种启动方式,每种启动方式只需要写一个相应的CatalinaAdaptor就可以了。

2.Bootstrap的启动过程

Bootstrap是Tomcat的入口,正常情况下启动Tomcat就是调用的Bootstrap的main方法

//org.apache.catalina.startip.Bootstrap
public static void main(String args[]){
	//先新建一个Bootstrap
	if(daemon == null){
		Bootstrap bootstrap = new Bootstrap();
		//初始化了ClassLoader,并用ClassLoader创建了Catalina实例,赋给catalinaDaemon变量
		bootstrap.init();
		daemon - bootstrap;
	} else {
		Thread.currentThread().setContextClassLoader(daemon.catalinaLoader);
	}
	String command = "start";
	if(arg.length > 0){
	 command = args[args.length - 1];
	}
	if(command.equals("startd")){
		args[arg.length-1] = "start";
		daemon.load(args);
		daemon.start();
	} else if (commond.equals("stopd")) {
		args[args.length-1] = "stop";
		daemon.stop();
	} else if (commond.equals("start")) {
		daemon.setAwait(true);
		daemon.load(args);
		daemon.start();
	} else if (command.equals("stop")) {
		daemon.stopServer(args);
	} else if (command.equals("configtest")) {
		daemon.load(args);
		if(null==daemon.getServer()){
			System.exit(1);
		}
		System.exit(0);
	} else {
			log.warn("Bootstrap: command \""+command + "\" does not exist.");
	}
} 

可以看到时这里的main非常简单,只有两部分内容:首先新建了Bootstrap,并执行init方法初始化;然后处理mian方法传入的命令, 如果args参数为空,默认执行start
在init方法里初始化了ClassLoader,并用ClassLoader创建了Catalina实例,然后赋给catalinaDaemon变量,后面对命令的操作都要用它来具体执行。
对start命令的处理调用了三个方法:setAwait(true)、load(args)和start()。这三个方法内部都使用反射调用了Catalina的相应方法进行具体执行

3.Catalina的启动过程

Catalina的启动主要是调用setAwait、load和start方法来完成的。setAwait方法用于设置Server启动完成后是否进入等等状态的标志, 如果为true则进入,否则不进入;load方法用于加载配置文件,创建并初始化Server;start方法用于启动服务器

4.Server的启动过程

Server接口中提供addService(Service service)、removeService(Service service)来添加和删除Service,Server的init方法和start方法分别循环调用了每个Service的init方法和start方法来启动所有Service。
Server的默认实现是org.apache.catalina.core.StandardServer, StandardServer继承LifecycleMBeanBase,LifecycleMBeanBase继承LifecycleBase,init和start方法就定义在LifecycleBase中,LifecycleBase里的init方法和start方法又调用initInternal方法和startInternal方法
这两个方法都是模板方法,由子类具体实现,所以调用StandardServer的init和start方法时会执行
StandardServer自己的initInternal和startInternal方法,这就是Tomcat生命周期的管理方式

//org.apache.catalina.core.StandardServer
protected void startInternal(){
	......
	synchronized(servicesLock){
		for(int i=0;i<services.length;i++){
			services[i].start();
		}
	}
}

protected void initInternal(){
	......
	for(int i=0;i<services.length;i++){
		services[i].init();
	}
}

StandadServer中还实现了await方法,Catalina中就是调用它让服务器进入等待状态的
处理的大概逻辑是首先判断端口号port,然后根据port的值分为三种处理方法
port为-2,则会直接退出,不进入循环
prot为-1,则会进入一个while(!stopAwait)的循环,并且在内部没有break跳出的语句,stopAwait标志只有调用了stop方法都会设置为true,所以port为-1时只有在外部调用stop才会退出循环
port为其他,则也会进入一个while(!stopAwait)的循环,不过同时会在port所在端口启动一个ServerSocket来监听关闭命令,如果接收到了则会使用break跳出循环

<!-- server.xml -->
<Server port = "8005" shutdown="SHUTDOWN">

5.Service的启动过程

Service的默认实现是org.apache.catalina.core.StandardService,StandardService也继承处LifecycleMBeanBase类,所以init和start方法最终也会调用initInternal和startInternal方法,这两个方法主要调用container、executors、mapperListener、connectors的init和start方法。
mapperListener是Mapper的监听器,可以监听container容器的变化,executors是用在connectors中管理线程的线程池,在server.xml配置文件中有用法

整个流程
Bootstrap - Catalina - StandardServer - StandardService - Container - MapperUstener - Executor - Connetor
init()方法一层调用一层返回之后start()方法再一层调用一层

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值