《Netty实战》阅读小记

  1. Netty,一个构建高度可伸缩的、异步的、事件驱动的网络编程应用的工具包。

  2. Netty是一款异步事件驱动的网络应用程序框架,支持快速地开发可维护的高性能面向协议的服务器和客户端。

  3. 阻塞IO《Netty实战》阅读小记_第1张图片

  4. 非阻塞IO(NIO)(NON-Blocking IO):通过使用选择器轮询的方式
    《Netty实战》阅读小记_第2张图片

  5. Netty的核心组件:一、Channel;二、回调;三、Future;四、事件和ChannelHandler。

  6. Channel代表一个到实体(如一个硬件设备、一个文件、一个网络套接字或者一个能够执行一个或者多个不同的I/O操作的程序组件)的开放连接,如读操作和写操作。

  7. JDK内置的Future会阻塞,Netty提供了自己的实现——ChannelFuture。ChannelFuture可以注册一个或者多个ChannelFutureListener实例,用于回调。

  8. ChannelHandler的实现负责接收并响应事件通知。
    《Netty实战》阅读小记_第3张图片

  9. 针对不同类型的事件来调用ChannelHandler;应用程序通过实现或者扩展Channelhandler来挂钩到事件的生命周期,并且提供自定义的应用程序逻辑;ChannelHandler有助于保持业务逻辑和网络处理代码的分离。
    《Netty实战》阅读小记_第4张图片

《Netty实战》阅读小记_第5张图片

《Netty实战》阅读小记_第6张图片

  1. ChannelHandler的方法是由网络事件驱动(触发)的。

  2. 每一个Channel被创建时会被分配它所专属的ChannelPipelineChannelPipelineChannelHandler的链表,按添加顺序执行处理逻辑。

  3. ChannelHandler被添加到ChannelPipeline时,它将会被分配一个ChannelHandlerContext,其代表了ChannelHandler和ChannelPipeline之间的绑定。虽然这个对象可以被用于获取底层的Channel,但是它主要被用于写出站数据。

  4. 当通过Netty发送或者接收一个消息的时候,就会发生一次数据转换。入站消息会被解码,也就是说,从字节转换为另一种格式,比如java对象;如果是出站,则会被编码为字节。
    《Netty实战》阅读小记_第7张图片

  5. Netty的Channel是线程安全的,如果多个线程都在向它写数据,消息将会被保证按顺序发送。

  6. NIO基于选择器,在那里可以请求在Channel状态发生变化时得到通知。选择器运行在一个检查变化并对其做出相应响应的线程上,在应用程序对状态的改变做出响应之后,选择器将会被重置,并将重复这个过程。
    《Netty实战》阅读小记_第8张图片

《Netty实战》阅读小记_第9张图片

  1. 相比于ByteBuffer只有一个索引用来读和写(使用flip()在读模式和写模式之间进行切换),ByteBuf分别有一个读索引和写索引。

  2. ByteBuf的get和set方法不会改变读写索引,read和write方法会改变读写索引。

  3. ByteBuf的直接缓冲区和堆缓冲区。

  4. PooledByteBufAllocator(池化ByteBuf,最大限度减少内存碎片,使用了jemalloc的高效方法来分配内存)。

  5. ByteBuf使用引用计数来释放对象,其实现了ReferenceCounted接口,和jvm不同的是,一般由最后访问(引用计数)对象的那一方来负责将它释放。
    在这里插入图片描述
    在这里插入图片描述
    《Netty实战》阅读小记_第10张图片
    《Netty实战》阅读小记_第11张图片

  6. ChannelHandler处理事件的时候,通过调用ChannelHandlerContext实现,将事件转发给同一个超类型的下一个ChannelHandlerChannelHandler通过ChannelHandlerContextChannelPipeline或者说其他的ChannelHandler交互。

  7. 每一个ChannelHandler通过EventLoop(I/O线程)来处理传递给它的事件。所以不要阻塞这个线程。

  8. ChannelHandlerContext代表了ChannelHandlerChannelPipeline之间的关联。

  9. ChannelHandlerContext有很多的方法,其中一些方法也存在于Channel和ChannelPipeline本身上,但是Channel或者ChannelPipeline上的这些方法会沿着整个ChannelPipeline进行传播,而调用位于ChannelHandlerContext的相同方法,只会传播给位于该ChannelPipeline中的下一个能够处理该事件的ChannelHandler。
    《Netty实战》阅读小记_第12张图片

《Netty实战》阅读小记_第13张图片
25. 如果要将一个ChannelHandler添加到多个ChannelPipeline中去,Channelhandler必须使用@Sharable注解,否则会报错,同时要保证这个ChannelHandler是线程安全的。
《Netty实战》阅读小记_第14张图片

  1. 同一个EventLoop会被多个Channel共享,这使得可以通过尽可能少量的Thread来支撑大量的Channel,而不是每个Channel分配一个Thread。
    《Netty实战》阅读小记_第15张图片

  2. 因为上图的EventLoop的分配方式可以看到,一个EventLoop可能会被分配给多个Channel,所以对于所有关联的Channel来说,ThreadLocal都将是一样的,所以尽量避免使用。
    《Netty实战》阅读小记_第16张图片

  3. 服务器致力于使用一个父Channel来接受来自客户端的连接,并创建子Channel以用于它们之间的通信;而客户端将最可能只需要一个单独的、没有父Channel的Channel来用于所有的网络交互。
    《Netty实战》阅读小记_第17张图片

《Netty实战》阅读小记_第18张图片
《Netty实战》阅读小记_第19张图片
29. 尽可能地重用EventLoop,以减少线程创建所带来的开销。
30. 编码器是将消息转换成适合于传输的格式(最有可能的是字节流);而对应的解码器则是将网络字节流转换回应用程序的消息格式。所以,编码器操作出站数据,解码器处理入站数据。
《Netty实战》阅读小记_第20张图片

  1. Netty的架构方式使得只需要简单地将一个ChannelHandler添加到ChannelPipeline中,便可以提供一项新功能,甚至像加密这样重要的功能。

你可能感兴趣的:(Netty)