最近工作需要,要对一些域名进行操作,需求是这样的,用从N个域名解析中找出某N个IP地址,最终的目的是要删除这些IP,所以第一步就是看那些域名解析到了这些ip上,因为涉及的域名数量很多,每个都dig一遍人肉去查看非常费时间,所以本着咱们运维自动化的精神,那个写脚本是必须的了,一劳永逸工作是非常值得做的,我们先来看脚本内容:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 |
#!/usr/bin/evn python import socket import sys def readFile(file): hosts=[] f = open(file) for i in f: hosts.append(i.strip()) f.close() return hosts def returnIP(domain): ip=[] try: results=socket.getaddrinfo(domain,None) for res in results: ip.append(res[4][0]) return list(set(ip)) except Exception,e: print str(e) def doResolve(fr): hosts=readFile(fr) domain={} for host in hosts: ip = returnIP(host) domain[host]=ip return domain if __name__=='__main__': domain=doResolve('modify_domain2.txt') delips=['ip1','ip2','ip3'] domain_res=[k for delip in delips for k,v in domain.items() if domain[k] is not None if delip in domain[k] ] print domain_res |
脚本逐行解释,脚本还是用到了上次我们提到的socket模块,然后定义了三个函数,readFile()函数是读取文件,然后返回一个存有域名的列表,returnIP()这个函数是做实际解析工作的,函数返回一个ip列表,这个函数是脚本核心所以我们详细解释下:
其中socket.getaddrinfo()函数返回解析的内容,它会函数返回一个元组,结构是这样的:
(family, socktype, proto, canonname, sockaddr)
family示协议族(1表示AF_UNIX,2表示AF_INET,10表示AF_INET6)
sockettype表示socket类型(1 即TCP,2 即UDP,还有3是原始套接字)
proto,表示套接字协议,6表示TCP,17表示UDP,其它的可以自己去查。
canonname,这个是ai_flags的标志位,如果设置返回规范主机名,如果不设置就是空,一般都是空
sockaddr如果是ipv4就返回ip和端口号,如果是ipv6,除了ip和端口,还会返回流信息和范围id.
我们来看一个例子,比如我们解析百度返回如下:
1 2 |
>>> socket.getaddrinfo('www.baidu.com',None) [(2, 1, 6, '', ('220.181.112.244', 0)), (2, 2, 17, '', ('220.181.112.244', 0)), (2, 3, 0, '', ('220.181.112.244', 0)), (2, 1, 6, '', ('220.181.111.188', 0)), (2, 2, 17, '', ('220.181.111.188', 0)), (2, 3, 0, '', ('220.181.111.188', 0))] |
有了以上的内容做基础,再看返回的信息就比较容易了,所以我也不多废话了,有问题的可以给我留言。
doResolve()函数其实就是调用以上两个函数将最终解析的结果以字典的形式返回,然后在主函数中调用,delips是要找的IP地址,最后用一个列表生成器生成解析到这些ip上的域名,脚本结束。
如果您觉得还不错,请帮忙转发,在此谢过。