Làm cách nào để hiển thị địa chỉ IP được hiển thị trên eth0 bằng tập lệnh?
Làm cách nào để hiển thị địa chỉ IP được hiển thị trên eth0 bằng tập lệnh?
Câu trả lời:
lưu cái này trong một tập tin và sau đó chạy bash <filename>
#!/bin/bash
ifconfig eth0 | grep "inet addr"
chính xác hơn để chỉ nhận được số hiển thị địa chỉ IP:
#!/bin/bash
ifconfig eth0 | grep "inet addr" | cut -d ':' -f 2 | cut -d ' ' -f 1
Cập nhật : Nếu điều này không phù hợp với bạn, hãy thử câu trả lời khác
grep "inet"
Để cung cấp tùy chọn khác, bạn có thể sử dụng ip addr
lệnh theo cách này để lấy địa chỉ IP:
ip addr show eth0 | grep "inet\b" | awk '{print $2}' | cut -d/ -f1
ip addr show eth0
hiển thị thông tin về eth0
grep "inet\b"
chỉ hiển thị dòng có địa chỉ IPv4 (nếu bạn muốn địa chỉ IPv6, hãy đổi nó thành "inet6\b"
)awk '{print $2}'
in trên trường thứ hai, trong đó có ipaddress / mặt nạ, ví dụ 172.20.20.15/25
cut -d/ -f1
chỉ mất phần địa chỉ IP.Trong một kịch bản:
#!/bin/bash
theIPaddress=$(ip addr show eth0 | grep "inet\b" | awk '{print $2}' | cut -d/ -f1)
Lấy từ /programming//a/14910952/1695680
hostname -i
Tuy nhiên, điều đó có thể trả về một địa chỉ IP cục bộ (127.0.0.1), vì vậy bạn có thể phải sử dụng và lọc:
hostname -I
Từ trang của tên máy chủ:
-i, --ip-address
Hiển thị địa chỉ mạng của tên máy chủ. Lưu ý rằng điều này chỉ hoạt động nếu tên máy chủ có thể được giải quyết. Tránh sử dụng tùy chọn này; sử dụng tên máy chủ --all-ip-địa chỉ thay thế.
-I, --all-ip-addresses
Hiển thị tất cả các địa chỉ mạng của máy chủ. Tùy chọn này liệt kê tất cả các địa chỉ được cấu hình trên tất cả các mặt của mạng. Giao diện loopback và địa chỉ liên kết cục bộ IPv6 bị bỏ qua. Trái với tùy chọn -i, tùy chọn này không phụ thuộc vào độ phân giải tên. Không đưa ra bất kỳ giả định nào về thứ tự của đầu ra.
ip addr show label 'enp*'
tốt hơn, nhưng tôi là người khó chịu, một cái gì đó như ip addr show label 'enp*' | grep -oP inet\ \\S+ | cut -d' ' -f2
có thể hoạt động ... thật đẹp
Phản hồi của @ markus-lindberg là yêu thích của tôi. Nếu bạn thêm -o -4
vào cờ của ip thì bạn sẽ có được đầu ra dễ phân tích (và nhất quán) hơn nhiều:
ip -o -4 a | awk '$2 == "eth0" { gsub(/\/.*/, "", $4); print $4 }'
-o
là viết tắt của --oneline
, có nghĩa là để giúp chính xác loại tình huống này. Các -4
sẽ được thêm vào giới hạn đến địa chỉ IPv4, đó là những gì tất cả các câu trả lời khác hàm ý.
ip
lá cờ. Sử dụng thuật sĩ cut
thay vì nâng cao awk
:ip -o -4 addr show eth0 scope global | awk '{print $4;}' | cut -d/ -f 1
cut
sau khi tôi biết awk
và tôi thích giảm thiểu số lượng lệnh trên đường ống của mình. Đề nghị tốt đẹp trong mọi trường hợp.
Dưới đây là một số oneliners .....
Awk
ifconfig eth0 | awk '/inet addr/{split($2,a,":"); print a[2]}'
hàm split trong lệnh awk ở trên chia tách cột thứ hai dựa trên dấu phân cách :
và lưu giá trị được tách thành một mảng kết hợp a
. Vì vậy, a[2]
giữ giá trị của phần thứ hai.
quyến rũ
ifconfig eth0 | sed -n '/inet addr/s/.*inet addr: *\([^[:space:]]\+\).*/\1/p'
Trong sed cơ bản, \(...\)
được gọi là nhóm bắt giữ được sử dụng để chụp các nhân vật. Chúng ta có thể giới thiệu những nhân vật bị bắt thông qua tham chiếu lại.\([^[:space:]]\+\)
bắt bất kỳ nhân vật nào nhưng không phải không gian một hoặc nhiều lần.
grep
ifconfig eth0 | grep -oP 'inet addr:\K\S+'
\K
loại bỏ các ký tự được khớp trước đó khỏi in tại trận chung kết và \S+
khớp với một hoặc nhiều ký tự không phải khoảng trắng.
Perl
ifconfig eth0 | perl -lane 'print $1 if /inet addr:(\S+)/'
Một hoặc nhiều ký tự không phải không gian bên cạnh inet addr:
chuỗi được ghi lại và cuối cùng chúng tôi chỉ in những ký tự bị bắt.
Bạn nên sử dụng ip
(thay vìifconfig
) như hiện tại, được duy trì và có lẽ quan trọng nhất cho các mục đích kịch bản, nó tạo ra một đầu ra nhất quán & có thể phân tích cú pháp. Sau đây là một vài cách tiếp cận tương tự:
Nếu bạn muốn địa chỉ IPv4 cho giao diện Ethernet của mình eth0
:
$ ip -4 -o addr show eth0 | awk '{print $4}'
192.168.1.166/24
Như một kịch bản:
$ INTFC=eth0
$ MYIPV4=$(ip -4 -o addr show $INTFC | awk '{print $4}')
$ echo $MYIPV4
192.168.1.166/24
Đầu ra được sản xuất ở trên là ký hiệu CIDR.Nếu ký hiệu CIDR không muốn, nó có thể bị xóa:
$ ip -4 -o addr show eth0 | awk '{print $4}' | cut -d "/" -f 1
192.168.1.166
Một tùy chọn khác mà IMHO là "thanh lịch nhất" lấy địa chỉ IPv4 cho bất kỳ giao diện nào được sử dụng để kết nối với máy chủ từ xa được chỉ định (trong trường hợp này là 8.8.8.8). Phép lịch sự của @gatoatigrado trong câu trả lời này :
$ ip route get 8.8.8.8 | awk '{ print $NF; exit }'
192.168.1.166
Như một kịch bản:
$ RHOST=8.8.8.8
$ MYIP=$(ip route get $RHOST | awk '{ print $NF; exit }')
$ echo $MYIP
192.168.1.166
Điều này hoạt động hoàn toàn tốt trên một máy chủ với một giao diện duy nhất, nhưng thuận lợi hơn cũng sẽ hoạt động trên các máy chủ có nhiều giao diện và / hoặc thông số kỹ thuật tuyến đường.
Mặc dù ip
sẽ là cách tiếp cận ưa thích của tôi, nhưng chắc chắn đó không phải là cách duy nhất để lột da con mèo này. Đây là một cách tiếp cận khác sử dụng hostname
nếu bạn thích thứ gì đó dễ dàng / ngắn gọn hơn:
$ hostname --all-ip-addresses | awk '{print $1}'
Hoặc, nếu bạn muốn địa chỉ IPv6:
$ hostname --all-ip-addresses | awk '{print $2}'
Như một kịch bản:
$ MYV4IP=$(hostname --all-ip-addresses | awk '{print $1}')
$ MYV6IP=$(hostname --all-ip-addresses | awk '{print $2}')
$ echo $MYV4IP
192.168.1.166
$ echo $MYV6IP
2601:7c1:103:b27:352e:e151:c7d8:3379
Tôi đề nghị sử dụng một thư viện python như netifaces được thiết kế đặc biệt cho mục đích này.
sudo pip install netifaces
python -c "import netifaces; print netifaces.ifaddresses('eth0')[netifaces.AF_INET][0]['addr']"
Để có được giao diện mạng mặc định đang sử dụng.
default_inf = netifaces.gateways()['default'][netifaces.AF_INET][1]
ip addr|awk '/eth0/ && /inet/ {gsub(/\/[0-9][0-9]/,""); print $2}'
Điều này chỉ sử dụng ip addr
mà là một thay thế cho ifconfig
vàawk
kết hợp với thay thế (gsub).
Chỉ một tùy chọn nữa có thể hữu ích nếu bạn không có awk (vì đó là trường hợp trong một số thiết bị nhúng):
ip addr show dev eth0 scope global | grep "inet\b" | cut -d/ -f 1 | egrep -o "([[:digit:]]{1,3}[.]{1}){3}[[:digit:]]{1,3}"
ifconfig eth0|grep 'inet '|awk '{print $2}'
điều này có thể được sử dụng với một người dùng bình thường quá.
ip addr show eth0 | grep "inet " | cut -d '/' -f1 | cut -d ' ' -f6
ip addr show | grep "inet " | cut -d '/' -f1 | cut -d ' ' -f6
cut
hai lần thay vì kết hợp awk
và cut
phân tích đầu ra. Lần tới, bạn nên kiểm tra tất cả các câu trả lời khác trước và đảm bảo bạn không đăng một giải pháp trùng lặp. Trong trường hợp này ở đây, tôi nghĩ rằng nó là tranh cãi cho dù đó là một bản sao hoặc chỉ tương tự, vì vậy xin vui lòng xem nó như một gợi ý chung. Cảm ơn.
Đây là cách ngắn nhất tôi có thể tìm thấy:
ip -f inet addr show $1 | grep -Po 'inet \K[\d.]+'
Thay thế $1
bằng giao diện mạng của bạn.
ip -f inet
báo cho ip chỉ trả về giá trị cho họ inet (ipv4).
grep -Po
yêu cầu grep xen kẽ giá trị tiếp theo dưới dạng perl-regex và chỉ in các giá trị khớp.
Regex \K[\d.]+
cho biết "vứt bỏ mọi thứ cho đến thời điểm này (\ K) và khớp với càng nhiều giá trị số theo sau là một dấu chấm trong một hàng càng tốt". Do đó, điều này sẽ chỉ khớp với địa chỉ IP và bỏ qua mọi thứ sau nó, bao gồm cả mặt nạ mạng con dạng ngắn \ XX.
trong những ngày này với nhiều giao diện (ví dụ: nếu bạn sử dụng docker) và giao diện đặt tên theo ETH không còn là chuẩn mực nữa
Tôi sử dụng lệnh này để trích xuất IP / Mặt nạ:
IPMASK=$(ip a s|grep -A8 -m1 MULTICAST|grep -m1 inet|cut -d' ' -f6)
Vì vậy, dù tôi có bao nhiêu giao diện và bất kể tên của chúng là gì, GREP sẽ chỉ lấy cái đầu tiên có tùy chọn MULTICAST.
Tôi sử dụng lệnh này để chỉ trích xuất IP mà không có mặt nạ:
IP=$(ip a s|grep -A8 -m1 MULTICAST|grep -m1 inet|cut -d' ' -f6|cut -d'/' -f1)
Tôi sử dụng các lệnh này trên các BDS & NIX khác nhau, nó không bao giờ thất bại;)
ip
, hãy sử dụng -o
tùy chọn.
Trong kịch bản của tôi, tôi đang sử dụng một cái gì đó như thế:
re="inet[[:space:]]+([0-9]+\.[0-9]+\.[0-9]+\.[0-9]+)"
if [[ $(ip addr show eth0) =~ $re ]]; then
echo ${BASH_REMATCH[1]}
else
echo "Cannot determin IP" 1>&2
fi
Nó không sinh ra bất kỳ quá trình.