这是阅读完李林峰的《Netty权威指南》之后,觉得本书中比较重点的部分,就做了摘抄,即加深了学习,又可以给大家提供一些帮助。
传统RPC调用性能差的三宗罪
1、网络传输方式问题。传统的RPC框架或者基于RMI等方式的远程服务(过程)调用采用了同步阻塞I/O,当客户端的并发压力或者网络延时增大之后,同步阻塞I/O会由于频繁的wait导致I/O线程经常性的阻塞,由于线程无法高效的工作,I/O处理能力自然下降。
采用BIO通信模型的服务端,通常有一个独立的Acceptor线程负责监听客户端的连接,接收到客户端连接之后,为其创建一个新的线程处理请求信息,处理完成之后,返回应答消息给客户端,线程销毁,这就是典型的一请求一应答模型。该架构最大的问题就是不具备弹性伸缩能力,当并发访问量增加之后,服务端的线程个数和并发访问数呈线性正比,由于线程是Java虚拟机非常宝贵的系统资源,当线程数膨胀之后,系统的性能急剧下降,随着并发量的继续增加,可能会发生句柄溢出、线程堆栈溢出等问题,并导致服务器最终宕机。
2、序列化性能差。Java序列化存在以下几个典型的问题:
1)Java序列化机制是Java内部的一种对象编解码技术,无法跨语言使用。例如对于异构系统之间的对接,Java序列化后的码流需要通过其他语言反序列化成原始对象(副本),目前很难支持。
2)相比于其他的开源序列化框架,Java序列化后的码流太大,无论是网络传输还是持久化到磁盘,都会导致额外的资源占用。
3)序列化性能差,资源占用率高(主要是CPU资源占用高)。
3、线程模型问题。由于采用同步阻塞I/O,这会导致每个TCP连接都占用1个线程,由于线程资源是JVM虚拟机非常宝贵的资源,当I/O读写阻塞导致线程无法及时释放时,会导致系统性能急剧下降,严重的甚至会导致虚拟机无法创建新的线程。 |