Prometheus-alertmanager组件使用

警报管理

Alertmanager工作过程

​ Alertmanager处理从客户端(通常是Prometheus服务器或其它工具的警报)发来的警报,然后Alertmanager对警报进行去重、分组,然后路由到不同的接收器,如电子邮件、短信或SaaS服务(PagerDuty等)。还可以使用Alertmanager管理维护警报。

image-20200808081048992

  • 先在Prometheus服务器上编写警报规则,这些规则将使用(exporter)收集的指标并在指定的阈值或标准上触发警报。当指标达到阈值或标准时,生成一个警报并将其推送到alertmanger。告警在Alertmanger上的HTTP端点上接收。
  • 收到警报后,alertmanager会处理警报并根据其标签进行路由。一旦路径确定,他们将由Alertmanager发送到外部目的地。如电子邮件、短信等工具。

alertmanager安装配置

详见文档

配置alertmanager

Alertmanager配置也是基于YAML的配置文件,主要由global,route,receivers这三部分组成。

简单样例(alertmanager.yml)

通过电子邮件发送任何收到的警报到另一个邮箱地址。

global:
  smtp_from: 'localhost:25'
  smtp_smarthost: 'alertmanager@example.com'
  smtp_require_tls: false

route:
  receiver: 'email'

receivers:
-name: 'email'
  email_configs:
  - to: 'alerts@example.com'

templates:
- '/ups/app/monitor/alertmanager/template/*.tmpl'
  • global: 全局配置,为其它块设置默认值
  • template: 包含保存警报模板的目录列表。由于alertmanager可以发送到各种目的地,因此需要能够自定义警报的外观及其包含的数据
  • route: 它告知alertmanager如何处理特定的传入警报。警报根据规则进行匹配然后采取相应的操作。
  • receivers(接收器):指定警报的目的地。每个接收器都有一个名称和相关配置

在Prometheus中配置alertmanager

在Prometheus中配置,告诉Prometheus关于Alertmanager的信息。在alerting块中配置alertmanger相关信息。

# Alertmanager configuration
alerting:
  alertmanagers:
  - static_configs:
    - targets:
      - progs:9093  # 对应启动的altermanager节点的9093端口

​ alerting块包含允许Prometheus识别一个或多个Alertmanager的配置。为此,Prometheus使用与查找抓取目标时相同的发现机制,在默认配置中是static_configs。与监控作业一样,它指定目标列表,此处是主机名progs加端口9093(Alertmanager默认端口)的形式。该列表假定你的Prometheus服务器可以解析progs主机名为IP地址,并且Alertmanager在该主机的端口9093上运行。

监控alertmanager

Alertmanager可以暴露了自身的相关指标作为被监控对象。创建一个作业来监控alertmanager

  - job_name: 'alertmanager'
    static_configs:
    - targets: ['localhost:9093']

​ 这将从http://localhost:9093/metrics收集指标并抓取一系列以alertmanager_为前缀的时间序列数据。这些数据包括按状态分类的警报计数、按接收器分类的成功和失败通知的计数、还可以包含Alertmanager集群状态指标。

image-20200808090452828

添加警报规则

与记录规则一样,警报规则也是在Prometheus服务器中配置加载的规则文件(使用YAML语句定义)。现在rules目录中创建一个新文件node_alerts.yml,以保存节点警报规则为例子进行说明。

在prometheus.yml配置文件中的rule_files块配置加载的规则文件
# Load rules once and periodically evaluate them according to the global 'evaluation_interval'.
rule_files:
  - "rules/*_rules.yml"
  - "rules/*_alerts.yml"

当前使用通配符加载该目录中以_rules.yml_alerts.yml结尾的所有文件。

添加警报规则

vi rules/node_alerts.yml

groups:
- name: node_alerts
  rules:
  - alert: InstanceDown
    expr: up{job="node_exporter"} == 0
    for: 10s
    labels:
      severity: critical
    annotations:
      summary: Host {{ $labels.instance }} is down!
  • 上面指定一个组名为node_alerts的警报规则,该组中的规则包含在rules的块中。

  • 每个规则通过alert子句指定它的名称,并且每个警报组中的警报名称必须唯一。

  • 触发警报表达式使用expr子句指定。

  • for子句控制在触发警报之前必须为true的时间长度。在这个示例中,指标up{job="node_exporter"}需要在触发警报之前的10秒中内等于0.这限制了警报误报或暂时状态的可能。

  • 使用标签(labels)装饰警报,指定要附加到警报的其它标签,这里添加了一个值为critical的severity的标签。警报上的标签与警报的名称组合构成警报的标识

  • 注解(annotations)装饰警报,用于展现更多的信息的标签,如描述、处理说明等。这里添加一个名为summary的标签来描述警报

重启Prometheus服务启用新的警报规则

打开web界面查看http://progs:9090/alerts

image-20200808093602083

警报触发

Prometheus以固定时间间隔(由参数evaluation_interval控制)评估所有的规则。默认值1分钟。在每个评估周期内,Prometheus运行每个警报规则中定义的表达式并更新警报状态。

警报状态
  • Inactive:警报未激活
  • Pending:警报已满足测试表达式条件,但仍在等待for子句指定的持续时间
  • Firing:警报已满足测试表达式条件,并且Pending的时间已超过for子句的持续时间

image-20200808102616600

Pending到Firing的转换可以确保警报更有效,且不会来回浮动。没有for子句的警报会自动从Inactive转换为Firing,只需要一个评估周期(evaluation_interval)即可触发。带有for子句的警报将首先转换为Pending,然后转换为Firing,因此至少需要两个评估周期才能触发。

警报的生命周期
  • 节点的可能不断变化,每隔一段由scrape_interval定义的时间被Prometheus抓取一次,对我们来说是15秒。
  • 根据每个evaluation_interval的指标来评估警报规则,对我们来说还是15秒。
  • 当警报表达式为true时(对于上面示例来说节点发生down),会创建一个警报并转换到Pending状态,执行for子句。
  • 在下一个评估周期中,如果警报测试表达式仍然为true,则检查for的持续时间。如果超过了持续时间,则警报将转换为Firing,生成通知并将其推送到Alertmanager。
  • 如果警报测试表达式不再为true,则Prometheus会将警报规则的状态从Pending更改为Inactive。
alertmanager的警报

通过http://progs:9090/alerts Web界面查看警报及其状态

image-20200808102928203

image-20200808104017188

处于Firing状态的警报已经推送到alertmanager,可以在alertmanager API(http://progs:9093/api/v1/alerts)查看

image-20200808105028055

[root@progs config]# curl http://progs:9093/api/v1/alerts| python -m json.tool
  % Total    % Received % Xferd  Average Speed   Time    Time     Time  Current
                                 Dload  Upload   Total   Spent    Left  Speed
100  1004  100  1004    0     0   172k      0 --:--:-- --:--:-- --:--:--  196k
{
    "data": [
        {
            "annotations": {
                "summary": "Host 192.168.10.181:9100 is down!"
            },
            "endsAt": "2020-08-08T02:37:48.046283806Z",
            "fingerprint": "2c28fee95b3f434c",
            "generatorURL": "http://progs:9090/graph?g0.expr=up%7Bjob%3D%22node_exporter%22%7D+%3D%3D+0&g0.tab=1",
            "labels": {
                "alertname": "InstanceDown",
                "hostname": "192.168.10.181",
                "instance": "192.168.10.181:9100",
                "job": "node_exporter",
                "severity": "critical"
            },
            "receivers": [
                "wechat"
            ],
            "startsAt": "2020-08-08T02:28:48.046283806Z",
            "status": {
                "inhibitedBy": [],
                "silencedBy": [],
                "state": "active"
            }
        },
        {
            "annotations": {
                "summary": "Host  is down!"
            },
            "endsAt": "2020-08-08T02:37:48.046283806Z",
            "fingerprint": "550e18fea3ef4d3d",
            "generatorURL": "http://progs:9090/graph?g0.expr=avg+by%28job%29+%28up%7Bjob%3D%22node_exporter%22%7D%29+%3C+0.75&g0.tab=1",
            "labels": {
                "alertname": "InstancesDown",
                "job": "node_exporter",
                "severity": "critical"
            },
            "receivers": [
                "wechat"
            ],
            "startsAt": "2020-08-08T02:28:48.046283806Z",
            "status": {
                "inhibitedBy": [],
                "silencedBy": [],
                "state": "active"
            }
        }
    ],
    "status": "success"
}
[root@progs config]# 

Prometheus为Pending和Firing状态中的每个警报创建指标(ALERT),如下:

image-20200808104820765

image-20200808104645101

添加模板

模板(template)是一种在警报中使用时间序列数据的标签和值的方法,可用于注解和标签。模板使用标准的Go模板语法,并暴露一些包含时间序列的标签和值的变量。标签以变量$labels形式表示,指标的值则是变量$value。

引用时间序列的值
  • summary注解中引用instance标签,使用{{$labels.instance}}
  • 引用时间序列的值,使用{{$value}}
  • 使用humanize函数,它使用指标前缀将数字转换为更易于阅读的形式

image-20200808110222171

路由

将不同属性的警报路由到不同的目的地。默认使用后序遍历路由

下面在alertmanager.yml文件中添加一些路由配置

global:
  smtp_from: 'localhost:25'
  smtp_smarthost: 'alertmanager@example.com'
  smtp_require_tls: false

route:
  group_by: ['instance']
  group_wait: 30s
  
  group_interval: 5m
  repeat_interval: 3h
  receiver: 'email'
  routes:
  - match:
      severity: critical
    receiver: pager
  - match_re:
      severity: ^(warning|critical)$
    receiver: support_team

receivers:
- name: 'email'
  email_configs:
  - to: 'alerts@example.com'
- name: 'support_team'
  email_configs:
  - to: 'support@example.com'
- name: 'pager'
  email_configs:
  - to: 'pager@example.com'

templates:
- '/ups/app/monitor/alertmanager/template/*.tmpl'
  • group_by: 控制Alertmanager分组警报的方式。默认所有警报分成一组
    • 示例指定标签instance对警报分组,意味着来自特定实例的所有警报分在一起
    • 分组会改变alertmanager的处理行为,当触发新警报时,等待group_wait中指定时间段,以便在触发警报之前是否收到改组的其它警报
  • group_interval:在发出警报后,如果收到该分组的下一次评估新警报,alertmanager等待group_interval指定的时间段,再发送新警报。防止警报分组的警报泛滥
  • repeat_interval:仅作用于单个警报,等待重新发送相同警报的时间段。不适用警报组
路由表

routes子句列出分支路由。通过标签匹配或正则表达式匹配将警报发送到指定的目的地。路由都是分支,可以继续设置分支路由。

标签匹配
  - match:
      severity: critical
    receiver: pager

将所有severity标签与critical值匹配,并将它们发送到pager接收器。

路由分支

新routes块嵌套已有的routes块中。

  routes:
  - match:
      severity: critical
    receiver: pager
    routes:
      - match:
        service: application
      receiver: support_team

当新警报severity标签为critical且service标签application都成功匹配时,将警报发送到接收器support_team。

正则表达式匹配
  - match_re:
      severity: ^(warning|critical)$
    receiver: support_team

它匹配severity标签中的warning或critical值。

路由遍历顺序

默认使用后序遍历路由,可以使用continue选项控制路由遍历顺序,该选项控制警报是否先序遍历路由,然后再返回已遍历路由树。continue默认选项为false,即后序遍历路由树。

延申知识点
  • 前序遍历(先序):前序遍历可以记为根左右,若二叉树为空,则结束返回。
  • 后序遍历:后序遍历可以记为左右根,也就是说在二叉树的遍历过程中,首先按照后序遍历的规则遍历左子树,接着按照后序遍历的规则遍历右子树,最后访问根节点。若二叉树为空,则结束返回。
  routes:
  - match:
      severity: critical
    receiver: pager
    continue: true

continue: true时,则警报将在此路由中触发(如果匹配),并继续执行下一个相邻路由。

接收器

指定接收警报的目的地。

receivers:
- name: 'pager'
  email_configs:
  - to: 'pager@example.com'
  slack_configs:
  - api_url: https://hooks.slack.com/service/ABC123/ABC123/EXAMPLE
    channel: '#monitoring'

添加Slack接收器,它会消息发送到Slack实例。示例中任何向pager接收器发送警报的路由都将被发送到Slack的#monitoring频道,并通过电子邮件发送到pager@example.com。

通知模板

使用Go template函数来引用外部模板,从而避免在配置文件中嵌入较长且复杂的字符串。

创建模板文件
cat > /ups/app/monitor/alertmanager/template/slack.tmpl <<-EOF
{{ define "slack.example.text" }}{{ .CommonAnnotations.summary }}{{ end}}
EOF

使用define函数定义了一个新模板,以end结尾,并取名为slack.example.text,然后在模板内的text中复制内容。

引用模板
  slack_configs:
  - api_url: https://hooks.slack.com/service/ABC123/ABC123/EXAMPLE
    channel: '#monitoring'
    text: '{{ template "slack.example.text" . }}'

使用了template选项来指定模板的名称。使用模板通知来填充text字段。

silence和维护

silence: 警报静音。当明确知道停止服务以进行维护作业时,并不希望触发警报。这种场景需要用到silence,设定特定时间段内屏蔽触发警报规则。

设置silence的方法

  • alertmanager Web控制台
  • amtool命令行工具

silence配置过程

alertmanager Web控制台设置silence
新建silence

image-20200809112318316

配置相关属性

image-20200809112419980

image-20200809114455169

amtool工具设置silence
用法
usage: amtool [<flags>] <command> [<args> ...]

View and modify the current Alertmanager state.

Config File: The alertmanager tool will read a config file in YAML format from one of two default config locations:
$HOME/.config/amtool/config.yml or /etc/amtool/config.yml

All flags can be given in the config file, but the following are the suited for static configuration:

  alertmanager.url
  	Set a default alertmanager url for each request

  author
  	Set a default author value for new silences. If this argument is not
  	specified then the username will be used

  require-comment
  	Bool, whether to require a comment on silence creation. Defaults to true

  output
  	Set a default output type. Options are (simple, extended, json)

  date.format
  	Sets the output format for dates. Defaults to "2006-01-02 15:04:05 MST"

Flags:
  -h, --help           Show context-sensitive help (also try --help-long and --help-man).
      --date.format="2006-01-02 15:04:05 MST"  
                       Format of date output
  -v, --verbose        Verbose running information
      --alertmanager.url=ALERTMANAGER.URL  
                       Alertmanager to talk to
  -o, --output=simple  Output formatter (simple, extended, json)
      --timeout=30s    Timeout for the executed command
      --version        Show application version.

Commands:
  help [<command>...]
  alert
    query* [<flags>] [<matcher-groups>...]
    add [<flags>] [<labels>...]
  silence
    add [<flags>] [<matcher-groups>...]
    expire [<silence-ids>...]
    import [<flags>] [<input-file>]
    query* [<flags>] [<matcher-groups>...]
    update [<flags>] [<update-ids>...]
  check-config [<check-files>...]
  cluster
    show*
  config
    show*
    routes [<flags>]
      show*
      test [<flags>] [<labels>...]

amtool配置文件

默认配置文件路径``$HOME/.config/amtool/config.ymlor/etc/amtool/config.yml`

# Define the path that `amtool` can find your `alertmanager` instance
alertmanager.url: "http://progs:9093"

# Override the default author. (unset defaults to your username)
author: me@example.com

# Force amtool to give you an error if you don't include a comment on a silence
comment_required: true
comment: default

# Set a default output format. (unset defaults to simple)
output: extended
新建silence

将在Alertmanager的http://progs:9093上添加一个新silence,它将警报与两个标签匹配:自动填充包含警报名称的alertname标签和service标签。并返回一个silence ID

/ups/app/monitor/alertmanager/bin/amtool --comment=testing --alertmanager.url=http://progs:9093 silence add alertname=InstancesGone service=application
  • 使用默认config.yml文件添加silence
/ups/app/monitor/alertmanager/bin/amtool silence add alertname=InstancesGone 
查询当前的silence列表
/ups/app/monitor/alertmanager/bin/amtool --alertmanager.url=http://progs:9093 silence query

image-20200809114529636

posted @ 2020-08-09 19:38  KuBee  阅读(1976)  评论(0编辑  收藏  举报