package com.mvp.common.annotation;
import java.lang.annotation.*;
@Target({ElementType.METHOD})
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface FetchClientIp {
}
package com.mvp.common.utils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.http.HttpHeaders;
import org.springframework.http.server.reactive.ServerHttpRequest;
import org.springframework.util.AntPathMatcher;
import org.springframework.util.CollectionUtils;
import org.springframework.util.PathMatcher;
import javax.servlet.http.HttpServletRequest;
import java.net.InetAddress;
import java.net.UnknownHostException;
import java.util.List;
import java.util.Optional;
/**
* @author liangkeshun
* @date 2022/7/28 00:27
*/
public class NetworkUtil {
private Logger log = LoggerFactory.getLogger(NetworkUtil.class);
private static final String IP_UNKNOWN = "unknown";
private static final String IP_LOCAL = "127.0.0.1";
private static final int IP_LEN = 15;
/**
* 获取客户端真实ip
* @param request request
* @return 返回ip
*/
public static String getip(ServerHttpRequest request) {
HttpHeaders headers = request.getHeaders();
String ipAddress = headers.getFirst("x-forwarded-for");
if (ipAddress == null || ipAddress.length() == 0 || IP_UNKNOWN.equalsIgnoreCase(ipAddress)) {
ipAddress = headers.getFirst("Proxy-Client-IP");
}
if (ipAddress == null || ipAddress.length() == 0 || IP_UNKNOWN.equalsIgnoreCase(ipAddress)) {
ipAddress = headers.getFirst("WL-Proxy-Client-IP");
}
if (ipAddress == null || ipAddress.length() == 0 || IP_UNKNOWN.equalsIgnoreCase(ipAddress)) {
ipAddress = Optional.ofNullable(request.getRemoteAddress())
.map(address -> address.getAddress().getHostAddress())
.orElse("");
if (IP_LOCAL.equals(ipAddress)) {
// 根据网卡取本机配置的IP
try {
InetAddress inet = InetAddress.getLocalHost();
ipAddress = inet.getHostAddress();
} catch (UnknownHostException e) {
// ignore
}
}
}
// 对于通过多个代理的情况,第一个IP为客户端真实IP,多个IP按照','分割
if (ipAddress != null && ipAddress.length() > IP_LEN) {
int index = ipAddress.indexOf(",");
if (index > 0) {
ipAddress = ipAddress.substring(0, index);
}
}
return ipAddress;
}
/**
* 获取客户端真实ip
* @param request request
* @return 返回ip
*/
public static String getip(HttpServletRequest request) {
String ipAddress = request.getHeader("x-forwarded-for");
if (ipAddress == null || ipAddress.length() == 0 || IP_UNKNOWN.equalsIgnoreCase(ipAddress)) {
ipAddress = request.getHeader("Proxy-Client-IP");
}
if (ipAddress == null || ipAddress.length() == 0 || IP_UNKNOWN.equalsIgnoreCase(ipAddress)) {
ipAddress = request.getHeader("WL-Proxy-Client-IP");
}
if (ipAddress == null || ipAddress.length() == 0 || IP_UNKNOWN.equalsIgnoreCase(ipAddress)) {
ipAddress = request.getRemoteHost();
if (IP_LOCAL.equals(ipAddress)) {
// 根据网卡取本机配置的IP
try {
InetAddress inet = InetAddress.getLocalHost();
ipAddress = inet.getHostAddress();
} catch (UnknownHostException e) {
// ignore
}
}
}
// 对于通过多个代理的情况,第一个IP为客户端真实IP,多个IP按照','分割
if (ipAddress != null && ipAddress.length() > IP_LEN) {
int index = ipAddress.indexOf(",");
if (index > 0) {
ipAddress = ipAddress.substring(0, index);
}
}
return ipAddress;
}
public static boolean isWhiteUrl(String requestUri,List<String> whitePathList) {
if (CollectionUtils.isEmpty(whitePathList)) {
return false;
}
PathMatcher pathMatcherToUse = new AntPathMatcher();
for (String pattern : whitePathList) {
if (pathMatcherToUse.match(pattern, requestUri)) {
return true;
}
}
return false;
}
}
package com.mvp.common.annotation.aspect;
import com.mvp.common.annotation.FetchClientIp;
import com.mvp.common.filter.GlobalHolder;
import com.mvp.common.utils.NetworkUtil;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.springframework.core.annotation.Order;
import org.springframework.http.server.reactive.ServerHttpRequest;
import org.springframework.stereotype.Component;
import org.springframework.web.context.request.RequestAttributes;
import org.springframework.web.context.request.RequestContextHolder;
import org.springframework.web.context.request.ServletRequestAttributes;
import javax.servlet.http.HttpServletRequest;
/*
*@ClassName FetchClientIpAspect
*@Author zhouhan
*@Date 2023/6/6 15:43
*/
@Aspect
@Component
@Order(value = 1)
public class FetchClientIpAspect {
@Around("@annotation(fetchClientIp)")
public Object around(ProceedingJoinPoint joinPoint, FetchClientIp fetchClientIp) throws Throwable {
RequestAttributes requestAttributes = RequestContextHolder.getRequestAttributes();
HttpServletRequest httpServletRequest = (HttpServletRequest) requestAttributes.resolveReference(RequestAttributes.REFERENCE_REQUEST);
String ip = NetworkUtil.getip(httpServletRequest);
GlobalHolder.setRealIp(ip);
//调用前处理
Object result = joinPoint.proceed();
//调用后处理
GlobalHolder.removeRealIp();
return result;
}
}