100次浏览 发布时间:2024-12-17 10:26:03
在分布式微服务框架中,底层通信大都选择netty,比如xxl-job、dubbo、nacos,es。netty轻轻松松支撑百万链接,底层到底做了那些优化?
多路IO不再由应用程序自己监视客户端连接,取而代之由内核替应用程序监视文件。
单reactor单线程
这是最简单的Reactor模型,可以看到有多个客户端连接到Reactor,Reactor内部有一个dispatch(分发器)。
有连接请求后,Reactor会通过dispatch把请求交给Acceptor进行处理,有IO读写事件之后,又会通过dispatch交给具体的Handler进行处理。
此时一个Reactor既然负责处理连接请求,又要负责处理读写请求,一般来说处理连接请求是很快的,但是处理具体的读写请求就要涉及到业务逻辑处理了,相对慢太多了。Reactor正在处理读写请求的时候,其他请求只能等着,只有等处理完了,才可以处理下一个请求。
单线程Reactor模型编程简单,比较适用于每个请求都可以快速完成的场景,但是不能发挥出多核CPU的优势,在一般情况下,不会使用单Reactor单线程模型。
单reactor多线程
可以看到,Reactor还是既要负责处理连接事件,又要负责处理客户端的写事件,不同的是,多了一个线程池的概念。
当客户端发起连接请求后,Reactor会把任务交给acceptor处理,如果客户端发起了写请求,Reactor会把任务交给线程池进行处理,这样一个服务端就可以同时为N个客户端服务了。
多reactor多线程
这就是主从Reactor模型了,可以看到mainReactor只负责连接请求,而subReactor只负责处理客户端的写事件。
应用在读操作,不需要数据从内核态拷贝到用户态中,采用共享模式。
对象池与内存池的都是为了提高 Netty 的并发处理能力,我们知道 Java 中频繁地创建和销毁对象的开销是很大的,所以很多人会将一些通用对象缓存起来,当需要某个对象时,优先从对象池中获取对象实例。通过重用对象,不仅避免频繁地创建和销毁所带来的性能损耗,而且对 JVM GC 是友好的,这就是对象池的作用。
Recycler 是 Netty 提供的自定义实现的轻量级对象回收站,借助 Recycler 可以完成对象的获取和回收。