diff --git a/shenyu-plugin/shenyu-plugin-fault-tolerance/shenyu-plugin-ratelimiter/src/main/java/org/apache/shenyu/plugin/ratelimiter/resolver/RemoteAddrKeyResolver.java b/shenyu-plugin/shenyu-plugin-fault-tolerance/shenyu-plugin-ratelimiter/src/main/java/org/apache/shenyu/plugin/ratelimiter/resolver/RemoteAddrKeyResolver.java index c624979d2dcf..a3beba1bb1a9 100644 --- a/shenyu-plugin/shenyu-plugin-fault-tolerance/shenyu-plugin-ratelimiter/src/main/java/org/apache/shenyu/plugin/ratelimiter/resolver/RemoteAddrKeyResolver.java +++ b/shenyu-plugin/shenyu-plugin-fault-tolerance/shenyu-plugin-ratelimiter/src/main/java/org/apache/shenyu/plugin/ratelimiter/resolver/RemoteAddrKeyResolver.java @@ -17,6 +17,7 @@ package org.apache.shenyu.plugin.ratelimiter.resolver; +import org.apache.commons.lang3.StringUtils; import org.apache.shenyu.spi.Join; import org.springframework.web.server.ServerWebExchange; @@ -25,6 +26,10 @@ @Join public class RemoteAddrKeyResolver implements RateLimiterKeyResolver { + private static final String[] HEADERS = {"X-Forwarded-For", "X-Real-IP", "Proxy-Client-IP", "WL-Proxy-Client-IP", "HTTP_CLIENT_IP", "HTTP_X_FORWARDED_FOR"}; + + private static final String UNKNOWN = "unknown"; + @Override public String getKeyResolverName() { return "REMOTE_ADDRESS_KEY_RESOLVER"; @@ -32,6 +37,28 @@ public String getKeyResolverName() { @Override public String resolve(final ServerWebExchange exchange) { + String ip; + for (String header : HEADERS) { + ip = exchange.getRequest().getHeaders().getFirst(header); + boolean isUnknown = StringUtils.isBlank(ip) || UNKNOWN.equalsIgnoreCase(ip); + if (!isUnknown) { + if (StringUtils.indexOf(ip, ',') > 0) { + String[] split = StringUtils.split(ip, ','); + for (int i = 0; i < split.length; i++) { + split[i] = split[i].trim(); + } + for (String subIp : split) { + boolean isUnknownSubIp = StringUtils.isBlank(subIp) || UNKNOWN.equalsIgnoreCase(subIp); + if (!isUnknownSubIp) { + ip = subIp; + break; + } + } + } + return ip; + } + } return Objects.requireNonNull(exchange.getRequest().getRemoteAddress()).getAddress().getHostAddress(); } + }