Java之获取Nginx代理之后的客户端IP

Java之获取Nginx代理之后的客户端IP

Nginx 代理接口之后,后台获取的IP地址都是127.0.0.1,解决办法是需要配置Nginx搭配后台获取的方法,获得设备的真实地址 。我们想要获取的就是nginx代理日志中的这个IP

nginx配置

首先在nginx代理的对应location增加如下配置

bash 复制代码
#保留代理之前的host 包含客户端真实的域名和端口号
proxy_set_header    Host  $host; 
#保留代理之前的真实客户端ip
proxy_set_header    X-Real-IP  $remote_addr;  
#这个Header和X-Real-IP类似,但它在多级代理时会包含真实客户端及中间每个代理服务器的IP
proxy_set_header    X-Forwarded-For  $proxy_add_x_forwarded_for;
#表示客户端真实的协议(http还是https)
proxy_set_header X-Forwarded-Proto $scheme;

示例

bash 复制代码
server {
        listen       9010;
        server_name  127.0.0.1;

        location ^~  /tob_server/ {
            #代理地址
            proxy_pass http://127.0.0.1:9012/tob_server/;

            #保留代理之前的host 包含客户端真实的域名和端口号
			proxy_set_header    Host  $host; 
			#保留代理之前的真实客户端ip
			proxy_set_header    X-Real-IP  $remote_addr;  
			#这个Header和X-Real-IP类似,但它在多级代理时会包含真实客户端及中间每个代理服务器的IP
			proxy_set_header    X-Forwarded-For  $proxy_add_x_forwarded_for;
			#表示客户端真实的协议(http还是https)
			proxy_set_header X-Forwarded-Proto $scheme;

            #解决跨域
            add_header Access-Control-Allow-Origin *;
            #解决nginx转发丢失cookie的问题
            proxy_cookie_path /tob_server/ /;

            #解决options请求
            if ($request_method = 'OPTIONS') {
                add_header 'Access-Control-Max-Age' 1728000;
                add_header 'Content-Type' 'text/plain; charset=utf-8';
                add_header 'Content-Length' 0;
                return 204;
            }
         }

         location \ {
            root   html;
            index  index.html index.htm;
         }
         
         #解决代理异常
         error_page  404 500 502 503 504  /50x.html;
         location = /50x.html {
            root   html;
         }
}

java获取客户端IP

获取客户端IP地址工具类

java 复制代码
public class IpUtils
{
    private static Logger logger = LoggerFactory.getLogger(IPUtils.class);
    
    /**
     * 获取客户端IP
     * 
     * @param request 请求对象
     * @return IP地址
     */
    public static String getIpAddr(HttpServletRequest request)
    {
        if (request == null)
        {
            return "unknown";
        }
        String ip = request.getHeader("x-forwarded-for");
        if (ip == null || ip.length() == 0 || "unknown".equalsIgnoreCase(ip))
        {
            ip = request.getHeader("Proxy-Client-IP");
        }
        if (ip == null || ip.length() == 0 || "unknown".equalsIgnoreCase(ip))
        {
            ip = request.getHeader("X-Forwarded-For");
        }
        if (ip == null || ip.length() == 0 || "unknown".equalsIgnoreCase(ip))
        {
            ip = request.getHeader("WL-Proxy-Client-IP");
        }
        if (ip == null || ip.length() == 0 || "unknown".equalsIgnoreCase(ip))
        {
            ip = request.getHeader("X-Real-IP");
        }

        if (ip == null || ip.length() == 0 || "unknown".equalsIgnoreCase(ip))
        {
            ip = request.getRemoteAddr();
        }

        return "0:0:0:0:0:0:0:1".equals(ip) ? "127.0.0.1" : getMultistageReverseProxyIp(ip);
    }

    /**
     * 从多级反向代理中获得第一个非unknown IP地址
     *
     * @param ip 获得的IP地址
     * @return 第一个非unknown IP地址
     */
    public static String getMultistageReverseProxyIp(String ip)
    {
        // 多级反向代理检测
        if (ip != null && ip.indexOf(",") > 0)
        {
            final String[] ips = ip.trim().split(",");
            for (String subIp : ips)
            {
                if (false == isUnknown(subIp))
                {
                    ip = subIp;
                    break;
                }
            }
        }
        return StringUtils.substring(ip, 0, 255);
    }

    /**
     * 检测给定字符串是否为未知,多用于检测HTTP请求相关
     *
     * @param checkString 被检测的字符串
     * @return 是否未知
     */
    public static boolean isUnknown(String checkString)
    {
        return StringUtils.isBlank(checkString) || "unknown".equalsIgnoreCase(checkString);
    }
}

这样就可以通过代码获取到客户端的真实IP地址了。

参考文章:

https://blog.csdn.net/u012812482/article/details/126066550

相关推荐
Initialize-le2 小时前
Nginx 504 超时、499 一堆?网关排查法
运维·nginx
哦虎!4 小时前
【JavaEE】网络初识
java
for_ever_love__4 小时前
MySQL ORDER BY 排序优化:从 Using filesort 到索引有序扫描(含双路 / 单路排序原理)
java·mysql·优化·存储·by·order·filesort
我是人✓5 小时前
Java文件上传三方式对比:从传统到SpringBoot
java·开发语言
欣栀♡5 小时前
JVM 频繁 Full GC 先看日志括号里的 cause,jstat 的 FGC 在 JDK 8 上会骗人
java·jvm
IT研究室6 小时前
最新计算机毕业设计选题推荐-基于spring boot的葡萄酒文化宣传网站-网站-文档指导-Java-springboot
java·spring boot·课程设计
慧都小项6 小时前
MyEclipse 中创建和测试 JAX-RS REST 接口:从项目配置到 REST Explorer
java·restful·myeclipse·jax-rs
Wang's Blog6 小时前
Java 项目实战: 交友项目 - 入门案例:编写 Dubbo 服务提供者
java·dubbo·交友
花间相见6 小时前
【计算基础|网络14】网络层:IP、ICMP 与 ping
网络·网络协议·tcp/ip
秋饼6 小时前
Spring AI 2.0 结构化输出企业级实战:从 BeanOutputConverter 源码到生产级解析容错
java·ai·技术分享·后端开发