I'm having some trouble with a simple problem. I would get the real client IP inside an HTTPServlet.
Since now I used:
request.getRemoteAddr()
But now it returns a false IP. eg: xxx.xxx.xxx.50 but my IP is something like xxx.xxx.xxx.159. (checked at http://whatismyipaddress.com/).
Now I tried to use:
request.getHeader("X-Forwarded-For")
It returns NULL.
I also took a probe with the following class:
public class IpUtils {
public static final String _255 = "(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)";
public static final Pattern pattern = Pattern.compile("^(?:" + _255 + "\\.){3}" + _255 + "$");
public static String longToIpV4(long longIp) {
int octet3 = (int) ((longIp >> 24) % 256);
int octet2 = (int) ((longIp >> 16) % 256);
int octet1 = (int) ((longIp >> 8) % 256);
int octet0 = (int) ((longIp) % 256);
return octet3 + "." + octet2 + "." + octet1 + "." + octet0;
}
public static long ipV4ToLong(String ip) {
String[] octets = ip.split("\\.");
return (Long.parseLong(octets[0]) << 24) + (Integer.parseInt(octets[1]) << 16)
+ (Integer.parseInt(octets[2]) << 8) + Integer.parseInt(octets[3]);
}
public static boolean isIPv4Private(String ip) {
long longIp = ipV4ToLong(ip);
return (longIp >= ipV4ToLong("10.0.0.0") && longIp <= ipV4ToLong("10.255.255.255"))
|| (longIp >= ipV4ToLong("172.16.0.0") && longIp <= ipV4ToLong("172.31.255.255"))
|| longIp >= ipV4ToLong("192.168.0.0") && longIp <= ipV4ToLong("192.168.255.255");
}
public static boolean isIPv4Valid(String ip) {
return pattern.matcher(ip).matches();
}
public static String getIpFromRequest(HttpServletRequest request) {
String ip;
boolean found = false;
if ((ip = request.getHeader("x-forwarded-for")) != null) {
StringTokenizer tokenizer = new StringTokenizer(ip, ",");
while (tokenizer.hasMoreTokens()) {
ip = tokenizer.nextToken().trim();
if (isIPv4Valid(ip) && !isIPv4Private(ip)) {
found = true;
break;
}
}
}
if (!found) {
ip = request.getRemoteAddr();
}
return ip;
}
}
It also returned the xxx.xxx.xxx.50 IP. :(
Now I don't know how to get the real client IP. If somebody knows the solution please make an answer.
In Java, you can use HttpServletRequest. getRemoteAddr() to get the client's IP address that's accessing your Java web application.
Methods to get client IP address in a servlet They are as follows: HttpServletRequest. getRemoteAddr(): This method returns the internet address of the client sending the request. HttpServletRequestgetRemoteHost(): This returns the host name of the client sending the request.
How do you find out what client machine is making a request to your servlet ? The ServletRequest class has functions for finding out the IP address or host name of the client machine. getRemoteAddr() gets the IP address of the client machine and getRemoteHost() gets the host name of the client machine.
I suppose that your problem is that you are running server somewhere in local network, so you get your IP in that network. However when you are trying to use online service that discovers your IP address your IP is the IP of your service provider's router or something like this. Using request.getRemoteAddr()
is correct. This is what such services do and they do not have other facilities.
When you have NAT (Network Address Translation) device before your servlet container
request.getRemoteAddr()
returns the address of NAT , since it initiate a new connection.
To solve your problem you should configure you NAT to send in a header the IP of the original client.
Then, to take the header from the request. In case you configure in NAT X-Forwarded-For header use this code: request.getHeader("X-Forwarded-For")
You function is correct, you can use it when you configure NAT.
Java
String ip = request.getRemoteAddr();
if (ip.equalsIgnoreCase("0:0:0:0:0:0:0:1")) {
InetAddress inetAddress = InetAddress.getLocalHost();
String ipAddress = inetAddress.getHostAddress();
ip = ipAddress;
}
model.addAttribute("IP", ip);
JSP <span><B>IP : <c:out value="${IP}" /></B></span> // Spring MAV
JSP
<%@ page language="java" contentType="text/html; charset=ISO-8859-1" pageEncoding="ISO-8859-1"%>
<%@ page import="java.net.InetAddress" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1">
<title>Displays Client IP Address</title>
</head>
<body>
<%
// paste above java code
out.println("<br><B>Clients IP : </B>"+ip);
%>
<span><br>Local Host : <%= request.getRemoteAddr() %></span>
<span><br>ServerPort : <%= request.getServerPort() %></span>
<span><br>Path : <%= request.getRequestURI()%></span>
</span>
</body>
</html>
If the jsp is deployed in local server and accessing this jsp returns 0:0:0:0:0:0:0:1. If accessing the application locally with ip then it returns IP.
RESTful Web Services with Jersey
@javax.ws.rs.Path("/ip")
public class GetIPInfo {
@GET @Produces(MediaType.TEXT_PLAIN)
public Response getIP(@Context javax.servlet.http.HttpServletRequest request) throws UnknownHostException {
String remoteHost = request.getRemoteHost();
String remoteAddr = request.getRemoteAddr();
if (remoteAddr.equals("0:0:0:0:0:0:0:1")) {
InetAddress localip = java.net.InetAddress.getLocalHost();
remoteAddr = localip.getHostAddress();
remoteHost = localip.getHostName();
}
int remotePort = request.getRemotePort();
String msgoutput = remoteHost + " (" + remoteAddr + " : " + remotePort + ")";
return Response.status(200).entity(msgoutput).build();
}
}
using JavaScript to find IP
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With