前言在内网穿透、四层负载均衡、TCP反向代理场景中一个老生常谈的痛点流量经过中转服务转发后后端只能获取代理本机IP丢失真实访客源IP。HTTP场景我们可以依靠X-Forwarded-For请求头传递客户端IP但纯TCP隧道、SSL透传、游戏服务、数据库代理等非HTTP业务没有请求头机制。Proxy Protocol代理协议正是为解决这一问题而生由HAProxy作者设计分为v1文本协议、v2二进制协议两个标准。本文重点讲解Proxy Protocol v1原理、报文格式、部署配置、坑点排查同时结合FRP内网穿透 Nginx真实业务场景演示。一、什么是 Proxy Protocol v1Proxy Protocol 核心思想TCP连接建立完成后、正式业务数据传输之前代理服务向后端发送一段携带客户端连接信息的头部后端服务解析头部还原原始客户端IP与端口。Proxy Protocol v1ASCII明文文本格式协议人类可读、调试友好是最早的正式版本。重要约束v1仅支持TCP协议TCP4 IPv4 / TCP6 IPv6不支持UDP无扩展字段。二、标准报文格式基础语法PROXY 协议族 源IP 目标IP 源端口 目标端口\r\n字段说明PROXY固定起始标记协议族TCP4IPv4 TCP连接TCP6IPv6 TCP连接UNKNOWN无法识别连接类型源IPSRC_ADDR真实客户端公网IP目标IPDST_ADDR代理服务与后端建立连接使用的IP源端口客户端对外发起连接端口目标端口后端监听端口\r\n强制结束符缺少换行符会导致解析失败真实示例IPv4场景PROXY TCP4 113.64.xx.xx 127.0.0.1 54132 81\r\n含义公网访客113.64.xx.xx:54132通过代理转发连接本机127.0.0.1:81。IPv6场景PROXY TCP6 2001:db8::1 ::1 41234 443\r\n报文长度限制v1头部最大长度108字节。头部发送完毕后紧接着发送原始业务数据流。完整数据流样例HTTP访问PROXY TCP4 113.64.xx.xx 127.0.0.1 54132 81\r\nGET / HTTP/1.1 Host: 43.227.71.58:39001 ...三、Proxy Protocol v1 vs v2 核心对比很多人分不清两个版本如何选择这里做清晰对比项目Proxy Protocol v1Proxy Protocol v2编码格式ASCII明文二进制支持传输协议仅TCPTCP4/TCP6TCP UDP可读性抓包直接可读调试方便二进制必须工具解析扩展性无扩展字段无法携带TLS、SNI信息支持TLV扩展字段解析性能文本拆分解析开销更高二进制固定结构解析更快头部最小长度不固定最小28字节适用场景老旧软件兼容、调试环境、简单TCP隧道生产大规模集群、UDP业务、云负载均衡行业建议新项目优先v2仅后端服务不支持v2时选择v1。注意发送端与接收端版本必须匹配混用直接导致连接失败。四、Nginx 如何接收 Proxy Protocol v1核心指令开启端口监听支持代理协议listen 81 proxy_protocol;⚠️关键特性只要添加proxy_protocol参数Nginx会强制要求所有接入该端口的TCP连接首个数据必须是合法Proxy Protocol头部。不带PP头部的连接Nginx直接主动断开客户端表现为连接超时、网页打不开。两个变量重点对应Windows Nginx踩坑$proxy_protocol_addrNginx原生内置变量。只要成功解析v1/v2头部变量值等于真实客户端IP。✅Windows官方Nginx 1.24.0默认可用不需要额外模块$remote_addrTCP连接直接对端地址。FRP场景下永远是127.0.0.1无法用来获取访客IP。拓展realip模块Windows官方包缺失Linux发行版Nginx通常自带ngx_http_realip_module可以使用set_real_ip_from 127.0.0.1; real_ip_header proxy_protocol;作用把解析出来的真实IP覆盖$remote_addr。⚠️Windows官方编译版Nginx不包含realip模块写入配置直接启动报错unknown directive set_real_ip_fromWindows环境解决方案直接使用$proxy_protocol_addr传递给后端不要使用realip系列指令。Windows Nginx 可用完整示例配置server { listen 81 proxy_protocol; server_name detayun.cn; location / { proxy_set_header Host $host; proxy_set_header X-Real-IP $proxy_protocol_addr; proxy_set_header X-Forwarded-For $proxy_protocol_addr; proxy_set_header X-Forwarded-Proto $scheme; proxy_pass http://detayun_server; } }避坑提醒不要继续使用 $proxy_add_x_forwarded_for该变量无法读取Proxy Protocol信息五、FRP内网穿透启用 Proxy Protocol v1 实战你的业务架构外网用户 → frps公网服务端 → frpc客户端TCP隧道→ Nginx:81 → Django后端frpc代理区块配置TCP隧道开启v1[[proxies]] name detayun3 type tcp localIP 127.0.0.1 localPort 81 remotePort 39001 proxyProtocolVersion v1必须遵守3条规则localPort必须与Nginx监听开启proxy_protocol的端口保持一致示例81修改配置后完全重启frpc重载不生效不要多个链路重复添加Proxy Protocol头部frpc加一次Nginx上游不要再嵌套代理。六、后端Django读取真实IP代码Nginx已经把真实IP放入HTTP请求头Django直接读取defget_real_ip(request):# 优先读取代理协议传递IPx_real_iprequest.META.get(HTTP_X_REAL_IP)ifx_real_ip:returnx_real_ip.strip()xffrequest.META.get(HTTP_X_FORWARDED_FOR)ifxff:returnxff.split(,)[0].strip()returnrequest.META.get(REMOTE_ADDR)七、高频踩坑清单重点覆盖你遇到的问题坑1listen xx proxy_protocol; 端口复用不能和普通访问共用端口。例如80端口用于局域网直接访问无PP头不能同时加上proxy_protocol。✅ 最佳实践端口隔离80局域网直连、其他普通穿透普通监听81专门接收frp携带Proxy Protocol的流量坑2frpc忘记配置 proxyProtocolVersionfrpc不会发送任何Proxy头部Nginx收不到合法头部直接断开连接网站无法访问。坑3Nginx变量写错依然拿到127.0.0.1# 错误写法 proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; # 正确写法 proxy_set_header X-Forwarded-For $proxy_protocol_addr;坑4Windows Nginx强行写入 set_real_ip_from缺少模块直接启动失败删除realip相关三行改用$proxy_protocol_addr。坑5v1报文缺少 \r\n 换行符部分代理程序实现有bug缺少结束换行Nginx解析头部失败连接中断。坑6混淆TCP隧道与HTTP隧道frptypehttp隧道依靠HTTP头X-Forwarded-For不需要Proxy ProtocolProxy Protocol只用于typetcp裸TCP隧道。八、故障排查方法论连通性判断公网访问能够打开网页 → frpc成功发送Proxy头部直接无法访问 → frp未发送头部或者端口不匹配。增加Nginx日志验证变量是否正常解析server { listen 81 proxy_protocol; log_format pp_log $proxy_protocol_addr | $remote_addr | $time_local $request $status; access_log logs/access_81.log pp_log; }访问后查看日志$proxy_protocol_addr存在公网IPNginx解析正常问题在后端代码$proxy_protocol_addr为空字符串frpc未发送Proxy Protocol v1头部。九、安全注意事项Proxy Protocol本身不存在签名校验头部可以伪造。不要直接对外公网开放开启proxy_protocol的端口仅信任内网代理frpc本机连接127.0.0.1。多层代理场景控制信任链路避免恶意用户伪造源IP实施限流绕过、风控绕过。十、总结Proxy Protocol v1 是明文TCP连接信息透传方案适合TCP隧道、SSL透传等非HTTP场景Windows官方Nginx无法使用realip模块依靠$proxy_protocol_addr获取真实IP端口隔离是最佳架构禁止普通流量与PP流量共用同一个监听端口FRP TCP隧道场景发送端版本与Nginx接收端保持一致v1/v2严格匹配如果业务以Web HTTP服务为主优先考虑frptypehttp隧道免去Proxy Protocol复杂配置。