Reactor线程模型
- Reactor单线程模型
所有的I/O操作都由同一个NIO线程完成。只适合小容量应用场景。不适合高负载大并发的应用场景。原因如下:
a、 一个NIO线程同时处理成百上千条线路,性能上无法支撑,即使CPU使用率达到百分之百,也无法满足海量消息编解码、读取、发送。
b、 当NIO线程负载过重后,处理会变慢,导致大量客户端连接超时,而超时可能重发,导致越来越积压严重。
c、 可靠性问题,一旦NIO线程跑飞了或者进入死循环,整个系统通信都不可用了,造成单点故障。 - Reactor多线程模型
由一组NIO线程来处理I/O操作。特点如下:
a、 有专门一个NIO线程--Acceptor线程用来监听服务端,接收客户端的TCP连接请求。
b、 网络IO操作--读写等由一个NIO线程池负责,线程池可以采用标准的JDK线程池实现,它包含一个任务队列和N个可用的线程,由这些NIO线程来完成消息的读取、发送和编解码操作。
c、 一个NIO线程可以同时处理N条链路。但是同一个链路只对应一个NIO线程,防止发生并发操作问题。
在绝大多数场景下,Reactor多线程模型可以满足性能要求。但是,个别特殊场景中,一个NIO线程负责监听和处理所有的客户端连接可能会存在性能问题。例如并发百万客户端连接,或者服务端需要对客户端握手进行安全认证,但是认证本身非常损耗性能。 - 主从Reactor多线程模型
特点是:服务端用来接收客户端连接的不再是一个单独的NIO线程,而是一个独立的NIO线程池。Acceptor接收到客户端TCP连接请求并处理完成后,将新创建的SocketChannel注册到IO线程池的某个IO线程上,由它负责SocketChanel的读写和编解码操作。Acceptor线程池仅仅用于客户端的登录、握手和安全认证,一旦链路创建成功,就将链路注册到后端的线程池中的Io线程上,有IO线程负责后续的操作。