Saya mencoba untuk mengganti alamat IP dalam dnsmasq logfile dengan nama hostnya. File log sedang 'diawasi' dengan perintah 'tail -f /var/log/dnsmasq.log' di konsol dan saya ingin menyalurkan output ke sed untuk mengganti alamat IP dengan nama host pada HANYA baris yang berisi teks 'permintaan'. Alamat IP selalu di akhir baris ini.
Baris contoh adalah:
Apr 1 00:47:43 dnsmasq[1004]: query[A] gs-loc.apple.com from 10.1.1.188
Saya percaya perintahnya akan dalam bentuk:
tail -f /var/log/dnsmasq.log | sed -e "s/'regex'/$(dig +short -x $1)/g"
'Regex' perlu mengidentifikasi baris yang berisi string "query", mengekstrak alamat IP dari akhir baris itu dan menyimpannya (entah bagaimana) dalam variabel - saya menggunakan notasi di $1
sini - yang digunakan dalam ekspresi ganti dengan menggali.
UPDATE: Saya dihilangkan untuk menyebutkan bahwa alamat IP akan selalu dalam bentuk 10.1.nn
text-processing
logs
ip-address
deanodley
sumber
sumber
Jawaban:
Sayangnya
sed
tidak dapat menjalankan perintah eksternal sementara juga melewati parameter yang diambil dari inputnya.Ini adalah solusi skrip Bash yang harus Anda lakukan:
Dipecah untuk penjelasan : ( hanya untuk tujuan kejelasan, mungkin tidak berfungsi saat disalin & ditempelkan )
sumber
Ini agak, agak berfungsi (tetapi menggunakan 'awk' bukan 'sed'):
... membutuhkan sedikit pemoles misalnya jika pencarian host gagal; mungkin 'permintaan' regex harus sedikit lebih spesifik.
Berikut ini penjelasan tentang perintah awk:
/ query / {...} jalankan {...} pada baris yang cocok dengan regex 'query' (cukup cetak yang lain)
IP = $ NF set variabel baru 'IP' ke nilai bidang terakhir pada baris (alamat IP)
$ NF = "" zap bidang terakhir pada baris
L = $ 0 atur variabel baru 'L' ke baris yang tersisa (yaitu tanpa alamat IP)
"host" IP | getline name jalankan 'host' pada alamat IP dan masukkan hasilnya dalam 'nama' variabel baru
$ 0 = nama atur baris saat ini ke output dari perintah 'host' sehingga kita dapat menggunakan $ NF pada perintah berikutnya.
print L, $ NF Print 'L' (baris input tanpa alamat IP) dan bidang terakhir dari perintah 'host' (nama host).
sumber
Berjalan
dig
untuk setiap alamat IP akan sangat tidak efisien dan menambah beban ke server DNS Anda. Saya akan gunakan diperl
sini:Itu menanyakan layanan nama sistem Anda, jadi mungkin
/etc/hosts
, DNS, mDNS, LDAP, NIS + ... atau apa pun yang dikonfigurasi untuk resolusi nama host di/etc/nsswitch.conf
atau setara pada sistem Anda, mungkin melalui layanan caching layanan nama sepertinscd
atausssd
, dan kami mengimplementasikan caching kami juga untuk menghindari permintaan alamat IP yang sama beberapa kali.Kami hanya mencocokkan untuk urutan
.
angka desimal terpisah -4 , bukan format alamat IPv4 lainnya, tetapi perhatikan bahwa untukinet_aton()
, memimpin 0s menyebabkan angka dianggap sebagai oktal, jadi010.010.010.010
sebenarnya8.8.8.8
(sama seperti kebanyakan hal yang menggunakan alamat IP sebagai argumen, tapi tidakdig -x
).Jika Anda membutuhkannya untuk menanyakan server DNS seperti yang
dig
dilakukan, Anda dapat menggunakannyaNet::DNS
sebagai gantigethostbyaddr()
:sumber