亚洲免费在线-亚洲免费在线播放-亚洲免费在线观看-亚洲免费在线观看视频-亚洲免费在线看-亚洲免费在线视频

How Tomcat Works(八)

系統(tǒng) 1810 0

下面接著分析Context容器,該接口最重要的方法是addWrapper()方法與creatWrapper()方法,添加具體的子容器,這里是Wrapper容器實例

這里要分析的是一個簡單的Context容器,它針對特定的客戶端請求,通過映射器找到要處理該特定請求的子容器實例(Wrapper)

具體流程是,Context容器首先調用額外的閥,最后調用基礎閥(這里是SimpleContextValve),在基礎閥里面通過映射器找到要 處理該請求的子容器Wrapper實例,然后再調用子容器Wrapper實例的各個閥(本示例的Wrapper只有基礎閥)(類似于composte模式 迭代)

下面是SimpleContext類的實現(xiàn),SimpleContext實現(xiàn)org.apache.catalina.Context接口和org.apache.catalina.Pipeline接口

      
        public
      
      
        class
      
       SimpleContext 
      
        implements
      
      
         Context, Pipeline {

    
      
      
        public
      
      
         SimpleContext() {
        pipeline.setBasic(
      
      
        new
      
      
         SimpleContextValve());
    }

    
      
      
        //
      
      
         子容器名稱與子容器實例映射
      
      
        protected
      
       HashMap children = 
      
        new
      
      
         HashMap();
    
      
      
        protected
      
       Loader loader = 
      
        null
      
      
        ;
    
      
      
        protected
      
       SimplePipeline pipeline = 
      
        new
      
       SimplePipeline(
      
        this
      
      
        );
    
      
      
        //
      
      
         servlet模式與子容器名稱映射
      
      
        protected
      
       HashMap servletMappings = 
      
        new
      
      
         HashMap();
    
      
      
        //
      
      
         映射器
      
      
        protected
      
       Mapper mapper = 
      
        null
      
      
        ;
    
      
      
        //
      
      
         映射器協(xié)議與映射器實例映射
      
      
        protected
      
       HashMap mappers = 
      
        new
      
      
         HashMap();
    
      
      
        private
      
       Container parent = 
      
        null
      
      
        ;
    
    
      
      
        /**
      
      
        
     * 添加servlet模式與子容器名稱(wrapper)到HashMap servletMappings容器
     * 
      
      
        @param
      
      
         pattern
     * 
      
      
        @param
      
      
         name
     
      
      
        */
      
      
        public
      
      
        void
      
      
         addServletMapping(String pattern, String name) {
        
      
      
        synchronized
      
      
         (servletMappings) {
            servletMappings.put(pattern, name);
        }
    }    

    
      
      
        /**
      
      
        
     * 根據(jù)servlet模式找到對應的子容器名稱(wrapper)(供映射器調用)
     * 
      
      
        @param
      
      
         pattern
     * 
      
      
        @return
      
      
        */
      
      
        public
      
      
         String findServletMapping(String pattern) {
        
      
      
        synchronized
      
      
         (servletMappings) {
            
      
      
        return
      
      
         ((String) servletMappings.get(pattern));
        }
    }

    
      
      
        /**
      
      
        
     * 獲取加載器
     * 
      
      
        @return
      
      
        */
      
      
        public
      
      
         Loader getLoader() {
        
      
      
        if
      
       (loader != 
      
        null
      
      
        )
            
      
      
        return
      
      
         (loader);
        
      
      
        if
      
       (parent != 
      
        null
      
      
        )
            
      
      
        return
      
      
         (parent.getLoader());
        
      
      
        return
      
       (
      
        null
      
      
        );
    }

    
      
      
        /**
      
      
        
     * 設置加載器
     * 
      
      
        @param
      
      
         loader
     
      
      
        */
      
      
        public
      
      
        void
      
      
         setLoader(Loader loader) {
        
      
      
        this
      
      .loader =
      
         loader;
    }

    
      
      
        /**
      
      
        
     * 添加子容器實例(wrapper)名稱與子容器實例(wrapper)到HashMap children容器
     * 
      
      
        @param
      
      
         child
     
      
      
        */
      
      
        public
      
      
        void
      
      
         addChild(Container child) {
        child.setParent((Container) 
      
      
        this
      
      
        );
        children.put(child.getName(), child);
    }

    
      
      
        /**
      
      
        
     * 根據(jù)名稱查找子容器實例wrapper(供映射器調用)
     * 
      
      
        @param
      
      
         name
     * 
      
      
        @return
      
      
        */
      
      
        public
      
      
         Container findChild(String name) {
        
      
      
        if
      
       (name == 
      
        null
      
      
        )
            
      
      
        return
      
       (
      
        null
      
      
        );
        
      
      
        synchronized
      
      
         (children) {
            
      
      
        //
      
      
         Required by post-start changes
      
      
        return
      
      
         ((Container) children.get(name));
        }
    }

    
      
      
        /**
      
      
        
     * 查找子容器數(shù)組
     * 
      
      
        @return
      
      
        */
      
      
        public
      
      
         Container[] findChildren() {
        
      
      
        synchronized
      
      
         (children) {
            Container results[] 
      
      = 
      
        new
      
      
         Container[children.size()];
            
      
      
        return
      
      
         ((Container[]) children.values().toArray(results));
        }
    }

    
      
      
        /**
      
      
        
     * 添加映射器實例
     * 
      
      
        @param
      
      
         mapper
     
      
      
        */
      
      
        public
      
      
        void
      
      
         addMapper(Mapper mapper) {
        
      
      
        //
      
      
         this method is adopted from addMapper in ContainerBase
        
      
      
        //
      
      
         the first mapper added becomes the default mapper
      
      
        mapper.setContainer((Container) 
      
        this
      
      ); 
      
        //
      
      
         May throw IAE
      
      
        this
      
      .mapper =
      
         mapper;
        
      
      
        synchronized
      
      
         (mappers) {
            
      
      
        if
      
       (mappers.get(mapper.getProtocol()) != 
      
        null
      
      
        )
                
      
      
        throw
      
      
        new
      
       IllegalArgumentException("addMapper:  Protocol '"
                        + mapper.getProtocol() + "' is not unique"
      
        );
            mapper.setContainer((Container) 
      
      
        this
      
      ); 
      
        //
      
      
         May throw IAE
      
      
                    mappers.put(mapper.getProtocol(), mapper);
            
      
      
        if
      
       (mappers.size() == 1
      
        )
                
      
      
        this
      
      .mapper =
      
         mapper;
            
      
      
        else
      
      
        this
      
      .mapper = 
      
        null
      
      
        ;
        }
    }

    
      
      
        /**
      
      
        
     * 根據(jù)協(xié)議查找映射器實例
     * 
      
      
        @param
      
      
         protocol
     * 
      
      
        @return
      
      
        */
      
      
        public
      
      
         Mapper findMapper(String protocol) {
        
      
      
        //
      
      
         the default mapper will always be returned, if any,
        
      
      
        //
      
      
         regardless the value of protocol
      
      
        if
      
       (mapper != 
      
        null
      
      
        )
            
      
      
        return
      
      
         (mapper);
        
      
      
        else
      
      
        synchronized
      
      
         (mappers) {
                
      
      
        return
      
      
         ((Mapper) mappers.get(protocol));
            }
    }

    
      
      
        public
      
      
         Mapper[] findMappers() {
        
      
      
        return
      
      
        null
      
      
        ;
    }

    
      
      
        /**
      
      
        
     * 根據(jù)請求找到子容器實例wrapper (供基礎閥調用該方法)
     * 
      
      
        @param
      
      
         request
     * 
      
      
        @param
      
      
         update
     * 
      
      
        @return
      
      
        */
      
      
        public
      
       Container map(Request request, 
      
        boolean
      
      
         update) {
        
      
      
        //
      
      
         this method is taken from the map method in
        
      
      
        //
      
      
         org.apache.cataline.core.ContainerBase
        
      
      
        //
      
      
         the findMapper method always returns the default mapper, if any,
        
      
      
        //
      
      
         regardless the
        
      
      
        //
      
      
         request's protocol
      
      
        Mapper mapper =
      
         findMapper(request.getRequest().getProtocol());
        
      
      
        if
      
       (mapper == 
      
        null
      
      
        )
            
      
      
        return
      
       (
      
        null
      
      
        );

        
      
      
        //
      
      
         Use this Mapper to perform this mapping
        
      
      
        //
      
      
         具體過程 (回調該對象下面方法)
        
      
      
        //
      
      
         根據(jù)request找到處理該請求的子容器wrapper名稱 調用方法 String findServletMapping(String pattern)
        
      
      
        //
      
      
         根據(jù)上面的子容器wrapper名稱找到子容器wrapper 調用方法 Container findChild(String name)
      
      
        return
      
      
         (mapper.map(request, update));
    }

    
      
      
        public
      
      
        void
      
       invoke(Request request, Response response) 
      
        throws
      
      
         IOException,
            ServletException {
        pipeline.invoke(request, response);
    }

    
      
      
        //
      
      
         method implementations of Pipeline
      
      
        public
      
      
         Valve getBasic() {
        
      
      
        return
      
      
         pipeline.getBasic();
    }

    
      
      
        public
      
      
        void
      
      
         setBasic(Valve valve) {
        pipeline.setBasic(valve);
    }

    
      
      
        public
      
      
        synchronized
      
      
        void
      
      
         addValve(Valve valve) {
        pipeline.addValve(valve);
    }

    
      
      
        public
      
      
         Valve[] getValves() {
        
      
      
        return
      
      
         pipeline.getValves();
    }

    
      
      
        public
      
      
        void
      
      
         removeValve(Valve valve) {
        pipeline.removeValve(valve);
    }

}
      
    

下面我們來分析映射器SimpleContextMapper的實現(xiàn)

      
        public
      
      
        class
      
       SimpleContextMapper 
      
        implements
      
      
         Mapper {

  
      
      
        /**
      
      
        
   * The Container with which this Mapper is associated.
   
      
      
        */
      
      
        private
      
       SimpleContext context = 
      
        null
      
      
        ;

  
      
      
        public
      
      
         Container getContainer() {
    
      
      
        return
      
      
         (context);
  }

  
      
      
        public
      
      
        void
      
      
         setContainer(Container container) {
    
      
      
        if
      
       (!(container 
      
        instanceof
      
      
         SimpleContext))
      
      
      
        throw
      
      
        new
      
      
         IllegalArgumentException
        (
      
      "Illegal type of container"
      
        );
    context 
      
      =
      
         (SimpleContext) container;
  }

  
      
      
        public
      
      
         String getProtocol() {
    
      
      
        return
      
      
        null
      
      
        ;
  }

  
      
      
        public
      
      
        void
      
      
         setProtocol(String protocol) {
  }


  
      
      
        /**
      
      
        
   * Return the child Container that should be used to process this Request,
   * based upon its characteristics.  If no such child Container can be
   * identified, return <code>null</code> instead.
   *
   * 
      
      
        @param
      
      
         request Request being processed
   * 
      
      
        @param
      
      
         update Update the Request to reflect the mapping selection?
   *
   * 
      
      
        @exception
      
      
         IllegalArgumentException if the relative portion of the
   *  path cannot be URL decoded
   
      
      
        */
      
      
        public
      
       Container map(Request request, 
      
        boolean
      
      
         update) {
    
      
      
        //
      
      
         Identify the context-relative URI to be mapped
      
      
    String contextPath =
      
        
      ((HttpServletRequest) request.getRequest()).getContextPath();
    String requestURI 
      
      =
      
         ((HttpRequest) request).getDecodedRequestURI();
    String relativeURI 
      
      =
      
         requestURI.substring(contextPath.length());
    
      
      
        //
      
      
         Apply the standard request URI mapping rules from the specification
      
      
    Wrapper wrapper = 
      
        null
      
      
        ;
    String servletPath 
      
      =
      
         relativeURI;
    String pathInfo 
      
      = 
      
        null
      
      
        ;
    String name 
      
      =
      
         context.findServletMapping(relativeURI);
    
      
      
        if
      
       (name != 
      
        null
      
      
        )
      wrapper 
      
      =
      
         (Wrapper) context.findChild(name);
    
      
      
        return
      
      
         (wrapper);
  }
}
      
    

映射器SimpleContextMapper最重要的方法是Container map(Request request, boolean update)

即根據(jù)客戶端請求找到對應的子容器實例wrapper,里面關鍵代碼是回調context容器實例的方法(持有對SimpleContext實例的引用)

接下里分析基礎閥的關鍵代碼(管道持有對基礎閥的引用)

      
        public
      
      
        class
      
       SimpleContextValve 
      
        implements
      
      
         Valve, Contained {

  
      
      
        protected
      
      
         Container container;

  
      
      
        public
      
      
        void
      
      
         invoke(Request request, Response response, ValveContext valveContext)
    
      
      
        throws
      
      
         IOException, ServletException {
    
      
      
        //
      
      
         Validate the request and response object types
      
      
        if
      
       (!(request.getRequest() 
      
        instanceof
      
       HttpServletRequest) ||
      !(response.getResponse() 
      
        instanceof
      
      
         HttpServletResponse)) {
      
      
      
        return
      
      ;     
      
        //
      
      
         NOTE - Not much else we can do generically
      
      
            }

    
      
      
        //
      
      
         Disallow any direct access to resources under WEB-INF or META-INF
      
      
    HttpServletRequest hreq =
      
         (HttpServletRequest) request.getRequest();
    String contextPath 
      
      =
      
         hreq.getContextPath();
    String requestURI 
      
      =
      
         ((HttpRequest) request).getDecodedRequestURI();
    String relativeURI 
      
      =
      
        
      requestURI.substring(contextPath.length()).toUpperCase();

    Context context 
      
      =
      
         (Context) getContainer();
    
      
      
        //
      
      
         Select the Wrapper to be used for this Request
      
      
    Wrapper wrapper = 
      
        null
      
      
        ;
    
      
      
        try
      
      
         {
      wrapper 
      
      = (Wrapper) context.map(request, 
      
        true
      
      
        );
    }
    
      
      
        catch
      
      
         (IllegalArgumentException e) {
      badRequest(requestURI, (HttpServletResponse) response.getResponse());
      
      
      
        return
      
      
        ;
    }
    
      
      
        if
      
       (wrapper == 
      
        null
      
      
        ) {
      notFound(requestURI, (HttpServletResponse) response.getResponse());
      
      
      
        return
      
      
        ;
    }
    
      
      
        //
      
      
         Ask this Wrapper to process this Request
      
      
            response.setContext(context);
    wrapper.invoke(request, response);
  }  
      
      
        public
      
      
         Container getContainer() {
    
      
      
        return
      
      
         container;
  }

  
      
      
        public
      
      
        void
      
      
         setContainer(Container container) {
    
      
      
        this
      
      .container =
      
         container;
  }

  
      
      
        private
      
      
        void
      
      
         badRequest(String requestURI, HttpServletResponse response) {
    
      
      
        try
      
      
         {
      response.sendError(HttpServletResponse.SC_BAD_REQUEST, requestURI);
    }
    
      
      
        catch
      
      
         (IllegalStateException e) {
      ;
    }
    
      
      
        catch
      
      
         (IOException e) {
      ;
    }
  }

  
      
      
        private
      
      
        void
      
      
         notFound(String requestURI, HttpServletResponse response) {
    
      
      
        try
      
      
         {
      response.sendError(HttpServletResponse.SC_NOT_FOUND, requestURI);
    }
    
      
      
        catch
      
      
         (IllegalStateException e) {
      ;
    }
    
      
      
        catch
      
      
         (IOException e) {
      ;
    }
  }

}
      
    

基礎閥持有對Context容器實例(SimpleContext)的引用,在它的關鍵方法void invoke(Request request, Response response, ValveContext valveContext)里面,先調用Context容器實例的Container map(Request request, boolean update)方法獲取子容器實例wrapper,最后調用子容器實例wrapper的invoke(Request request, Response response)方法

至于管道類SimplePipeline與上文相同,此處不再描述

---------------------------------------------------------------------------?

本系列How Tomcat Works系本人原創(chuàng)?

轉載請注明出處 博客園 刺猬的溫馴?

本人郵箱: chenying998179 # 163.com ( #改為@

本文鏈接 http://www.cnblogs.com/chenying99/p/3235730.html

How Tomcat Works(八)


更多文章、技術交流、商務合作、聯(lián)系博主

微信掃碼或搜索:z360901061

微信掃一掃加我為好友

QQ號聯(lián)系: 360901061

您的支持是博主寫作最大的動力,如果您喜歡我的文章,感覺我的文章對您有幫助,請用微信掃描下面二維碼支持博主2元、5元、10元、20元等您想捐的金額吧,狠狠點擊下面給點支持吧,站長非常感激您!手機微信長按不能支付解決辦法:請將微信支付二維碼保存到相冊,切換到微信,然后點擊微信右上角掃一掃功能,選擇支付二維碼完成支付。

【本文對您有幫助就好】

您的支持是博主寫作最大的動力,如果您喜歡我的文章,感覺我的文章對您有幫助,請用微信掃描上面二維碼支持博主2元、5元、10元、自定義金額等您想捐的金額吧,站長會非常 感謝您的哦!!!

發(fā)表我的評論
最新評論 總共0條評論
主站蜘蛛池模板: 咪咪色在线视频 | 宅男噜噜噜66一区二区 | 日本一级一片免在线观看 | 五月天激情婷婷 | 成人亚洲视频 | 久久精品国产亚洲高清 | 成人毛片免费视频播放 | 99视频精品全国在线观看 | 激情影院在线观看 | 国产高清国内精品福利 | 国产精品98视频全部国产 | 美女黄色免费在线观看 | 久久羞羞 | 久一视频在线观看 | 亚洲精品老司机综合影院 | 久青草青综合在线视频 | 亚洲四虎永久在线播放 | 午夜在线播放免费高清观看 | 99re6久精品国产首页 | 久久婷婷成人综合色 | 最新黄色免费网站 | 国产亚洲精品精品国产亚洲综合 | 久久国产精品亚洲综合 | 日本国产成人精品视频 | 欧美一区二区三区播放 | 末成年娇小性色xxxxx视频 | 亚洲一区精品中文字幕 | 成人人观看的免费毛片 | 97最新| 久久免费高清 | 无遮挡无遮挡91桃色在线观看 | 99视频在线免费观看 | 青青热久久国产久精品 | 俄罗斯一级毛片免费视频 | 在线看的成人性视频 | 色接久久| 99视频在线免费观看 | 狠狠亚洲 | 亚洲系列在线 | 黄色毛片毛茸茸 | 国产免费人人看大香伊 |