最近幫朋友寫了一個朋友寫了一個腳本實現的功能就是對應主機組中的主機對應的cpu,網卡,硬盤進行分組,能夠根據時間段來獲取數據,添加進screen 手動實現是一件極其麻煩的事情,這樣只查看對應的項就方便多了。python
我改了下也能按照多個主機來實現添加screen,也能根據主機組來實現正則表達式
爲了方便這邊是就是用python 提供的api庫來實現了api
#!/usr/bin/env python #coding:utf8 from pyzabbix import ZabbixAPI from itertools import chain import time import datetime import socket import sys import re class make_screen(object): def __init__(self,name='',columns=2,delete=False,check=False,width="500",heigth="100",start_time='',stop_time=''): #def __init__(self): self.columns = columns self.dynamic = 0 self.width=width self.heigth=heigth self.check=check self.delete=delete self.name=name self.start_time=self.f_date(start_time) self.stop_time=self.f_date(datetime.datetime.now()) if stop_time == 'now' else self.f_date(stop_time) # print self.start_time # print self.stop_time self.history=True self.user='admin' #帳號 self.passwd='zabbix' #密碼 self.server=' #鏈接你的zabbix服務器的url self.login() # sys.exit(1) def f_date(self,date): #獲取到日期而後對日期進行分割,用字典生成對應的年,月,日,小時,分鐘 對應的字典 #print date c=re.split(r'-|:|\s',str(date).split('.')[0]) d=[x.lstrip('0') for x in c if x.lstrip('0')] if len(d) >6: print 'your input time is err' sys.exit(1) return dict(zip('ymdhM',d)) def hosts(self,hosts): #輸入多個主機生成主機組 self.hosts=[x for x in hosts if x] #print self.hosts #def k_filter(self,*filter): def k_filter(self,filter): self.filter=[x for x in filter] def search(self,string): #生成須要過濾主機的key_ #print '|'.join(self.filter) if re.search(r'%s' % '|'.join(self.filter), string): return string else: return def login(self): #登陸的zabbix主機 self.zapi = ZabbixAPI(self.server) self.zapi.login(self.user,self.passwd) return self.zapi def g_hostgroup(self,g_name): #獲取這個主機組的全部主機 return self.zapi.hostgroup.get(output='extend',filter={'name':g_name})[0].get('groupid') def g_host(self,name): if not self.e_hostgroup(name): #判斷這個主機組是否存在的 調用def e_hostgroup(self,g_name) 方法 print "don't have name hostgroup" sys.exit(1) host=set() g_host=self.zapi.host.get(output='extend',groupids=self.g_hostgroup(name)) #從 for x in g_host: host.add(x.get('host')) self.hosts=[x for x in host] #以主機組獲取對應的所有主機 #print self.hosts def e_hostgroup(self,g_name): #判斷主機組存在 return self.zapi.hostgroup.exists(name=g_name) def g_item(self): #獲取主機對應的的全部item,生成item:key對應的字典 items={} for hostname in self.hosts: host=self.zapi.item.get( output='extend', filter={'host':hostname,}, ) for x in host: #print x.get('key_') if self.search(x.get('key_')): #print x.get('key_') items[x.get("itemid")]=x.get("value_type") if len(items) == 0: print '''host don't have any item''' sys.exit(1) # print items return items #def v_item(self): def g_history(self): #一個graph可能有不少個item組成的,只要graph中有一個item有數據都認爲這個graph是能夠用,獲取歷史一個時間段的數據進行歷史的判斷,我這裏是根據字典對應的value進行判斷,你也能夠把對應的value進行累加判斷,我這樣的作法會把數據爲0的也添加進去 start_time=time.mktime(datetime.datetime(int(self.start_time.get('y',0)),int(self.start_time.get('m',0)),int(self.start_time.get('d',0)),int(self.start_time.get('h',0)),int(self.start_time.get('M',0))).timetuple()) stop_time=time.mktime(datetime.datetime(int(self.stop_time.get('y',0)),int(self.stop_time.get('m',0)),int(self.stop_time.get('d',0)),int(self.stop_time.get('h',0)),int(self.stop_time.get('M',0))).timetuple()) print start_time print stop_time g_item=self.g_item() v_item={} for history in g_item.keys(): # print g_item[history] if g_item[history] == '0': get_history=self.zapi.history.get(history='0',output='extend',itemids=history,time_from=str(start_time),time_till=str(stop_time)) elif g_item[history] == '3': get_history=self.zapi.history.get(output='extend',itemids=history,time_from=str(start_time),time_till=str(stop_time)) else: 'now only support integer and fload,do you can modify' sys.exit(1) for y in get_history: if v_item.has_key(history): v_item[history].append(y.get('value')) else: v_item[history]=[] v_item[history].append(y.get('value')) # print v_item return v_item.keys() #return v_item.keys() #return self.v__item def gid_host(self,g_gid): #在引用g_graphitem return self.zapi.host.get(output='extend',graphids=g_gid) def key_graph(self,k_graph): #獲取graph 和主機名,這邊的排序是根據主機名來排序 for x in self.zapi.graph.get(output='extend',graphids=k_graph): return [k_graph,x.get('name')] def g_graphitem(self): graphs=set() g_dict={} s_graphs=[] if self.history: #是否根據歷史中item來判斷 g_item=self.g_history() else: g_item=self.g_item().keys() # for itemid in g_item: #獲取沒有重複的多有graph v=self.zapi.graphitem.get( output='extend', itemids=itemid, ) for id in v: # print id graphs.add(id.get('graphid')) if len(graphs) == 0: #這個主機組中沒有graph 就退出了 print '''don't have any graph''' sys.exit(1) #print graphs k_g={} for x in graphs: #def key_graph c=self.key_graph(x) #print c k_g[c[0]]=c[1] #print k_g for x in graphs: if len(self.gid_host(x))>1: print 'gid_host have problem' sys.exit(1) for y in self.gid_host(x): #獲取主機id 生成{主機名:{組名:組id}的字典下面須要排序 if g_dict.get(y.get('host')): g_dict[y.get('host')][k_g.get(x)]=x #pass # print "host corresponding two graph" # sys.exit(1) else: g_dict[y.get('host')]={} if not g_dict[y.get('host')].has_key(k_g.get(x)): g_dict[y.get('host')][k_g.get(x)]=x # print y #pass nor=[] err=[] # print g_dict #sys.exit(1) ip_d={} #正則能匹配到ip但不是真正的ip好比1-192.168.1.102-3306 這個也能匹配,這個字典主要實現ip轉換{192.168.1.102:1-192.168.1.102-3306} for x in g_dict: #把正常的ip加進去nor 不是就加入到err 以便下面能使用socket.inet_aton排序 if re.search(r'\d{1,3}(\.\d{1,3})',x): if re.search(r'\-', x): #匹配到了的話就加入到字典裏面轉換下以便根據ip排序不會報錯,我這裏使用的是re.split 以上面的格式split不必定你能使用你能夠使用re.findall替代匹配的真正的ip ip_d[re.split(r'-',x)[0]]=x nor.append(re.split(r'-',x)[0]) else: nor.append(x) else: err.append(x) #print nor #sys.exit(1) nor_id=[] err_id=[] for x in sorted(nor,key=socket.inet_aton): if ip_d.has_key(x): #這邊已經排序完成,而後就把ip替換掉192.168.1.102-3306 x=ip_d.get(x) #實現字典中的內切字典也進行排序 for y in sorted(g_dict.get(x).keys()): nor_id.append(g_dict.get(x).get(y)) for x in sorted(err): #不是ip的話直接排序,就行了,內切字典也進行排序 for y in sorted(g_dict.get(x).keys()): err_id.append(g_dict.get(x).get(y)) # print nor_id # sys.exit(1) s_graphs=chain(nor_id,err_id) #for z in sorted(g_dict.keys(),key=socket.inet_aton): # s_graphs.append(g_dict.get(z)) #print g_dict #sys.exit(1) #print 1 x = 0 y = 0 graph_list=[] #這裏就生成對應screen所須要的參數 for graph in s_graphs: # print graph graph_list.append({ "resourcetype":'0', "resourceid": graph, "width": self.width, "height": self.heigth, "x": str(x), "y": str(y), "colspan": "0", "rowspan": "0", "elements": "0", "valign": "0", "halign": "0", "style": "0", "url": "", "dynamic": str(self.dynamic) }) x += 1 if x == int(self.columns): x = 0 y += 1 #print graph_list return graph_list def c_screen(self): #生成screen graphids=self.g_graphitem() columns = int(self.columns) if len(graphids) % self.columns == 0: vsize = len(graphids) / self.columns else: vsize = (len(graphids) / self.columns) + 1 # print graphids self.zapi.screen.create(name=self.name,hsize=self.columns,vsize=vsize,screenitems=graphids) def e_screen(self): #判斷screen是否存在了 list_exists=self.zapi.screen.exists(name=self.name) if list_exists: print '%s is exists' % self.name sys.exit(1) def check_screen(self,c_name): #是否生成screen進行驗證下 if not self.zapi.screen.exists(name=c_name): print "%s add failure" %(c_name) def g_screen(self,g_id): #刪除的功能,建議手動刪除 s_name={} for x in self.zapi.screen.get(output='extend'): s_name[x.get('name')]=x.get('screenid') if g_id in s_name: self.zapi.screen.delete(s_name[g_id],) def d_screen(self,id): self.zapi.screen.delete(id,) def run(self): #self.g_history() self.e_screen() self.c_screen() if __name__ == '__main__': from optparse import OptionParser parser = OptionParser() parser.add_option('-G', dest='graphname', help='Zabbix Host Graph to create screen from') parser.add_option('-c', dest='columns', type=int, help='number of columns in the screen') parser.add_option('--group', dest='group', help='the hostgroup name') parser.add_option('-f', dest='filter',action="append", help='what do you filter string') parser.add_option('--hosts',dest='hosts',action='append', help='many hosts to get key') parser.add_option('--delete',dest='delete',type=int, help='do you want to delete screen') parser.add_option('--delete-name',dest='delete_name', help='remove name?') parser.add_option('--check',dest='check',type=int, help='check screen is ok?') parser.add_option('-w',dest='width', help='screen width'), parser.add_option('--check-name',dest='check_name', help='check name?') parser.add_option('-l',dest='heigth', help='screen heigth') parser.add_option('--start',dest='start', help='start in history time') parser.add_option('--stop',dest='stop',default=datetime.datetime.now(), help='stop in history time') options,args=parser.parse_args() if options.delete: a=make_screen(delete=options.delete) a.g_screen(options.delete_name) sys.exit() if options.check: a=make_screen(check=options.check) a.check_screen(options.check_name) sys.exit(2) #print re.split(r':|,',options.filter[0]) if options.hosts and options.group: print "options.hosts and groups.group have value as the same time" sys.exit(1) elif not (options.hosts or options.group): print "options.hosts and groups.group must the one have a value" sys.exit(1) # print re.split(r':|,',options.hosts[0]) #print options.hosts a=make_screen(columns=options.columns,name=options.graphname,width=options.width,heigth=options.heigth,start_time=options.start,stop_time=options.stop) #a=make_screen() if options.hosts: a.hosts(re.split(r':|,',options.hosts[0])) #a.hosts('10.0.15.123','10.0.15.1') if options.group: a.g_host(options.group) a.k_filter(re.split(r':|,',options.filter[0])) a.run()
python filter_screen.py -G "SFA-HPC-網絡流量" -f "net.if.in" -c 2 --group zabbix -w 800 -l 100 --start 2014-8-6-20-00 --stop now 服務器
這裏in 和out都在一個graph中,只要一個graph中有一個item有數據就會出來對應的grpah網絡
cpuapp
注意:socket
python filter_screen.py -G "SFA-HPC-網絡流量" -f "net.if.in[eth0]" -c 2 --group zabbix -w 800 -l 100 --start 2014-8-6-20-00 --stop now ide
這樣就會出問題,正則表達式中[]是或url
正確spa
python filter_screen.py -G "SFA-HPC-網絡流量" -f "net.if.in\[eth0\]" -c 2 --group zabbix -w 800 -l 100 --start 2014-8-6-20-00 --stop now
[]須要對齊轉義
若是有不少screen,你能夠寫個循環腳本進行循環,這樣見簡化繁瑣了
有何問題請向我反映謝謝~~~~~~~~~~