nginx通过max_fails和fail_timeout将超时视为失败信号,结合proxy_next_upstream timeout触发被动健康检查与请求重试,实现自动节点隔离;需配置proxy_connect_timeout、proxy_read_timeout及keepalive长连接避免误判。

Nginx 实现故障转移并自动隔离响应超时的节点,关键不是靠“检测超时”本身,而是把超时当作一种失败信号,触发内置的被动健康检查与请求重试机制。它不主动探测,但会在真实请求中记录超时行为,并据此临时下线节点。
配置带超时感知的 upstream 组
在 http 块中定义 upstream 时,必须显式启用对超时的识别和处置:
-
max_fails=2表示连续发生 2 次失败(含超时)即标记该节点为不可用 -
fail_timeout=10s表示该节点被标记后,在 10 秒内不再接收新请求;同时这 10 秒也是“连续失败”的统计窗口 - 节点被标记为 down 后,已有连接不受影响,新请求自动绕过
例如:
upstream api_cluster {
server 192.168.1.10:8000 max_fails=2 fail_timeout=10s;
server 192.168.1.11:8000 max_fails=2 fail_timeout=10s;
server 192.168.1.12:8000 backup;
}
让超时真正触发故障转移
仅配置 max_fails 和 fail_timeout 不够——Nginx 默认只在连接拒绝(connection refused)或网络中断时计为失败。要让 proxy_read_timeout 或 proxy_connect_timeout 触发剔除,必须配合 proxy_next_upstream:
- 在
location块中启用timeout选项,表示只要发生超时(无论 connect 还是 read),就视为可重试错误 - 同时加上
error和常见网关错误码,覆盖更全的失败场景
location /api/ {
proxy_pass http://api_cluster;
proxy_connect_timeout 3s;
proxy_read_timeout 8s; # 设为略高于后端 P95 耗时
proxy_send_timeout 8s;
proxy_next_upstream error timeout http_500 http_502 http_503 http_504;
proxy_next_upstream_tries 3;
proxy_next_upstream_timeout 12s;
}
避免误判:用长连接减少假性超时
高频短连接容易因 TIME_WAIT 拥塞、端口耗尽或内核连接队列满,导致连接建立缓慢甚至失败,被误判为超时。解决方式是复用连接:
- 在 upstream 中加
keepalive 32,保持最多 32 个空闲连接 - 在 location 中启用 HTTP/1.1 长连接:
proxy_http_version 1.1; proxy_set_header Connection "";
验证超时是否真能隔离节点
- 手动停掉一台后端服务,用
curl -v http://your-domain/api/test持续请求 - 查看 Nginx 错误日志
/var/log/nginx/error.log,搜索upstream timed out或no live upstreams - 若看到请求自动落到其他节点且无报错,说明
timeout已被proxy_next_upstream正确捕获并重试
不复杂但容易忽略











