Nginx UDP负载均衡如何配置proxy_pass_header保留原始源目IP
Nginx UDP负载均衡原始IP包头透传配置方案
核心前提说明
- 常规Nginx UDP反向代理默认会对转发的数据包做双向地址改写:源IP替换为Nginx自身内网IP,目的IP替换为后端容器IP,这是反向代理的默认工作逻辑,和你观察到的包头现象一致。
proxy_pass_header类参数仅作用于HTTP协议层的自定义头部,完全不影响四层IP包头的地址字段,无法通过这类参数实现IP透传需求。- 你需要的「转发时保留原始源IP(客户端IP)、原始目的IP(服务端对外IP)」效果,属于透明代理场景,需要依赖内核TPROXY能力配合Nginx对应配置实现,不能仅靠Nginx单一配置完成。
配置步骤
1. 环境前置检查
- 确认当前Nginx已编译stream模块:执行
nginx -V,输出结果包含--with-stream即为符合要求。 - 开启内核必要参数,执行如下命令临时生效,写入
/etc/sysctl.conf可永久生效:
sysctl -w net.ipv4.ip_forward=1 sysctl -w net.ipv4.conf.all.route_localnet=1
2. Nginx配置修改
UDP负载均衡配置需要写在stream块下,核心是添加transparent透明代理参数,参考配置如下:
stream { # 定义后端UDP服务集群 upstream udp_service { server 172.17.x.y:【替换为你的UDP服务实际监听端口】; } server { listen 【替换为服务对外暴露的端口】 udp; # 核心配置:开启透明代理,允许转发时保留原始IP地址 proxy_bind $remote_addr transparent; proxy_pass udp_service; # 按需调整UDP超时参数 proxy_timeout 10s; proxy_connect_timeout 5s; } }
配置完成后执行nginx -t校验语法,确认无误后重载Nginx配置。
3. 路由与iptables规则配置
开启透明代理后,Nginx发往后端的数据包源IP为真实客户端IP、目的IP为服务端对外IP192.x.x.y,必须配置策略路由保证数据包能正确送达后端容器,同时后端回包能原路返回Nginx:
# 新增编号100的策略路由表,编号可自定义 ip rule add fwmark 1 table 100 ip route add local 0.0.0.0/0 dev lo table 100 # 替换<UDP服务端口>为你实际的业务端口,<容器内网网段>替换为实际的容器网段(例如172.17.0.0/16) # 给发往业务端口的入站UDP包打标记 iptables -t mangle -A PREROUTING -p udp --dport <UDP服务端口> -j MARK --set-mark 1 # 给容器返回的UDP回包打标记,保证回包经过Nginx处理 iptables -t mangle -A PREROUTING -s <容器内网网段> -p udp --sport <UDP服务端口> -j MARK --set-mark 1
4. 容器侧配置
- 将容器的默认网关设置为Nginx所在的内网IP172.17.x.x,避免回包直接路由到公网导致连接失败。
- 容器不需要绑定服务端对外IP192.x.x.y,仅需保证和Nginx内网网段连通即可。
效果验证
所有配置完成后,在容器侧对业务端口抓包,即可看到收到的UDP包头满足预期:
- 源IP:真实客户端IP 192.x.x.x
- 目的IP:原始服务端对外IP 192.x.x.y
注意:如果Nginx和容器部署在不同宿主机,需要确保两台宿主机之间没有其他做地址转换的网络设备,同时两端同步配置对应路由规则,保证非本机IP的数据包可正常转发。
内容的提问来源于stack exchange,提问作者Suraj
相关产品推荐
相关产品推荐

