netty ChannelPipeline的事件傳輸機制(入站和出站的方法)
文章目錄
- 一、Netty的事件型別
- 1、入站事件傳播方法
- 1.1、ChannelHandlerContext#fireChannelRegistered()
- 1.2、ChannelHandlerContext#fireChannelActive()
- 1.3、ChannelHandlerContext#fireChannelRead(Object)
- 1.4、ChannelHandlerContext#fireChannelReadComplete()
- 1.5、ChannelHandlerContext#fireExceptionCaught(Throwable)
- 1.6、ChannelHandlerContext#fireUserEventTriggered(Object)
- 1.7、ChannelHandlerContext#fireChannelWritabilityChanged()
- 1.8、ChannelHandlerContext#fireChannelInactive()
- 1.9、ChannelHandlerContext#fireChannelUnregistered()
- 2、出站事件傳播方法:
- 2.1、ChannelHandlerContext#bind(SocketAddress, ChannelPromise)
- 2.2、ChannelHandlerContext#connect(SocketAddress, SocketAddress, ChannelPromise)
- 2.3、ChannelHandlerContext#write(Object, ChannelPromise)
- 2.4、ChannelHandlerContext#flush()
- 2.5、ChannelHandlerContext#read()
- 2.6、ChannelHandlerContext#disconnect(ChannelPromise)
- 2.7、ChannelHandlerContext#close(ChannelPromise)
- 2.8、ChannelHandlerContext#deregister(ChannelPromise)
- 3、下圖描述了在ChannelPipeline中ChannelHandlers如何處理I/O事件
- 二、ChannelPipeline的結構
- 三、HeadContext的作用
- 四、TailContext的作用
- 五、Inbound事件流
- 六、Outbound 事件流
原部落格,點選這裡
一、Netty的事件型別
從ChannelPipeline的傳輸的事件型別角度,Netty的事件可以分為Inbound和Outbound事件。
Inbound事件是一個通知事件,當某件事已經發生了,然後通過Inbound事件進行通知,Inbound通常發生在Channel的狀態的改變或IO事件就緒
Outbound事件都是請求事件, 請求某件事情的發生, 然後通過Outbound事件進行通知。
1、入站事件傳播方法
1.1、ChannelHandlerContext#fireChannelRegistered()
作用:觸發事件告知Inbound ChannelHandler:ChannelHandlerContext的Channel註冊於其EventLoop,呼叫ChannelInboundHandler的channelRegistered
1.2、ChannelHandlerContext#fireChannelActive()
作用:觸發事件告知Inbound ChannelHandler:ChannelHandlerContext的Channel現在處於活動狀態,呼叫ChannelInboundHandler的channelActive
1.3、ChannelHandlerContext#fireChannelRead(Object)
作用:觸發事件告知Inbound ChannelHandler:當前Channel正在從對等方讀取訊息,呼叫ChannelInboundHandler的channelRead。
1.4、ChannelHandlerContext#fireChannelReadComplete()
作用:觸發事件告知Inbound ChannelHandler:當前讀操作讀取的最後一條訊息被channelRead(ChannelHandlerContext, Object)}使用,呼叫ChannelInboundHandler的channelReadComplete。
1.5、ChannelHandlerContext#fireExceptionCaught(Throwable)
作用:觸發事件告知Inbound ChannelHandler:丟擲Throwable異常,呼叫ChannelInboundHandler的exceptionCaught。
1.6、ChannelHandlerContext#fireUserEventTriggered(Object)
作用:觸發事件告知Inbound ChannelHandler:使用者事件正在觸發,呼叫ChannelInboundHandler的userEventTriggered。
1.7、ChannelHandlerContext#fireChannelWritabilityChanged()
作用:觸發事件告知Inbound ChannelHandler:Channel的可寫狀態發生更改,呼叫ChannelInboundHandler的channelWritabilityChanged。
1.8、ChannelHandlerContext#fireChannelInactive()
作用:觸發事件告知Inbound ChannelHandler:ChannelHandlerContext的Channel現在是不活動的,並已達到其生命週期的結束,呼叫ChannelInboundHandler的channelInactive
1.9、ChannelHandlerContext#fireChannelUnregistered()
作用:觸發事件告知Inbound ChannelHandler:ChannelHandlerContext的Channel從其EventLoop登出,呼叫ChannelInboundHandler的channelUnregistered
2、出站事件傳播方法:
2.1、ChannelHandlerContext#bind(SocketAddress, ChannelPromise)
作用:請求繫結到給定的SocketAddress,並在操作完成後通知ChannelFuture,原因可能是操作成功,也可能是錯誤,呼叫ChannelOutboundHandler的bind
2.2、ChannelHandlerContext#connect(SocketAddress, SocketAddress, ChannelPromise)
作用:請求連線到給定的SocketAddress,並在操作完成後通知ChannelFuture,原因可能是操作成功,也可能是錯誤,呼叫ChannelOutboundHandler的connect
2.3、ChannelHandlerContext#write(Object, ChannelPromise)
作用:請求通過這個ChannelHandlerContext通過ChannelPipeline寫入訊息。此方法不會請求實際重新整理,因此請確保在希望請求將所有掛起資料重新整理到實際傳輸時呼叫flush()。
2.4、ChannelHandlerContext#flush()
作用:請求通過此ChannelOutboundInvoker重新整理所有掛起的訊息。
2.5、ChannelHandlerContext#read()
作用:請求從Channel讀取資料到第一個入站緩衝區,如果讀取資料,則觸發ChannelInboundHandler#channelRead(ChannelHandlerContext, Object)事件,並觸發ChannelInboundHandler#channelReadComplete(ChannelHandlerContext) channelReadComplete事件,以便處理程式可以決定繼續讀取。如果已經有一個掛起的讀操作,這個方法什麼也不做。
2.6、ChannelHandlerContext#disconnect(ChannelPromise)
作用:請求斷開與遠端對等點的連線,並在操作完成後通知ChannelFuture,原因可能是操作成功,也可能是錯誤,呼叫ChannelOutboundHandler的disconnect
2.7、ChannelHandlerContext#close(ChannelPromise)
作用:請求關閉Channel,並在操作完成後通知ChannelFuture,原因可能是操作成功,也可能是錯誤,呼叫ChannelOutboundHandler的close。關閉後,就不可能再重用它了。
2.8、ChannelHandlerContext#deregister(ChannelPromise)
作用:請求從之前分配的EventExecutor取消註冊,並在操作完成後通知ChannelFuture,原因可能是操作成功,也可能是錯誤,呼叫ChannelOutboundHandler的deregister。
3、下圖描述了在ChannelPipeline中ChannelHandlers如何處理I/O事件
這個圖是原始碼io.netty.channel.ChannelPipeline介面的備註部分提供的。
二、ChannelPipeline的結構
ChannelPipeline的資料結構是雙向連結串列。
三、HeadContext的作用
Outbound事件最後都是通過HeadContext完成(HeadContext最後呼叫NioSocketChannelUnsafe響應的方法完成),Inbound事件是從HeadContext開始。
四、TailContext的作用
一個處理位元組和訊息的特殊的捕獲全部事件的處理程式,Outbound事件是從tailContext開始,Inbound事件是在tailContext結束。
五、Inbound事件流
在Channel中呼叫DefaultChannelPipeline.fireChannelActive,接下來在Channel交給自己的DefaultChannelPipeline執行了,因為是Inbound事件,所以從HeadContext->TailContext。DefaultChannelPipeline中Inbound事件傳遞過程:
Context.fireChannelActive -> Connect.findContextInbound -> Connect.invokeChannelActive(final AbstractChannelHandlerContext next)-> next.invokeChannelActive -> nextHandler.channelActive -> nextContext.fireChannelActive
六、Outbound 事件流
6.1、Outbound事件流過程
以 Bootstrap.connect 的事件流為例,大致如下:
Bootstrap.connect -> Bootstrap.doResolveAndConnect-> Bootstrap.doResolveAndConnect0-> Bootstrap.doConnect-> AbstractChannel.connect->DefaultChannelPipeline.connect->NioSocketChannelUnsafe.connect->NioSocketChannel.doConnect->SocketChannel.connect
最後都是到了Channel,然後Channel交給自己的DefaultChannelPipeline執行,因為是 Outbound 事件,所以從TailContext ->HeadContext,HeadContext最後呼叫NioSocketChannelUnsafe響應的方法完成,事件流的NioSocketChannelUnsafe.connect->NioSocketChannel.doConnect->SocketChannel.connect部分就是在HeadContext裡面執行的。
6.2、DefaultChannelPipeline中事件傳遞過程
Context.connect -> Context.findContextOutbound -> next.invokeConnect -> handler.connect -> Context.connect
一致迴圈從TailContext 將事件傳遞到HeadContext。
相關文章
- 【Netty】ChannelHandler和ChannelPipelineNetty
- Netty背後的事件驅動機制Netty事件
- Netty原始碼解析 -- ChannelPipeline機制與讀寫過程Netty原始碼
- 【Netty】Netty傳輸Netty
- Android輸入系統(一)輸入事件傳遞流程和InputManagerService的誕生Android事件
- iOS中觸控事件的傳遞和響應機制iOS事件
- iOS 中的事件傳遞和響應機制 - 原理篇iOS事件
- iOS 中的事件傳遞和響應機制 - 實踐篇iOS事件
- iOS 中的事件傳遞和響應機制 – 實踐篇iOS事件
- 史上最詳細的iOS之事件的傳遞和響應機制iOS事件
- Android事件傳遞機制Android事件
- 深入淺出Netty:ChannelPipelineNetty
- Android中觸控事件的傳遞機制Android事件
- Android TouchEvent事件傳遞機制Android事件
- Android onTouch事件傳遞機制Android事件
- Redis的事件機制Redis事件
- netty系列之:channelPipeline詳解Netty
- FTP的傳輸有兩種方式:ASCII傳輸模式和二進位制資料傳輸模式FTPASCII模式
- Android10_原理機制系列_事件傳遞機制Android事件
- Netty使用及事件傳遞Netty事件
- ios,android和javascript的UI事件機制iOSAndroidJavaScriptUI事件
- JS的事件物件與事件機制JS事件物件
- Netty原始碼解析 -- 事件迴圈機制實現原理Netty原始碼事件
- Netty學習筆記(番外篇) - ChannelHandler、ChannelPipeline和ChannelHandlerContext的聯絡Netty筆記Context
- Netty 框架學習 —— 傳輸Netty框架
- Android觸控事件傳遞機制Android事件
- Android View 事件傳遞機制剖析AndroidView事件
- Netty 框架學習 —— ChannelHandler 與 ChannelPipelineNetty框架
- Netty學習之ChannelHandler&ChannelPipelineNetty
- Netty之DefaultAttributeMap與AttributeKey的機制和原理Netty
- AngularJS 的髒值檢查和事件機制AngularJS事件
- 淺談前端和移動端的事件機制前端事件
- Javascript事件模型系列(二)事件的捕獲-冒泡機制及事件委託機制JavaScript事件模型
- Android輸入系統(二)IMS的啟動過程和輸入事件的處理Android事件
- netty系列之:基於流的資料傳輸Netty
- Netty原始碼分析(七):初識ChannelPipelineNetty原始碼
- redis的事件處理機制Redis事件
- WebSocket的事件觸發機制Web事件