Edited at

想像できそうなdig情報を一覧するスクリプト

More than 5 years have passed since last update.


はじめに

何らかの原因でDNS情報をもらえない時に毎回思いついたものを「dig A XXXX.domain.co.jp」とかしていたので、まとめておいて一括で探そうよ。いつも検索しているものはなんだっけとかなるし。


コード


popular_record_search.rb

# coding:utf-8

@fqdn = ARGV[0]

if @fqdn.nil?
print "FQDN or is empty, please write like a \n"
print "\"ruby popular_record_search.rb sample.co.jp\"\n"
exit 1
end

def search(fqdn)
soa = {'soa' => [""]}
ns = {'ns' => [""]}
mx = {'mx' => ["", "mail.", "mx."]}
a = {'a' => ["", "www.", "ftp.", "mail.", "imap.", "pop.", "smtp.", "localhost."]}
txt = {'txt' => [""]}
records = [soa, ns, mx, a, txt]

records.each do |record|
record.each do |type, hosts|
puts ";; #{type} record"
hosts.each do |host|
answer = `dig #{type} #{host}#{@fqdn} +noall +answer |grep -v ^;`.sub("\n","")
unless answer == ""
puts answer
end
end
end
end
end

search(@fqdn)

exit 0


あまりに単純なんですが、それぞれのレコードごとに調べるホストをハッシュにしておいて、それらを配列にしてdigするっていうだけです。requireでそれ相応のものとかありそうですが、取り急ぎ感。


追記

指摘を頂いたので、resolv のライブラリを使った方法でちょっと書いてみた。入れ子が5段階でちょっとどうなのかなとか思うけれども。


popular_record_search2.rb

# coding: utf-8

require 'resolv'

@domain = ARGV[0]

if @domain.nil?
print "DOMAIN or is empty, please write like a \n"
print "\"ruby popular_record_search.rb sample.co.jp\"\n"
exit 1
end

def search(fqdn)
resolv = Resolv::DNS.new(:nameserver =>['8.8.8.8'])

soa = {'SOA' => [""]}
ns = {'NS' => [""]}
mx = {'MX' => ["", "mail.", "mx."]}
a = {'A' => ["", "www.", "ftp.", "mail.", "imap.", "pop.", "smtp.", "localhost."]}
txt = {'TXT' => [""]}
records = [soa, ns, mx, a, txt]

records.each do |key|
key.each do |type, hosts|
puts "; #{type} RECORD"
hosts.each do |host|
fqdn = "#{host}#{@domain}"

case type
when 'SOA'
resolv.each_resource(fqdn, Resolv::DNS::Resource::IN::SOA) do |resource|
puts "TTL is #{resource.ttl}"
puts "#{fqdn}\tIN\t#{type}\t#{resource.mname}"
end
when 'NS'
resolv.each_resource(fqdn, Resolv::DNS::Resource::IN::NS) do |resource|
puts "#{fqdn}\tIN\t#{type}\t#{resource.name}"
end
when 'MX'
resolv.each_resource(fqdn, Resolv::DNS::Resource::IN::MX) do |resource|
puts "#{fqdn}\tIN\t#{type}\t#{resource.preference}\t#{resource.exchange}"
end
when 'A'
resolv.each_resource(fqdn, Resolv::DNS::Resource::IN::A) do |resource|
puts "#{fqdn}\tIN\t#{type}\t#{resource.address}"
end
when 'TXT'
resolv.each_resource(fqdn, Resolv::DNS::Resource::IN::TXT) do |resource|
puts "#{fqdn}\tIN\t#{type}\t#{resource.strings}"
end
end
end
end
end
end

search(@domain)

exit 0


なんとなくgoogleのDNSを仮指定しています。少し時間つかったのはresourceがどんなメソッドをもっているのかわからなかったので、.methodsで一覧見たりとか。表記は変わってしまったけど、一応名前解決はできるようになった。先の例はレコードが入っている列を抽出していただけだったけども、こっちはIP自体とかTTL自体とかをとれるので、いろいろ他の作業とかでも取り回しが良さそうでナイスです。


最後に

調べるホスト名で他も調べたほうが良いとか、よくあるホスト名とかしりたいです。このまま.zoneのファイルにするとかも場合によっては考えるか...です。あんまガンガン用途はなさそうですが。