hosts-ping: moving averages added
[svn/Prometheus-QoS/.git] / optional-tools / hosts-ping.py
CommitLineData
00902283 1#!/usr/bin/python
2# -*- coding: utf-8 -*-
3
4import ping, socket
bf2122f6 5import os, time, json
00902283 6
7# (G)2013 xChaos, Arachne Labs http://arachne.cz + SPOJE.NET http://spoje.net
8
9hosts = "/etc/hosts"
10timeout = 1500 #timeout in ms
11interval = 200 #ping interval in ms
12attempts = 10
13
14tld = ".czf"
15domain = ".brevnov.czf"
16smokeping_prefix = "Klienti"
17smpater_prefix = "Backbone"
18smokeping_babble_length = 3
19smpater_babble_length = 2
20smokeping_html = "/var/www/html/web/sites/sysifos/hosts-ping/index.html"
21smpater_html = "/var/www/html/web/sites/sysifos/hosts-ping/backbone.html"
bf2122f6 22smokeping_avg_html = "/var/www/html/web/sites/sysifos/hosts-ping/avg.html"
23smpater_avg_html = "/var/www/html/web/sites/sysifos/hosts-ping/backbone-avg.html"
24smokeping_avg_json = "/var/www/html/web/sites/sysifos/hosts-ping/smokeping.json"
25smpater_avg_json = "/var/www/html/web/sites/sysifos/hosts-ping/smpater.json"
00902283 26smokeping_url = "http://sisyfos.brevnov.czf/cgi-bin/smokeping.cgi?filter=%s&target=%s"
27smpater_url = "http://tartarus.brevnov.czf/cgi-bin/smokeping.cgi?filter=%s&target=%s"
28table_head = """
29<table class="decorated last">
30<caption>hosts ping (%s)</caption><thead><tr>
31<th style="text-align: right;">#</th>
32<th>hostname</th>
bf2122f6 33<th style="text-align: right;">loss</th>
00902283 34<th style="text-align: right;">avg</th>
35<th style="text-align: right;">best</th>
36<th style="text-align: right;">worst</th>
37</tr></thead><tbody>
38"""
39table_end = """
40</tbody></table>
41<br />
bf2122f6 42<p>Page generated by (G)2013 xChaos hosts-ping version 0.2-a</p>
00902283 43"""
44
45def try_to_ping(host):
46 sum = 0.0
47 best = None
48 worst = None
49 loss = 0
50
51 for i in range(0, attempts):
52 try:
53 delay = ping.Ping(host, timeout = timeout).do() #timeout in ms
54 time.sleep(interval/1000)
55
56 if delay:
57 sum += delay
58
59 if not best or best > delay:
60 best = delay
61
62 if not worst or worst < delay:
63 worst = delay
64
65 else:
66 loss += 1
67
68 except socket.error, e:
69 loss += 1
70
71 return (sum/attempts, best, worst, loss)
72
73
74def smokenam_style(hostname, prefix, babble_length):
75
76 if not tld in hostname:
77 hostname += domain
78
79 babble = hostname.split('.')
80 return '.'.join([prefix,] + [a_tooth for a_tooth in reversed(babble)][1:babble_length] + ['-'.join(babble),])
81
82
bf2122f6 83def append_host(html, host, base_url, counter, red_treshold, green_treshold):
00902283 84 style = {'right': 'text-align: right;'}
85 columns = ('loss','avg','best','worst')
00902283 86
87 for kolikaty, column in enumerate(columns):
88 style[column] = style['right']
89
90 if not host[column]:
91 host[column] = 0 #don't want it to be "None" type
92
93 if host[column] > red_treshold[kolikaty]:
94 style[column] += ' color: red;'
95 elif host[column] < green_treshold[kolikaty]:
96 style[column] += ' color: green;'
97
bf2122f6 98 loss = 100*host['loss']/host['attempts']
99 html.write( ('<tr class="%s"><td style="%s">%d</td><td><a href="%s" target="_blank" class="blue">%s</a></td><td style="%s">%.1f%%</td>' + "\n")
100 % (('even', 'odd')[counter % 2], style['right'], counter, base_url % (host['name'], host['smokename']), host['name'], style['loss'], loss))
00902283 101
102 if host['avg'] and host['best'] and host['worst']:
bf2122f6 103 html.write( ('<td style="%s">%.1f</td><td style="%s">%.1f</td><td style="%s">%.1f</td></tr>' + "\n")
00902283 104 % (style['avg'], host['avg'], style['best'], host['best'], style['worst'], host['worst']))
105 else:
106 html.write(3*('<td style="%s">-</td>' % style['loss']) + "\n")
107
bf2122f6 108
109def merge_json_avgs(filename, smoke_array):
110
111 try:
112 avg_dict = json.load(open(filename))
113
114 for host in smoke_array:
115 avg = avg_dict.get(host['ip'])
116 if avg:
117 if host['avg'] and avg['avg'] and avg['attempts']+host['attempts']-avg['loss']-host['loss'] > 0:
118 host['avg'] = ((avg['attempts']-avg['loss'])*avg['avg']+(host['attempts']-host['loss'])*host['avg'])/(avg['attempts']+host['attempts']-avg['loss']-host['loss'])
119
120 if not host['best'] or host['best'] > avg['best']:
121 host['best'] = avg['best']
122
123 if not host['worst'] or host['worst'] < avg['worst']:
124 host['worst'] = avg['worst']
125
126 host['attempts'] += avg['attempts']
127 host['loss'] += avg['loss']
128
129 except:
130 pass #start from scratch...
131
132
133def save_json(filename, smoke_array):
134 smoke_dict = {}
135
136 for host in smoke_array:
137 smoke_dict[host['ip']] = host
138
139 json.dump(smoke_dict, open(filename, 'w'))
140
141
00902283 142# main program
143
144smokeping = []
145smpater = []
146
147for radek in open(hosts):
148 if radek[0] != '#':
149 is_smokeping = 'smokeping' in radek and not 'hidden' in radek
150 is_smpater = 'smpater' in radek
151 if is_smokeping or is_smpater:
152 slovo = radek.split("\t")
bf2122f6 153 host = { 'ip': slovo[0], 'name': slovo[1].split(' ')[0], 'attempts': attempts }
00902283 154 (host['avg'], host['best'], host['worst'], host['loss']) = try_to_ping(host['ip'])
155
156 if is_smokeping:
157 host['smokename'] = smokenam_style(host['name'], smokeping_prefix, smokeping_babble_length)
158 smokeping.append(host)
159 else:
160 host['smokename'] = smokenam_style(host['name'], smpater_prefix, smpater_babble_length)
161 smpater.append(host)
162
163# smokeping
164
bf2122f6 165red_treshold = (0, 100, 50, 200)
166green_treshold = (0, 7, 5, 20)
00902283 167html = open(smokeping_html, 'w')
bf2122f6 168html.write("<h1>Aktuální odezva klientských zařízení</h1>");
00902283 169html.write(table_head % time.ctime());
170
171for kolikaty, host in enumerate(sorted(smokeping, key = lambda host: -host['loss']*attempts*timeout-host['avg'])):
bf2122f6 172 append_host(html, host, smokeping_url, kolikaty+1, red_treshold, green_treshold)
00902283 173
bf2122f6 174html.write(table_end)
175html.close()
00902283 176
177# smpater
178
bf2122f6 179red_treshold = (0, 50, 20, 100)
180green_treshold = (0, 5, 2, 10)
00902283 181html = open(smpater_html, 'w')
bf2122f6 182html.write("<h1>Aktuální odezva páteřních routerů</h1>");
183html.write(table_head % time.ctime());
184
185for kolikaty, host in enumerate(sorted(smpater, key = lambda host: -host['loss']*attempts*timeout-host['avg'])):
186 append_host(html, host, smpater_url, kolikaty+1, red_treshold, green_treshold)
187
188html.write(table_end)
189html.close()
190
191# smokeping average
192
193red_treshold = (1000, 100, 20, 500)
194green_treshold = (0, 7, 5, 20)
195merge_json_avgs(smokeping_avg_json, smokeping)
196html = open(smokeping_avg_html, 'w')
197html.write("<h1>Průměrná odezva klientských zařízení</h1>");
198html.write(table_head % time.ctime());
199
200for kolikaty, host in enumerate(sorted(smokeping, key = lambda host: -host['loss']*attempts*timeout-host['avg'])):
201 append_host(html, host, smokeping_url, kolikaty+1, red_treshold, green_treshold)
202
203html.write(table_end)
204html.close()
205save_json(smokeping_avg_json, smokeping)
206
207# smpater average
208
209red_treshold = (100, 50, 10, 200)
210green_treshold = (0, 5, 2, 10)
211merge_json_avgs(smpater_avg_json, smpater)
212html = open(smpater_avg_html, 'w')
213html.write("<h1>Průměrná odezva páteřních routerů</h1>");
00902283 214html.write(table_head % time.ctime());
215
216for kolikaty, host in enumerate(sorted(smpater, key = lambda host: -host['loss']*attempts*timeout-host['avg'])):
bf2122f6 217 append_host(html, host, smpater_url, kolikaty+1, red_treshold, green_treshold)
00902283 218
bf2122f6 219html.write(table_end)
220html.close()
221save_json(smpater_avg_json, smpater)
This page took 0.318844 seconds and 4 git commands to generate.