server和service的启动过程

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/fan510988896/article/details/73603671
服务器与服务
server接口中提供addService(Service service)和removeService(Service service)来添加和删除服务
server的init方法和start方法会分别循环调用每个service的init方法和start方法来启动所有的服务

org.apache.catalina.core.StandardServer    标准的服务器

Lifecycle-MBeanBase                                   生命周期


server的默认实现类:

org.apache.catalina.core.StandardServer

继承关系:

public final class StandardServer extends LifecycleMBeanBase implements Server
public abstract class LifecycleMBeanBase extends LifecycleBase implements JmxEnabled
public abstract class LifecycleBase implements Lifecycle
init和start方法就在LifecycleBase里面,但是LifecycleBase又调用了initInternal,startInternal方法
initInternal,startInternal方法都是模板方法,由子类具体实现,所以调用StandardServer的init和start方法时
会执行StandardServer自己的initInternal,startInternal方法。这就是Tomcat生命周期的管理方式。

StandardServer自己的initInternal,startInternal方法分别调用每个service的start和init方法:

protected void startInternal() throws LifecycleException {
    this.fireLifecycleEvent("configure_start", (Object)null);
    this.setState(LifecycleState.STARTING);
    this.globalNamingResources.start();
    Object var1 = this.servicesLock;
    synchronized(this.servicesLock) {
        for(int i = 0; i < this.services.length; ++i) {
            this.services[i].start();
        }
    }
}
StandardServer还实现了await方法,Catalina中就是调用它让服务器进入等待状态的。
该方法的处理逻辑是首先判断端口号port,然后根据port的值分为三种情况:
port为-2:
    直接退出,不进入循环。
port为-1:
    进入一个while(!stopAwait)的循环,并且在内部没有break跳出的语句,stopAwait标志是有调用stop方法才会设置
    为true,所以port为-1时只有在外部调用stop方法才会退出循环。
port为其他值:
    也会进入一个while(!stopAwait)的循环,不过同时会在port所在端口启动一个ServerSocket来监听关闭命令,如果接受到了
    则会是用break跳出循环。
    这里的端口port和关闭命令shutdown是在conf/server.xml中配置的,如下:
    <Server port="8005" shutdown="SHUTDOWN">
    这时会在8005端口监听SHUTDOWN命令,如果接收到了就会关闭tomcat。如果不想是用网络命令来关闭服务器,可以将端口设置为-1


service的默认实现类:
      org.apache.catalina.core.StandardService

继承关系:

public class StandardService extends LifecycleMBeanBase implements Service
StandardService也继承自LifecycleMBeanBase,所以它的init和start方法最终也会调用initInternal和startInternal
protected void initInternal() throws LifecycleException {
    super.initInternal();
    if(this.engine != null) {
        this.engine.init();//启动了
    }

    Executor[] arr$ = this.findExecutors();
    int arr$1 = arr$.length;

    int len$;
    for(len$ = 0; len$ < arr$1; ++len$) {
        Executor i$ = arr$[len$];
        if(i$ instanceof JmxEnabled) {
            ((JmxEnabled)i$).setDomain(this.getDomain());
        }

        i$.init();//启动了
    }

    this.mapperListener.init();//启动了
    Object var11 = this.connectorsLock;
    synchronized(this.connectorsLock) {
        Connector[] var12 = this.connectors;
        len$ = var12.length;

        for(int var13 = 0; var13 < len$; ++var13) {
            Connector connector = var12[var13];

            try {
                connector.init();//启动了
            } catch (Exception var9) {
                String message = sm.getString("standardService.connector.initFailed", new Object[]{connector});
                log.error(message, var9);
                if(Boolean.getBoolean("org.apache.catalina.startup.EXIT_ON_INIT_FAILURE")) {
                    throw new LifecycleException(message);
                }
            }
        }

    }
}
StandardService中的initInternal和startInternal方法主要调用了container,executors,mapperListener,connectors的init和start方法。
mapperListener是Mapper的监听器,可以监听container容器的变化
executors是用在connectors中管理线程的线程池,在config/server.xml中如下:
<Service name="Catalina">
    <Executor name="tomcatThreadPool" namePrefix="catalina-exec-"
            maxThreads="150" minSpareThreads="4"/>
    <Connector port="8080" protocol="HTTP/1.1"
                   connectionTimeout="20000"
                   redirectPort="8443" />
</Service>
这样Connector就配置了一个叫tomcatThreadPoold的线程池,最多可以同时启动150个线程,最少要有4个可用线程

猜你喜欢

转载自blog.csdn.net/fan510988896/article/details/73603671