通过python metrics计算应用性能指标

前言:

     最近公司在折腾应用级别的性能监控,现在已经有C、Java的版本了。 貌似还缺少我们组专用的Python版本。 现在做Metrics的公司有OneApm,就在我们的楼上。  oneapm的各种计算统计的api和dashboard面板虽然很好用,毕竟还是需要付费的。 今天就说下,我们是如何在python下获取metrics性能指标的.     这里透露下metric性能监控的架构,client其实是各个语言的metrics模块,数据的存取是Elasticsearch,前端的显示暂时是Kibana,当然kibana优缺点很鲜明,他不能很好的定制化页面,包括权限管理.   对于client –> elasticsearch集群的过程,可以增加本地一个本地转发节点完成,像scribe、logstash那样.

那么metries是什么?  是用来统计计算应用的性能指标,  频率, 耗时 ,大小长短…

举个例子,一个用python开发的爬虫服务:

一共处理了多少页面? 
每秒钟的请求数是多少(TPS)?
平均每个请求处理的时间?
请求处理的最长耗时?
等待处理的请求队列长度?
每个函数在1分 5分 15分,分别的平均值在多少?

上面的这些需求就很适合用metrices来实现. 

metrics原本是java的包,现在各个语言也都有基于metrices统计开发的模块。比如python的appmetrics,这名字就知道是应用监控 . 以前用python自己实现过一个简单的metrics,当然代码写得太low,不得见人…  这次结合appmetrics来说说五中metrics类型的区别,及应用场景。 

文章写得不太严谨, 请砖家拍砖,另外标注下原文地址,http://xiaorui.cc/?p=2447

一共有五种 Metrics 类型

Gauges:

Gauges,最简单的度量指标,只有一个简单的返回值,例如,我们想衡量一个待处理队列中任务的个数

gauge可以是字符串,也可以是数字.

gauge = metrics.new_gauge("gauge_test")
gauge.notify("version 1.0")
gauge.get()
{'kind': 'gauge', 'value': 'version 1.0'}

Counter:

Counter,就是计数器,inc增加,dec减少.  在appmetrics里面只暴露了notify

counter = metrics.new_counter("test")
counter.notify(10)   #xiaorui.cc
counter.notify(-5)
counter.get()
{'kind': 'counter', 'value': 5}
counter.notify("wrong")
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "appmetrics/simple_metrics.py", line 40, in notify
    value = int(value)
ValueError: invalid literal for int() with base 10: 'wrong'

Meters:
Meters,度量一系列事件发生的速率(rate),例如TPS。Meters会统计最近1分钟,5分钟,15分钟,还有全部时间的速率。

meter = metrics.new_meter(“meter_test”)
meter.notify(1)
meter.notify(1)
meter.notify(3)
meter.get()

返回结果:

{'count': 5, 'kind': 'meter', 'five': 0.0066114184713530035, 'mean': 0.27743058841197027, 'fifteen': 0.0022160607980413085, 'day': 2.3147478365093123e-05, 'one': 0.031982234148270686}

count: 总数
mean: 平均值
one: 1分钟
five: 5分钟
fifteen: 15分钟
day: 一天的平均值
kind: “meter”

我们可以对比下java metrices运行结果:

             count = 134
         mean rate = 2.13 events/second
     1-minute rate = 2.52 events/second
     5-minute rate = 3.16 events/second
    15-minute rate = 3.32 events/second

注:非常像 Unix 系统中 uptime 和 top 中的 load.

Histograms

Histogram统计数据的分布情况。比如最小值,最大值,中间值,还有中位数,75百分位, 90百分位, 95百分位, 98百分位, 99百分位, 和 99.9百分位的值(percentiles)。

import time, random
@metrics.with_histogram("test")
def my_worker():
	time.sleep(random.random())

my_worker()  #xiaorui.cc
metrics.get("test")

返回结果:

{
	'arithmetic_mean': 0.41326093673706055,
	'kind': 'histogram',
	'skewness': 0.2739718270714368,
	'harmonic_mean': 0.14326954591313346,
	'min': 0.0613858699798584,
	'standard_deviation': 0.4319169569113129,
	'median': 0.2831099033355713,
	'histogram': [(1.0613858699798584, 3), (2.0613858699798584, 0)],
	'percentile': [(50, 0.2831099033355713), (75, 0.2831099033355713), (90, 0.895287036895752), (95, 0.895287036895752), (99, 0.895287036895752), (99.9, 0.895287036895752)],
	'n': 3,
	'max': 0.895287036895752,
	'variance': 0.18655225766752892,
	'geometric_mean': 0.24964828731906127,
	'kurtosis': -2.3333333333333335
}

运行之后结果大致如下:
             count = 56
               min = 1122
               max = 99650
              mean = 48735.12
            stddev = 28609.02
            median = 49493.00
              75% <= 72323.00
              95% <= 90773.00
              98% <= 94011.00
              99% <= 99650.00
            99.9% <= 99650.00

Timers

Timer其实是 Histogram 和 Meter 的结合, 在appmetrices里面没有直接的Timers的实现,但是可以通过Tagging实现.

metrics.new_histogram("test1")
metrics.new_gauge("test2")
metrics.new_meter("test3")
metrics.tag("test1", "group1")
metrics.tag("test3", "group1")
metrics.tags()
metrics.metrics_by_tag("group1")

返回的结果

{
	'test1': {
		'arithmetic_mean': 0.0,
		'skewness': 0.0,
		'harmonic_mean': 0.0,
		'min': 0,
		'standard_deviation': 0.0,
		'median': 0.0,
		'histogram': [(0, 0)],
		'percentile': [(50, 0.0), (75, 0.0), (90, 0.0), (95, 0.0), (99, 0.0), (99.9, 0.0)],
		'n': 0,
		'max': 0,
		'variance': 0.0,
		'geometric_mean': 0.0,
		'kurtosis': 0.0
	},
	'test3': {
		'count': 0,
		'five': 0.0,
		'mean': 0.0,
		'fifteen': 0.0,
		'day': 0.0,
		'one': 0.0
	}
}

如果用java metrics运行之后结果如下.

             count = 38
         mean rate = 1.90 calls/second
     1-minute rate = 1.66 calls/second
     5-minute rate = 1.61 calls/second
    15-minute rate = 1.60 calls/second
               min = 13.90 milliseconds
               max = 988.71 milliseconds
              mean = 519.21 milliseconds
            stddev = 286.23 milliseconds
            median = 553.84 milliseconds
              75% <= 763.64 milliseconds
              95% <= 943.27 milliseconds
              98% <= 988.71 milliseconds
              99% <= 988.71 milliseconds
            99.9% <= 988.71 milliseconds

使用经验总结,

一般情况下,当我们需要统计某个函数或者action被调用的频率,会使用Meters。当我们需要统计某个函数的执行耗时,会使用Histograms。当我们既要统计频率又要统计耗时的时候,我们会使用Timers。所以说,Timers的数据最全。 


大家觉得文章对你有些作用! 如果想赏钱,可以用微信扫描下面的二维码,感谢!
另外再次标注博客原地址  xiaorui.cc

发表评论

邮箱地址不会被公开。 必填项已用*标注