在使用腾讯云CLB负载均衡时,后端服务器需要正确配置才能获取到客户端的真实IP地址 🌐。CLB会将客户端真实IP存储在HTTP头部中。
📋 基本原理
腾讯云CLB将客户端真实IP存储在以下HTTP头部:
- Header名称:
X-Forwarded-For
- Nginx变量:
$http_x_forwarded_for
🔧 配置方法
方法一:日志记录真实IP
在Nginx日志格式中添加 $http_x_forwarded_for
变量:
log_format main '$remote_addr - $remote_user [$time_local] "$request" '
'$status $body_bytes_sent "$http_referer" '
'"$http_user_agent" "$http_x_forwarded_for"';
方法二:使用realip模块
编译时添加模块
# 编译时添加realip模块
--with-http_realip_module
--with-stream_realip_module # 可选,用于stream代理
Nginx配置
# 设置信任的负载均衡器IP段
#set_real_ip_from 0.0.0.0/0; # 信任所有IP(不推荐)
#set_real_ip_from 192.168.3.0/24; # 信任特定网段
set_real_ip_from 负载均衡的ip或ip网段; # 推荐:指定CLB的IP段
# 指定真实IP的头部字段
real_ip_header X-Forwarded-For;
而对于阿里云,则是使用X-Real-IP,nginx配置修改如下
#set_real_ip_from 0.0.0.0/0;
#set_real_ip_from 192.168.3.0/24;
set_real_ip_from 负载均衡的ip或ip网段;
real_ip_header X-Real-IP;
如果要设置header到X-Real-IP中,nginx配置如下:
# proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Real-IP $http_x_forwarded_for;
关于proxy_add_x_forwarded_for
proxy_add_x_forwarded_for这个字段,会以追加的形式把多级代理的代理ip加起来,以逗号隔开,越靠近客户端的排在前面,越靠近最后服务端的排在后面,但存在被伪造的可能性,比如使用以下命令测试:
curl http://localhost -H 'X-Forwarded-For: 1.1.1.1' -H 'X-Real-IP: 2.2.2.2'
日志打印出来的ip可能会是”1.1.1.1, 127.0.0.1, 192.168.100.101, 192.168.100.102”,其中1.1.1.1排在最前面,但他不是最真实的客户端ip
对于伪造代ip的处理方法
只需要在第一个代理设置proxy_set_header X-Real-IP $remote_addr;就好了,然后再应用端直接引用$http_x_real_ip就行。
附加说明
根据腾讯云官方文档说明,如果是四层协议则后端是可以直接从源IP获得客户端IP,以下是摘抄信息:
负载均衡获取客户端真实 IP 的说明
CLB 的四层(TCP/UDP/TCP SSL)和七层(HTTP/HTTPS)服务均支持直接在后端 CVM 上获取客户端真实 IP,无需进行额外配置。
四层负载均衡,在后端 CVM 上获取的源 IP 即为客户端 IP。
七层负载均衡,您可以通过 X-Forwarded-For 或 remote_addr 字段来直接获取客户端 IP。