可通过nginx配置自定义请求头(如x-forwarded-by、x-proxy-path)和扩展log_format,结合$upstream_addr、$http_x_proxy_path等变量,记录代理节点名、上游地址及转发路径,实现全链路追踪。

可以通过在 Nginx 配置中添加自定义请求头和日志格式,记录请求经过的代理路径(比如从哪台上游、是否被重写、原始 Host 和 URI 等),从而还原完整的转发链路。
在请求头中注入代理路径信息
利用 proxy_set_header 在每次代理转发时追加标识,例如当前代理节点名称、上游地址、跳数等。推荐使用唯一可识别的节点名(如 node-a、lb-prod)而非 IP,便于维护:
- 在 upstream 或 location 块中添加:
proxy_set_header X-Forwarded-By "$hostname";
记录当前 Nginx 实例主机名 - 若需标记上游目标:
proxy_set_header X-Upstream "$upstream_addr";
(注意:该变量在 proxy_pass 后才可用,建议配合 map 或 log_format 使用) - 叠加路径追踪(类似 HTTP 的
Traceparent思路):proxy_set_header X-Proxy-Path "$http_x_proxy_path, $hostname";
这样每经一层就追加一次,最终日志里能看到完整跳转序列,如node-lb1, node-app2, node-cache
定制 access_log 格式,捕获关键转发字段
默认日志不包含上游信息,需扩展 log_format 并引用 Nginx 内置变量:
- 定义日志格式(在 http 块中):
log_format trace '$remote_addr - $remote_user [$time_local] ' <br> "\"$request\" $status $body_bytes_sent ' <br> "\"$http_referer\" \"$http_user_agent\" ' <br> "$upstream_addr $upstream_http_x_trace_id $http_x_proxy_path';
- 关键变量说明:
$upstream_addr:实际转发到的上游地址(含端口,支持多台时显示具体选中的那台)
$upstream_http_x_trace_id:从上游响应头中获取的 trace ID(需上游返回该 header)
$http_x_proxy_path:客户端携带或上一层注入的路径标记 - 在 server 或 location 中启用:
access_log /var/log/nginx/trace.log trace;
结合 map 模块动态标记上游身份
当使用动态 upstream(如基于 consul 或 resolver)时,$upstream_addr 可能是 IP+端口,不易读。可用 map 将其映射为服务名:
- 在 http 块顶部添加:
map $upstream_addr $upstream_name {<br> default "unknown";<br> "10.0.1.10:8080" "api-v1-primary";<br> "10.0.1.11:8080" "api-v1-standby";<br> "10.0.2.5:3000" "frontend-react";<br>} - 然后在 log_format 或 proxy_set_header 中使用
$upstream_name替代原始地址
验证与调试技巧
上线前建议用 curl 快速验证头信息是否注入、日志是否生效:
- 检查响应头:
curl -I http://your-domain.com/api/test
查看是否返回X-Forwarded-By、X-Proxy-Path等 - 实时观察日志:
tail -f /var/log/nginx/trace.log | grep -E "(your-ip|api)" - 若发现
$upstream_addr为空,通常因未真正触发 proxy_pass(比如被 rewrite 跳过、命中了 return 或 try_files),需确认 location 匹配逻辑











