直接答案
连接重置表示已建立的 TCP 连接被一端或中间设备异常终止;先确定发生在发送前、响应前还是流式传输中。
这篇内容解决什么问题
解决 Node.js socket hang up、ECONNRESET、Python connection reset by peer 和 API 连接意外关闭。
先确认症状与影响范围
Node.js 常显示 ECONNRESET 或 socket hang up,Python 可能显示 ConnectionResetError。它说明连接曾经建立,但没有正常完成 HTTP 生命周期。
只在复用旧连接、长时间空闲或流式生成时出现,通常与 keep-alive、idle timeout 或中间代理有关;新连接也立即重置则需检查 TLS 和目标主机。
- 记录重置发生在请求上传、等待响应还是接收流式事件之后。
- 比较新连接与连接池复用、非流式与流式请求。
- 确认同一时间代理、网关和上游哪一层先关闭连接。
常见原因与责任边界
RST 可能由客户端、操作系统、企业代理、负载均衡器、API 网关或模型上游发出。仅凭客户端异常栈无法确认责任方。
- 复用了已经超过服务端 idle timeout 的连接。
- 代理或上游在响应完成前关闭长连接。
- 并发或连接池压力导致套接字被回收。
- TLS 中间设备、网络切换或服务重启打断现有连接。
按层执行最小诊断
用 curl 详细 timing 和目标 SDK 分别执行短请求。若关闭连接复用后恢复,检查连接池的最大空闲时间;若只在流式中断,进入 SSE 页面核对事件和代理缓冲。
抓包或基础设施日志可能包含敏感网络信息,只有管理员在受控环境中按需收集。一般支持请求先提供时间、request ID 和客户端异常阶段。
- 01标记阶段确认连接在写请求、等首字节或读响应时重置。
- 02短请求对照测试模型列表和最小非流式请求。
- 03连接复用对照比较新连接与 keep-alive 连接池表现。
- 04关联日志按五元组、UTC 时间和 request ID 检查代理与网关。
curl -sS --http1.1 -H 'Connection: close' --connect-timeout 10 --max-time 60 -o /tmp/reset-body.json -w 'remote=%{remote_ip} status=%{http_code} total=%{time_total}
' 'https://<your-api-host>/v1/models' -H "Authorization: Bearer ${API_KEY:?set API_KEY first}"针对根因完成修复
将客户端连接池 idle 生命周期设置得短于服务端,限制连接与请求并发,并确保代理支持目标响应时长。瞬时重置只对可安全重放请求有限重试。
- 01校准 keep-alive主动淘汰接近服务端 idle timeout 的空闲连接。
- 02限制池大小设置最大连接、空闲连接和排队时限。
- 03修正代理让 read/idle timeout 和 SSE 转发符合业务响应时长。
- 04有限重试加入退避并避免重放有副作用的工具调用。
验证修复而不是只看一次成功
在连续短请求、空闲后复用和长流式三个场景中观察重置率。确认连接池指标不会持续增长,取消请求后套接字会释放。
- 新连接与连接复用都能稳定工作。
- 空闲时间超过阈值的连接不会再次借出。
- 长流式请求不会被最短一层代理提前重置。
安全边界与升级证据
不要把关闭 TLS、使用明文 HTTP 或禁用企业安全代理作为长期修复。抓包和调试日志必须限制访问并删除 Authorization 与业务载荷。
- 不在日志记录完整请求头或响应内容。
- 不对非幂等动作自动重放。
- 临时网络对照完成后恢复组织策略。
官方来源与核验范围
本文以协议规范和客户端官方文档为事实依据。错误文案、重试头和配置字段可能随服务或客户端版本变化;执行前请核对来源,并对日志与请求样例脱敏。
查看技术核验方法