512

How can I determine the IP address of a given request from within a controller? For example (in express):

app.post('/get/ip/address', function (req, res) {
    // need access to IP address here
})
Jonas
  • 121,568
  • 97
  • 310
  • 388
Shamoon
  • 41,293
  • 91
  • 306
  • 570

33 Answers33

628

In your request object there is a property called socket, which is a net.Socket object. The net.Socket object has a property remoteAddress, therefore you should be able to get the IP with this call:

request.socket.remoteAddress

(if your node version is below 13, use the deprecated now request.connection.remoteAddress)

EDIT

As @juand points out in the comments, the correct method to get the remote IP, if the server is behind a proxy, is request.headers['x-forwarded-for']

EDIT 2

When using express with Node.js:

If you set app.set('trust proxy', true), req.ip will return the real IP address even if behind proxy. Check the documentation for further information

SwiftiSwift
  • 7,528
  • 9
  • 56
  • 96
topek
  • 18,609
  • 3
  • 35
  • 43
  • 14
    This gives me an IP address different from what whatismyip.com gives me. Why would that be? – Shamoon Nov 12 '11 at 22:23
  • You mean that you are connecting from localhost? What does it give you? – topek Nov 12 '11 at 22:34
  • 5
    I have my API service installed on a http://no.de instance. When I try to access it from my computer, I get an IP address of "10.2.XXX.YYY" whereas my real world IP is "67.250.AAA.BBB" – Shamoon Nov 12 '11 at 22:36
  • 1
    That means you are behind a proxy. Try to get the `HTTP_X_FORWARDED` header, which should be sent by the proxy, with `req.headers['HTTP_X_FORWARDED']` – topek Nov 12 '11 at 22:48
  • That's bad. Still you may want to investigate the headers, maybe there is another useful one. If this does not help, I would ask the no.de support. – topek Nov 12 '11 at 23:00
  • 8
    it's request.headers['X-Forwarded-For'] – 0x6A75616E Nov 13 '11 at 00:42
  • 5
    Note that net.Stream is now net.Socket, and the documentation lives here: http://nodejs.org/api/net.html#net_class_net_socket – monsur Mar 01 '13 at 05:02
  • 11
    For anyone whose interested, for Heroku it's: `request.headers['x-forwarded-for']` – FueledPublishing Oct 22 '14 at 10:51
  • 1
    @FueledPublishing This is true for all hosts behind a load balancer. Which is pretty much every single Node.js host out there. – Pier-Luc Gendreau Jan 13 '15 at 08:28
  • 2
    is it possible to spoof `request.connection.remoteAddress`, or is this safe to use as guard for accepting IP connections? – knutole Mar 27 '15 at 18:45
  • doesn't seem to work sometimes. I'm getting undefined for some clients (mostly from web crawlers/bots/exploit scanners). why? – ninjaneer May 03 '15 at 22:37
  • Try the "request-ip" module written by @pbojinov ! It takes care of several cases: 'x-client-i, x-cluster-client-ip, x-forwarded,... – Didier68 Sep 11 '18 at 16:40
  • By the standards, request.headers['x-forwarded-for'] should be filled by the proxies in the following format: , , , ... So, *the first one in the list* is the required address. But some proxies do not follow the standards, and then you have to investigate. Some (most of them) add another custom header, containing the client ip. I'd recommend to parse X-Forwarded-For in your app, and analyze custom header afterwards. And only if they didn't give you a *valid* IP, use request.connection.remoteAddress || '127.0.0.1' – Sergei Kovalenko Oct 21 '19 at 19:59
  • Can anyone please update the answer to explain what `"if the server is behind a proxy"` means? Are there any common scenarios that provide an example of a server being behind a proxy? It is maybe, for example, if you have cloudflare enabled on your site? – user1063287 Sep 18 '20 at 09:11
  • To answer my own comment question, in case it helps anyone else, yes using cloudflare is an example of a server being behind a proxy, i found this article was helpful: [What is a Proxy Server and How Does it Work?](https://blogvaronis2.wpengine.com/what-is-a-proxy-server) and also ended up using this SO answer as a solution for getting IP when using a proxy: https://stackoverflow.com/a/45415758 – user1063287 Sep 18 '20 at 10:23
  • i tried this but always get 127.0.0.1 how can we get real ip visitor or user who accessed the application – naufal syarifuddin Dec 02 '20 at 02:49
  • 2
    This answer is now deprecated https://stackoverflow.com/a/65928931/8186898 – Nino Filiu Jan 27 '21 at 23:31
527
var ip = req.headers['x-forwarded-for'] ||
     req.socket.remoteAddress ||
     null;

Note that sometimes you can get more than one IP address in req.headers['x-forwarded-for']. Also, an x-forwarded-for header will not always be set which may throw an error.

The general format of the field is:

x-forwarded-for: client, proxy1, proxy2, proxy3

where the value is a comma+space separated list of IP addresses, the left-most being the original client, and each successive proxy that passed the request adding the IP address where it received the request from. In this example, the request passed through proxy1, proxy2, and then proxy3. proxy3 appears as remote address of the request.

This is the solution suggested by Arnav Gupta with a fix Martin has suggested below in the comments for cases when x-forwarded-for is not set :

var ip = (req.headers['x-forwarded-for'] || '').split(',').pop().trim() || 
         req.socket.remoteAddress

Suggestion using modern JS:

  • processing x-forwarded-for only if set, if so, take the first address
  • other parameters use optional chaining (?.)
const parseIp = (req) =>
    req.headers['x-forwarded-for']?.split(',').shift()
    || req.socket?.remoteAddress

console.log(parseIp(req))
// => 127.0.0.1
Mike
  • 23,542
  • 14
  • 76
  • 87
Edmar Miyake
  • 12,047
  • 3
  • 37
  • 38
  • 21
    How to prevent spoofing of these headers though? – Domi May 27 '14 at 11:21
  • 2
    If you're behind a proxy that sets these headers it will append to the end of the list of addresses. The last one will be set by your proxy, the previous ones may come from previous load balancers or "spoofed" from the client. I imagine you could tell your LB to overwrite the header as well. – reconbot Jul 06 '14 at 22:22
  • 8
    This usually works well but for some reason I recently got the error "Cannot read property 'remoteAddress' of undefined" because apparently everything was null/undefined, including `req.connection.socket`. I'm not sure why/what conditions cause that to be the case but it would be good to check that `req.connection.socket` exists to avoid your server crashing if this happens. – Matt Browne Nov 14 '14 at 20:02
  • 9
    Last line req.connection.socket.remoteAddress throwing error. Be carefully. – yAnTar Dec 18 '14 at 16:57
  • to log precisely it is a good idea to log everything. i could send forwarded for for myself and not use any proxy and you will delete my address, replace with my value. – Shimon Doodkin Feb 12 '15 at 22:21
  • Very noob I am here, but would like to ask, Im very new here, what is `req`? What does that `req` object holds, or how should I initiate req object so that I can use `req.headers` etc. – Sanjay Mar 02 '15 at 05:35
  • 2
    ^ you'll want to learn what the core node web server-related modules are, as well as what express is http://expressjs.com – markthethomas Mar 05 '15 at 00:08
  • To remove the unwanted stuff and just getting the IP address use regular expression. var IP = (req.headers['x-forwarded-for'] || req.connection.remoteAddress).match("[0-9]+.[0-9].+[0-9]+.[0-9]+$")[0]; – Node.JS Jul 07 '15 at 16:28
  • 2
    Heads up: the regexp will only work on IPv4 and should not be used in production. – Niro Oct 23 '15 at 03:15
  • Good answer. Can someone concisely explain, why req.connection.remoteAddress returns something to the tune of :ffff::10.101.214.230 instead of IP? It seems like IPV6 condensed on a priv network IP number. – Jeffz Oct 23 '15 at 20:29
  • My way inspired by you guys! ``var user_ip = false; if (req.headers['x-forwarded-for']) { user_ip = req.headers['x-forwarded-for'].split(', ')[0]; } user_ip = user_ip || req.connection.remoteAddress || req.socket.remoteAddress || req.connection.socket.remoteAddress;`` – Tim Jan 26 '16 at 13:58
  • 25
    The returned ip address is ::1. Why? – Bagusflyer Feb 11 '16 at 03:10
  • 6
    @bagusflyer this is your localhost IP address – Andrei Shostik Jun 26 '16 at 15:49
  • Please tell me why you use this sequence? ``` req.headers['x-forwarded-for'] || req.connection.remoteAddress || req.socket.remoteAddress || req.connection.socket.remoteAddress;``` I don't understand - why is this particular order? – kurumkan Oct 30 '16 at 13:42
  • 1
    Best case scenario is `var ip = req.headers['x-forwarded-for'].split(',').pop() || req.connection.remoteAddress || req.socket.remoteAddress || req.connection.socket.remoteAddress` – Arnav Gupta Jan 05 '17 at 07:34
  • 5
    Looking at the way pop() works, it seems like you are going to get the last proxy and not the client which is what you want. Am I wrong? – Michel Apr 11 '18 at 02:09
  • 2
    I agree @Michel I would use `shift()` – Steve Kehlet Apr 19 '18 at 01:40
  • 2
    Issue: Error occurs when `x-forwarded-for` returns `undefined`. Fix: Add `|| ""` after header reading. So finally: `var ip = (req.headers['x-forwarded-for'] || '').split(',').pop() ... ` – Martin May 16 '18 at 12:29
  • 4
    Surprised no one mentions this one. You need to trim your array results in case `x-forwarded-for` returns multiple ips. Otherwise you get an invalid ip address with a leading whitespace. Do it like `req.headers['x-forwarded-for'] || '').split(',').pop().trim();` or do the split with a comma and space `split(, )` – Kurt Van den Branden Nov 20 '18 at 09:35
  • 5
    That's not right, that'll give you the last proxy before it hit your server, not the client's IP, which is the first ip in the array. `req.headers['x-forwarded-for'] || '').split(',')[0]` is the client's IP – Ruben Serrate Oct 21 '19 at 09:57
  • 1
    @Bagusflyer ```::1``` is the loopback address in IPv6. It is like the IPv6 version of 127.0.0.1. – Anuj Sharma May 05 '21 at 14:38
145

If using express...

req.ip

I was looking this up then I was like wait, I'm using express. Duh.

Byron Whitlock
  • 52,691
  • 28
  • 123
  • 168
King Friday
  • 25,132
  • 12
  • 90
  • 84
  • 2
    Will return a variation of 127.0.0.1 if the server is running behind a proxy. Use [Edmar's answer](https://stackoverflow.com/questions/8107856/how-to-determine-a-users-ip-address-in-node/19524949#19524949) or [set x-real-ip](https://stackoverflow.com/questions/8107856/how-to-determine-a-users-ip-address-in-node/53819302#53819302). – Dan Dascalescu May 29 '20 at 08:07
  • 9
    @DanDascalescu If you set `app.set('trust proxy', true)`, `req.ip` will return the real IP address even if behind proxy. [Check the documentation for further information](http://expressjs.com/en/4x/api.html#req.ip). – Ahmed Tounsi May 10 '21 at 22:46
35

You can stay DRY and just use node-ipware that supports both IPv4 and IPv6.

Install:

npm install ipware

In your app.js or middleware:

var getIP = require('ipware')().get_ip;
app.use(function(req, res, next) {
    var ipInfo = getIP(req);
    console.log(ipInfo);
    // { clientIp: '127.0.0.1', clientIpRoutable: false }
    next();
});

It will make the best attempt to get the user's IP address or returns 127.0.0.1 to indicate that it could not determine the user's IP address. Take a look at the README file for advanced options.

mikemaccana
  • 110,530
  • 99
  • 389
  • 494
Val Neekman
  • 17,692
  • 14
  • 63
  • 66
  • 44
    " or returns 127.0.0.1 to indicate that it could not determine the user's IP address" There is quite a big difference between 127.0.0.1 and unknown... – Nepoxx Mar 13 '15 at 13:15
  • 7
    It returned something weird for me `:ffff:(not my IP address)` when tested from Heroku. @edmar-miyake's answer is working properly for me. – Nilloc Apr 11 '15 at 05:15
  • I wonder what the would IP be if you were to use the right2left lookup in the 'x-forwarded-for' case. var ip_info = get_ip(req, right_most_proxy=True), as in some setup, the client IP might be the right most IP. – Val Neekman Apr 15 '15 at 20:54
  • 4
    That method is returning `clientIp: '::1'` for me. It doesn't seem to work. – JamEngulfer Jan 11 '16 at 11:48
  • @JamEngulfer - ipware only works if the ip address is properly passed down to your app via request.headers[ ]. example: AWS LBS send the Ip address in 'x-forwarded-for' while custom NginX many use other variables. ipware makes the best attempt to figure the IP address out, but only if the IP has been passed down in the headers. – Val Neekman Mar 01 '16 at 16:33
  • Oh. That's a shame. My application was receiving the web traffic directly, so I guess that's not possible. – JamEngulfer Mar 02 '16 at 09:35
  • checking the source code of the package request-ip at https://github.com/pbojinov/request-ip/blob/master/index.js it seems more complete than the package ipware since it checks x-forwarded-for and all sorts of other headers – Giorgio Oct 19 '17 at 11:37
26

You can use request-ip, to retrieve a user's ip address. It handles quite a few of the different edge cases, some of which are mentioned in the other answers.

Disclosure: I created this module

Install:

npm install request-ip

In your app:

var requestIp = require('request-ip');

// inside middleware handler
var ipMiddleware = function(req, res, next) {
    var clientIp = requestIp.getClientIp(req); // on localhost > 127.0.0.1
    next();
};

Hope this helps

pbojinov
  • 907
  • 9
  • 17
  • 4
    checking the source code of the package request-ip at https://github.com/pbojinov/request-ip/blob/master/index.js it checks x-forwarded-for and all sorts of other headers for popular load balancers like AWS ELB, Cloudflare, Akamai, nginx, Rackspace LB and Riverbed's Stingray – Giorgio Oct 19 '17 at 11:39
  • 1
    it returns `null` for me. – S.M_Emamian Jun 18 '19 at 10:00
  • The same thing instead use `request.headers['x-forwarded-for']` – Prathamesh More Jan 24 '20 at 07:35
18

request.headers['x-forwarded-for'] || request.connection.remoteAddress

If the x-forwarded-for header is there then use that, otherwise use the .remoteAddress property.

The x-forwarded-for header is added to requests that pass through load balancers (or other types of proxy) set up for HTTP or HTTPS (it's also possible to add this header to requests when balancing at a TCP level using proxy protocol). This is because the request.connection.remoteAddress the property will contain the private IP address of the load balancer rather than the public IP address of the client. By using an OR statement, in the order above, you check for the existence of an x-forwarded-for header and use it if it exists otherwise use the request.connection.remoteAddress.

Naveen DA
  • 4,148
  • 4
  • 38
  • 57
Ben Davies
  • 607
  • 8
  • 8
17

Following Function has all the cases covered will help

var ip;
if (req.headers['x-forwarded-for']) {
    ip = req.headers['x-forwarded-for'].split(",")[0];
} else if (req.connection && req.connection.remoteAddress) {
    ip = req.connection.remoteAddress;
} else {
    ip = req.ip;
}console.log("client IP is *********************" + ip);
ashishyadaveee11
  • 1,021
  • 15
  • 17
17

I have tried all of them didn't work though,

console.log(clientIp);
console.log(req.ip);

console.log(req.headers['x-forwarded-for']);
console.log(req.connection.remoteAddress);
console.log(req.socket.remoteAddress);
console.log(req.connection.socket.remoteAddress.split(",")[0]);

When running an Express app behind a proxy for me Nginx, you have to set the application variable trust proxy to true. Express offers a few other trust proxy values which you can review in their documentation, but below steps worked for me.

  1. app.set('trust proxy', true) in your Express app.

app.set('trust proxy', true);

  1. Add proxy_set_header X-Forwarded-For $remote_addr in the Nginx configuration for your server block.
  location /  {
                proxy_pass    http://localhost:3001;
                proxy_http_version 1.1;
                proxy_set_header Upgrade $http_upgrade;
                proxy_set_header Connection 'upgrade';
                proxy_set_header Host $host;
                proxy_set_header X-Forwarded-For $remote_addr;  # this line
                proxy_cache_bypass $http_upgrade; 
        }
  1. You can now read off the client’s IP address from the req.header('x-forwarded-for') or req.connection.remoteAddress; Full code for ipfilter
module.exports =  function(req, res, next) {
    let enable = true; // true/false
    let blacklist = ['x.x.x.x'];
    let whitelist = ['x.x.x.x'];
    let clientIp = req.header('x-forwarded-for') || req.connection.remoteAddress;
    if (!clientIp) {
        return res.json('Error');
    }
    if (enable
        && paths.some((path) => (path === req.originalUrl))) {

        let blacklist = blacklist || [];
        if (blacklist.some((ip) => clientIp.match(ip) !== null)) {
            return res.json({ status: 401, error: 'Your IP is black-listed !'});
        }
        let whitelist = whitelist || [];
        if (whitelist.length === 0 || whitelist.some((ip) => clientIp.match(ip) !== null)) {
            next();
            return;
        } else {
            return res.json({ status: 401, error: 'Your IP is not listed !'});
        }
    }
    next();
};
ANIK ISLAM SHOJIB
  • 3,002
  • 1
  • 27
  • 36
  • 3
    Thank you for this! This is ultimately what got me up and running -- the modification to nginx.conf (which nobody else mentioned, oddly). – Netside Oct 25 '20 at 03:27
14

Warning:

Don't just blindly use this for important rate-limiting:

let ip = request.headers['x-forwarded-for'].split(',')[0];

It's very easy to spoof:

curl --header "X-Forwarded-For: 1.2.3.4" "https://example.com"

In that case ther user's real IP address will be:

let ip = request.headers['x-forwarded-for'].split(',')[1];

I'm surprised that no other answers have mentioned this.

Community
  • 1
  • 1
  • 4
    The [top answer](https://stackoverflow.com/questions/8107856/how-to-determine-a-users-ip-address-in-node/19524949#19524949) does handle this by `pop()`ing from the array, which is more general than getting the element at index 1, which can be [fooled](https://stackoverflow.com/a/52286044/1269037) by `curl --header "X-Forwarded-For: 1.2.3.4, 5.6.7.8" "https://example.com"`. – Dan Dascalescu May 29 '20 at 08:06
10

There are two ways to get the ip address :

  1. let ip = req.ip

  2. let ip = req.connection.remoteAddress;

But there is a problem with above approaches.

If you are running your app behind Nginx or any proxy, every single IP addresses will be 127.0.0.1.

So, the best solution to get the ip address of user is :-

let ip = req.header('x-forwarded-for') || req.connection.remoteAddress;
J. Parashar
  • 1,477
  • 2
  • 15
  • 24
Mansi Teharia
  • 1,037
  • 11
  • 11
8

function getCallerIP(request) {
    var ip = request.headers['x-forwarded-for'] ||
        request.connection.remoteAddress ||
        request.socket.remoteAddress ||
        request.connection.socket.remoteAddress;
    ip = ip.split(',')[0];
    ip = ip.split(':').slice(-1); //in case the ip returned in a format: "::ffff:146.xxx.xxx.xxx"
    return ip;
}
Ahmad Agbaryah
  • 487
  • 5
  • 5
  • 1
    You are right, if you want the ip as string, then you can replace the last line with: ip = ip.split(':').slice(-1)[0] – Ahmad Agbaryah Sep 14 '17 at 08:29
  • Code-only answers are discouraged. Can you explain how this answer is better than the older, better explained, and (much) more upvoted [answers](https://stackoverflow.com/questions/8107856/how-to-determine-a-users-ip-address-in-node/19524949#19524949)? – Dan Dascalescu May 29 '20 at 07:55
7

In node 10.14 , behind nginx, you can retrieve the ip by requesting it through nginx header like this:

proxy_set_header X-Real-IP $remote_addr;

Then in your app.js:

app.set('trust proxy', true);

After that, wherever you want it to appear:

var userIp = req.header('X-Real-IP') || req.connection.remoteAddress;
Alexandru
  • 81
  • 1
  • 6
6

If you're using express version 3.x or greater, you can use the trust proxy setting (http://expressjs.com/api.html#trust.proxy.options.table) and it will walk the chain of addresses in the x-forwarded-for header and put the latest ip in the chain that you've not configured as a trusted proxy into the ip property on the req object.

Michael Lang
  • 2,157
  • 3
  • 22
  • 29
5

If you're using express.js then,

app.post('/get/ip/address', function (req, res) {
      res.send(req.ip);
})
Rahul Mane
  • 51
  • 1
  • 1
5

var ipaddress = (req.headers['x-forwarded-for'] || 
req.connection.remoteAddress || 
req.socket.remoteAddress || 
req.connection.socket.remoteAddress).split(",")[0];
Mian Mudassar
  • 61
  • 1
  • 2
4

There were a lot of great points here but nothing that was comprehensive, so here's what I ended up using:

function getIP(req) {
  // req.connection is deprecated
  const conRemoteAddress = req.connection?.remoteAddress
  // req.socket is said to replace req.connection
  const sockRemoteAddress = req.socket?.remoteAddress
  // some platforms use x-real-ip
  const xRealIP = req.headers['x-real-ip']
  // most proxies use x-forwarded-for
  const xForwardedForIP = (() => {
    const xForwardedFor = req.headers['x-forwarded-for']
    if (xForwardedFor) {
      // The x-forwarded-for header can contain a comma-separated list of
      // IP's. Further, some are comma separated with spaces, so whitespace is trimmed.
      const ips = xForwardedFor.split(',').map(ip => ip.trim())
      return ips[0]
    }
  })()
  // prefer x-forwarded-for and fallback to the others
  return xForwardedForIP || xRealIP || sockRemoteAddress || conRemoteAddress
}
Deminetix
  • 2,866
  • 26
  • 21
3

If you get multiple IPs , this works for me:

var ipaddress = (req.headers['x-forwarded-for'] || 
req.connection.remoteAddress || 
req.socket.remoteAddress || 
req.connection.socket.remoteAddress).split(",")[0];
Kirill Chatrov
  • 822
  • 6
  • 11
3

Simple get remote ip in nodejs:

var ip = req.header('x-forwarded-for') || req.connection.remoteAddress;
Dũng IT
  • 2,751
  • 30
  • 29
3

req.connection has been deprecated since node@12.12.0. Using req.connection.remoteAddress to get the client IP might still work but is discouraged.

Luckily, req.socket.remoteAddress has been there since node@0.5.10 and is a perfect replacement:

The string representation of the remote IP address. For example, '74.125.127.100' or '2001:4860:a005::68'. Value may be undefined if the socket is destroyed (for example, if the client disconnected).

Nino Filiu
  • 16,660
  • 11
  • 54
  • 84
2

I realize this has been answered to death, but here's a modern ES6 version I wrote that follows airbnb-base eslint standards.

const getIpAddressFromRequest = (request) => {
  let ipAddr = request.connection.remoteAddress;

  if (request.headers && request.headers['x-forwarded-for']) {
    [ipAddr] = request.headers['x-forwarded-for'].split(',');
  }

  return ipAddr;
};

The X-Forwarded-For header may contain a comma-separated list of proxy IPs. The order is client,proxy1,proxy2,...,proxyN. In the real world, people implement proxies that may supply whatever they want in this header. If you are behind a load balancer or something, you can at least trust the first IP in the list is at least whatever proxy some request came through.

Misha Nasledov
  • 2,003
  • 1
  • 15
  • 18
2

I use this for ipv4 format

req.connection.remoteAddress.split(':').slice(-1)[0]
Cris
  • 2,824
  • 24
  • 23
2

You can Get User Ip with Express Like this

req.ip

For Example In This case we get the user Ip and send it back to the user With req.ip

app.get('/', (req, res)=> { 
    res.send({ ip : req.ip})
    
})
Taha.kh
  • 81
  • 4
  • `req.ip` may also include an IPv4 subnet prefix `::ffff:` - as explained [in this answer](https://stackoverflow.com/a/33790357/1649787). easy to filter out --> `req.ip.toString().replace('::ffff:', '');` – neonwatty Oct 05 '22 at 15:14
2

For me using kubernetes ingress (NGINX):

req.headers['x-original-forwarded-for']

Worked like a charm in Node.js

Nikos445
  • 21
  • 5
1

If you are using Graphql-Yoga you can use the following function:

const getRequestIpAddress = (request) => {
    const requestIpAddress = request.request.headers['X-Forwarded-For'] || request.request.connection.remoteAddress
    if (!requestIpAddress) return null

    const ipv4 = new RegExp("(?:(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.){3}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)")

    const [ipAddress] = requestIpAddress.match(ipv4)

    return ipAddress
}
Arsham Gh
  • 11
  • 1
1

I'm using express behind nginx and

req.headers.origin

did the trick for me

Matan Livne
  • 173
  • 3
  • 6
  • This answer seems off. `req.headers.orgin` returns the IP address the client browser application was pointing to, not the IP of the client itself. – zipzit Dec 28 '21 at 19:56
1

Well, finaly my solution was IT DEPENDS ! For exampe if you have NGINX as a webserver look at you config for example:

server {
    listen 443 ssl;
    server_name <your-domain>;

    ssl_certificate /etc/letsencrypt/live/<your-domain>/fullchain.pem; # managed by Certbot
    ssl_certificate_key /etc/letsencrypt/live/<your-domain>/privkey.pem; # managed by Certbot
    
    location / {
        proxy_pass http://localhost:8000;
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr; # THIS LINE !!!!
    }
}

so the focus is on $remote_addr => x-real-ip

so in nodejs only type req.headers["x-real-ip"]

and thats it !

Talal Zeid
  • 231
  • 1
  • 2
  • 5
0
    const express = require('express')
    const app = express()
    const port = 3000

    app.get('/', (req, res) => {
    var ip = req.ip
    console.log(ip);
    res.send('Hello World!')
    })

   // Run as nodejs ip.js
    app.listen(port, () => {
    console.log(`Example app listening at http://localhost:${port}`)
    })
0

In a shell, you would just curl https://api.ipify.org

So, let's observe this to port it to node.js!

curl is a application to fetch data from websites, we pass the website "https://api.ipify.org" as the argument. We could use node-fetch to replace curl!

The data we get from the website is our IP address, It's some sort of thing which just fetches your IP.

So to sum it up:

const fetch = require('node-fetch');

fetch('https://api.ipify.org')
  .then(response => {/* whatever */})
  .catch(err => {/* whatever */})
0

First, install request-ip in your project

import requestIp from 'request-ip';
const clientIp = requestIp.getClientIp(req); 
console.log(clientIp)

If you work on localhost, the result might come ::1 because ::1 is real IP Address and is IPV6 notation for localhost.

Nick Manning
  • 2,828
  • 1
  • 29
  • 50
0

Using ValidatorJS in Typescript. Here is NodeJS middleware:

// Extract Client IP Address
app.use((req, res, next) => {
    let ipAddress = (req.headers['x-forwarded-for'] as string || '').split(',')[0]
    if (!validator.isIP(ipAddress))
        ipAddress = req.socket.remoteAddress?.toString().split(':').pop() || ''
    if (!validator.isIP(ipAddress))
        return res.status(400).json({errorMessage: 'Bad Request'})

    req.headers['x-forwarded-for'] = ipAddress
    next()
})

Here I am assuming all requests should have a valid IP address and hence return a response with code 400 if there is no valid IP address found.

iamcrypticcoder
  • 2,609
  • 4
  • 27
  • 50
0

If using express

const ip = req.ip?.replace(/^.*:/, '') //->192.168.0.101

or

const ip_raw = req.headers['x-forwarded-for'] ||
     req.socket.remoteAddress ||
     null; //->:ffff:192.168.0.101
const ip = ip_raw?.replace(/^.*:/, '')//->192.168.0.101

note: req.ip?.replace(/^.*:/, '')
            ^             ^
      null secure      regular expressin
    (if ip=!null continue to apply a regular expression)
codeMaster
  • 176
  • 1
  • 4
-1

we can check with this code in node js

const os       = require('os');
const interfaces = os.networkInterfaces();

let addresses = [];

for (var k in interfaces) {

    for (var k2 in interfaces[k]) {

        const address = interfaces[k][k2];

        if ( (address.family === 'IPv4' || address.family === 'IPv6')  && 
            !address.internal) {

            addresses.push(address.address);

        }
    }
}
console.log(addresses);
Monu
  • 27
  • 5
  • 1
    A good answer will always include an explanation why this would solve the issue, so that the OP and any future readers can learn from it. – Tyler2P Dec 25 '21 at 15:21
  • 1
    The OP asked for the IP of the client sending the request. Not the local IP of the application serving the route. – exceptionsAreBad Jun 07 '22 at 17:06
-10

Had the same problem...im also new at javascript but i solved this with req.connection.remoteAddress; that gave me th IP address (but in ipv6 format ::ffff.192.168.0.101 ) and then .slice to remove the 7 first digits.

var ip = req.connection.remoteAddress;

if (ip.length < 15) 
{   
   ip = ip;
}
else
{
   var nyIP = ip.slice(7);
   ip = nyIP;
}
aCo
  • 1
  • this is not a good method, as ipv6 is NOT just 7 digits + IPv4, but can be totally different. – Radek Jan 12 '16 at 12:50
  • @Radek if you validate the start of the address, it conforms to spec(see https://en.wikipedia.org/wiki/IPv6_address ctrl-f search for "IPv4-mapped") `ip= (ip.length<15?ip:(ip.substr(0,7)==='::ffff:'?ip.substr(7):undefined))` would replace the if... in above code – unsynchronized Jul 22 '16 at 01:10
  • i personally wrap getClientIp() from npm request-ip to create `function getClientIp4(req){ var ip=typeof req==='string'?req:getClientIp(req); return (ip.length<15?ip:(ip.substr(0,7)==='::ffff:'?ip.substr(7):undefined)); }` which accepts either a previously fetched ip, or a request object as input and gives ip or undefined as a result – unsynchronized Jul 22 '16 at 01:15