网关:172.16.0.48 反向代理到 Nginx:172.16.0.32 Nginx 只允许来源是网关 172.16.0.48 访问,拒绝所有其它 IP。
关键点:经过代理转发,Nginx 拿到的源 IP,默认不是真实客户端,而是网关 172.16.0.48,直接用 allow/deny 就可以实现。 注意区分两种场景:①四层转发(TCP 代理);②七层 HTTP 代理。
场景:网关是 HTTP 反向代理,把 http 请求转发给 172.16.0.32 的 Nginx。编辑 nginx server/location 块:
|
1 2 3 4 5 6 7 8 9 10 11 12 13 |
server { listen 80; server_name _;
# 只放行网关,其余全部拒绝 allow 172.16.0.48; deny all;
location / { root html; index index.html; } } |
??重要前提:网关是直接 http 代理访问 nginx,没有做 X?Forwarded?For 篡改访问控制;此时 nginx 看到的 remote_addr 就是172.16.0.48。 不要拿 $http_x_forwarded_for 做访问控制!这个 header 客户端可以伪造,不安全。
|
1 2 |
nginx -t nginx -s reload |
原理:allow 可以写多条,从上到下匹配,最后 deny all; 拒绝其余所有 IP。 依然记住:allow/deny 匹配的是 $remote_addr(TCP 真实连接源 IP),不要用 X?Forwarded?For 做权限校验。
直接写多条 allow(写在 server /location 块内)
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 |
server { listen 80; server_name _;
# 白名单IP列表 allow 172.16.0.48; allow 172.16.0.49; allow 172.16.0.50; # 也支持网段 allow 192.168.1.0/24;
deny all; # 不在上面白名单全部拒绝403
location / { root html; index index.html; } } |
直接在 Nginx 服务器172.16.0.32操作系统防火墙限制,不管 Nginx 配置,网络层面只允许172.16.0.48访问 80/443,其它 IP 全部 drop。
|
1 2 3 4 5 6 7 8 9 |
# 删除80、443公开放行 firewall-cmd --permanent --remove-service=http firewall-cmd --permanent --remove-service=https
# 仅允许网关访问80、443 firewall-cmd --permanent --add-rich-rule='rule family="ipv4" source address="172.16.0.48/32" port protocol="tcp" port="80" accept' firewall-cmd --permanent --add-rich-rule='rule family="ipv4" source address="172.16.0.48/32" port protocol="tcp" port="443" accept'
firewall-cmd --reload |
如果网关是四层 TCP 转发,Nginx 用stream处理 tcp 流量,ngx_stream_access_module做 IP 限制:
|
1 2 3 4 5 6 7 8 |
stream { server { listen 80; allow 172.16.0.48; deny all; proxy_pass backend; } } |
在 nginx 日志格式加上$remote_addr,看日志确认连接来源 IP:
|
1 2 3 4 |
log_format main '$remote_addr - $remote_user [$time_local] "$request" ' '$status $body_bytes_sent "$http_referer" ' '"$http_user_agent" "$http_x_forwarded_for"'; access_log /var/log/nginx/access.log main; |
执行 tail -f /var/log/nginx/access.log,确认请求过来时remote_addr是172.16.0.48。
网关:172.16.0.48 反向代理到 Nginx:172.16.0.32 Nginx 只允许来源是网关 172.16.0.48 访问,拒绝所有其它 IP。
关键点:经过代理转发,Nginx 拿到的源 IP,默认不是真实客户端,而是网关 172.16.0.48,直接用 allow/deny 就可以实现。 注意区分两种场景:①四层转发(TCP 代理);②七层 HTTP 代理。
场景:网关是 HTTP 反向代理,把 http 请求转发给 172.16.0.32 的 Nginx。编辑 nginx server/location 块:
|
1 2 3 4 5 6 7 8 9 10 11 12 13 |
server { listen 80; server_name _;
# 只放行网关,其余全部拒绝 allow 172.16.0.48; deny all;
location / { root html; index index.html; } } |
??重要前提:网关是直接 http 代理访问 nginx,没有做 X?Forwarded?For 篡改访问控制;此时 nginx 看到的 remote_addr 就是172.16.0.48。 不要拿 $http_x_forwarded_for 做访问控制!这个 header 客户端可以伪造,不安全。
|
1 2 |
nginx -t nginx -s reload |
原理:allow 可以写多条,从上到下匹配,最后 deny all; 拒绝其余所有 IP。 依然记住:allow/deny 匹配的是 $remote_addr(TCP 真实连接源 IP),不要用 X?Forwarded?For 做权限校验。
直接写多条 allow(写在 server /location 块内)
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 |
server { listen 80; server_name _;
# 白名单IP列表 allow 172.16.0.48; allow 172.16.0.49; allow 172.16.0.50; # 也支持网段 allow 192.168.1.0/24;
deny all; # 不在上面白名单全部拒绝403
location / { root html; index index.html; } } |
直接在 Nginx 服务器172.16.0.32操作系统防火墙限制,不管 Nginx 配置,网络层面只允许172.16.0.48访问 80/443,其它 IP 全部 drop。
|
1 2 3 4 5 6 7 8 9 |
# 删除80、443公开放行 firewall-cmd --permanent --remove-service=http firewall-cmd --permanent --remove-service=https
# 仅允许网关访问80、443 firewall-cmd --permanent --add-rich-rule='rule family="ipv4" source address="172.16.0.48/32" port protocol="tcp" port="80" accept' firewall-cmd --permanent --add-rich-rule='rule family="ipv4" source address="172.16.0.48/32" port protocol="tcp" port="443" accept'
firewall-cmd --reload |
如果网关是四层 TCP 转发,Nginx 用stream处理 tcp 流量,ngx_stream_access_module做 IP 限制:
|
1 2 3 4 5 6 7 8 |
stream { server { listen 80; allow 172.16.0.48; deny all; proxy_pass backend; } } |
在 nginx 日志格式加上$remote_addr,看日志确认连接来源 IP:
|
1 2 3 4 |
log_format main '$remote_addr - $remote_user [$time_local] "$request" ' '$status $body_bytes_sent "$http_referer" ' '"$http_user_agent" "$http_x_forwarded_for"'; access_log /var/log/nginx/access.log main; |
执行 tail -f /var/log/nginx/access.log,确认请求过来时remote_addr是172.16.0.48。