遇到了我遇到过的最不寻常的问题之一。
我将 PostgreSQL 数据库安装在 Windows 服务器上,并监听所有 IP 地址:
listen_addresses = '*'
我可以在各种客户端设备(Linux 或 Windows 操作系统)上访问和发送查询,没有任何问题。
我只遇到了某个特定 Linux 客户端的问题,如果我可以这么说的话,当查询响应有点“重”时,由于某种原因,该客户端无法执行查询。
我将尝试通过示例进行详细说明。
我在那台机器上有 psql 客户端,远程 Windows 服务器上的 postgresql 数据库中有一个用户表,该数据库有大约 20 条记录,所以当我运行此查询时:
select "firstName", "createdAt", "updatedAt", username from users limit 13;
我正常得到结果:
firstName | createdAt | updatedAt | username
-------------+-------------------------------+-------------------------------+-------------
User 1 | 2017-01-26 12:48:52.995+01 | 2017-01-26 12:48:52.995+01 | user1
User 2 | 2019-08-24 10:29:16.16329+02 | 2019-08-24 10:29:16.16329+02 | user2
User 3 | 2018-10-05 11:45:14.127813+02 | 2018-10-05 11:45:14.127813+02 | user3
User 4 | 2017-09-27 18:53:56.535867+02 | 2017-09-27 18:53:56.535867+02 | user4
User 5 | 2017-03-28 11:46:27.03684+02 | 2017-03-28 11:46:27.03684+02 | user5
User 6 | 2017-03-28 11:46:40.840481+02 | 2017-03-28 11:46:40.840481+02 | user6
User 7 | 2018-05-22 12:43:08.397247+02 | 2018-05-22 12:43:08.397247+02 | user7
User 8 | 2017-03-28 11:46:36.24854+02 | 2017-03-28 11:46:36.24854+02 | user8
User 9 | 2022-04-30 14:04:02.24541+02 | 2022-04-30 14:04:02.24541+02 | user9
User 10 | 2022-04-30 14:04:02.24541+02 | 2022-04-30 14:04:02.24541+02 | user10
User 11 | 2022-04-30 14:04:02.24541+02 | 2022-04-30 14:04:02.24541+02 | user11
User 12 | 2022-04-30 14:04:02.24541+02 | 2022-04-30 14:04:02.24541+02 | user12
User 13 | 2022-04-30 14:04:02.24541+02 | 2022-04-30 14:04:02.24541+02 | user13
(13 rows)
任何限制最多 13 个的查询都可以毫无问题地返回数据。
但是在向结果中再添加一行(查询中限制 14 行)后,我立即得到以下结果:
server closed the connection unexpectedly
This probably means the server terminated abnormally
before or while processing the request.
The connection to the server was lost. Attempting reset: Succeeded.
当我查询其他表时,我也遇到了同样的问题,具有较低限制的数据将成功返回,但是当我在查询中获得更高的负载增加限制时,它会失败。
查看服务器上的 postgresql 日志,我得到以下信息:
CEST FATAL: connection to client lost
CEST LOG: could not receive data from client: An existing connection was forcibly closed by the remote host.
使用 npm [email protected] 或任何其他版本在我的节点应用程序中执行相同的查询,我遇到了同样的问题,在响应数据较少时成功,并且当它无法获取更多行时:
Error: read ECONNRESET
at TCP.onStreamRead (internal/stream_base_commons.js:209:20) {
errno: -104,
code: 'ECONNRESET',
syscall: 'read'
}
我还在客户端计算机上进行了一些wireshark pcap转储,同时进行这些查询,并注意到当我收到错误时,wireshark日志如下所示:
3301 2.220496557 25.67.20.168 25.20.186.130 TCP 68 [TCP Dup ACK 2839#1] 45208 → 5432 [ACK] Seq=27 Ack=1 Win=64542 Len=0 SLE=2729 SRE=3143
我对wireshark和网络问题了解不多,但看起来与重复确认“TCP Dup ACK”问题有关。
所有这一切都更加奇怪,因为我只在一个 linux (ubuntu) 客户端上遇到这个问题,其他客户端工作正常,没有任何问题,其中大约有 10 个 windows/linux-ubuntu 混合。
我猜这很可能是网络问题。
我将不胜感激任何有关此事的线索。
如果客户端和服务器都认为对方挂断了,那么显然是网络问题。
您没有告诉我们这些查询需要多长时间,但您可能在某些中间网络组件中遇到超时,该组件决定应该终止这个看似空闲的连接(有些人不知道有是 HTTP 之外的其他协议)。您可以通过在服务器上设置
tcp_keepalives_idle
来防止这种情况。 这里是有关该主题的更多信息。
这很可能是另一个问题,但肯定是网络问题。