Tomcat的源码分析(五)-Pipeline-value管道

本文深入剖析Tomcat中Pipeline的实现原理,包括其生命周期管理与请求处理过程。详细介绍了如何通过Pipeline-value模式串联起各个组件,实现请求的逐级处理。

一、Tomcat的Pipeline-value管道实现

        Pipeline管道的实现分为生命周期管理和处理请求。

在Engin的管道中依次执行Engin的各个Value,最后执行StandardEnginValue,依次类推StandardWrapperValue.

(Filter用到的FilterChain就是这种模式,FilterChain相当于Pipeline,每个Filter相当于一个Value,Servlet相当于最后的BaseValue)

由于Container容器负责具体Servlet的处理,也就是负责处理请求(http请求),

而Container是使用Pipeline-value管道来处理请求的。

Pipeline-value是属于责任链模式。

责任链模式是指在一个请求处理过程中有多个处理者依次对请求进行处理,每个处理者负责处理自己的,处理完交给下一位处理。

Pipeline-value 特点:每个Pipeline都有特定的Value,而且是管道最后一个执行,这个Value叫BaseValue,BaseValue是不可删除的。上层的BaseValue会调用下层容器的管道。流程如上图所示,

四个容器的BaseValue分别是StandardEngineValue,StandardHostValue,StandardContextValue和StandardWrapperValue。

 1、Pipeline管道的生命周期管理

      Container的Pipeline在ContainerBase中定义,在生命周期的startInternal,stopInternal,destroyInternal调用相应的生命周期方法。管道不需要初始化无initInternal方法。

         启动Container的同时也内部调用启动Pipeline管道。

             在ConainerBase类的   startInternal()里面调用了 ((Lifecycle) pipeline).start();就会调用Lifecycle的start方法,

而Lifecycle接口的基本实现类是 LifecycleBase类,在LifecycleBase类里面执行了start()方法,然后在PipeLine的具体实现类StandardPipeLine实现startInternal()方法。

package org.apache.catalina.core.ContainerBase类:


    /**
     * The Pipeline object with which this Container is associated.
     */
    protected final Pipeline pipeline = new StandardPipeline(this);

  /**
     * Start this component and implement the requirements
     * of {@link org.apache.catalina.util.LifecycleBase#startInternal()}.
     *
     * @exception LifecycleException if this component detects a fatal error
     *  that prevents this component from being used
     */
    @Override
    protected synchronized void startInternal() throws LifecycleException {

        // Start our subordinate components, if any
        logger = null;
        getLogger();
        Cluster cluster = getClusterInternal();
        if ((cluster != null) && (cluster instanceof Lifecycle))
            ((Lifecycle) cluster).start();
        Realm realm = getRealmInternal();
        if ((realm != null) && (realm instanceof Lifecycle))
            ((Lifecycle) realm).start();

        // Start our child containers, if any
        Container children[] = findChildren();
        List<Future<Void>> results = new ArrayList<>();
        for (int i = 0; i < children.length; i++) {
            results.add(startStopExecutor.submit(new StartChild(children[i])));
        }

        boolean fail = false;
        for (Future<Void> result : results) {
            try {
                result.get();
            } catch (Exception e) {
                log.error(sm.getString("containerBase.threadedStartFailed"), e);
                fail = true;
            }

        }
        if (fail) {
            throw new LifecycleException(
                    sm.getString("containerBase.threadedStartFailed"));
        }

        // Start the Valves in our pipeline (including the basic), if any
        if (pipeline instanceof Lifecycle)
            ((Lifecycle) pipeline).start();


        setState(LifecycleState.STARTING);

        // Start our thread
        threadStart();

    }



/**
     * Stop this component and implement the requirements
     * of {@link org.apache.catalina.util.LifecycleBase#stopInternal()}.
     *
     * @exception LifecycleException if this component detects a fatal error
     *  that prevents this component from being used
     */
    @Override
    protected synchronized void stopInternal() throws LifecycleException {

        // Stop our thread
        threadStop();

        setState(LifecycleState.STOPPING);

        // Stop the Valves in our pipeline (including the basic), if any
        if (pipeline instanceof Lifecycle &&
                ((Lifecycle) pipeline).getState().isAvailable()) {
            ((Lifecycle) pipeline).stop();
        }

        // Stop our child containers, if any
        Container children[] = findChildren();
        List<Future<Void>> results = new ArrayList<>();
        for (int i = 0; i < children.length; i++) {
            results.add(startStopExecutor.submit(new StopChild(children[i])));
        }

        boolean fail = false;
        for (Future<Void> result : results) {
            try {
                result.get();
            } catch (Exception e) {
                log.error(sm.getString("containerBase.threadedStopFailed"), e);
                fail = true;
            }
        }
        if (fail) {
            throw new LifecycleException(
                    sm.getString("containerBase.threadedStopFailed"));
        }

        // Stop our subordinate components, if any
        Realm realm = getRealmInternal();
        if ((realm != null) && (realm instanceof Lifecycle)) {
            ((Lifecycle) realm).stop();
        }
        Cluster cluster = getClusterInternal();
        if ((cluster != null) && (cluster instanceof Lifecycle)) {
            ((Lifecycle) cluster).stop();                    //停止了stop管道
        }
    }


  开始启动pipeline 管道 --》 ((Lifecycle) pipeline).start();的pipeline是StandardPipeline类:

 org.apache.catalina.core.ContainerBase类的startInternal方法:


    /**
     * The Pipeline object with which this Container is associated.
     */
    protected final Pipeline pipeline = new StandardPipeline(this);

// Start the Valves in our pipeline (including the basic), if any
        if (pipeline instanceof Lifecycle)
            ((Lifecycle) pipeline).start();

                   

由于LifecycleBase继承自Lifecycle,所以 ((Lifecycle) pipeline).start(); start()方法在LifecycleBase类里面调用,也就是调用了LifecycleBase的start方法,由于Pipeline接口下的默认实现类是StandardPipeline,在StandardPipeline类里面具体实现了startInternal方法。

org.apache.catalina.core.StandardPipeline类

    protected Valve basic = null;

    protected Valve first = null;

   
 /**
     * Start {@link Valve}s) in this pipeline and implement the requirements
     * of {@link LifecycleBase#startInternal()}.
     *
     * @exception LifecycleException if this component detects a fatal error
     *  that prevents this component from being used
     */
    @Override
    protected synchronized void startInternal() throws LifecycleException {

        // Start the Valves in our pipeline (including the basic), if any
        Valve current = first;
        if (current == null) {
            current = basic;
        }
        while (current != null) {    //遍历Value链里的所有Value并调用start方法
            if (current instanceof Lifecycle)
                ((Lifecycle) current).start();
            current = current.getNext();
        }

        setState(LifecycleState.STARTING);    //设置LifecycleState状态
    }
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值