Prometheus技术讲义

1简介

Prometheus是一个开源的系统监控和告警系统,现在已经加入到CNCF基金会,成为继k8s之后第二个在CNCF维护管理的项目,在kubernetes容器管理系统中,通常会搭配prometheus进行监控,prometheus支持多种exporter采集数据,还支持通过pushgateway进行数据上报prometheus在性能上可以支持上万台规模的集群。

作为新一代的监控框架,Prometheus 具有以下特点:

 强大的多维度数据模型。

 时间序列数据通过 metric 名和键值对来区分。

 所有的 metrics 都可以设置任意的多维标签。

 数据模型更随意,不需要刻意设置为以点分隔的字符串。

 可以对数据模型进行聚合,切割和切片操作。

 支持双精度浮点类型,标签可以设为全 unicode。

 灵活而强大的查询语句(PromQL):在同一个查询语句,可以对多个metrics 进行乘法、加法、连接、取分数位等操作。

 易于管理:Prometheus server 是一个单独的二进制文件,可直接在本地工作,不依赖于分布式存储。

 高效:平均每个采样点仅占 3.5 bytes,且一个 Prometheus server 可以处理数百万的 metrics。

 使用 pull 模式采集时间序列数据,这样不仅有利于本机测试而且可以避免有问题的服务器推送坏的 metrics。

 可以采用 push gateway 的方式把时间序列数据推送至 Prometheus server 端。

 可以通过服务发现或者静态配置去获取监控的 targets。

 有多种可视化图形界面。

 易于伸缩。

2架构图

 

3 prometheus组件介绍

 Prometheus Server: 用于收集和存储时间序列数据。

 Client Library: 客户端库,检测应用程序代码,当Prometheus抓取实例的HTTP端点时,客户端库会将所有跟踪的metrics指标的当前状态发送到prometheus server端。

 Exporters: prometheus支持多种exporter,通过exporter可以采集metrics数据,然后发送到prometheus server端

 Alertmanager: 从 Prometheus server 端接收到 alerts 后,会进行去重,分组,并路由到相应的接收方,发出报警,常见的接收方式有:电子邮件,微信,钉钉, slack等。

 Grafana:监控仪表盘

 pushgateway: 各个目标主机可上报数据到pushgatewy,然后prometheus server统一从pushgateway拉取数据。

 

4基本原理

Prometheus的基本原理是通过HTTP协议周期性抓取被监控组件的状态,任意组件只要提供对应的HTTP接口就可以接入监控。不需要任何SDK或者其他的集成过程。这样做非常适合做虚拟化环境监控系统,比如VM、Docker、Kubernetes等。输出被监控组件信息的HTTP接口被叫做exporter 。目前互联网公司常用的组件大部分都有exporter可以直接使用,比如Varnish、Haproxy、Nginx、MySQL、Linux系统信息(包括磁盘、内存、CPU、网络等等)。

5服务过程

● Prometheus Daemon负责定时去目标上抓取metrics(指标)数据,每个抓取目标需要暴露一个http服务的接口给它定时抓取。Prometheus支持通过配置文件、文本文件、Zookeeper、Consul、DNS SRV Lookup等方式指定抓取目标。Prometheus采用PULL的方式进行监控,即服务器可以直接通过目标PULL数据或者间接地通过中间网关来Push数据。

● Prometheus在本地存储抓取的所有数据,并通过一定规则进行清理和整理数据,并把得到的结果存储到新的时间序列中。

● Prometheus通过PromQL和其他API可视化地展示收集的数据。Prometheus支持很多方式的图表可视化,例如Grafana、自带的Promdash以及自身提供的模版引擎等等。Prometheus还提供HTTP API的查询方式,自定义所需要的输出。

● PushGateway支持Client主动推送metrics到PushGateway,而Prometheus只是定时去Gateway上抓取数据。

● Alertmanager是独立于Prometheus的一个组件,可以支持Prometheus的查询语句,提供十分灵活的报警方式。

6部署

解压prometheus-2.17.2.linux-amd64.tar.gz 到指定文件夹,修改配置文件prometheus.yml,配置需要抓取监控数据的服务的地址。使用命令./prometheus --config.file=prometheus.yml  --web.listen-address=:9090启动prometheus。

7度量类型

7.1、Counter(计数器类型)

Counter类型的指标代表的是一种计数器,是随时间只增不减永远不会减少(除非系统或者服务发生了重置)的。Counter一般用于累计值,例如记录请求次数,任务完成数、错误发生次数;还可以计算其在一段时间范围内的增量和变化速率,如果是counter类型的数据,首先应该想到是否要使用rate()或者increase()函数来计算其变化速率。

不是Counter类型的度量却当做Counter类型来计算,会得到一个错误的结果。例如,使用计数器来计算当前正在运行的进程的数量;应该使用Gauge。

7.2、Gauge(仪表测量类型)

Gauge类型的指标值是可增可减的,可以用于反应当前应用的状态。比如在监控主机时,主机当前的内存大小(node_meomory_MemFree),可用内存大小(node_memory_MemAvailable)。或者主机CPU使用率,内存使用率,温度等。

7.3、Histogram(直方图类型)

Histogram是对数据进行采样的指标类型,用来展示数据集的频率分布。Histogram是表示数值分布的图形,它将数值分组到一个一个的bucket当中,然后计算每个bucket中值出现次数。在Histogram上,X轴表示表示数值的范围(例如人的身高/网站请求响应时间),Y轴表示对应数值出现的频次(对应身高/响应时间出现的次数)。在直方图上,对于各数值出现的次数,分布是否对称都显示的很清楚(对于这类数据如果只是简单的对数值取最小、最大或平均是没有多大意义的)。统计学上有一个段子是说:一个统计学家非常自信地去趟一条平均深度只有1米的河,后来他淹死了(类似把互联网大佬的身家和自己来平均一下)。这是取平均值的一个严重缺陷。

7.4、Summary(摘要类型)

Summary类型和Histogram类型相似,主要也用于表示一段时间内数据采样(通常是请求持续时间或响应时间)结果,它直接存储了quantile(分位数)数据,而不是根据统计区间计算出来的。

什么是分位数?大家可度娘一下。总之,分位数能更好地表示数值的分布,也可以找出异常数值,便于优化。

Summary与Histogram相比,区别如下:

都包含 < basename>_sum和< basename>_count;

Histogram需要通过< basename>_bucket计算quantile,而Summary直接存储了 quantile的值。

用例:

# 事件发生总的次数

# 事件产生的值的总和

# 事件产生的值的分布情况

8查询语法

常用表达式:fun(metric_name{Instant vector selectors}[Range Vector Selectors])

Prometheus提供了一种名为PromQL (Prometheus查询语言)的功能查询语言,该语言允许用户实时选择和聚合时间序列数据。查询的结果可以显示为图表,如在Prometheus本身内置的Web控制台展示,又或者使用诸如Grafana数据展示工具。

● 瞬时向量选择器(Instant vector selectors)可以即时为每个度量选择一个样本值(最近的一个值),最简单的形式就是只给定度量名称,这样将返回所有包含此度量名称的时间序列元素的瞬时向量。可以通过在度量名称后的大括号{}中附加以逗号分隔的标签匹配器列表来进一步筛选这些时间序列。

在PromQL中,使用以下符号对标签值进行正则匹配:

= (等于),标签的值必须相等,并且区分大小写。

!=(不等于),标签的值必须不相等,并且区分大小写。

=~(模糊匹配),标签的值正则(模糊)匹配。

!~(模糊匹配取反),标签的值正则(模糊)匹配后取反。

● 范围向量选择器(Range Vector Selectors)与瞬时向量类似,只是它从当前瞬间选择一个样本范围。从语法上讲,范围向量所持续的时间是放在瞬时向量选择器末尾的中括号[]中,用来获取指定的时间间隔内瞬时向量的所有值。

● 偏移修饰器(Offset modifier)

Offset 在瞬时/范围向量选择器中用于对过去一段时间的偏移计算,例如,计算5分钟前CPU的空闲率

avg(irate(node_cpu_seconds_total{nodename=~"monitor01", mode="idle"}[1m] offset 5m))

注意:offset 的使用范围是在:瞬时/范围向量选择器中

9常用函数

https://prometheus.io/docs/prometheus/latest/querying/functions/

● increase()函数,该函数结合counter数据类型使用,获取区间向量中的第一个和最后一个样本并返回其增长量。如果除以[区间]时间(秒)就可以获取该时间内的平均增长率。

# 获取近1分钟内网卡接收的字节数,如果不除以时间,则为区间内累计增量。

increase(node_network_receive_bytes_total{device=~"ens.*",nodename=~"monitor01"}[1m])

● rate()函数,该函数配置counter数据类型使用,用于获取在这个时间段内的平均每秒增量。

# 通过rate()函数获取在1分钟时间内网卡每秒接收字节数,如果再乘以区间时间,则同increase()函数。

rate(node_network_receive_bytes_total{device=~"ens.*",nodename=~"monitor01"}[1m])

以下查询结果同increase()函数。

rate(node_network_receive_bytes_total{device=~"ens.*",nodename=~"monitor01"}[1m]) * 60

● irate()函数,用于计算指定时间范围内每秒瞬时增长率,是基于该时间范围内最后两个数据点来计算。rate和irate函数都用于计算某个指标在一定时间间隔内的变化速率。但是它们的计算方法有所不同:irate取的是在指定时间范围内的最后两个数据点来算速率,而rate会取指定时间范围内所有数据点,算出一组速率,然后取平均值作为结果。

所以官网文档说:irate适合快速变化(fast-moving)的计数器(counter),而rate适合缓慢变化(slow-moving)的计数器(counter)。

● sum()函数,在实际工作中CPU大多是多核心,而node_cpu_seconds_total会将每个核的数据都单独显示出来,但我们关心的是CPU总的使用情况,因此可以使用sum()函数求和后得出一条总的数据,使用sum()函数获取实例在1分钟时间内,user在所有vCPU上的使用百分比之和

# sum(increase(node_cpu_seconds_total{nodename=~"monitor01",mode="user"}[1m])/60)

 

● count()函数,该函数用于进行统计,或用来做一些模糊判断,比如判断服务器连接数大于某个值,为真则返回1,否则返回null。

例如统计vCPU数

count(node_cpu_seconds_total{nodename="monitor01",mode="idle"})

或者统计当前TCP建立连接数是否大于200

count(node_netstat_Tcp_CurrEstab{nodename=~"monitor01"} >200 )

● topk()函数,该函数可以从大量数据中取出排行前N的数值,N可以自定义。

# 例如从所有主机中找出近5分钟网卡流量排名前3的主机(Counter类型数据)。

topk(3,rate(node_network_receive_bytes_total{device=~'ens.*'}[5m]))

或者用increase

topk(3,increase(node_network_receive_bytes_total{device=~'ens.*'}[5m])/300)

# 例如从所有主机中找出连接数前3的主机(Gauge类型数据)。

topk(3,node_netstat_Tcp_CurrEstab)  

● predict_linear()函数,根据前一个时间段的值来预测未来某个时间点数据的走势。例如,我们可以用predict_linear()函数,根据近1天的磁盘使用来预测磁盘在未来2天增长情况,大概在未来多长时间可以将磁盘占满。

predict_linear(node_filesystem_free_bytes{device="rootfs",nodename=~"monitor01",mountpoint="/"}[1d],2*86400)

 

 

 

Logo

K8S/Kubernetes社区为您提供最前沿的新闻资讯和知识内容

更多推荐