Bootstrap.main()->Bootstrap.init()
bootstrap.init() 方法中設定catalinaDaemon
建立 Connector 對象
Bootstrap.main()->Bootstrap.start()->Catalina.start()->Catalina.load()->Catalina.createStartDigester()
createStartDigester() 方法
1. 建立connector對象,并判斷server.xml 中是否配置線程池,如果配置線程池則建立線程池
- 為connector對象設定除executor外的其它屬性資訊
- 把目前connector添加到StandardService.connectors 數組中。
Connector
構造
通過protocol協定來判斷使用那個protocolHandler。
setProtocol 方法
tomcat 預設配置 是以BIO的模式啟動的,預設會調用org.apache.coyote.http11.Http11Protocol。
下面我們以Http11Protocol來分析Connector。
startInternal() 方法
1. 設定tomcat狀态為,正在啟動
2. 啟動 connector。
Http11Protocol
- 在構造方法中建立JIoEndpoint和Http11ConnectionHandler對象
- 設定 socket 參數
AbstractEndpoint.start() 方法
JIoEndpoint 繼承 AbstractEndpoint
JIoEndpoint .bind() 方法
在這建立connector的socket服務,使用serverSocket監聽入站連接配接。
JIoEndpoint.startInternal() 方法
1. 判斷線程池是否為空,如果為空則建立預設的線程池。(server.xml的connector中配置的線程池)
2. 根據server.xml中的connector中的acceptorThreadCount屬性來确定建立幾個接受請求處理的線程。
Acceptor類,負責處理接受用戶端請求的處理。
server.xml 中配置如下:
acceptorThreadCount 個數建議和CPU的個數一緻。
createExecutor() 方法
預設建立的線程池,最小線程數為10,最大線程數為200,空閑時間為60秒,隊列為LinkedBlockingQueue,隊列大小預設為Ineteger.MAX_VALUE。
這裡需要注意的是,如果隊列中的元素沒有存滿,那麼線程的數量一直會是10,而不會自動擴大到200。是以建議大家自己設定一個線程池,而不要用預設的
Acceptor 類
Acceptor.run() 方法
-
擷取之前建立的serverSocket。
2.設定socket的參數
- 調用processSocket 處理請求的socket
processSocket() 方法
把socket封裝成SocketWrapper對象 傳給SocketProcessor對象,并送出給線程池處理。
SocketProcessor
負責解析http協定資訊。
SOcketProcessor重要屬性
inputBuffer:包裝socket的inputStream,并解析http協定資訊。
outputBuffer:包裝socket的outputStream,負責響應使用者的資料。
run() 方法
在process方法中處了解析http協定資訊。
Http11Processor.process() 方法
Http11Protocol.process()->Http11Processor.process() 代碼如下:
擷取socket的輸入流和輸出流
Http11Processor構造方法
在這裡,構造Request和Response對象。
解析http協定
解析完後的資料存儲到 AbstractInputBuffer的下面兩個屬性中
protected Request request;
protected MimeHeaders headers;
request對象就是 HttpServletRequest 對象的原型。
解析完之後,調用下面的service方法。
這裡的service方法會調用servlet中的service方法并傳入request和response對象,然後根據請求的方法來決定調用的是servlet的doGet方法還是doPost或其它的方法。
到此 Connector的整理流程就結束了。
簡單梳理下
1. Connector
根據協定來選擇協定的處理類,tomcat預設的處理類是Http11Protocol。
2. JIoEndpoint
- 建立ServerSocket 連接配接
- 建立接受請求的線程 Acceptor對象。
- 建立處理請求的線程池 executor。
3. Http11Processor
主要負責解析http協定的
1. 解析請求行 (來确定http協定、請求的url、請求的method)
2. 解析請求頭 headers
3.并把解析後的結果交給 Container 處理
connector 可配置的部分參數
參數值根據自己項目做響應修改。下面的隻是個例子
<Connector port="8080" protocol="HTTP/1.1"
acceptCount="1000"
disableUploadTimeout="true"
enableLookups="false"
keepAliveTimeout="20"
maxThreads="500"
minThreads="500"
maxProcessor="500"
minSpareThreads="20"
maxKeepAliveRequests="1"
connectionTimeout="20"
redirectPort="8443"
allowTrace="false"
acceptorThreadCount="2"
acceptorThreadPriority="7"
socket.tcpNoDelay="true"
threadPriority="8"
tcpNoDelay="true"
compression="on"
emptySessionPath="true"
/>
本人簡書blog位址:http://www.jianshu.com/u/1f0067e24ff8
點選這裡快速進入簡書
GIT位址:http://git.oschina.net/brucekankan/
點選這裡快速進入GIT