错误消息中的“ 无法分配请求的地址 ”部分来自内核TCP堆栈。间歇性遇到时,这通常意味着可用套接字的空间已用完,因为处于等待状态的套接字过多(TIME_WAIT
,或者可能性较小,FIN_WAIT_1
或FIN_WAIT_2
)
套接字端口的范围可以通过输出cat /proc/sys/net/ipv4/ip_local_port_range
。普通Linux内核的默认值通常为32768 61000
。
netstat -ton|grep WAIT
当系统繁忙时,您可以在客户端和pgBouncer的主机上检查结果。该-o
标志将显示与等待状态有关的超时计数器。
如果TCP套接字的总数接近于61000-32768=28232
该范围,则可能是您耗尽了该范围。由于关闭的套接字TIME_WAIT
在正常情况下会花费60秒处于状态,因此,如果客户端主机在一分钟内连接超过28232次,则新连接将失败,并出现上述错误,直到释放端口为止。
作为第一种解决方法,可以扩展TCP端口范围:
# echo "1025 65535" >/proc/sys/net/ipv4/ip_local_port_range
如果不满意,请检查tcp_tw_recycle
和tcp_tw_reuse
标志,也可以通过/proc/sys/net/ipv4
和进行调整sysctl
。
它们被定义为(from man tcp
):
tcp_tw_recycle(布尔值;默认值:禁用;从Linux 2.4开始)
启用TIME_WAIT套接字的快速回收。启用这个
不建议使用此选项,因为这会在工作时引起问题-
NAT(网络地址转换)。
tcp_tw_reuse(布尔值;默认:禁用;自Linux 2.4.19 / 2.6起)
允许重新使用TIME_WAIT套接字进行新连接
从协议的角度来看是安全的。没有它就不能改变
咨询/请求技术专家。
就个人而言tcp_tw_recycle
,面对MySQL客户端应用程序的此问题,我取得了成功,但我不建议这样做,因为我对TCP的理解充其量只是肤浅的。