PHP most accurate / safe way to get real user IP address in 2017

You have to collaborate with your sysops team (or if you're wearing that hat too, you will need to do some research). The header check is used when your network infrastructure is configured in certain ways where the remote requester is one of your network appliances instead of the end user.

This sort of thing happens when your web server(s) sit behind a load balancer or firewall or other appliance that needs to interrogate the payload to properly handle it. An example is when a load balancer terminated ssl and forwards the request on to the web server without ssl. When this occurs the remote address becomes the load balancer. It also happens with firewall appliances that do the same thing.

Most instances the device will offer configuration to set a header value in the request with the original remote ip address. The header is usually what you'd expect but it can in some cases be different or even configurable.

What's more, depending on your web server configuration (apache, nginx or other) may not support or be currently configured to support certain custom headers such as the common ip header.

The point is us you will need to investigate your network configuration to ensure that the original requester's ip makes it all the way through to your application code and in what form.


Short answer:

$ip = $_SERVER['REMOTE_ADDR'];


As of 2021 (and still) $_SERVER['REMOTE_ADDR']; is the only reliable way to get users ip address, but it can show erroneous results if behind a proxy server.
All other solutions imply security risks or can be easily faked.


If you'd like to use a pre-built library, you can use Whip.

Using pre-made libraries are usually better because most of them will have been checked thoroughly by an active community. Some of them, especially the ones that have been around for a long time, have more features built-in.

But if you want to code it yourself to learn the concept, then it's ok I guess. I recommend packaging it as a stand alone library and releasing it as open-source :)

EDIT: I do not recommend using the remote IP in security mechanisms as they are not always reliable.


From a security POV, nothing but $_SERVER['REMOTE_ADDR'] is reliable - that's just the simple truth, unfortunately.

All the variables prefixed with HTTP_ are in fact HTTP headers sent by the client, and there there's no other way to transfer that information while requests pass through different servers.
But that of course automatically means that clients can spoof those headers.

You can never, ever trust the client.

Unless it is you ... If you control the proxy or load-balancer, it is possible to configure it so that it drops such headers from the original request.
Then, and only then, you could trust an e.g. X-Client-IP header, but really, there's no need to at that point ... your webserver can also be configured to replace REMOTE_ADDR with that value and the entire process becomes transparent to you.

This will always be the case, no matter which year we are in ... for anything related to security - only trust REMOTE_ADDR.
Best case scenario is to read the HTTP_ data for statistical purposes only, and even then - make sure that the input is at least a valid IP address.