CNode

请教一个 socket hang up 的报错问题【已解决】

问答
ZZhangDianPeng发布于8 年前最后回复8 年前10 回复10467 浏览0 收藏

请教一个问题,在使用 http.request的 时候偶现 socket hang up,报错如下: at createHangUpError (_http_client.js:329:15) 而且只有在用使用agent的时候会出现, agent配置如下: opts = { maxSockets: 100, maxFreeSockets: 10, timeout: 10 * 60 * 1000, keepAliveTimeout: 30000 }

Node版本8.7.0 agentkeepalive版本 2.2.0

另外使用官方的agent也会出现这个问题

查看回复

回复 (10)

D
dewfall123#1·8 年前

如果连接成功之前调用 req.abort(),则依次触发以下事件: ... 'error' 事件并带上错误信息 'Error: socket hang up' 和错误码 'ECONNRESET'。

socket hang up是建立连接失败, 看下是不是服务器不支持keep-alive

Z
ZhangDianPeng#2·8 年前
引用 dewfall123如果连接成功之前调用 req.abort(),则依次触发以下事件: ... 'error' 事件并带上错误信息 'Error: socket hang up' 和错误码 'ECONNRESET...

@dewfall123 通过抓包找到原因了,是因为公司运维nginx配置问题

nginx 配置的 keepalive_timeout 只有 5s

而 agentkeepalive 中的 freeKeepAliveTimeout 配置是 30 s

所以在长连接的情况下,如果 socket 处于空闲状态的超过 5s,那么 nginx 侧会主动强制断掉 socket 连接,这时恰好客户端如果又在这个连接上发了一个请求,触发 socket hang up 报错信息,所以在并发量比较大的情况下,偶尔会触发这个报错。

所以建议如果配置长连接的情况下,服务端的 freeKeepAliveTimeout 时间一定要比客户端的长,才不会出现该问题。

如果是用 Node 启动作为服务端的话,可以通过 server.keepAliveTimeout 设置超时时间。

官方的这个 默认值 是 5s, 感觉是一个坑,时间太短,如果对应的客户端使用长连接的话,建议将其调大。

G
Gitforxuyang#3·8 年前

@ZhangDianPeng nginx关闭socket时应该会通知客户端吧。 node应该收到信息后将socket释放掉。 所以你们只有在并发量很大的时候才能遇到是吧?

Z
ZhangDianPeng#4·8 年前
引用 Gitforxuyang@ZhangDianPeng nginx关闭socket时应该会通知客户端吧。 node应该收到信息后将socket释放掉。 所以你们只有在并发量很大的时候才能遇到是吧?

@Gitforxuyang nginx在通知客户端的后,客户端还没有接收到,这个时候客户端会再次发请求,但是nginx已经强制关掉了socket,导致当前这个请求挂掉

R
royalrover#5·8 年前

默认的keepAliveTimeout是1s吧,默认的一般都够了,30s的心跳包有点太大了

R
royalrover#7·8 年前

http.agent的配置项只有timeout和keepAliveMsecs吧,你的配置keepAliveTimeout不太对。

R
royalrover#8·8 年前
引用 ZhangDianPeng@dewfall123 通过抓包找到原因了,是因为公司运维nginx配置问题 nginx 配置的 keepalive timeout 只有 5s 而 agentkeepalive 中的 fre...

@ZhangDianPeng 只要保证后端业务服务器的keepalive超时和nginx的超时一致即可,没法估计客户端什么时候会开启下一个。请求另外,你们的nginx与后端服务器采用的是长连接吗?如果采用默认的短连接,性能更差

参与回复
登录后即可参与回复。登录