Netty Pipeline、channel、Context之间的数据流向
2018-03-01 22:58
375 查看
以下所绘制图形均基于Netty4.0.28版本。
一、connect(outbound类型事件)
当用户调用channel的connect时,会发起一个outbound类型的事件,该事件将在pipeline中传递(pipeline.connect),首先由tail handler处理,该handler只是将事件透传给下一个outbound类型的用户Handler(如果有),事件依次传递下去,直到传递到head handler,该handler会调用unsafe.connect()向eventloop(nio的selector)注册一个读事件。
二、connect成功之后数据流图(inbound类型事件)
当用户发起一个connect请求后,当连接可用时,eventloop(底层使用nio的selector)会引发一个ChannelActive事件,该事件最先有unsafe捕获,之后会调用pipeline.fireChannelActive()将该事件在pipeline中传播,紧接着会根据inbound类型事件的传递方式在各个handler和context之间进行链式传递。其中,有一个比较关注的地方是,在channelActive事件触发的时候,如果channel被设置成autoRead,那么此时还会调用channel.read()方法,该方法并不是真正的从channel读取数据,而是向eventloop注册读事件(因为一个channel在向eventloop中注册时,默认不注册任何事件),关于channel.read的过程可以看下文的另一张图。
三、channel.read事件流图(outbound类型事件)
当用户调用channel.read()后,会发起一个outbound类型的事件,该事件最先会由pipeline中tail handler处理,该handler只是将该事件透传给前面一个outbound类型的用户handler(如果有的话),这样依次继续向前传递,直到传递到head handler,该handler会调用unsafe.read()向eventloop注册读事件(也就是向nio的selector上添加读事件)
四、channel.write(outbound类型事件)
与channel.read()类型,wirte也是一个outbound类型事件,该事件最先会由pipeline中的tail handler透传给前面的一个outbound类型的用户handler(如果有的话),这样依次传递,直到传递给head handler,该handler会调用unsafe.write()方法,这里的wirte并不会执行真正的发送,而是将要发送的数据缓存起来,直到调用flush时,这些数据才会执行真正的网络io。
五、flush(outbound类型事件)
如前文所示,flush也是一个outbound类型的事件,与wirte不同,flush会执行真正的网络io操作。
六、当channel有数据可读时(inbound类型事件)
当eventloop层检测到网络层有数据可读时(nio的selector返回相应的seleciontKeys),该事件会首先传递给unsafe,紧接着会调用pipeline.fireChannelRead(),将事件开始在pipeline中传递,该事件最先会有head handler处理(head.fireChannelRead()),该handler直接将事件透传给下一个inbound类型的用户handler(如果有的话),该事件依次向下传递,直到传递到tail handler。
一、connect(outbound类型事件)
当用户调用channel的connect时,会发起一个outbound类型的事件,该事件将在pipeline中传递(pipeline.connect),首先由tail handler处理,该handler只是将事件透传给下一个outbound类型的用户Handler(如果有),事件依次传递下去,直到传递到head handler,该handler会调用unsafe.connect()向eventloop(nio的selector)注册一个读事件。
二、connect成功之后数据流图(inbound类型事件)
当用户发起一个connect请求后,当连接可用时,eventloop(底层使用nio的selector)会引发一个ChannelActive事件,该事件最先有unsafe捕获,之后会调用pipeline.fireChannelActive()将该事件在pipeline中传播,紧接着会根据inbound类型事件的传递方式在各个handler和context之间进行链式传递。其中,有一个比较关注的地方是,在channelActive事件触发的时候,如果channel被设置成autoRead,那么此时还会调用channel.read()方法,该方法并不是真正的从channel读取数据,而是向eventloop注册读事件(因为一个channel在向eventloop中注册时,默认不注册任何事件),关于channel.read的过程可以看下文的另一张图。
三、channel.read事件流图(outbound类型事件)
当用户调用channel.read()后,会发起一个outbound类型的事件,该事件最先会由pipeline中tail handler处理,该handler只是将该事件透传给前面一个outbound类型的用户handler(如果有的话),这样依次继续向前传递,直到传递到head handler,该handler会调用unsafe.read()向eventloop注册读事件(也就是向nio的selector上添加读事件)
四、channel.write(outbound类型事件)
与channel.read()类型,wirte也是一个outbound类型事件,该事件最先会由pipeline中的tail handler透传给前面的一个outbound类型的用户handler(如果有的话),这样依次传递,直到传递给head handler,该handler会调用unsafe.write()方法,这里的wirte并不会执行真正的发送,而是将要发送的数据缓存起来,直到调用flush时,这些数据才会执行真正的网络io。
五、flush(outbound类型事件)
如前文所示,flush也是一个outbound类型的事件,与wirte不同,flush会执行真正的网络io操作。
六、当channel有数据可读时(inbound类型事件)
当eventloop层检测到网络层有数据可读时(nio的selector返回相应的seleciontKeys),该事件会首先传递给unsafe,紧接着会调用pipeline.fireChannelRead(),将事件开始在pipeline中传递,该事件最先会有head handler处理(head.fireChannelRead()),该handler直接将事件透传给下一个inbound类型的用户handler(如果有的话),该事件依次向下传递,直到传递到tail handler。
相关文章推荐
- 图解Netty之Pipeline、channel、Context之间的数据流向。
- Netty学习总结(4)——图解Netty之Pipeline、channel、Context之间的数据流向
- Netty学习总结(4)——图解Netty之Pipeline、channel、Context之间的数据流向
- 步步为营VS 2008 + .NET 3.5(13) - DLINQ(LINQ to SQL)之用户自定义函数、在不同的DataContext之间做更新、缓存、获取信息、数据加载选项和延迟加载
- NIO(2) Channel之间数据传输
- JAVA-4NIO之Channel之间的数据传输方法
- Java的NIO之不同channel之间传输数据
- 利用channel在goroutins之间控制同步和传递数据
- EF数据存贮问题二之“无法定义这两个对象之间的关系,因为它们附加到不同的 ObjectContext 对象”
- DLINQ(LINQ to SQL)之用户自定义函数、在不同的DataContext之间做更新、缓存、获取信息、数据加载选项和延迟加载
- Netty中Channel、ChannelPipeline、ChannelHandler、ChannelHandlerContext之间的关系
- 步步为营VS 2008 + .NET 3.5(13) - DLINQ(LINQ to SQL)之用户自定义函数、在不同的DataContext之间做更新、缓存、获取信息、数据加载选项和延迟加载
- 步步为营VS 2008 + .NET 3.5(13) - DLINQ(LINQ to SQL)之用户自定义函数、在不同的DataContext之间做更新、缓存、获取信息、数据加载选项和延迟加载
- 利用channel在goroutins之间控制同步和传递数据
- Java基础知识强化之IO流笔记76:NIO之 Channel(通道)之间的数据传输
- netty源码分析(十二)Channel与ChannelHandler及ChannelHandlerContext之间的关系分析
- 网页之间数据传递之一sendRedirect
- thrift/swift:服务端数据类型和client端数据类型之间的直接转换
- javascript表单之间的数据传递! 选择自 itfly 的 Blog
- jdk5 Exchanger 线程之间数据交换