课件和 Demo 地址
https://github.com/geektime-geekbang/geek_netty
作者回复: 一次可能读到多个完整的消息,所以传下去有必要,这样至少前面完整的消息能及时处理,一次也可能读不完,传下去也没必要,一方面,后面的处理器会帮你存起来这些半包数据,另外你可以写一些处理器做些别的事情,总体思想还是有数据就往外扔,而不是死等着,因为这是一个数据流,等意义也不大
作者回复: 1 你估计看错了类,所以你没有看懂,你看的那个类估计是DefaultMaxBytesRecvByteBufAllocator
所以我用中文注释了过那个类:
“//无人调用,加一个@Deprecated标识下”
2 io.netty.channel.AdaptiveRecvByteBufAllocator.HandleImpl#readComplete会尝试缩小,缩小比例不完全一样(以512为界限,有2种):一种是减小1倍,一种是减小16
3 "什么是16次最优,不是其它的2的幂次方倍?"我意思这个本身不是问题,因为写32的话,别人也会问为什么不是16,“雨露均沾”是说给别人读的机会,所以要控制中的次数。
你每次笔记记得挺细致的,哈哈
作者回复: 可以查看下你的线程模型有没有问题(后面的第五章也会提及,IO型的业务要独立出线程池),然后这个问题需要查很多因素,具体可以
参考上次做直播的ppt说到的一个类似问题(第九个问题):
https://github.com/geektime-geekbang/geek_netty/
如果还有疑问,或者不清楚,可以继续提个问题。谢谢
作者回复: 一般情况(你问的情况),op_read一直注册在,不是重新注册,也不需要重新注册。重新注册的场景是出现在自己主动取消读监听后,又重新注册时,比如流量整形的读暂停到读恢复。正常没有开启各种复杂特性时都是一直注册在,所以只要有数据,就自动处理各种handler。
作者回复: 是的,你可以通过参数调整大点,或者对于io型的业务最好独立出一个线程池来做,参考第五章,下周三更新。
作者回复: 处理业务那节就介绍了,简单说就是:寻找pipeline中下一个具有执行资格的handler然后来执行。因为不是所有的hanlder都具有资格,比如你触发的是读事件,那专门服务于写事件的handler就不需要执行。
作者回复: 分两种情况:
1 对于同一个连接而言,实际上收到的数据顺序是按顺序的,因为都是同一个线程(NioEventLoop)来处理的;
2 而如果不同连接,那就不一定了,它不能保证NioEventLoop的处理是按你发送的顺序来。因为他们不定是同一个NioEventLoop,每个NioEventLoop处理速度可能因工作量不同而不同。
作者回复: 赋值的地方有多个,例如:
io.netty.channel.nio.AbstractNioChannel#doBeginRead
注册读。