详解Netty组件: ChannelOption类

3,002 阅读4分钟

可以设置一系列的ChannelOption(通道选项)。ChannelOption类中定义了一系列选项

1 SO_RCVBUF和SO_SNDBUF

这两个为TCP传输选项,每个TCP socket(套接字)在内核中都有一个发送缓冲区和一个接收缓冲区,这两个选项就是用来设置TCP连接的两个缓冲区大小的。TCP的全双工工作模式以及TCP的滑动窗口对两个独立的缓冲区都有依赖。

2 TCP_NODELAY

此为TCP传输选项,如果设置为true就表示立即发送数据。TCP_NODELAY用于开启或关闭Nagle算法。如果要求高实时性,有数据发送时就马上发送,就将该选项设置为true(关闭Nagle算法);如果要减少发送次数、减少网络交互,就设置为false(开启Nagle算法),等累积一定大小的数据后再发送。关于TCP_NODELAY的值,Netty默认为true,而操作系统默认为false。

Nagle算法将小的碎片数据连接成更大的报文(或数据包)来最小化所发送报文的数量,如果需要发送一些较小的报文,则需要禁用该算法。Netty默认禁用Nagle算法,报文会立即发送出去,从而最小化报文传输的延时。

TCP_NODELAY的值设置为true表示关闭延迟,设置为false表示开启延迟。其值与是否开启Nagle算法是相反的。

3 SO_KEEPALIVE

此为TCP传输选项,表示是否开启TCP的心跳机制。true为连接保持心跳,默认值为false。启用该功能时,TCP会主动探测空闲连接的有效性。需要注意的是:默认的心跳间隔是7200秒,即2小时。Netty默认关闭该功能

4 SO_REUSEADDR

此为TCP传输选项,为true时表示地址复用,默认值为false。

有四种情况需要用到这个参数设置:

  1. 当有一个地址和端口相同的连接socket1处于TIME_WAIT状态时,而又希望启动一个新的连接socket2要占用该地址和端口。
  2. 有多块网卡或用IP Alias技术的机器在同一端口启动多个进程,但每个进程绑定的本地IP地址不能相同。
  3. 同一进程绑定相同的端口到多个socket(套接字)上,但每个socket绑定的IP地址不同。
  4. 完全相同的地址和端口的重复绑定,但这只用于UDP的多播,不用于TCP。

Socket连接状态(如TIME_WAIT)和连接建立时三次握手以及断开时四次挥手有关,

5 SO_LINGER

此为TCP传输选项,可以用来控制socket.close()方法被调用后的行为,包括延迟关闭时间。

  • 此选项设置为-1,就表示socket.close()方法在调用后立即返回,但操作系统底层会将发送缓冲区的数据全部发送到对端

  • 设置为0,就表示socket.close()方法在调用后会立即返回,但是操作系统会放弃发送缓冲区数据,直接向对端发送RST包,对端将收到复位错误

  • 此选项设置为非0整数值,就表示调用socket.close()方法的线程被阻塞,直到延迟时间到来,发送缓冲区中的数据发送完毕,若超时,则对端会收到复位错误。

SO_LINGER的默认值为-1,表示禁用该功能。

6 SO_BACKLOG

此为TCP传输选项,表示服务端接收连接的队列长度,如果队列已满,客户端连接将被拒绝。

服务端在处理客户端新连接请求时(三次握手)是顺序处理的,所以同一时间只能处理一个客户端连接,多个客户端到来的时候,服务端将不能处理的客户端连接请求放在队列中等待处理,队列的大小通过SO_BACKLOG指定。

  1. 服务端对完成第二次握手的连接放在一个队列(暂时称A队列)
  2. 如果进一步完成第三次握手,再把连接从A队列移动到新队列(暂时称B队列)
  3. 接下来应用程序会通过调用accept()方法取出握手成功的连接,而系统则会将该连接从B队列移除。
  4. A和B队列的长度之和是SO_BACKLOG指定的值,当A和B队列的长度之和大于SO_BACKLOG值时,新连接将会被TCP内核拒绝。所以,如果SO_BACKLOG过小,accept速度可能会跟不上,A和B队列全满,导致新客户端无法连接。

如果连接建立频繁,服务器处理新连接较慢,那么可以适当调大这个参数。

7 SO_BROADCAST

此为TCP传输选项,表示设置为广播模式。