一、先讲核心:为什么 504 要查后端日志和响应时间?

504(Gateway Timeout)的本质是:

Nginx 已经成功连上后端服务,但后端处理请求太慢,在规定时间内没有返回完整响应,Nginx 主动超时断开。

和 502 有本质区别:

  • 502 = 连不上后端(后端挂了、端口没开、进程崩了)→ 查端口、查进程、查连接
  • 504 = 连上了,但后端处理太慢 → 查后端处理速度、程序异常、资源瓶颈

所以排查 504 的重心,一定是「后端为什么这么慢」,而不是「能不能连上后端」。后端日志和 $upstream_response_time 就是定位这个问题的两个核心抓手。


二、$upstream_response_time 是什么?

这是 Nginx 内置变量,单位是秒,记录的是:

从 Nginx 把请求转发给后端开始,到 Nginx 收到后端完整响应头为止,所消耗的时间。

直白说:就是后端处理这个请求花了多久。

  • 这个值越小,后端响应越快
  • 这个值接近 / 超过 proxy_read_timeout(默认 60s),就会触发 504

补充:和它容易混淆的变量

变量 含义
$request_time 整个请求总耗时(从用户请求到Nginx返回完所有数据),包含网络传输时间
$upstream_response_time 纯后端处理耗时,只算后端处理的时间,是排查后端性能的核心指标

三、为什么排查 504 必须看这两个?

1. 看 $upstream_response_time:先定性,是真慢还是配置问题

通过 Nginx 访问日志里的这个字段,可以快速确认:

  1. 是所有请求都慢,还是个别接口慢
  2. 响应时间是刚好超过超时阈值,还是远大于阈值(后端完全卡死)
  3. 是不是 Nginx 超时时间设太短了(比如后端本来就需要 70s,Nginx 只设了 30s 超时)

实操示例

Nginx 日志格式里配置这个变量(生产标准配置):

log_format main '$remote_addr - $remote_user [$time_local] "$request" '
                '$status $body_bytes_sent "$http_referer" '
                '"$http_user_agent" $upstream_response_time';

排查时直接过滤 504 请求,看对应的响应时间:

awk '$9 == 504 {print $7, $upstream_response_time}' access.log

也可以统计所有请求的后端响应时间排序,找最慢的接口:

awk '{print $7, $NF}' access.log | sort -k2 -rn | head -10

2. 看后端日志:定位根因,为什么慢

$upstream_response_time 只能告诉你「后端慢了」,但为什么慢必须看后端日志。 常见导致后端处理慢的根因,都要从后端日志里找证据:

  1. 程序报错/异常:空指针、数据库连接失败、依赖服务超时
  2. 慢查询:SQL 没加索引、大表全表扫描,数据库卡住
  3. 死锁/阻塞:资源竞争、线程池打满、队列积压
  4. 内存溢出/GC:Java 程序频繁 Full GC,程序暂停
  5. 磁盘IO瓶颈:大量写日志、读写文件,进程卡在 IO

举个典型场景: 网站返回 504,Nginx 看到 upstream_response_time 稳定 60s 超时;去后端日志一看,全是数据库查询超时,最终定位到某条 SQL 没加索引,大促流量上来直接把库打慢。


四、502 vs 504 排查思路对比(强化记忆)

错误码 本质 排查优先级 核心看什么
502 Bad Gateway 后端连不上、连接被拒绝 先查端口、进程、连接 ss 端口监听、后端进程是否存活
504 Gateway Timeout 后端处理超时、响应太慢 先查响应时间、后端日志 $upstream_response_time、后端应用日志、服务器资源

五、补充:504 完整排查步骤

  1. 看 Nginx 访问日志:确认 504 占比、对应接口、upstream_response_time 数值
  2. 看 Nginx 超时配置:proxy_read_timeout 是否设置过短
  3. 看后端应用日志:有没有报错、慢请求、异常堆栈
  4. 看后端服务器资源:CPU、内存、磁盘 IO、数据库负载
  5. 压测验证:单独调用后端接口,复现慢的场景

六、易错点(面试/排障坑)

  1. ❌ 误区:504 是 Nginx 出问题了 ✅ 纠正:绝大多数 504 根因都在后端,Nginx 只是超时保护,避免请求无限挂起。
  2. ❌ 误区:$request_time 就是后端处理时间 ✅ 纠正:$request_time 包含用户网络传输、后端处理、Nginx 转发全部时间;纯后端耗时看 $upstream_response_time。
  3. ❌ 误区:504 一定是后端程序 bug ✅ 纠正:也可能是服务器资源耗尽(CPU、内存、磁盘打满),或者数据库、缓存等依赖服务慢。

🔗 相关笔记