debian-django-statsd-mozilla/django_statsd/panel.py

113 lines
3.3 KiB
Python

from collections import defaultdict
from django.conf import settings
from django.utils.translation import ugettext_lazy as _, ungettext
from debug_toolbar.panels import Panel
from django_statsd.clients import statsd
def munge(stats):
# Munge the stats back into something easy for a template.
results = []
for stat in sorted(stats.keys()):
values = stats[stat]
name, type_ = stat.split('|')
total = sum([x * y for x, y in values])
data = {'name': name, 'type': type_,
'count': len(values),
'total': total,
'values': values}
results.append(data)
return results
def times(stats):
results = []
if not stats:
return results
all_start = stats[0][1]
all_end = max([t[3] for t in stats])
all_duration = all_end - all_start
for stat, start, duration, end in stats:
start_rel = (start - all_start)
start_ratio = (start_rel / float(all_duration))
duration_ratio = (duration / float(all_duration))
try:
duration_ratio_relative = duration_ratio / (1.0 - start_ratio)
except ZeroDivisionError:
duration_ratio_relative = 0
results.append([stat.split('|')[0],
# % start from left.
start_ratio * 100.0,
# % width
duration_ratio_relative * 100.0,
duration,
])
results.sort(key=lambda r: r[1])
return results
def times_summary(stats):
results = []
if not stats:
return results
timings = defaultdict(list)
for stat in stats:
timings[stat[0].split('|')[0]].append(stat[2])
for stat, v in timings.items():
if not v:
continue
v.sort()
count = len(v)
vmin, vmax = v[0], v[-1]
vsum = sum(v)
mean = vsum / float(count)
results.append({
'stat': stat,
'count': count,
'sum': vsum,
'lower': vmin,
'upper': vmax,
'mean': mean,
})
return results
class StatsdPanel(Panel):
title = _('Statsd')
has_content = True
template = 'toolbar_statsd/statsd.html'
def __init__(self, *args, **kwargs):
super(StatsdPanel, self).__init__(*args, **kwargs)
self.statsd = statsd
try:
self.statsd.reset()
except AttributeError:
raise ValueError('To use the toolbar, your STATSD_CLIENT must'
'be set to django_statsd.clients.toolbar')
@property
def nav_subtitle(self):
length = len(self.statsd.cache) + len(self.statsd.timings)
return ungettext('%s record', '%s records', length) % length
def process_response(self, request, response):
config = getattr(settings, 'TOOLBAR_STATSD', {})
if 'roots' in config:
for key in ['timers', 'counts']:
self.record_stats({key: config['roots'][key]})
self.record_stats({
'graphite': config.get('graphite'),
'statsd': munge(self.statsd.cache),
'timings': times(self.statsd.timings),
'timings_summary': times_summary(self.statsd.timings),
})