send_timeout和keepalive_timeout是防御Slow Read与慢速攻击的关键:前者限制响应发送时两次写操作间的空闲时间(建议15–30秒),后者控制长连接空闲超时(建议15–30秒),需配合reset_timedout_connection on;并协同proxy超时参数调优。

调优 send_timeout 和 keepalive_timeout 是防御 Slow Read 与连接资源耗尽类慢速攻击的关键动作。它们不直接拦截恶意请求,而是快速识别并切断“假忙真拖”的连接,释放 worker 进程、socket 和内存资源。
send_timeout:专治慢读响应(Slow Read)
这个参数控制 Nginx 向客户端发送响应时,两次成功写操作之间的最大等待时间。它不是整个响应的总耗时限制,而是盯住“空闲间隔”——比如发完一个 TCP 包后,等了 25 秒才发下一个,哪怕总响应只用了 30 秒,也会被断开。
- 默认值 60 秒太宽松,攻击者可配合极小接收窗口(如 TCP Window = 1 byte)长期挂起连接
- 常规 Web 页面或 API 接口建议设为 15–30 秒;真实弱网用户极少出现连续 15 秒完全无法接收数据的情况
- 流式场景(如 SSE、长轮询)需单独在对应
location块中调高,同时必须加proxy_buffering off;,避免缓冲掩盖慢读行为 - 若启用反向代理,还需同步收紧
proxy_read_timeout和proxy_send_timeout,防止上游拖累下游超时判断
keepalive_timeout:清理僵尸长连接
该参数定义 HTTP/1.1 长连接空闲多久后关闭。默认 75 秒在高并发下极易堆积大量 TIME_WAIT 状态连接,尤其被 Slowloris 类攻击利用后,worker_connections 很快被占满。
- 建议统一设为 15–30 秒,兼顾浏览器兼容性(多数现代浏览器支持 30 秒 keep-alive)和资源回收效率
- 仅改 timeout 不够,必须搭配
reset_timedout_connection on;,让 Nginx 超时后发 RST 强制中断,而非 FIN 等待四次挥手,大幅缩短 socket 占用周期 - 不要设为 0(禁用 keepalive),虽能杜绝空闲连接,但会显著增加 TCP 握手开销和 TLS 重建压力,得不偿失
- 若业务明确不需要长连接(如纯 API 网关),可在 server 或 location 级用
keepalive_timeout 0;+keepalive_requests 1;彻底关闭
两个参数协同生效的典型场景
攻击者建立连接、发完整请求、服务器开始生成大响应,但客户端以极低速率读取——此时连接既不属于 keepalive 空闲态,也不属于请求处理中,而是在 send_timeout 监控范围内缓慢消耗资源。若 keepalive_timeout 过长,这类连接可能在响应未完成前就先因空闲超时被误杀;若 send_timeout 过长,则连接会长期滞留在“发送中”状态,占用 worker。
- 推荐组合:
keepalive_timeout 20s;+send_timeout 25s;,留出合理错峰空间 - 所有超时值应在
http块全局设置,并在特定server或location中按需覆盖,避免遗漏 - 上线前务必用
ab、weighttp或专用慢速攻击工具(如 slowhttptest)验证效果,观察netstat -ant | grep :80 | wc -l和nginx -T | grep worker_connections的实际连接数变化



















