天天看點

Netty3 源碼分析 - ClientBootstrap

Bootstrap是 通道初始化輔助類 提供了初始化通道或子通道所需要的資料結構,那麼ClientBootstrap就是用戶端的,而且會執行連接配接操作。

Netty3 源碼分析 - ClientBootstrap

配置通道,就是把相應的鍵值對選項傳遞給底層:  ClientBootstrap b = ...;  // Options for a new channel  b.setOption("remoteAddress", new InetSocketAddress("example.com", 8080));  b.setOption("tcpNoDelay", true);  b.setOption("receiveBufferSize", 1048576);

配置通道流水線,每個通道有自己的pipeline,建議的方式是調用Bootstrap.setPipelineFactory(ChannelPipelineFactory)來制定ChannelPipelineFactory :  ClientBootstrap b = ...;  b.setPipelineFactory(new MyPipelineFactory());

 public class MyPipelineFactory implements ChannelPipelineFactory {    public ChannelPipeline getPipeline() throws Exception {      // Create and configure a new pipeline for a new channel.      ChannelPipeline p = Channels.pipeline();      p.addLast("encoder", new EncodingHandler());      p.addLast("decoder", new DecodingHandler());      p.addLast("logic",   new LogicHandler());      return p;    }  }

另一種方式,隻在特定情況下适用(在Bootstrap的源碼中有解釋),就是利用預設的pipeline,并且讓新的Channel來淺拷貝它:  ClientBootstrap b = ...;  ChannelPipeline p = b.getPipeline();

 // Add handlers to the default pipeline.  p.addLast("encoder", new EncodingHandler());  p.addLast("decoder", new DecodingHandler());  p.addLast("logic",   new LogicHandler());

淺拷貝意味着預設pipeline裡面的Handler,隻是他們的引用增加到了新的ChannelPipeline中,是以要注意那些Handler是否有副作用。是以不适合在伺服器端為每個新來的連接配接打開一個Channel的情況,為不同的Channel定制不同的配置。

此外 ClientBootstrap隻是一個輔助類,沒有配置設定和管理任何資源,真正管理資源的是構造器中傳入的 ChannelFactory的實作,是以用同樣的 ChannelFactory  來構造多個Bootstrap執行個體,為不同的通道應用不同的設定是完全OK的。

bind方法:  綁定操作,在綁定和連接配接需要分開的時候用到。  比如在嘗試連接配接之前,可以通過Channel.setAttachment(Object)為這個通道設定一個attachment  這樣一旦連接配接建議,就可以通路這個attachment。   ChannelFuture bindFuture = bootstrap.bind(new InetSocketAddress("192.168.0.15", 0));   Channel channel = bindFuture.getChannel();   channel.setAttachment(dataObj);   channel.connect(new InetSocketAddress("192.168.0.30", 8080)); 在ChannelHandler中可以向下面這樣通路。   public class YourHandler extends SimpleChannelUpstreamHandler {       public void channelConnected(ChannelHandlerContext ctx, ChannelStateEvent e) throws Exception {           Object dataObject = ctx.getChannel().getAttachment();       }   }

詳細的源碼注釋可以看我的Github。

繼續閱讀