Linux Bash脚本提取IP地址



我想在我的debian 7.3上制作大脚本(类似于翻译和更多新的用户友好型环境)。我有个问题。我只想使用命令提供的一些信息。例如,我的ifconfig看起来像:

eth0      Link encap:Ethernet  HWaddr 08:00:27:a3:e3:b0  
          inet addr:192.168.1.103  Bcast:192.168.1.255  Mask:255.255.255.0
          inet6 addr: fe80::a00:27ff:fea3:e3b0/64 Scope:Link
          UP BROADCAST RUNNING MULTICAST  MTU:1500  Metric:1
          RX packets:1904 errors:0 dropped:0 overruns:0 frame:0
          TX packets:2002 errors:0 dropped:0 overruns:0 carrier:0
          collisions:0 txqueuelen:1000 
          RX bytes:1309425 (1.2 MiB)  T

我只想在行中显示IP地址:ECHO"您的IP地址为:(IP_ADDRESS)"。是否有任何命令可以让我做这样的事情,可以在流中搜索我想获得的信息?我知道grepsed,但我对它们并不好。

编辑:首先要感谢您帮助我解决这个问题,现在我知道了更多。其次说项目正在进行中。如果有人对此感兴趣,只是我。

如果目标是在Internet方向上找到IP地址,则应该是一个很好的解决方案。<<<<<<<<

编辑2021:添加" sed"one_answers" grep"版本和新的"尴尬"版本(有些是GNU)


要查找连接到Internet的IP添加剂的内容,我们可以使用ip route命令。借助Linux的较新版本,您可以通过典型输出获得更多信息:

ip route get 8.8.8.8
8.8.8.8 via 10.36.15.1 dev ens160 src 10.36.15.150 uid 1002
    cache

因此,要获得 ip 您需要在 src 之后找到IPstrong> grep

ip route get 8.8.8.8 | awk -F"src " 'NR==1{split($2,a," ");print a[1]}'
ip route get 8.8.8.8 | awk 'match($0,/src (S*)/,a)&&$0=a[1]'
ip route get 8.8.8.8 | awk '{for(i=1;i<=NF;i++)if($i~/src/)$0=$(i+1)}NR==1'
ip route get 8.8.8.8 | sed -E 's/.*src (S+) .*/1/;t;d'
ip route get 8.8.8.8 | sed 's/.*src ([^ ]*).*/1/;t;d'
ip route get 8.8.8.8 | sed  -nE '1{s/.*?src (S+) .*/1/;p}'
ip route get 8.8.8.8 | grep -oP 'src K[^ ]+'
10.36.15.150

,如果您喜欢接口使用 awk 的名称, SED GREP

ip route get 8.8.8.8 | awk -F"dev " 'NR==1{split($2,a," ");print a[1]}'
ip route get 8.8.8.8 | awk 'match($0,/dev (S*)/,a)&&$0=a[1]'
ip route get 8.8.8.8 | awk '{for(i=1;i<=NF;i++)if($i~/dev/)$0=$(i+1)}NR==1'
ip route get 8.8.8.8 | sed -E 's/.*?dev (S+) .*/1/;t;d'
ip route get 8.8.8.8 | sed 's/.*dev ([^ ]*).*/1/;t;d'
ip route get 8.8.8.8 | sed  -nE '1{s/.*?dev (S+) .*/1/;p}'
ip route get 8.8.8.8 | grep -oP 'dev K[^ ]+'
ens192

ip route不会打开任何连接,它只是显示了到达8.8.8.8所需的路由。8.8.8.8是Google的DNS。

如果您想将其存储到变量中,请:

my_ip=$(ip route get 8.8.8.8 | awk -F"src " 'NR==1{split($2,a," ");print a[1]}')
my_interface=$(ip route get 8.8.8.8 | awk -F"dev " 'NR==1{split($2,a," ");print a[1]}')

为什么其他解决方案可能会失败:

ifconfig eth0

  • 如果您的界面有另一个名称(eno1,wifi,venet0等)
  • 如果您有多个接口
  • IP连接方向不是
  • 的多个列表中的第一个

Hostname -I

  • 可能只能获得127.0.1.1
  • 不适用于所有系统。
  • 不仅给所有连接到Internet的IP。-i, - all-ip-addresses主机的所有地址

只获取您的IP地址:

echo `ifconfig eth0 2>/dev/null|awk '/inet addr:/ {print $2}'|sed 's/addr://'`

这将为您提供ETH0的IP地址。

编辑:由于Ubuntu最新版本中的接口的名称更改,因此不再起作用。相反,您可以使用以下方式:

hostname --all-ip-addresseshostname -I,它可以执行相同的操作(给您主机的所有IP地址)。

如果要使空间分开IPS列表,您可以使用hostname命令与--all-ip-addresses(短-I)flag

hostname -I

如下所述:将IP地址放入BASH变量中。有更好的方法吗?

ip -4 addr show eth0 | grep -oP "(?<=inet ).*(?=/)"

可能并非所有情况(尤其是如果您有几个情况NIC),这将有所帮助:

hostname -I | awk '{ print $1 }'
ip route get 8.8.8.8| grep src| sed 's/.*src (.* )/1/g'|cut -f1 -d ' '

选择您的选择:

$ cat file
eth0      Link encap:Ethernet  HWaddr 08:00:27:a3:e3:b0
          inet addr:192.168.1.103  Bcast:192.168.1.255  Mask:255.255.255.0
          inet6 addr: fe80::a00:27ff:fea3:e3b0/64 Scope:Link
          UP BROADCAST RUNNING MULTICAST  MTU:1500  Metric:1
          RX packets:1904 errors:0 dropped:0 overruns:0 frame:0
          TX packets:2002 errors:0 dropped:0 overruns:0 carrier:0
          collisions:0 txqueuelen:1000
          RX bytes:1309425 (1.2 MiB)  T
$ awk 'sub(/inet addr:/,""){print $1}' file
192.168.1.103
$ awk -F'[ :]+' '/inet addr/{print $4}' file
192.168.1.103
  /sbin/ifconfig eth0 | grep 'inet addr:' | cut -d: -f2 | awk '{ print $1}'

在我看来,实现您需要的最简单,最优雅的方法是:

ip route get 8.8.8.8 | tr -s ' ' | cut -d' ' -f7

ip route get [host]-给您用于到达远程主机的网关,例如:

8.8.8.8 via 192.168.0.1 dev enp0s3  src 192.168.0.109

tr -s ' '-删除任何额外的空间,现在您有均匀性,例如:

8.8.8.8 via 192.168.0.1 dev enp0s3 src 192.168.0.109

cut -d' ' -f7-将字符串截断为"空间分离的字段,然后从中选择7个字段,例如:

192.168.0.109

只是一个注释,因为我只是花了一些时间在服务器上删除了botched升级。事实证明,(几年前)我已经实施了一项测试,以查看是否存在动态添加的接口(例如ETH0:1),如果是这样,我将把某些proggis绑定到ETH0上的" Main" IP。基本上,这是" ifconfig | grep ... | sed ..."解决方案的变体(加上'eth0:'存在)。
升级带来了新的净工具,随之而来的输出略有变化:

旧的ifconfig:

eth0      Link encap:Ethernet  HWaddr 42:01:0A:F0:B0:1D
          inet addr:10.240.176.29  Bcast:10.240.176.29  Mask:255.255.255.255
          UP BROADCAST RUNNING MULTICAST  MTU:1460  Metric:1
          ...<SNIP>

新版本将显示以下内容:

eth0: flags=4163<UP,BROADCAST,RUNNING,MULTICAST>  mtu 1460
      inet 10.240.212.165  netmask 255.255.255.255  broadcast 10.240.212.165
      ...<SNIP>

捕捉" eth0:'"的狩猎以及" inet addr:'搜索破裂(不介意称为'em0','br0'或'wlan0'的接口界面...)。当然,您可以检查" INET"(或" Inet6"),并使ADDR:零件可选,但是近距离观察,您会发现所有内容或多或少都改变了,'mask'现在是" NetMask",..。

" IP路线..."建议很漂亮 - 所以也许:

_MyIP="$( ip route get 8.8.8.8 | awk 'NR==1 {print $NF}' )"
if [ "A$_MyIP" == "A" ]
then
    _MyIPs="$( hostname -I )"
    for _MyIP in "$_MyIPs"
    do
        echo "Found IP: "$_MyIP""
    done
else
    echo "Found IP: $_MyIP"
fi

好吧,无论如何。由于所有提出的解决方案似乎都有失败的情况,请检查可能的边缘案例 - 没有ETH,多重ETH&amp;lo,什么时候"主机名-i"失败,...然后决定最佳解决方案,检查它的工作原理,否则第二好。

Cheers'n'啤酒!

对以前的ip route ...解决方案之一进行了轻微的修改,这消除了对GREP的需求:

ip route get 8.8.8.8 | sed -n 's|^.*src (.*)$|1|gp'

如果只想使用SED来提取IP地址:

ifconfig eth0 2>/dev/null sed -n 's/.*[[:space:]]([[:digit:]][[:digit:]]*.[[:digit:]][[:digit:]]*.[[:digit:]][[:digit:]]*.[[:digit:]][[:digit:]]*).*/1/p'

对以前仅使用ipsedip route ...解决方案之一进行了稍作修改,并且仅适当地隔离IPv4 IP:

ip -4 route get 1.1.1.1 | sed -n 's/^.*src ([0-9.]*).*$/1/p'
awk '/inet addr:/{gsub(/^.{5}/,"",$2); print $2}' file
192.168.1.103

假设您已经安装了JQ,并且您的界面名称为ETH0,我发现这是最清洁的在许多我尝试过的许多事情中:

ip -4 -br -j addr show dev eth0 | jq -r '.[0].addr_info[0].local'

相关内容

  • 没有找到相关文章

最新更新