Netty背後的事件驅動機制
Netty簡介
Netty是 一個非同步事件驅動的網路應用程式框架,用於快速開發可維護的高效能協議伺服器和客戶端。
事件驅動模型
通常,我們設計一個事件處理模型的程式有兩種思路
輪詢方式
執行緒不斷輪詢訪問相關事件發生源有沒有發生事件,有發生事件就呼叫事件處理邏輯。
事件驅動方式
事件發生時主執行緒把事件放入事件佇列,在另外執行緒不斷迴圈消費事件列表中的事件,呼叫事件對應的處理邏輯處理事件。事件驅動方式也被稱為訊息通知方式,其實是設計模式中觀察者模式的思路。
借用O'Reilly大神關於事件驅動模型解釋圖
主要包括4個基本元件:
事件佇列(event queue):接收事件的入口,儲存待處理事件
分發器(event mediator):將不同的事件分發到不同的業務邏輯單元
事件通道(event channel):分發器與處理器之間的聯絡渠道
事件處理器(event processor):實現業務邏輯,處理完成後會發出事件,觸發下一步操作
可以看到,相對傳統輪詢模式,事件驅動有如下優點:
可擴充套件性好,分散式的非同步架構,事件處理器之間高度解耦,可以方便擴充套件事件處理邏輯
高效能,基於佇列暫存事件,能方便並行非同步處理事件
下圖描述了Netty進行事件處理的流程。Channel是連線的通道,是ChannelEvent的產生者,而ChannelPipeline可以理解為ChannelHandler的集合。
事件分為上行(Upstream)和下行(Downstream)兩種
當伺服器從客戶端收到一個訊息,那麼與之相關的就是一個上行事件(Upstream Event),Pipeline中的UpstreamChannelHandler會處理它;如果伺服器要響應這個客戶端,那麼與響應訊息對應的就是下行事件(Downstream Event),Pipeline中的DownstreamChannelHandler會處理它。
ChannelEvent是資料或者狀態的載體,例如傳輸的資料對應MessageEvent,狀態的改變對應ChannelStateEvent。當對Channel進行操作時,會產生一個ChannelEvent,併傳送到ChannelPipeline。ChannelPipeline會選擇一個ChannelHandler進行處理。這個ChannelHandler處理之後,可能會產生新的ChannelEvent,並流轉到下一個ChannelHandler。
我們引用Netty官方包裡的一個例子,一個簡單的EchoServer,它接受客戶端輸入,並將輸入原樣返回。
public void run() {
// Configure the server.
ServerBootstrap bootstrap = new ServerBootstrap(
new NioServerSocketChannelFactory(
Executors.newCachedThreadPool(),
Executors.newCachedThreadPool()));
// Set up the pipeline factory.
bootstrap.setPipelineFactory(new ChannelPipelineFactory() {
public ChannelPipeline getPipeline() throws Exception {
return Channels.pipeline(new EchoServerHandler());
}
});
// Bind and start to accept incoming connections.
bootstrap.bind(new InetSocketAddress(port));
}
EchoServerHandler是這裡的業務處理邏輯
public class EchoServerHandler extends SimpleChannelUpstreamHandler {
@Override
public void messageReceived(
ChannelHandlerContext ctx, MessageEvent e) {
// Send back the received message to the remote peer.
e.getChannel().write(e.getMessage());
}
}
其中MessageEvent就是一個事件。這個事件攜帶了一些資訊(ChannelBuffer),例如這裡e.getMessage()就是訊息的內容,而EchoServerHandler則描述了處理這種事件的方式,一旦某個事件觸發,相應的Handler則會被呼叫,並進行處理(解碼成了一個資料物件),並生成了一個新的MessageEvent,並傳遞給下一步進行處理。
在Netty裡,所有事件都來自ChannelEvent介面,這些事件涵蓋監聽埠、建立連線、讀寫資料等網路通訊的各個階段。而事件的處理者就是ChannelHandler,這樣,不但是業務邏輯,連網路通訊流程中底層的處理,都可以通過實現ChannelHandler來完成了。事實上,Netty內部的連線處理、協議編解碼、超時等機制,都是通過Handler完成的。
技術討論 & 疑問建議 & 個人部落格
版權宣告: 本部落格所有文章除特別宣告外,均採用 CC BY-NC-SA 3.0 許可協議,轉載請註明出處!
參考:https://github.com/code4craft/netty-learning/blob/master/publish/all.md
相關文章
- [譯]理解 Node.js 事件驅動機制Node.js事件
- 資料驅動背後的“陷阱”
- spring — Spring中的事件驅動機制解析Spring事件
- MySQL 索引機制背後的隱藏之道MySql索引
- 拇指記者深入Android公司,打探事件分發機制背後的祕密Android事件
- 事件驅動的微服務-事件驅動設計事件微服務
- Iterator(迭代器)的用法及其背後機制的探究
- Netty原始碼解析 -- 事件迴圈機制實現原理Netty原始碼事件
- 深入理解 ngrx effect 背後的工作機制
- RocketMQ 事件驅動:雲時代的事件驅動有啥不同?MQ事件
- 從事件驅動程式設計模型分析Handler訊息傳遞機制事件程式設計模型
- 180609-Spring之事件驅動機制的簡單使用Spring事件
- 漫談 Greenplum 開源背後的動機
- 從原始碼角度剖析 setContentView() 背後的機制原始碼View
- netty ChannelPipeline的事件傳輸機制(入站和出站的方法)Netty事件
- Redis的事件機制Redis事件
- Repository的事件驅動事件
- 響應式流的核心機制——背壓機制
- 我的理解——物件導向、事件驅動、後設資料物件事件
- 淺談JS事件機制與React事件機制JS事件React
- 走進snabbdom—Vue2背後的Virtual-DOM的機制Vue
- JS的事件物件與事件機制JS事件物件
- “網路實名制”的背後薦
- 淺談前端和移動端的事件機制前端事件
- Javascript事件模型系列(二)事件的捕獲-冒泡機制及事件委託機制JavaScript事件模型
- [AI]重新審視“幻肢”現象背後的意識機制AI
- 理解 Android Binder 機制(一):驅動篇Android
- Redis 中的事件驅動模型Redis事件模型
- 我對事件驅動的理解事件
- 原型鏈的繼承機制及其背後的程式設計哲學原型繼承程式設計
- DOM事件機制事件
- react事件機制React事件
- redis事件機制Redis事件
- qt事件機制QT事件
- Spring:事件驅動Spring事件
- 我們為什麼會沉迷遊戲?遊戲背後的8個驅動力遊戲
- jQuery的事件機制,事件物件介紹,外掛機制,多庫共存,each()jQuery事件物件
- redis的事件處理機制Redis事件