Prometheus
官网:https://prometheus.io/
Prometheus
的优点:
- 对
Kubernetes
支持得很好,目前来看,Prometheus
就是Kubernetes
监控的标配。 - 生态庞大,有各种各样的
Exporter
,支持各种各样的时序库作为后端的Backend
存储,也有很好的支持多种不同语言的SDK
,供业务代码嵌入埋点。
Prometheus
的缺点:
- 易用性差一些,比如告警策略需要修改配置文件,协同起来比较麻烦。当然了,对于 IaC 落地较好的公司,反而认为这样更好,不过在国内当下的环境来看,还无法走得这么靠前,大家还是更喜欢用 Web 界面来查看监控数据、管理告警规则。
Exporter
参差不齐,通常是一个监控目标一个Exporter
,管理起来成本比较高。- 容量问题,
Prometheus
默认只提供单机时序库,集群方案需要依赖其他的时序库。
1. 二进制安装
Prometheus
的下载地址:https://prometheus.io/download/
1.1 安装 Prometheus
mkdir -p /opt/prometheus
wget https://github.com/prometheus/prometheus/releases/download/v2.37.1/prometheus-2.37.1.linux-amd64.tar.gz
tar xf prometheus-2.37.1.linux-amd64.tar.gz
cp -far prometheus-2.37.1.linux-amd64/* /opt/prometheus/
# service
cat <<EOF >/etc/systemd/system/prometheus.service
[Unit]
Description="prometheus"
Documentation=https://prometheus.io/
After=network.target
[Service]
Type=simple
ExecStart=/opt/prometheus/prometheus --config.file=/opt/prometheus/prometheus.yml --storage.tsdb.path=/opt/prometheus/data --web.enable-lifecycle --enable-feature=remote-write-receiver --query.lookback-delta=2m --web.enable-admin-api
Restart=on-failure
SuccessExitStatus=0
LimitNOFILE=65536
StandardOutput=syslog
StandardError=syslog
SyslogIdentifier=prometheus
[Install]
WantedBy=multi-user.target
EOF
systemctl enable prometheus
systemctl start prometheus
systemctl status prometheus
ExecStart
启动命令参数含义如下:
--config.file=/opt/prometheus/prometheus.yml
指定 Prometheus 的配置文件路径
--storage.tsdb.path=/opt/prometheus/data
指定 Prometheus 时序数据的硬盘存储路径
--web.enable-lifecycle
启用生命周期管理相关的 API,比如调用 /-/reload 接口就需要启用该项
--enable-feature=remote-write-receiver
启用 remote write 接收数据的接口,启用该项之后,categraf、grafana-agent 等 agent 就可以通过 /api/v1/write 接口推送数据给 Prometheus
--query.lookback-delta=2m
即时查询在查询当前最新值的时候,只要发现这个参数指定的时间段内有数据,就取最新的那个点返回,这个时间段内没数据,就不返回了
--web.enable-admin-api
启用管理性 API,比如删除时间序列数据的 /api/v1/admin/tsdb/delete_series 接口
如果正常启动,Prometheus
默认会在 9090 端口监听,访问这个端口就可以看到 Prometheus
的 Web
页面。
Prometheus
在配置文件 prometheus.yml
里配置了抓取规则。
scrape_configs:
- job_name: 'prometheus'
static_configs:
- targets: ['localhost:9090']
localhost:9090
是暴露监控数据的地址,没有指定接口路径,默认使用 /metrics
,没有指定 scheme
,默认使用 HTTP
,所以实际请求的是 http://localhost:9090/metrics 。
1.2 安装 Node-Exporter
Prometheus
生态的机器监控比较简单,就是在所有的目标机器上部署 Node-Exporter
,然后在抓取规则中给出所有 Node-Exporter
的地址就可以了。
下载 https://prometheus.io/download/#node_exporter 下载之后解压就可以直接运行了,比如使用 nohup(生产环境建议使用 systemd 托管) 简单启动的话,可以输入下面这一行命令。
nohup ./node_exporter &> output.log &
Node-Exporter
默认的监听端口是 9100,我们可以通过下面的命令看到 Node-Exporter
采集的指标。
curl -s localhost:9100/metrics
然后把 Node-Exporter
的地址配置到 prometheus.yml
中即可。修改了配置之后,记得给 Prometheus
发个 HUP
信号,让 Prometheus
重新读取配置:kill -HUP
。最终 scrape_configs
部分变成下面这段内容。
scrape_configs:
- job_name: 'prometheus'
static_configs:
- targets: ['localhost:9090']
- job_name: 'node_exporter'
static_configs:
- targets: ['localhost:9100']
其中 targets
是个数组,如果要监控更多机器,就在 targets
中写上多个 Node-Exporter
的地址,用逗号隔开。之后在 Prometheus
的 Web
上(菜单位置 Status -> Targets),就可以看到相关的 Targets
信息了。
Node-Exporter
默认内置了很多 collector
,比如 cpu
、loadavg
、filesystem
等,可以通过命令行启动参数来控制这些 collector
,比如要关掉某个 collector
,使用 --no-collector
,如果要开启某个 collector
,使用 --collector
。具体可以参考 Node-Exporter
的 README。Node-Exporter
默认采集几百个指标,有了这些数据,我们就可以演示告警规则的配置了。
1.3 配置告警规则
Prometheus
进程内置了告警判断引擎,prometheus.yml
中可以指定告警规则配置文件,默认配置中有个例子。
rule_files:
# - "first_rules.yml"
# - "second_rules.yml"
我们可以把不同类型的告警规则拆分到不同的配置文件中,然后在 prometheus.yml
中引用。比如 Node-Exporter
相关的规则,我们命名为 node_exporter.yml
,最终这个 rule_files
就变成了如下配置。
rule_files:
- "node_exporter.yml"
我设计了一个例子,监控 Node-Exporter
挂掉以及内存使用率超过 1% 这两种情况。这里我故意设置了一个很小的阈值,确保能够触发告警。
groups:
- name: node_exporter
rules:
- alert: HostDown
expr: up{job="node_exporter"} == 0
for: 1m
labels:
severity: critical
annotations:
summary: Host down {{ $labels.instance }}
- alert: MemUtil
expr: 100 - node_memory_MemAvailable_bytes / node_memory_MemTotal_bytes * 100 > 1
for: 1m
labels:
severity: warn
annotations:
summary: Mem usage larger than 1%, instance:{{ $labels.instance }}
最后,给 Prometheus
进程发个 HUP
信号,让它重新加载配置文件。
kill -HUP `pid of prometheus`
之后,我们就可以去 Prometheus
的 Web
上(Alerts
菜单)查看告警规则的判定结果了。
我们从图中可以看出,告警分成 3 个状态,Inactive
、Pending
、Firing
。
HostDown
这个规则当前是 Inactive
状态,表示没有触发相关的告警事件,MemUtil
这个规则触发了一个事件,处于 Firing
状态。那什么是 Pending
状态呢?触发过阈值但是还没有满足持续时长( for 关键字后面指定的时间段)的要求,就是 Pending
状态。比如 for 1m
,就表示触发阈值的时间持续 1 分钟才算满足条件,如果规则判定执行频率是 10 秒,就相当于连续 6 次都触发阈值才可以。
如果我们还希望在告警的时候收到消息通知,比如邮件、短信等,就需要引入 AlertManager
组件了。
1.4 安装 Alertmanager
下载地址 https://prometheus.io/download/#alertmanager
alertmanager.service
内容
[Unit]
Description="alertmanager"
After=network.target
[Service]
Type=simple
ExecStart=/usr/local/alertmanager/alertmanager
WorkingDirectory=/usr/local/alertmanager
Restart=on-failure
SuccessExitStatus=0
LimitNOFILE=65536
StandardOutput=syslog
StandardError=syslog
SyslogIdentifier=alertmanager
[Install]
WantedBy=multi-user.target
把 Alertmanager
解压到 /usr/local/alertmanager
目录,通过 ExecStart
可以看出,直接执行二进制就可以,实际 Alertmanager
会读取二进制同级目录下的 alertmanager.yml
配置文件。我使用 163 邮箱作为 SMTP
发件服务器,下面我们来看下具体的配置。
alertmanager.yml
global:
smtp_from: 'username@163.com'
smtp_smarthost: 'smtp.163.com:465'
smtp_auth_username: 'username@163.com'
smtp_auth_password: '这里填写授权码'
smtp_require_tls: false
route:
group_by: ['alertname']
group_wait: 30s
group_interval: 1m
repeat_interval: 1h
receiver: 'email'
receivers:
- name: 'web.hook'
webhook_configs:
- url: 'http://127.0.0.1:5001/'
- name: 'email'
email_configs:
- to: 'ulricqin@163.com'
inhibit_rules:
- source_match:
severity: 'critical'
target_match:
severity: 'warning'
equal: ['alertname', 'dev', 'instance']
首先配置一个全局 SMTP,然后修改 receivers。receivers 是个数组,默认例子里有个 web.hook,我又加了一个 email 的 receiver,然后配置 route.receiver 字段的值为 email。email_configs 中的 to 表示收件人,多个人用逗号分隔,比如 to: ‘user1@163.com, user2@163.com’,最后收到的邮件内容大概是这样的,你可以看一下我给出的样例。
收到告警邮件,就说明这整个告警链路走通了。
1.5 安装 Grafana
Grafana
是一个数据可视化工具,有丰富的图表类型,视觉效果很棒,插件式架构,支持各种数据源,是开源监控数据可视化的标杆之作。Grafana
可以直接对接 Prometheus
。
它分为两个版本,企业版和开源版,开源版本遵照 AGPLV3
协议,只要不做二次开发商业化分发,是可以直接使用的。我这里就下载了开源版本,选择 tar.gz
包,下载之后解压缩,执行 ./bin/grafana-server
即可一键启动,Grafana
默认的监听端口是 3000,访问后就可以看到登录页面了,默认的用户名和密码都是 admin。
我们使用 Grafana
,主要是使用 Dashboard
看图。Grafana
社区有很多人制作了各式各样的大盘,以 JSON
格式上传保存在了 https://grafana.com/grafana/dashboards/,我们想要某个 Dashboard
,可以先去这个网站搜索一下,看看是否有人分享过,特别方便。因为我们已经部署了 Node-Exporter
,那这里就可以直接导入 Node-Exporter
的大盘,大盘 ID 是 1860,写到图中对应的位置,点击 Load
,然后选择数据源点击 Import
即可。
2. Docker 安装
参考:
Docker搭建Prometheus+grafana监控系统
prometheus监控gpu
networks:
monitor:
driver: bridge
services:
prometheus:
image: prom/prometheus
container_name: prometheus
hostname: prometheus
restart: always
volumes:
- /data/prometheus/data:/prometheus
- /data/prometheus/rules:/etc/prometheus/rules
- /data/prometheus/conf/prometheus.yml:/etc/prometheus/prometheus.yml
ports:
- "9090:9090"
networks:
- monitor
alertmanager:
image: prom/alertmanager
container_name: alertmanager
hostname: alertmanager
restart: always
volumes:
- /data/alertmanager/config/alertmanager.yml:/etc/alertmanager/alertmanager.yml
depends_on:
- prometheus
ports:
- "9093:9093"
networks:
- monitor
node-exporter:
image: quay.io/prometheus/node-exporter
container_name: node-exporter
hostname: node-exporter
restart: always
environment:
TZ: Asia/Shanghai
volumes:
depends_on:
- prometheus
ports:
- "9100:9100"
networks:
- monitor
grafana:
image: grafana/grafana
container_name: grafana
hostname: grafana
restart: always
volumes:
- /data/grafana/data:/var/lib/grafana
depends_on:
- prometheus
ports:
- "3000:3000"
networks:
- monitor
3. 系统架构
Pushgateway
:用于接收短生命周期任务的指标上报,是PUSH
的接收方式。因为Prometheus
主要是PULL
的方式拉取监控数据,这就要求在拉取的时刻,监控对象得活着,但是很多短周期任务,比如cronjob
,可能半秒就运行结束了,就没法拉取了。为了应对这种情况,才单独做了Pushgateway
组件作为整个生态的补充。Service discovery
:我们演示抓取数据时,是直接在prometheus.yml
中配置的多个Targets
。这种方式虽然简单直观,但是也有弊端,典型的问题就是如果Targets
是动态变化的,而且变化得比较频繁,那就会造成管理上的灾难。所以Prometheus
提供了多种服务发现机制,可以动态获取要监控的目标,比如Kubernetes
的服务发现,可以通过调用kube-apiserver
动态获取到需要监控的目标对象,大幅降低了抓取目标的管理成本。
Prometheus
主要使用拉模式获取指标,辅以推模式(Pushgateway
的职能)。很多监控系统都是推模式,比如 Datadog
、Open-Falcon
、Telegraf+InfluxDB
组合。推拉两种方式,在监控领域讨论也比较多,它们各有优缺点和适用场景。
所以结论就来了:中间件类使用拉模式,自研的服务使用推模式,自研的服务如果都接入了注册中心,则也可以使用拉模式。
当然,推拉的选择还有一个点比较关键,就是网络通路问题,特别是网络 ACL 限制比较严格的环境,很多都是可出不可进,比如典型的 NAT 出网,这种情况下推模式的适配性更好,也就是说对 ACL 更友好一些。另一个关键点是短周期任务或批处理任务,通常不太可能监听 HTTP 端口,这种大概率也是推模式。
最后就是可控性问题,拉模式,监控系统是主动的一方,可以控制频率;推模式,客户端是主动的一方,如果代码写“挫”了,就会给监控系统造成很大压力。前面我们提到拉模式需要有很好的服务发现机制,Prometheus 采取的就是拉模式,因此它对监控目标动态发现机制的苛求度很高。