【翻译】Prometheus最佳实践 Summary和Histogram
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了【翻译】Prometheus最佳实践 Summary和Histogram相关的知识,希望对你有一定的参考价值。
参考技术AHistogram 和 Summary都是复杂的指标,不仅仅是因为直方图和summary包含了多个时间序列,而且它们还较难使用正确。
Histo和summary都是采样观测,典型的采样维度有 响应大小 和 请求时长 。它们跟踪观测值的数量和观测值的总和,从而使您可以计算观测值的平均值。 请注意,观察值的数量(在Prometheus中显示为带有“ _count”后缀的时间序列)本质上是一个计数器(如上所述,它只会增加)。 观测值的总和(以带有_sum后缀的时间序列显示)也可以充当计数器,只要没有负面的观测值即可。 显然,请求持续时间或响应大小永远不会为负。 但是,原则上,您可以使用摘要和直方图来观察负值(例如,摄氏温度)。 在这种情况下,观察值的总和可能会下降,因此您无法再对其应用“ rate()”。
例如,在Histo或者summary上计算5分钟内的平均请求时长,使用如下的PromQL
Histo(而不是summary)的一个直接用途是对落入指定观察值桶中的观察值进行计数。
你可能会有诸如这样的SLO:百分之95的请求都要在300ms内完成返回。在这个场景下,定义一个Histo,定义一个桶的界限为300ms。然后当这个桶的数量小于百分之95的时候就告警。
如下的表达式可以计算上文所述的SLO
你可以以一种非常相似的方式估计Apdex分数。以请求时长为例,配置上界为目标请求时长,另一个桶配置为最大忍受时长(通常是目标请求时长的四倍)。例如目标请求时长为300ms,最大忍受请求时长为1.2s。如下的表达式计算了每5分钟的Apdex分数
注: Apdex分数计算
请注意,我们将两个存储桶的总和相除。 原因是直方图存储桶是[累积]( https://en.wikipedia.org/wiki/Histogram#Cumulative_histogram )。 le =“ 0.3” 存储桶也包含在 le =“ 1.2” 存储桶中; 将其除以2即可解决此问题。
该计算与传统的Apdex分数不完全匹配,因为它包括计算中满意和可忍受的部分中的误差。
你可以使用 summary 和 histogram 来计算 φ-分位数,φ在0到1之间,左右都为闭区间。φ分位数是一个用来计算前φ界限的观测值。换句话说,就是大家平时讲的pxx。p50即是中位数。为了打字方便,后面用 分位数 来行文。
Summary 和 Histogram 的一个区分要点是 summary 在客户端侧计算分位数,然后直接暴露它们,然而 histogram 在客户端侧暴露桶的技术,然后在服务端侧使用 histogram_quantitle() 函数来计算分位数。
请注意表中最后一项的重要性。 让我们回到在300毫秒内处理95%请求的SLO。 这次,您不想显示300毫秒内已处理请求的百分比,而是显示第95个百分位数,即您为95%的请求提供服务的请求持续时间。 为此,您可以配置 summary 为0.95位数,衰减时间为5分钟(例如),也可以配置直方图,并在300ms标记附近添加几个存储桶,例如 le =“ 0.1” , le =“ 0.2” , le =“ 0.3” 和 le =“ 0.45” 。 如果您的服务使用多个实例进行复制运行,则将从其中的每个实例收集请求持续时间,然后将所有内容汇总到整体的95%。 但是,从 summary 汇总预先计算的分位数很少是有意义的。 在这种特定情况下,平均分位数会产生统计上无意义的值。
使用 histograms ,使用 histogram_quantile() 可以完全实现聚合。
此外,如果您的SLO发生变化并且您现在想要绘制第90个百分位,或者您想将最近10分钟而不是最近5分钟考虑在内,则只需调整上面的表达式即可,而无需重新配置客户端。
分位数,无论是在客户端计算还是在服务端计算,都是一个估计值。理解分位数的误差对我们非常重要。
让我们从上面 histogram 的例子继续,想象你通常的请求时长基本上都是220ms,或者换句话说,如果你绘制出了正确的 histogram ,你将会在220ms处看到一个超级大的尖峰。在上面配置的Prometheus直方图度量标准中,几乎所有观察结果以及第95个百分位都将落入标有“ le =“ 0.3””的存储桶中,即从200ms到300ms的存储桶。 直方图实现可确保真实的第95个百分位数在200毫秒至300毫秒之间。 要返回单个值(而不是间隔),它会应用线性插值,在这种情况下将产生295ms。 计算得出的分位数给您的印象是您接近违反SLO,但实际上,第95个百分位数略高于220ms,这是与您的SLO相当舒适的距离。
我们的思想实验的下一步:更改后端路由会为所有请求持续时间增加固定的100ms。 现在,请求持续时间在320毫秒处急剧增加,几乎所有观察结果都会从300毫秒下降到450毫秒。 尽管正确值接近320ms,但第95个百分位数计算为442.5ms。 虽然您仅在SLO之外,但计算得出的第95分位数看起来要差得多。
Summary 就没有上述的问题,除非它在客户端侧使用了估计算法。不幸的是,如果你想要在多个客户端之间聚合,那你无法使用 summary
幸运的是,由于你合适的选择了桶的边界,即使在观测值的分布非常锋利的尖刺的这个人为的例子,直方图能够正确识别,如果你是内或您的SLO之外。同样,分位数的实际值越接近我们的SLO(或换句话说,我们实际上最感兴趣的值),计算出的值就越准确。
现在让我们再次修改实验。在新的设置中,请求持续时间的分布在150ms处有一个尖峰,但不像以前那样尖锐,仅占观察值的90%。 10%的观察结果平均分布在150毫秒至450毫秒之间的长尾巴中。根据这种分布,第95个百分位数恰好在我们的300ms SLO处。使用直方图,由于第95个百分位数的值恰好与铲斗边界之一重合,因此计算得出的值是准确的。甚至略有不同的值也将是准确的,因为相关存储区中的(人为)均匀分布正是存储区中线性插值所假定的。
摘要报告的分位数误差现在变得更加有趣。摘要中的分位数误差是在φ维度中配置的。在我们的情况下,我们可能配置为0.95±0.01,即计算出的值将介于94%和96%之间。具有上述分布的第94位为270ms,第96位为330ms。摘要报告的第95个百分位数的计算值可以在270ms和330ms之间的任何位置,很遗憾,这是SLO内明显与SLO外明显之间的所有差异。
最重要的是:如果使用 summary ,则可以通过调整 维度 来控制误差。如果使用直方图,则可以控制 bucket分配 来调整误差(通过选择适当的桶布局)。
分布较宽时,φ的微小变化会导致观测值的较大偏差。分布较锐利时,观测值的较小间隔将覆盖φ的较大间隔。也就是说,整体宽泛的时候,分位数一点点变化,都会导致分位值的较大变化。整体较紧凑的时候,很小的分位值差值,就能覆盖很大的分位数比例。
两条经验法则:
1.如果需要聚合,请选择 histogram 。
2.否则,如果您对将要观察的值的范围和分布有所了解,请选择 histogram 。无论值的范围和分布是什么,如果都需要准确的分位数,请选择 summary 。
Prometheus监控系列最佳实践
Prometheus是继kubernetes第二个从CNCF中毕业的项目,个人也是非常的喜欢这款通过数据指标发现和预测告警的开源监控平台,官方的话就不多说了,根据官网的介绍有以下功能,但是有些简短的概括了你也不一定知道,所以加了一些个人的白话
官方截图
Prometheus之白话文一段
- 实现高纬度的数据模型
- 时间序列数据通过 metric 名和键值对来区分,这里你可以区分多(隔离)环境的监控指标。
- 所有的 metrics 都可以设置任意的多维标签,可以自定义添加多个,比如这个服务的监控属于哪个团队的。
- 数据模型更随意,不需要刻意设置为以点分隔的字符串;
- 可以对数据模型进行聚合,切割和切片操作;
- 支持双精度浮点类型,标签可以设为全 unicode;
看到这可能你还是不知道啥意思,那就等接下来用到的时候就恍然大悟了...
- 强大的PromQL语句
- 支持查询语句,可以通过PromSQL进行数值之间的比较
- 可以通过PromSQL内嵌的函数计算指标的变化,比如平均值,增长率等等...
- 出色的可视化
- 个人觉得一点都不咋出色,哈哈,还是结合
Grafana
使用吧,毕竟人家专业啊~
- 个人觉得一点都不咋出色,哈哈,还是结合
- 高效的存储
- 可以根据需求设置指标数据的存储天数,也可以持久化存储,比如通过
remotestorageadapter
- 可以根据需求设置指标数据的存储天数,也可以持久化存储,比如通过
- 使用简单
- 部署简单
- 支持动态发现
- 支持热加载
- 支持配置文件格式检查
- 精准的告警
- 告警指的不是
Prometheus
,而是Alertmanager
- 可以设置沉默时间,可以对告警进行分组,可以对告警进行匹配从而决定告警邮件发给哪些负责人
- 支持多种告警媒介,比如常用的
slack
,企业微信
,钉钉
,邮件
还有一些国外常用的,你也可以自己定制;
- 告警指的不是
- 支持多语言客户端库
- 对常见的编程语言都是支持的
- 拥有丰富的exporter生态
- 完美的支持常见的中间件,数据库,主机等等监控
- 还有一些有时候会被忽略的监控对象比如:证书有效期,域名有效期等等
- 比如还有jmx,snmp,vmi等等exporter,这些你可以在github.com搜索
prometheus exporter
看到
上面整那么多的意思就是除了Zabbix
,Prometheus也是没有什么不能监控的,甚至做的更简单,更人性化,但是这里不会介绍太多Prometheus的指标类型,网上很多,就不想整了,大家可以看一下https://yunlzheng.gitbook.io/prometheus-book/introduction
写的算是很走心了,大部分还是要自己实践中琢磨到底如何做。
Prometheus之少不了的部署篇
ServerName | ServerVersion | Functions | 配置文件 |
---|---|---|---|
Promethues | v2.12.0 | 数据处理 | prometheus.yaml |
influxdb | v1.7 | 监控指标的持久化存储 | influxdb.conf |
remotestorageadapter | latest | 数据远程转存适配器 | |
alertmanager | v0.19.0 | 告警管理 | config.yml |
pushgateway | v0.10.0 | 实现push模式推送指标 | |
grafana | v6.0.0 | 数据的可视化展示平台 | grafana.ini |
cadvisor | v0.32.0 | 分析正在运行容器的指标和性能数据 | |
Docker | v18.03.0-ce | 容器运行时 | |
docker-compose | v1.11.2 | 容器编排工具 |
但是你可以直接拿来使用和测试,使用docker-compose
管理的配置清单,对于还没有k8s环境的人来说,也算是福音了。docker-compose-monitor-platform.yml
:
version: ‘3.4‘
services:
influxdb:
image: influxdb:1.7
command: -config /etc/influxdb/influxdb.conf
container_name: influxdb
ports:
- "8086:8086"
restart: always
volumes:
- /data/influxdb:/var/lib/influxdb
environment:
- INFLUXDB_DB=prometheus
- INFLUXDB_ADMIN_ENABLED=true
- INFLUXDB_ADMIN_USER=admin
- INFLUXDB_ADMIN_PASSWORD=admin
- INFLUXDB_USER=prom
- INFLUXDB_USER_PASSWORD=prom
deploy:
resources:
limits:
cpus: ‘0.5‘
memory: 300M
reservations:
cpus: ‘0.25‘
memory: 200M
remotestorageadapter:
image: gavind/prometheus-remote-storage-adapter:1.0
container_name: prometheus-remote-storage-adapter
ports:
- 9201:9201
environment:
- INFLUXDB_PW=prom
restart: always
command: [‘-influxdb-url=http://192.168.0.112:8086‘, ‘-influxdb.database=prometheus‘, ‘-influxdb.retention-policy=autogen‘,‘-influxdb.username=prom‘]
alertmanager:
image: prom/alertmanager:latest
container_name: alertmanager
ports:
- "9093:9093"
restart: always
volumes:
- /opt/alertmanager/config.yml:/etc/alertmanager/config.yml
command: [‘--config.file=/etc/alertmanager/config.yml‘]
prometheus:
image: prom/prometheus:v2.12.0
container_name: prometheus
restart: always
volumes:
- /opt/prometheus/conf/:/etc/prometheus/
ports:
- "9090:9090"
command: [‘--web.external-url=http://192.168.0.112:9090‘,‘--config.file=/etc/prometheus/prometheus.yml‘,‘--storage.tsdb.path=/prometheus/data‘,‘--web.enable-lifecycle‘,‘--web.enable-admin-api‘,‘--web.console.templates=/prometheus/consoletest‘,‘--web.page-title=Prometheues监控平台‘,]
pushgateway:
container_name: pushgateway
image: prom/pushgateway:v1.0.0
restart: always
ports:
- "9091:9091"
command: [‘--persistence.file="/pushgateway/data"‘,‘--persistence.interval=5m‘,‘--web.external-url=http://192.168.0.112:9091‘,‘--web.enable-admin-api‘,‘--log.format=json‘,‘--log.level=info‘,‘--web.enable-lifecycle‘]
deploy:
resources:
limits:
cpus: ‘0.5‘
memory: 300M
reservations:
cpus: ‘0.25‘
memory: 200M
grafana:
container_name: grafana
image: grafana/grafana:6.4.0
restart: always
ports:
- "3000:3000"
volumes:
- /data/grafana/grafana.ini:/etc/grafana/grafana.ini
- /data/grafana:/var/lib/grafana
deploy:
resources:
limits:
cpus: ‘0.5‘
memory: 300M
reservations:
cpus: ‘0.25‘
memory: 200M
# user: "104"
cadvisor:
image: google/cadvisor:latest
container_name: cadvisor
restart: always
ports:
- 8080:8080
volumes:
- /:/rootfs:ro
- /var/run:/var/run:rw
- /sys:/sys:ro
- /var/lib/docker/:/var/lib/docker:ro
要注意几点:
docker-compose-monitor-platform.yml
中需要的目录,你需要创建出来- 配置文件格式我想你是有方法找到的,比如
docker cp
,比如去官网或者github找 - 下面是几个主要的配置文件,Alertmanager和Prometheus的配置文件
Prometheus之你可以自定义修改的配置文件
prometheus.yml
global:
scrape_interval: 2m # 设置采集数据指标的时间为2m, 默认是每1分钟采集一次,采集的频率会影响存储和服务器性能
evaluation_interval: 15s # 15秒钟评估一下告警规则,默认是每1分钟评估一次
external_labels:
monitor: ‘Prometheues监控平台‘
rule_files:
- "prom.rules"
alerting:
alertmanagers:
- scheme: http
static_configs:
- targets: [‘192.168.0.112:9093‘]
scrape_configs:
- job_name: ‘qa-prometheus‘
# 默认的metrics_path标签值为: ‘/metrics‘
# 默认的scheme值为: ‘http‘.
static_configs:
- targets: [‘192.168.0.112:9090‘]
- job_name: pushgateway
static_configs:
- targets: [‘192.168.0.112:9091‘]
labels:
instances: pushgateway
instanceserver: 192.168.0.112
honor_labels: true
config.yaml
global:
resolve_timeout: 1m #该参数定义了当Alertmanager持续多长时间未接收到告警后标记告警状态为resolved(已解决),该参数的定义可能会影响到告警恢复通知的接收时间,默认值是5分钟
smtp_smarthost: smtp.163.net:465 # 邮箱服务器,注意需要加上端口
smtp_from: xxx # 发送者邮箱
smtp_auth_username: xxx # 使用发送者邮箱进行验证时使用的用户名
smtp_auth_password: xxx # 使用发送者邮箱进行验证时使用的密码(客户端授权码)
smtp_require_tls: false # 是否需要进行tls验证
slack_api_url: ‘xxx‘
templates:
- ‘/etc/alertmanager/template/*.tmpl‘
# 所有报警信息进入后的根路由,用来设置报警的分发策略
route: # 主要定义了告警的路由匹配规则,以及Alertmanager需要将匹配到的告警发送给哪一个receiver,【因此这里详细设置就能灵活实现通过匹配标签过滤告警发送到对应的开发owner】
# 这里的标签列表是接收到报警信息后的重新分组标签,例如,接收到的报警信息里面有许多具有 cluster=A 和 alertname=LatncyHigh 这样的标签的报警信息将会批量被聚合到一个分组里面
group_by: [‘alertname‘,‘cluster‘]
# 当一个新的报警分组被创建后,需要等待至少group_wait时间来初始化通知,这种方式可以确保您能有足够的时间为同一分组来获取多个警报,然后一起触发这个报警信息。
group_wait: 10s
# 当第一个报警发送后,等待‘group_interval‘时间来发送新的一组报警信息。
group_interval: 5m
# 如果一个报警信息已经发送成功了,等待‘repeat_interval‘时间来重新发送他们
repeat_interval: 4h
# 默认的receiver:如果一个报警没有被一个route匹配,则发送给默认的接收器
receiver: default
# 上面所有的属性都由所有子路由继承,并且可以在每个子路由上进行覆盖。
routes:
- receiver: ‘default‘
group_wait: 10s
continue: true
- receiver: ‘slack‘
group_wait: 10s
match:
env: yourenv
continue: true
inhibit_rules:
- source_match:
env: yourenv
target_match:
env: yourenv
equal: [‘alertname‘, ‘cluster‘]
receivers:
- name: ‘default‘
email_configs:
- to: ‘xxx‘ # 发送给谁
send_resolved: true
到这里,Prometheus监控平台就基本上部署完成了,接下来就是要看看自己监控哪些服务了,根据自己的监控对象接入到Prometheus中
以上是关于【翻译】Prometheus最佳实践 Summary和Histogram的主要内容,如果未能解决你的问题,请参考以下文章
在微服务架构下基于 Prometheus 构建一体化监控平台的最佳实践
Prometheus监控的最佳实践——关于监控的3项关键指标