![](/img/trans.png)
[英]How to get real client ip behind docker load balancer using plain tcp?
[英]How to get the real IP of a client in a pyramid server behind a nginx proxy
我有一个金字塔应用程序,在某些地方使用request.environ['REMOTE_ADDR']
。
该应用程序由端口6543上的Python Paste提供,而端口80上的nginx服务器将请求转发到Paste服务器。
nginx配置的灵感来自Pyramid食谱:
server {
listen 80; ## listen for ipv4
listen [::]:80 default ipv6only=on; ## listen for ipv6
server_name localhost;
access_log /var/log/nginx/localhost.access.log;
location / {
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_pass http://127.0.0.1:6543;
}
在Pyramid应用程序中,变量request.environ ['REMOTE_ADDR']现在始终等于127.0.0.1。 我看到了一些解决这个问题的策略,但我不知道是否有推荐的方法来解决这个问题。
这是我正在考虑的事情:
添加一个NewRequest订户,如有必要,它将替换request.environ ['REMOTE_ADDR']:
if 'HTTP_X_REAL_IP' in event.request.environ: event.request.environ['REMOTE_ADDR'] = event.request.environ['HTTP_X_REAL_IP']
在点击金字塔图层之前使用wsgi中间件修改request.environ。
别的
您使用哪种策略来部署Pyramid应用程序? 如果我有两个nginx代理会怎么样? (第一个服务于LAN,第二个服务器直接连接到互联网)。
如果您通过use = egg:PasteDeploy#prefix
paste.deploy.config.PrefixMiddleware
在WSGI管道中使用paste.deploy.config.PrefixMiddleware
,它将自动将X-Forwarded-For
转换为REMOTE_ADDR
。 它对于反向代理的其他属性也很好,例如它会将X-Forwarded-Proto
转换为wsgi.url_scheme
以确保如果用户访问https,则生成的URL也是https。
http://pythonpaste.org/deploy/class-paste.deploy.config.PrefixMiddleware.html
我在nginx后面使用gevent服务器,我使用request.client_addr
来获取客户端的IP地址。
如果您没有WSGI pipline,或者不想使用paste
,那么添加一个事件处理程序:
config.add_subscriber(reverseProxyProtocolCorrection,'pyramid.events.NewRequest')
事件处理程序可以像:
def reverseProxyProtocolCorrection(event):
event.request.scheme = 'https' if event.request.headers['X-Forwarded-Proto']=='https' else 'http'
event.request.remote_addr=parseXForward(event.request.headers['X-Forwarded-For'],event.request.remote_addr)
并确保您的代理设置标题
在nginx中:
location / {
proxy_pass http://yourapp;
proxy_redirect off;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $remote_addr;
}
在PHP我做:
if($_SERVER["HTTP_X_FORWARDED_FOR"]){
$ip = $_SERVER["HTTP_X_FORWARDED_FOR"];
}else{
$ip = $_SERVER["REMOTE_ADDR"];
}
或许在python中类似,$ ip是你真正的ip
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.