Netty 4.x

1. 高性能通讯框架,解决的是  "网络层" 的问题, 包括并发太多时,已经阻塞的IO(read/write) 导致新连接无法connect, accept的问题,

    以及内存拷贝,上下文切换等问题。 主要的 目的是为了让你的 带宽能够完全发挥,不受 socket读写线程的影响。

 

2. 线程模型reactor:

   2.1  单线程, 一个accept线程(NIO, 只处理到 connect/accpet,可以认为打开了一个新句柄,发送了ACK给client )  + 1个 read 线程 + 1个write线程

   2.2  多线程,一个accpet线程 + n个read + n个write(1个write?)

   2.3  主从线程池模型,

             (bossPool负责 connect,accept, ssl头,ACK,新句柄等等)

             (workPool 负责 read,write, encode, decode)

 

3.  NioEventLoop 是个好东西,  accept 也靠他, 读写也靠他。

ServerBootstrap bootstrap = new ServerBootstrap();

EventLoopGroup bossGroup = new NioEventLoopGroup();
EventLoopGroup workGroup = new NioEventLoopGroup();

    执行过程中不会被其他线程抢占, 设定的大小不应该过大。

    workGroup中的NioEventLoop需要特别注意,不要在这种中间增加“业务”代码, 

参照:

2.4. Netty线程开发最佳实践

2.4.1. 时间可控的简单业务直接在IO线程上处理

如果业务非常简单,执行时间非常短,不需要与外部网元交互、访问数据库和磁盘,不需要等待其它资源,则建议直接在业务ChannelHandler中执行,不需要再启业务的线程或者线程池。避免线程上下文切换,也不存在线程并发问题。

2.4.2. 复杂和时间不可控业务建议投递到后端业务线程池统一处理

对于此类业务,不建议直接在业务ChannelHandler中启动线程或者线程池处理,建议将不同的业务统一封装成Task,统一投递到后端的业务线程池中进行处理。

过多的业务ChannelHandler会带来开发效率和可维护性问题,不要把Netty当作业务容器,对于大多数复杂的业务产品,仍然需要集成或者开发自己的业务容器,做好和Netty的架构分层。

2.4.3. 业务线程避免直接操作ChannelHandler

对于ChannelHandler,IO线程和业务线程都可能会操作,因为业务通常是多线程模型,这样就会存在多线程操作ChannelHandler。为了尽量避免多线程并发问题,建议按照Netty自身的做法,通过将操作封装成独立的Task由NioEventLoop统一执行,而不是业务线程直接操作,相关代码如下所示:

图2-31 封装成Task防止多线程并发操作

如果你确认并发访问的数据或者并发操作是安全的,则无需多此一举,这个需要根据具体的业务场景进行判断,灵活处理。

 

 

目前看来,Netty的定位:

1. 网关

2. 消息推送

 

posted @ 2015-03-24 15:23  njuzhoubing  阅读(401)  评论(0编辑  收藏  举报