If I check with google, I can see my public IP. Is there something on the Ubuntu command-line which will yield me the same answer?
22 Answers
If you are not behind a router, you can find it out using ifconfig
.
If you are behind a router, then your computer will not know about the public IP address as the router does a network address translation. You could ask some website what your public IP address is using curl
or wget
and extract the information you need from it:
curl -s https://checkip.dyndns.org | sed -e 's/.*Current IP Address: //' -e 's/<.*$//'
or shorter
curl https://ipinfo.io/ip
-
31ty - right after I posted, I realized that I didn't google for an answer first: looks like this will work
curl -s checkip.dyndns.org|sed -e 's/.*Current IP Address: //' -e 's/<.*$//'
Other possibilities are listed here: go2linux.org/what-is-my-public-ip-address-with-linux– kfmfe04Jan 16, 2012 at 12:01 -
1
-
1To clarify: That was a hack, and a very ugly one at that, so I did an edit to make it simpler and something that people can remember.– jrgJan 16, 2012 at 16:17
-
2Exacly as Giovanni P stated. The OP should change the accepted anwser.– loostroApr 11, 2014 at 21:45
-
49
For finding the external ip, you can either use external web-based services, or use system based methods. The easier one is to use the external service, also the ifconfig
based solutions will work in your system only if you're not behind a NAT
. the two methods has been discussed below in detail.
Finding external IP using external services
The easiest way is to use an external service via a commandline browser or download tool. Since wget
is available by default in Ubuntu, we can use that.
To find your ip, use-
$ wget -qO- https://ipecho.net/plain ; echo
Courtesy:
- https://hawknotes.blogspot.in/2010/06/finding-your-external-ip-address.html
- https://ipecho.net/plain
You could also use lynx
(browser) or curl
in place of wget
with minor variations to the above command, to find your external ip.
Using curl
to find the ip:
$ curl https://ipecho.net/plain
For a better formatted output use:
$ curl https://ipecho.net/plain ; echo
A faster (arguably the fastest) method using dig
with OpenDNS
as resolver:
The other answers here all go over HTTP to a remote server. Some of them require parsing of the output, or rely on the User-Agent header to make the server respond in plain text. They also change quite frequently (go down, change their name, put up ads, might change output format etc.).
- The DNS response protocol is standardised (the format will stay compatible).
- Historically DNS services (OpenDNS, Google Public DNS, ..) tend to survive much longer and are more stable, scalable and generally looked after than whatever new hip whatismyip.com HTTP service is hot today.
- (for those geeks that care about micro-optimisation), this method should be inherently faster (be it only by a few micro seconds).
Using dig with OpenDNS as resolver:
$ dig +short myip.opendns.com @resolver1.opendns.com
111.222.333.444
Copied from: https://unix.stackexchange.com/a/81699/14497
Finding external IP without relying on external services
- If you know your network interface name
Type the following in your terminal:
$ LANG=c ifconfig <interface_name> | grep "inet addr" | awk -F: '{print $2}' | awk '{print $1}'
In the above, replace <interface_name>
with the name of your actual interface, e.g: eth0
, eth1
, pp0
, etc...
Example Usage:
$ LANG=c ifconfig ppp0 | grep "inet addr" | awk -F: '{print $2}' | awk '{print $1}'
111.222.333.444
- If you don't know your network interface name
Type the following in your terminal (this gets the name and ip address of every network interface in your system):
$ LANG=c ifconfig | grep -B1 "inet addr" |awk '{ if ( $1 == "inet" ) { print $2 } else if ( $2 == "Link" ) { printf "%s:" ,$1 } }' |awk -F: '{ print $1 ": " $3 }'
Example Usage:
$ LANG=c ifconfig | grep -B1 "inet addr" |awk '{ if ( $1 == "inet" ) { print $2 } else if ( $2 == "Link" ) { printf "%s:" ,$1 } }' |awk -F: '{ print $1 ": " $3 }'
lo: 127.0.0.1
ppp0: 111.222.333.444
N.B: Outputs are indicative and not real.
Courtesy: https://www.if-not-true-then-false.com/2010/linux-get-ip-address/
UPDATE
LANG=c
has been added toifconfig
based usages, so that it always gives the english output, irrespective of locale setting.
-
1@Z9iT, Sure.. It should work in any linux distribution provided that you have wget installed. As said if you have either curl or lynx already available please use that instead. You would need root permission to install so use
sudo apt-get install wget
– saji89Jun 1, 2012 at 12:19 -
16The commands with ifconfig do only work, if you are not behind a NAT. Jan 23, 2013 at 15:52
-
3
-
3This proposal using dig is pretty nice unix.stackexchange.com/questions/22615/… Mar 14, 2015 at 15:31
-
6The last version without external services only works, if your computer is connected directly to the internet which is rarely the case, otherwise you only get your local IP address.– rubo77Oct 5, 2015 at 2:42
My favorite has always been :
curl ifconfig.me
simple, easy to type.
You will have to install curl first ;)
If ifconfig.me is down try icanhazip.com and or ipecho.net
curl icanhazip.com
or
curl ipecho.net
-
3@Z9iT, I just checked this now. Yes, it would output the external ip in your terminal.– saji89Jun 1, 2012 at 13:13
-
7The response time from
ifconfig.me
seems quite a bit slower thanipecho.net
. Oct 25, 2013 at 14:57 -
3If you don't have
curl
but havewget
:wget -U curl -qO- ifconfig.me
Aug 14, 2014 at 20:16 -
2
-
1@AsfandYarQazi - working here. You can try one of the alternates , icanhazip.com– PantherJan 20, 2016 at 12:48
icanhazip.com is my favorite.
curl icanhazip.com
You can request IPv4 explicitly:
curl ipv4.icanhazip.com
If you don't have curl
you can use wget
instead:
wget -qO- icanhazip.com
-
Thanks! I had to try many suggested above until I found some that is IPv6-capable. It's a shame that such services are usually still IPv4-only. Feb 24, 2019 at 17:20
-
This seems to be a good choice, it is run by CloudFlare now: major.io/2021/06/06/a-new-future-for-icanhazip Apr 16, 2022 at 19:08
Running my own service, designed to be simple and stupid, ident.me.
Its API and implementation are documented at https://api.ident.me/
Examples from the terminal (add https://
for security at the expense of speed):
curl ident.me
curl v4.ident.me
curl v6.ident.me
-
1
-
1I find the icanhazip.com solution faster and it includes a newline in the output. Aug 19, 2014 at 0:00
-
1
-
3Kudos! 2 years and you are still maintaining it. Well done. "IDENTify ME", is what comes to my mind, when I need ip check :)– MohnishSep 28, 2015 at 1:37
-
2aws is faster
time curl http://checkip.amazonaws.com
->0.91s
vs.241s
forident.me
Let's just pray aws doesnt go down ;) Apr 12, 2018 at 1:41
You could use a DNS request instead of HTTP request to find out your public IP:
$ dig +short myip.opendns.com @resolver1.opendns.com
It uses resolver1.opendns.com
dns server to resolve the magical myip.opendns.com
hostname to your ip address.
-
3This is really fast. I did one warmup execution, then 10 executions each of this and
curl icanhazip.com
. Average for thecurl
version: 174ms. Average for the DNS-only version: 9ms. ~19x faster. See also: unix.stackexchange.com/a/81699/8383 Mar 10, 2015 at 21:06 -
1@AdamMonsen Thank you for the link. The point of using DNS (as the answer that you've linked says) is that the response is standard (and unlikely to change) and the service (OpenDNS) might stick around longer than most of its http alternatives. The time it takes to make the request might be shadowed by the command start up time.– jfsMar 11, 2015 at 0:40
-
1Yep. I wouldn't be surprised if
curl
itself is slower thandig
. Even if they were rewritten to be as similar as possible,curl
would still be slower; it uses HTTP (including DNS) anddig
only uses DNS. Mar 11, 2015 at 4:16
Amazon AWS
curl https://checkip.amazonaws.com
Sample output:
123.123.123.123
Also works on browser: http://checkip.amazonaws.com
I like it because:
- it returns just the plaintext IP in the reply body, nothing else
- it is from a well known provider which is unlikely to go offline anytime soon
-
1Was looking for solution with some known name, thank you Nov 10, 2019 at 2:41
The one i'm using is :
wget -O - -q icanhazip.com
Yes, you can have ip :-)
-
3I prefer
curl icanhazip.com
sometimeswget
is the only one available, but sometimes nowget
is available as well andcurl
is your only option (like OS/X). Either waycurl icanhazip.com
is almost as easy ascurl ifconfig.me
but much funnier ;-) Aug 25, 2012 at 20:38
For this, STUN was invented. As a client you can send a request to a publicly available STUN server and have it give back the IP address it sees. Sort of the low level whatismyip.com as it uses no HTTP and no smartly crafted DNS servers but the blazingly fast STUN protocol.
Using stunclient
If you have stunclient
installed (apt-get install stuntman-client
on debian/ubuntu) you can simply do:
$stunclient stun.services.mozilla.com
Binding test: success
Local address: A.B.C.D:42541
Mapped address: W.X.Y.Z:42541
where A.B.C.D
is the IP address of your machine on the local net and W.X.Y.Z
is the IP address servers like websites see from the outside (and the one you are looking for). Using sed
you can reduce the output above to only an IP address:
stunclient stun.services.mozilla.com |
sed -n -e "s/^Mapped address: \(.*\):.*$/\1/p"
However, your question was how to find it using the command line, which might exclude using a STUN client. So I wonder...
Using bash
A STUN request can be handcrafted, sent to an external STUN server using netcat
and be post-processed using dd
, hexdump
and sed
like so:
$echo -en '\x00\x01\x00\x08\xc0\x0c\xee\x42\x7c\x20\x25\xa3\x3f\x0f\xa1\x7f\xfd\x7f\x00\x00\x00\x03\x00\x04\x00\x00\x00\x00' |
nc -u -w 2 stun.services.mozilla.com 3478 |
dd bs=1 count=4 skip=28 2>/dev/null |
hexdump -e '1/1 "%u."' |
sed 's/\.$/\n/'
The echo defines a binary STUN request (0x0001 indicates Binding Request) having length 8 (0x0008) with cookie 0xc00cee and some pasted stuff from wireshark. Only the four bytes representing the external IP are taken from the answer, cleaned and printed.
Working, but not recommended for production use :-)
P.S. Many STUN servers are available as it is a core technology for SIP and WebRTC. Using one from Mozilla should be safe privacy-wise but you could also use another: STUN server list
-
2+1 for the geekiest and actually most apropos technology. The http query works, which is what I've been using all my life, but I like that there's actually been some thought put into the question. I didn't know this. Thanks!– Mike SOct 18, 2016 at 17:47
-
1
-
1
-
Type in this exactly, press Enter where indicated:
telnet ipecho.net 80
Enter
GET /plain HTTP/1.1
Enter
HOST: ipecho.net
Enter
BROWSER: web-kit
Enter
Enter
This manually submits a HTTP request, which will return your IP at the bottom of a HTTP/1.1 200 OK reply
Example output:
$ telnet ipecho.net 80
Trying 146.255.36.1...
Connected to ipecho.net.
Escape character is '^]'.
GET /plain HTTP/1.1
HOST: ipecho.net
BROWSER: web-kit
HTTP/1.1 200 OK
Date: Tue, 02 Jul 2013 07:11:42 GMT
Server: Apache
Expires: Mon, 26 Jul 1997 05:00:00 GMT
Cache-Control: no-cache
Pragma: no-cache
Vary: Accept-Encoding
Transfer-Encoding: chunked
Content-Type: text/html
f
111.222.333.444
0
-
6Nice, this worked well, not having to install curl was an advantage for me: one liner: printf "GET /plain HTTP/1.1\nHOST: ipecho.net\nBROWSER: web-kit\n\n" | nc ipecho.net 80– OzoneMar 19, 2014 at 5:32
You can read a web page using only bash, without curl
, wget
:
$ exec 3<> /dev/tcp/icanhazip.com/80 && # open connection
echo 'GET /' >&3 && # send http 0.9 request
read -u 3 && echo $REPLY && # read response
exec 3>&- # close fd
-
This combined with
checkip.amazonaws.com
is the fastest for me Apr 12, 2018 at 1:44 -
1
-
This answer is poetry to me. So elegant, and so cool to do it only using
bash
. Bravo and +1 Apr 22 at 19:48
I have a stupid service for this by telnet. Something like this:
telnet myip.gelma.net
Your IPv4: xxx.xxx.xxx.xxx
Your IPv6: ::ffff:xxxx:xxxx
Feel free to use it.
-
It prints:
Trying 2600:3c03::f03c:91ff:fe96:cc28...
andtelnet: Unable to connect to remote host: Network is unreachable
Jul 23, 2021 at 17:56 -
Unreachable here too -- it appears gelma.net may no longer be offering this service in 2022 (or may be using a different method now) Aug 11, 2022 at 13:45
These will get the local IPs:
ifconfig
or for shorter output:
ifconfig | grep inet
also
ip addr show
and probably:
hostname -I
This should get the external IP
wget http://smart-ip.net/myip -O - -q ; echo
N.B. If you don't mind to installing curl
, this as well:
curl http://smart-ip.net/myip
-
1
ifconfig | sed -nre '/^[^ ]+/{N;s/^([^ ]+).*addr: *([^ ]+).*/\1,\2/p}'
will print the local interfaces and corresponding V4 IP's– HannuJun 27, 2014 at 18:09 -
1
ifconfig | sed -nre '/^[^ ]+/{N;N;s/^([^ ]+).*addr: *([^ ]+).*addr: *([^ ]+).*/\1,\2,\3/p}'
- v4 and v6 IPs.– HannuJun 27, 2014 at 18:15
For those of us with login access to our routers, using a script to ask the router what its' WAN IP address is is the most efficient way to determine the external IP address. For instance the following python script prints out the external IP for my Medialink MWN-WAPR300N router:
import urllib, urllib2, cookielib
import re
from subprocess import check_output as co
cookie_jar = cookielib.CookieJar()
opener = urllib2.build_opener(urllib2.HTTPCookieProcessor(cookie_jar))
urllib2.install_opener(opener)
def get(url, values=None):
data = None
if values: data = urllib.urlencode(values)
req = urllib2.Request(url, data)
rsp = urllib2.urlopen(req)
return rsp.read()
router = co(['ip', '-o', 'ro', 'list', '0.0.0.0/0']).split()[2]
url = "http://" + router
get(url+"/index.asp")
get(url+"/LoginCheck", dict(checkEn='0', Username='admin', Password='admin'))
page = get(url+"/system_status.asp")
for line in page.split("\n"):
if line.startswith("wanIP = "):
print line.split('"')[1]
exit(1)
Note that this is not very secure (as is the case with plaintext credentials & logging in to most routers), and is certainly not portable (needs to be changed for each router). It is however very fast and a perfectly reasonable solution on a physically secure home network.
To customize the script for another router, I recommend using the tamperdata addon in firefox to determine what HTTP requests to make.
-
2You should try getting the IP address of the router grammatically. For example
router = subprocess.check_output(['ip', '-o', 'ro', 'list', '0.0.0.0/0']).split()[2]
. Jun 2, 2014 at 2:26
Many home routers can be queried by UPnP:
curl "http://fritz.box:49000/igdupnp/control/WANIPConn1" -H "Content-Type: text/xml; charset="utf-8"" -H "SoapAction:urn:schemas-upnp-org:service:WANIPConnection:1#GetExternalIPAddress" -d "<?xml version='1.0' encoding='utf-8'?> <s:Envelope s:encodingStyle='http://schemas.xmlsoap.org/soap/encoding/' xmlns:s='http://schemas.xmlsoap.org/soap/envelope/'> <s:Body> <u:GetExternalIPAddress xmlns:u='urn:schemas-upnp-org:service:WANIPConnection:1' /> </s:Body> </s:Envelope>" -s
Then, grep the ip address from the answer.
grep -Eo '\<[[:digit:]]{1,3}(\.[[:digit:]]{1,3}){3}\>'
If you are using DD-WRT then this works for me:
curl -s 192.168.1.1 | grep "ipinfo" | awk -v FS="(IP: |</span)" '{print $2}'
or
curl -s -u your_ddwrt_username:your_ddwrt_password http://192.168.1.1 | grep "ipinfo" | awk -v FS="(IP: |</span)" '{print $2}'
Where 192.168.1.1 is the Gateway/Router LAN IP Address of the DD-WRT router.
The -s component means silent (i.e. don't show the curl progress information).
- Oh, I should mention that I use the above with "DD-WRT v24-sp2 (01/04/15) std".
If you have installed lynx in Ubuntu type
lynx bot.whatismyipaddress.com
use ip
!
ip addr show
then look for the relevant adapter (not lo
, and usually eth0
), and locate the ip address near inet
.
-
3
-
1this works on our company servers -- if you do: ip addr show | grep inet (grep not absolutely required but better for output) you will get all ip addresses, local and external (including inet 6 protocol) - our servers are using CENTOS if your server does not somehow have the ip command. Similar output to: ifconfig | grep inet Aug 11, 2022 at 13:48
Maybe I am a little late, but inxi can do it fairly easy.
Install inxi
sudo apt install inxi
Then run the following command
inxi -i
Example with my information blocked out using the z
option for copy and paste to sites like this:
~$ inxi -iz
Network: Card: NVIDIA MCP77 Ethernet driver: forcedeth
IF: eth0 state: up speed: 1000 Mbps duplex: full mac: <filter>
WAN IP: <filter>
IF: eth0 ip-v4: <filter> ip-v6-link: N/A
Where it says <filter>
is where your WAN IP, IPv4, MAC address etc will appear
-
Although not the fastest, it is the prettiest with color output. Jul 23, 2021 at 18:01
-
-
@FrameGrace So, what's your point? Most of these answers here are using external ways to get your Public IP. If I really wanted to use 100% local my command with my OpenWRT router is
ssh [email protected] 'ip addr show pppoe-wan' | awk '/inet/ {print $2}'
, but my command won't work for everyone else here.– TerranceAug 26, 2021 at 13:06
Simply issue a traceroute for any website or service..
sudo traceroute -I google.com
Line 2 always seems to be my public IP address after it gets past my router gateway.
user@user-PC ~ $ sudo traceroute -I google.com
traceroute to google.com (173.194.46.104), 30 hops max, 60 byte packets
1 25.0.8.1 (25.0.8.1) 230.739 ms 231.416 ms 237.819 ms
2 199.21.149.1 (199.21.149.1) 249.136 ms 250.754 ms 253.994 ms**
So, make a bash command.
sudo traceroute -I google.com | awk -F '[ ]' '{ if ( $2 ="2" ) { print $5 } }'
And the output...
(199.21.149.1)
I don't think relying on PHP scripts and the sort is good practice.
-
this is interesting, though really slow and doesn't get my external ip like this– rubo77Oct 5, 2015 at 2:46
-
1This answer is too inaccurate to be useful. In my corporate environment I don't get my IP address at all. The only way it works is if you understand how your local routers and switches are crafted, and even then it may not be on line 2 depending on the number of local hops you jump through. There's no way to make a coherent algorithm out of this technique, and there are many other solutions here that are simpler and will get you the proper answer every time.– Mike SOct 18, 2016 at 17:52
-
While it may work in some special configurations, I have actually never seen my external IP in a traceroute. It is usually either my gateway (if I am not behind NAT), or my router's gateway, but mostly some other router further away.– mivkFeb 14, 2017 at 11:52
-
A command with no dependencies except 8.8.8.8 being a GOogle DNS:
echo $(ip route get 8.8.8.8 | awk '{print $NF; exit}')
-
This only tells you the IP-address of your local outgoing interface.– guntbertSep 17, 2015 at 16:15
-
the command does show the public ip address if I run it on a cloud server. wasn;t that the question?– RolfSep 17, 2015 at 20:48
-
-
I am using a CENTOS server hosted by a remote company, and this works just fine on the command line. Aug 11, 2022 at 13:56
notify-send
.ifconfig eth1 | sed -nre '/^[^ ]+/{N;s/^([^ ]+).*inet *([^ ]+).*/\2/p}'
where eth1 is the network device o interest, you can omit the 'et1' string to show all ips of all adapters. Instead of\2
you can write\1 \2
to show the names of each adapter too.