如何从Java的HTTP头中检索IP地址
我很好奇,如果有任何图书馆已经处理了这种东西,或者我必须再次自己做。 所以,我想从我的服务器上的访问者HTTP头请求中获取IP地址字段,并在Java中完成整个事情? 任何帮助将是很好的。 提前致谢。
使用javax.servlet.http.HttpServletRequest
对象的getHeader(String Name)
方法来检索Remote_Addr
variables的值。 这里是示例代码:
String ipAddress = request.getHeader("Remote_Addr");
如果此代码返回空string,则使用这种方式:
String ipAddress = request.getHeader("HTTP_X_FORWARDED_FOR"); if (ipAddress == null) { ipAddress = request.getRemoteAddr(); }
即使有一个被接受的答案已经被高度赞成,我想提出一个替代scheme,并指出接受答案的缺点。
指定 request.getHeader("Remote_Addr")
与request.getRemoteAddr()
完全相同。 因此,检查两者是没有意义的。 另请注意, getRemoteAddr
是javax.servlet.ServletRequest
(即HTTP不可知)的一个方法,而getHeader
位于javax.servlet.http.HttpServletRequest
。
此外,一些代理使用Client-IP
而不是X-Forwarded-For
。 有关讨论,请参阅https://stackoverflow.com/a/7446010/131929 。
我不知道X-Forwarded-For
使用HTTP_X_FORWARDED_FOR
有多可靠。 在Java中,我宁愿使用直接,简短的forms。 有关讨论,请参阅https://stackoverflow.com/a/3834169/131929 。 大小写没有区别,因为getHeader
被指定为敏感的情况。
Java替代
public final class ClientIpAddress { // CHECKSTYLE:OFF // https://stackoverflow.com/a/11327345/131929 private static Pattern PRIVATE_ADDRESS_PATTERN = Pattern.compile( "(^127\\.)|(^192\\.168\\.)|(^10\\.)|(^172\\.1[6-9]\\.)|(^172\\.2[0-9]\\.)|(^172\\.3[0-1]\\.)|(^::1$)|(^[fF][cCdD])", Pattern.CANON_EQ); // CHECKSTYLE:ON private ClientIpAddress() { } /** * Extracts the "real" client IP address from the request. It analyzes request headers * {@code REMOTE_ADDR}, {@code X-Forwarded-For} as well as {@code Client-IP}. Optionally * private/local addresses can be filtered in which case an empty string is returned. * * @param request HTTP request * @param filterPrivateAddresses true if private/local addresses (see * https://en.wikipedia.org/wiki/Private_network#Private_IPv4_address_spaces and * https://en.wikipedia.org/wiki/Unique_local_address) should be filtered ie omitted * @return IP address or empty string */ public static String getFrom(HttpServletRequest request, boolean filterPrivateAddresses) { String ip = request.getRemoteAddr(); String headerClientIp = request.getHeader("Client-IP"); String headerXForwardedFor = request.getHeader("X-Forwarded-For"); if (StringUtils.isEmpty(ip) && StringUtils.isNotEmpty(headerClientIp)) { ip = headerClientIp; } else if (StringUtils.isNotEmpty(headerXForwardedFor)) { ip = headerXForwardedFor; } if (filterPrivateAddresses && isPrivateOrLocalAddress(ip)) { return StringUtils.EMPTY; } else { return ip; } } private static boolean isPrivateOrLocalAddress(String address) { Matcher regexMatcher = PRIVATE_ADDRESS_PATTERN.matcher(address); return regexMatcher.matches(); } }
PHP的替代品
function getIp() { $ip = $_SERVER['REMOTE_ADDR']; if (empty($ip) && !empty($_SERVER['HTTP_CLIENT_IP'])) { $ip = $_SERVER['HTTP_CLIENT_IP']; } elseif (!empty($_SERVER['HTTP_X_FORWARDED_FOR'])) { // omit private IP addresses which a proxy forwarded $tmpIp = $_SERVER['HTTP_X_FORWARDED_FOR']; $tmpIp = filter_var( $tmpIp, FILTER_VALIDATE_IP, FILTER_FLAG_IPV4 | FILTER_FLAG_NO_PRIV_RANGE | FILTER_FLAG_NO_RES_RANGE ); if ($tmpIp != false) { $ip = $tmpIp; } } return $ip; }