bigywater.tech
微服务 · 17

反向代理的请求流程与配置分层:读头、选 upstream、转发、回写,listener、路由、上游三层

一个请求经过 nginx 反向代理,到了后端会变成什么样?响应回来又被改了什么?listener、路由、上游三层是怎么一层层选下去的?这篇用一个回显请求的后端和 nginx 1.31.6 把默认行为逐项量出来。

Host: u
默认配置下,client 的 Host: shop.example.test 到后端变成了 upstream 组的名字(proxy_set_header Host $host 之后恢复)
3 个头
默认配置下后端看不到的信息:X_under(下划线头被丢弃)、X-Forwarded-For、X-Real-IP
X-Secret-Internal
后端的内部响应头默认原样转发给了 client,要用 proxy_hide_header 去掉

转发的请求

实测 · 本机执行输出
  client 发出的请求头: Host: 'shop.example.test', X-Trace: 't-1', Accept-Encoding: 'gzip', X-Empty: '', X_under: 'u1', User-Agent: 'v17-client'
  后端看到的请求行(默认配置): GET /hello?a=1 HTTP/1.1     (常见写法): GET /hello?a=1 HTTP/1.1
  请求头             | client 发的           | 后端看到的(默认配置)  | 后端看到的(常见写法)        
  ----------------+---------------------+--------------+--------------------
  Accept-Encoding | 'gzip'              | 'gzip'       | 'gzip'             
  Host            | 'shop.example.test' | 'u'          | 'shop.example.test'
  User-Agent      | 'v17-client'        | 'v17-client' | 'v17-client'       
  X-Empty         | ''                  | ''           | ''                 
  X-Forwarded-For | -                   | (没有)         | '127.0.0.1'        
  X-Real-IP       | -                   | (没有)         | '127.0.0.1'        
  X-Trace         | 't-1'               | 't-1'        | 't-1'              
  X_under         | 'u1'                | (没有)         | (没有)               

Host、X-Forwarded-For 等默认不是你以为的样子;带下划线的请求头被丢弃。

回写的响应

实测 · 本机执行输出
  响应头               | 直连后端                          | 经过 nginx(默认)                  | 经过 nginx(hide X-Secret-Internal + pass Server)
  ------------------+-------------------------------+-------------------------------+-----------------------------------------------
  connection        | (没有)                          | keep-alive                    | keep-alive                                    
  content-length    | 106                           | 93                            | 93                                            
  date              | Sun, 18 Oct 2026 15:26:26 GMT | Sun, 18 Oct 2026 15:26:26 GMT | Sun, 18 Oct 2026 15:26:26 GMT                 
  keep-alive        | timeout=5                     | (没有)                          | (没有)                                          
  server            | BaseHTTP/0.6 Python/3.14.8    | nginx/1.31.6                  | BaseHTTP/0.6 Python/3.14.8                    
  x-backend         | b1                            | b1                            | b1                                            
  x-secret-internal | yes                           | yes                           | (没有)                                          

Server 被换掉、逐跳头被去掉、内部头原样泄露。

三层配置

实测 · 本机执行输出
  listener | Host 头       | 路径           | 状态码 | 落到哪里        
  ---------+--------------+--------------+-----+-------------
  端口 P1    | shop.test    | /api/users   | 200 | b1          
  端口 P1    | shop.test    | /static/a.js | 200 | b2          
  端口 P1    | shop.test    | /other       | 200 | shop-default
  端口 P1    | unknown.test | /api/users   | 404 | no-such-host
  端口 P2    | admin.test   | /api/users   | 200 | b2          
  端口 P2    | shop.test    | /x           | 200 | b2          
  第一层 listener(端口 + server_name 选 server 块)→ 第二层路由(location 选一条规则)→ 第三层上游(upstream 里选一台后端)。Host 对不上任何 server_name 时落到该端口的 default_server;P2 上只有一个 server 块,所以不管 Host 是什么都落到它

listener 选 server 块,路由选 location,上游选后端;Host 对不上落到 default_server。

分步演示

反向代理的请求流程与配置分层
本步的对象

    本文用到的工具与边界

    • 本机 macOS 27 arm64 / Python 3.14.8 / Go / nginx / Envoy / etcd / Consul / Nacos / OpenTelemetry / Prometheus(按各篇注明用到哪些及版本);所有服务都是本机自己起的进程,端口 9150 以上,只监听 127.0.0.1,不连任何外部服务,不碰本机已有的实例;故障用 kill -9 进程、让连接断开或在代码里注入延迟与错误来制造;计时用 time.perf_counter,数字每次运行会有小幅抖动。nginx 是 Homebrew 的 1.31.6,自己起的实例(端口 9150 起,error.log 与临时文件在 vtmp/);后端是本进程里的 Python http.server,把收到的请求原样回显;nginx 1.31.6 默认用 HTTP/1.1 连上游(我没有测旧版本的默认值,所以不能说旧版本也一样)
    • 没有验证:其它版本的 nginx 默认值;proxy_set_header 在多层 location 里的继承规则;server_name 的通配与正则匹配优先级;HTTP/2 和 HTTP/3 的 listener;Envoy / Traefik 等其它网关的默认改写
    京ICP备2026067502号-1京公网安备11010502063487号