NettyServer

1、private Map< String, Channel> channels:< ip:port, channel> 所有通道。

2、private ServerBootstrap bootstrap : netty 服務(wù)端啟動器。

3、private io.netty.channel.Channel channel:服務(wù)端監(jiān)聽通道。

4、private EventLoopGroup bossGroup;Netty boss線程組(負(fù)責(zé)連接事件)

5、private EventLoopGroup workerGroup : nety work線程組(負(fù)責(zé)IO事件)

代碼@1:調(diào)用父類的構(gòu)造方法,主要初始化AbstractPeer(channelHandler、url)和AbstractEndpoint(codec2、timeout、idleTimeout )

代碼@2:根據(jù)URL中的host與端口,創(chuàng)建localAddress。

代碼@3:如果配置了< dubbo:parameter key = “bind.ip” value = “”/> 與 < dubbo:parameter key = “bind.port” />,則用該IP與端口創(chuàng)建bindAddress,通常用于多網(wǎng)卡,如果未配置,bindAddress與 localAddress綁定的IP與端口一樣。

代碼@4:初始化accepts與idleTimeout ,這兩個(gè)參數(shù)未被其他地方使用。

代碼@5,調(diào)用doOpen方法,正式在相應(yīng)端口建立網(wǎng)絡(luò)監(jiān)聽。

1.2、源碼分析NettyServer#doOpen


代碼@1:創(chuàng)建Netty服務(wù)端啟動幫助類ServerBootstrap.

代碼@2:創(chuàng)建服務(wù)端Boss線程,線程名:.NettyServerBoss,主要負(fù)責(zé)客戶端的連接事件,主從多Reactor線程模型中的主線程(連接事件)。

代碼@3:創(chuàng)建服務(wù)端Work線程組,線程名:NettyServerWorker-序號,線程個(gè)數(shù)取自參數(shù):iothreads,默認(rèn)為(CPU核數(shù)+1)與32取小值,顧名思義,IO線程數(shù),主要處理讀寫事件,編碼、解碼都在IO線程中完成。

代碼@4:創(chuàng)建用戶Handler,這里是NettyServerHandler。

代碼@5:Netty啟動的常規(guī)寫法,關(guān)注如下內(nèi)容:

addLast(“decoder”, adapter.getDecoder()) : 添加解碼器

addLast(“encoder”, adapter.getEncoder()) :添加編碼器

addLast(“handler”, nettyServerHandler) :添加業(yè)務(wù)Handler。

這里簡單介紹一下流程:

1、客戶端建立與服務(wù)端連接,此時(shí)Boss線程的連接事件觸發(fā),建立TCP連接,并向IO線程注冊該通道(Channel0)的讀事件。

2、當(dāng)客戶端向服務(wù)端發(fā)送請求消息后,IO線程中的讀事件觸發(fā),會首先調(diào)用adapter.getDecoder() 根據(jù)對應(yīng)的請求協(xié)議(例如dubbo)從二進(jìn)制流中解碼出一個(gè)完整的請求對象,然后傳入到業(yè)務(wù)handler,例如nettyServerHandler,執(zhí)行相應(yīng)的事件方法,例如recive方法。

3、當(dāng)服務(wù)端向Channel寫入響應(yīng)結(jié)果時(shí),首先編碼器會按照協(xié)議編碼成二進(jìn)制流,供客戶端解碼。