FastAPI WebSocket 无法获取真实 IP 错误记录
FastAPI WebSocket 无法获取真实 IP 错误记录
问题描述
在使用 FastAPI WebSocket 服务时,发现无法获取设备的真实 Remote IP,所有连接均显示为内网地址 10.x.x.1
。以下是完整的排查过程及解决方案。
排查步骤
1. 基础信息检查
• 现象复现:通过 ws.client
确认连接的 IP 和端口均为 10.x.x.1
。
• Header 检查:WebSocket 请求头中未发现 X-Forwarded-For
、X-Real-IP
等代理相关字段。
• 网络拓扑验证:
公网 36.x.x.x -> 防火墙 NAT (10.x.x.1) -> 内部服务
端口映射示例:
36.x.x.x:18000 ➔ 10.x.x.180:8000
36.x.x.x:10002 ➔ 10.x.x.112:8001
2. 对比不同服务的表现
• 正常服务(10…x.x.112:8001):成功获取真实 IP(如 112.x.x.x
)。
• 异常服务(10.x.x.180:8000):无论内网或外网访问,Remote IP 均为 10.x.x.1
。
3. FastAPI IP 获取方式验证
通过以下代码尝试获取 IP,结果一致为 10.x.x.1
:
# 方式 1: 握手信息
client_ip = websocket.client.host
# 方式 2: 底层连接
client_ip = websocket._receive.client.host
# 方式 3: 请求头检查
headers = websocket.headers
x_forwarded_for = headers.get("x-forwarded-for", "undefined")
4. 防火墙 NAT 规则差异分析
• 关键发现:
• 正常服务所在主机(10.x.x.112)的 NAT 规则为 Disabled。
• 异常服务所在主机(10.x.x.180)的 NAT 规则为 Enabled。
根本原因
防火墙 NAT 模式配置错误
当 NAT 规则启用(Enabled)时,防火墙会劫持并重写源 IP,导致后端服务只能看到防火墙的内网地址(10.x.x.1
)。
而在 NAT 禁用(Disabled)模式下,原始源 IP 得以保留。
解决方案
-
调整防火墙 NAT 规则
将异常服务的 NAT 规则从 Enabled 改为 Disabled,确保源 IP 透传到后端服务。 -
验证结果
迁移服务到禁用 NAT 的规则组后,成功获取真实公网 IP。
额外发现:残留配置文件导致 IP 异常
现象
某次测试中获取到 47.x.x.x
(阿里云 Nginx IP),但预期应为 36.x.x.x
(设备直连 IP)。
排查
• 客户端配置冲突:旧版 .env
文件未清理,导致部分设备误连到阿里云代理服务器。
• 路径优先级问题:旧配置文件 software/.env
覆盖了新版 iot_client/.env
。
修复
• 清理所有遗留的 software/.env
文件。
• 统一客户端配置路径,确保仅使用 iot_client/.env
。
预防措施
-
代理头配置
如果必须启用 NAT,需在反向代理(如 Nginx)中配置以下 Header:proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; proxy_set_header X-Real-IP $remote_addr;
后端服务需读取这些字段以获取真实 IP。
-
配置管理规范
• 定期清理过期配置文件。
• 使用版本控制工具管理环境变量。 -
NAT 模式选择原则
• 直连场景:禁用 NAT 以保留源 IP。
• 需要隐藏内网时:启用 NAT 但需配置代理头。
总结与思考
• 网络层问题优先:IP 异常时首先检查防火墙、NAT、路由规则。
• 环境隔离的重要性:配置文件残留可能导致“幽灵问题”,需建立清理机制。
• 防御性编程:在代码中兼容多种 IP 获取方式:
def get_client_ip(websocket):
headers = websocket.headers
x_forwarded_for = headers.get("x-forwarded-for", "").split(",")[0]
return x_forwarded_for or websocket.client.host
通过系统性排查,最终定位到 NAT 规则和环境配置两大核心问题。此类问题需结合网络架构与代码实现综合分析,避免陷入“单点验证”的误区。
本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.kler.cn/a/596825.html 如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!