postgresql 连接客户端存在 CLOSE_WAIT、TIME_WAIT 状态

ssh 192.168.56.100

# netstat -antp|grep -i "5672" |grep -v "ESTABLISHED" 
tcp        1      0 192.168.56.100:52674       192.168.56.150:5672         CLOSE_WAIT  116553/postgres: pe
tcp        1      0 192.168.56.100:37251       192.168.56.150:5672         CLOSE_WAIT  46480/postgres: pei
tcp        1      0 192.168.56.100:47048       192.168.56.150:5672         CLOSE_WAIT  118735/postgres: pe
tcp       95      0 192.168.56.100:56547       192.168.56.150:5672         CLOSE_WAIT  94628/postgres: pei
tcp        0      0 192.168.56.100:55290       192.168.56.150:5672         TIME_WAIT   - 

网络状态细节可以baidu,这里只是简单描述下

CLOSE_WAIT 被动关闭
192.168.56.150端关闭连接之后,本地已经接收到FIN,但是还没有发送自己的FIN的时刻,连接处于CLOSE_WAIT状态。
这个资源就一直被程序占着。

TIME_WAIT 主动关闭
192.168.56.100端主动关闭连接的一方保持的状态,
解决思路就是让服务器能够快速回收和重用那些TIME_WAIT的资源。

TIME_WAIT 状态可以通过调整os和postgresql的参数来优化
1)os参数

# sysctl -a |grep -i tcp_keepalive

net.ipv4.tcp_keepalive_intvl = 30
net.ipv4.tcp_keepalive_probes = 9
net.ipv4.tcp_keepalive_time = 600

附上系统的默认值
net.ipv4.tcp_keepalive_intvl = 15
net.ipv4.tcp_keepalive_probes = 3
net.ipv4.tcp_keepalive_time = 7200

2)postgresql 参数

select ps.name,ps.setting,ps.unit,ps.category,ps.short_desc
from pg_settings ps
where 1=1
and ps.category like '%Client Connection Defaults / Other Defaults%'
;

          name           | setting | unit |                  category                   |                        short_desc                        
-------------------------+---------+------+---------------------------------------------+----------------------------------------------------------
 dynamic_library_path    | $libdir |      | Client Connection Defaults / Other Defaults | Sets the path for dynamically loadable modules.
 gin_fuzzy_search_limit  | 0       |      | Client Connection Defaults / Other Defaults | Sets the maximum allowed result for exact search by GIN.
 local_preload_libraries |         |      | Client Connection Defaults / Other Defaults | Lists shared libraries to preload into each backend.
 tcp_keepalives_count    | 0       |      | Client Connection Defaults / Other Defaults | Maximum number of TCP keepalive retransmits.
 tcp_keepalives_idle     | 0       | s    | Client Connection Defaults / Other Defaults | Time between issuing TCP keepalives.
 tcp_keepalives_interval | 0       | s    | Client Connection Defaults / Other Defaults | Time between TCP keepalive retransmits.
(6 行记录)

tcp_keepalives_idle (integer)
指定不活动多少秒之后通过 TCP 向客户端发送一个 keepalive 消息。
0 值表示使用默认值。
这个参数只有在支持 TCP_KEEPIDLE 或 TCP_KEEPALIVE 符号的系统或 Windows 上才可以使用。
在其他系统上,它必须为零。在通过 Unix 域套接字连接的会话中,这个参数被忽略并且总是读作零。

注意: 在 Windows 上,值若为 0,系统会将该参数设置为 2 小时,因为 Windows 不支持读取系统默认值。

tcp_keepalives_interval (integer)
指定在多少秒之后重发一个还没有被客户端告知已收到的 TCP keepalive 消息。
0 值表示使用系统默认值。
这个参数只有在支持TCP_KEEPINTVL符号的系统或 Windows 上才可以使用。
在其他系统上,必须为零。在通过 Unix域套接字连接的会话中,这个参数被忽略并总被读作零。

注意: 在 Windows 上,值若为 0,系统会将该参数设置为 1 秒,因为 Windows 不支持读取系统默认值。

tcp_keepalives_count (integer)
指定与客户端的服务器连接被认为死掉之前允许丢失的 TCP keepalive 数量。
0 值表示使用系统默认值。
这个参数只有在支持TCP_KEEPCNT符号的系统上才可以使用。
在其他系统上,必须为零。在通过 Unix 域套接字连接的会话中,这个参数被忽略并总被读作零。

注意: Windows 不支持该参数,且必须为零。

postgresql 如果参数 tcp_keepalives_count、tcp_keepalives_idle、tcp_keepalives_interval 设置为非0值,则使用postgresql 参数值,否则使用os对应的参数值

参数对应关系,第一列为postgresql参数,第二列为os参数

tcp_keepalives_idle       tcp_keepalive_time
tcp_keepalives_interval   tcp_keepalive_intvl
tcp_keepalives_count      tcp_keepalive_probes 
原文地址:https://www.cnblogs.com/ctypyb2002/p/9793045.html