Prometheus AlertManager 实战

2023年 5月 4日 51.1k 0

prometheus的兄弟alertmanager就是一个专门负责报警的组建,它独立于prometheus项目,自行运行并接收来自prometheus的请求,然后使用多种方式进行报警,之所以不是直接集成到prometheus中。本次prometheus和alertmanager采用pod configmap挂载的方式进行安装。
Prometheus AlertManager 实战
Prometheus

AlerManager 简介

Prometheus包含了一个报警模块,那就是AlertManager,主要用于接受Prometheus发送的告警信息,它支持丰富的告警通知渠道,而且很容易做到告警信息进行去重,降噪,分组等,是一个前卫的告警通知系统
prometheus-architecture.png-94.6kB

安装 AlerManager

prometheus配置文件官方文档
https://prometheus.io/docs/alerting/configuration/
首先,我们需要先指定配置文件 ,这里我们还是创建一个ConfigMap资源对象

cat >> prometheus-alert-conf.yaml <<EOF
apiVersion: v1
kind: ConfigMap
metadata:
  name: alert-config
  namespace: kube-system
data:
  config.yml: |-
    global:
      # 在没有报警的情况下声明为已解决的时间
      resolve_timeout: 5m
      # 配置邮件发送信息
      smtp_smarthost: 'smtp.163.com:465'
      smtp_from: 'xxx@163.com'
      smtp_auth_username: 'xxx@163.com'
      smtp_auth_password: '授权密码'
      smtp_hello: '163.com'
      smtp_require_tls: false
    # 所有报警信息进入后的根路由,用来设置报警的分发策略
    route:
      # 这里的标签列表是接收到报警信息后的重新分组标签,例如,接收到的报警信息里面有许多具有 cluster=A 和 alertname=LatncyHigh 这样的标签的报警信息将会批量被聚合到一个分组里面
      group_by: ['alertname', 'cluster']
      # 当一个新的报警分组被创建后,需要等待至少group_wait时间来初始化通知,这种方式可以确保您能有足够的时间为同一分组来获取多个警报,然后一起触发这个报警信息。
      group_wait: 30s

      # 当第一个报警发送后,等待'group_interval'时间来发送新的一组报警信息。
      group_interval: 5m

      # 如果一个报警信息已经发送成功了,等待'repeat_interval'时间来重新发送他们
      repeat_interval: 5m

      # 默认的receiver:如果一个报警没有被一个route匹配,则发送给默认的接收器
      receiver: default

      # 上面所有的属性都由所有子路由继承,并且可以在每个子路由上进行覆盖。
      routes:
      - receiver: email
        group_wait: 10s
        match:
          team: node
    receivers:
    - name: 'default'
      email_configs:
      - to: '604419314@qq.com'
        send_resolved: true
    - name: 'email'
      email_configs:
      - to: '604419314@qq.com'
        send_resolved: true
EOF

授权密码申请,这里以163邮箱为例
image_1dfb0mbpms4ekj2k8i7mjjb5p.png-445.2kB
我们现在创建alertmanager的配置文件

[root@abcdocker prometheus]# kubectl create -f prometheus-alert-conf.yaml
configmap/alert-config created

[root@yzsjhl82-138 prometheus]# kubectl get cm -n kube-system
NAME                                 DATA   AGE
alert-config                         1      25s
coredns                              1      40d
extension-apiserver-authentication   6      40d
grafana-config                       1      20h
kube-flannel-cfg                     2      40d
kubernetes-dashboard-settings        1      40d
prometheus-config                    1      23m

#这里已经显示我们创建好的alert-config

现在我们在之前的prometheus pod的yaml文件中添加这个容器
这里我们将上面创建的aler-config这个configmap资源对象volume的形式挂载到/etc/alertmanager目录下去,然后在启动参数中指定--config.file=/etc/alertmanager/config.yml

      - name: alermanager
        image: prom/alertmanager:v0.15.3
        imagePullPolicy: IfNotPresent
        args:
        - "--config.file=/etc/alertmanager/config.yml"
        - "--storage.path=/alertmanager/data"
        ports:
        - containerPort: 9093
          name: http
        volumeMounts:
        - mountPath: "/etc/alertmanager"
          name: alertcfg
        resources:
          requests:
            cpu: 100m
            memory: 256Mi
          limits:
            cpu: 200m
            memory: 1024Mi
  ...
      - name: alertcfg
        configMap:
          name: alert-config

在0.15版本,alertmanager的WORKDIR发生了变化,变成/etc/alertmanager默认情况下存储路径--storage.path是相对目录data/,因此alertmanager会在我们上面挂载的ConfigMap中去创建这个目录,所以会报错,这里通过--storage.path参数来解决

#更新deployment
[root@abcdocker prometheus]# kubectl apply -f  prometheus.deploy.yaml
deployment.extensions/prometheus configured

如果不会修改yaml可以直接使用我的yaml文件

apiVersion: extensions/v1beta1
kind: Deployment
metadata:
  name: prometheus
  namespace: kube-system
  labels:
    app: prometheus
spec:
  template:
    metadata:
      labels:
        app: prometheus
    spec:
      serviceAccountName: prometheus
      containers:
      - image: prom/prometheus:v2.4.3
        name: prometheus
        command:
        - "/bin/prometheus"
        args:
        - "--config.file=/etc/prometheus/prometheus.yml"
        - "--storage.tsdb.path=/prometheus"
        - "--storage.tsdb.retention=7d"
        - "--web.enable-admin-api"  # 控制对admin HTTP API的访问,其中包括删除时间序列等功能
        - "--web.enable-lifecycle"  # 支持热更新,直接执行localhost:9090/-/reload立即生效
        ports:
        - containerPort: 9090
          protocol: TCP
          name: http
        volumeMounts:
        - mountPath: "/prometheus"
          subPath: prometheus
          name: data
        - mountPath: "/etc/prometheus"
          name: config-volume
        resources:
          requests:
            cpu: 400m
            memory: 100Mi
          limits:
            cpu: 400m
            memory: 2Gi
      - name: alermanager
        image: prom/alertmanager:v0.15.3
        imagePullPolicy: IfNotPresent
        args:
        - "--config.file=/etc/alertmanager/config.yml"
        - "--storage.path=/alertmanager/data"
        ports:
        - containerPort: 9093
          name: http
        volumeMounts:
        - mountPath: "/etc/alertmanager"
          name: alertcfg
        resources:
          requests:
            cpu: 100m
            memory: 256Mi
          limits:
            cpu: 200m
            memory: 1024Mi
      securityContext:
        runAsUser: 0
      volumes:
      - name: data
        persistentVolumeClaim:
          claimName: prometheus
      - configMap:
          name: prometheus-config
        name: config-volume
      - name: alertcfg
        configMap:
          name: alert-config

查看一下pod启动状态

[root@abcdocker prometheus]# kubectl get pod -n kube-system |grep prometheus
prometheus-5486fc867b-cb7z6             2/2     Running     0          2m20s

AlertManager容器启动之后,我们还需要在Prometheus中配置下AlertManager的地址,让Prometheus能够访问AlertManager

    alerting:
      alertmanagers:
        - static_configs:
          - targets: ["localhost:9093"]

配置截图
333.png-221.1kB
接下来更新一下Prometheus配置文件

[root@abcdocker prometheus]# kubectl delete -f prometheus.configmap.yaml
configmap "prometheus-config" deleted

[root@abcdocker prometheus]# kubectl create -f prometheus.configmap.yaml
configmap/prometheus-config created

[root@abcdocker prometheus]# curl -X POST http://10.101.143.162:9090/-/reload
#确保更新配置没有报错(刷新比较慢可以等等)

现在prometheus alertmanager并没有告警的规则,还需要我们添加报警规则

Prometheus 报警规则

上面我们将prometheus和alertmanager进行了关联,但是现在并没有报警规则,所以这里还需要配置一些报警规则。让prometheus触发报警

#首先在prometheus.configmap.yaml文件中添加报警规则,下面的文件就是prometheus报警的规则文件
    rule_files:
    - /etc/prometheus/rules.yml

22.png-139.5kB
报警规则允许基于Prometheus表达式语言来定义报警规则条件,并在出发报警时发送给外部
我们上面已经将/etc/promtehus进行挂载了,所以这里只需要修改prometheus-configmap就可以了。

  rules.yml: |
    groups:
    - name: abcdocker-test-rule
      rules:
      - alert: NodeMemoryUsage
        expr: (node_memory_MemTotal_bytes - (node_memory_MemFree_bytes+node_memory_Buffers_bytes + node_memory_Cached_bytes)) / node_memory_MemTotal_bytes * 100 > 50
        for: 1m
        labels:
          team: node
        annotations:
          summary: "{{ $labels.instance }}:High Memory Usage detected"
          description: "{{ $labels.instance }}: Memory usage us avive 50% (current value is :: {{ $value }})"



#配置相关参数说明
  rules.yml: |
    groups:
    - name: abcdocker-test-rule
      rules:  #规则
      - alert: NodeMemoryUsage #报警名称(内存报警)
        expr: (node_memory_MemTotal_bytes - (node_memory_MemFree_bytes + node_memory_Buffers_bytes + node_memory_Cached_bytes)) / node_memory_MemTotal_bytes * 100 > 50 #规则表达式
        for: 1m  #等待1分钟执行查询条件
        labels:
          team: node   #当我们触发报警后,带有team=node的标签,并且这里走的是我们alertmanager node标签,这里对应的就是我们的email接收器
        annotations:  #指定另外一组标签,不会将这个标签当做我们告警的身份标示(不会在我们报警信息里操作)这里主要是用于额外的展示,例如发送给邮件里面>的报警信息
          summary: "{{ $labels.instance }}:High Memory Usage detected"   #label标签,instance代表节点名称
          description: "{{ $labels.instance }}: Memory usage us avive 50% (current value is :: {{ $value }})" #描述:相当于报警信息 $value代表当前值

说明一点expr所执行的命令是可以在prometheus上获取到数据的
配置截图
image_1demkqmb81ul89i78bof0nqs54a.png-175.1kB
完整配置如下

[root@yzsjhl82-135 prometheus]# cat prometheus.configmap.yaml
apiVersion: v1
kind: ConfigMap
metadata:
  name: prometheus-config
  namespace: kube-system
data:
  prometheus.yml: |
    global:
      scrape_interval: 15s
      scrape_timeout: 15s
    alerting:
      alertmanagers:
        - static_configs:
          - targets: ["localhost:9093"]
    rule_files:
    - /etc/prometheus/rules.yml
    scrape_configs:
    - job_name: 'prometheus'
      static_configs:
      - targets: ['localhost:9090']
    - job_name: 'kubernetes-node'
      kubernetes_sd_configs:
      - role: node
      relabel_configs:
      - source_labels: [__address__]
        regex: '(.*):10250'
        replacement: '${1}:9100'
        target_label: __address__
        action: replace
    - job_name: 'kubernetes-cadvisor'
      kubernetes_sd_configs:
      - role: node
      scheme: https
      tls_config:
        ca_file: /var/run/secrets/kubernetes.io/serviceaccount/ca.crt
      bearer_token_file: /var/run/secrets/kubernetes.io/serviceaccount/token
      relabel_configs:
      - action: labelmap
        regex: __meta_kubernetes_node_label_(.+)
      - target_label: __address__
        replacement: kubernetes.default.svc:443
      - source_labels: [__meta_kubernetes_node_name]
        regex: (.+)
        target_label: __metrics_path__
        replacement: /api/v1/nodes/${1}/proxy/metrics/cadvisor

  rules.yml: |
    groups:
    - name: abcdocker-test-rule
      rules:
      - alert: NodeMemoryUsage
        expr: (node_memory_MemTotal_bytes - (node_memory_MemFree_bytes+node_memory_Buffers_bytes + node_memory_Cached_bytes)) / node_memory_MemTotal_bytes * 100 > 20
        for: 1m
        labels:
          team: node
        annotations:
          summary: "{{ $labels.instance }}:High Memory Usage detected"
          description: "{{ $labels.instance }}: Memory usage us avive 50% (current value is :: {{ $value }})"

报警说明
本次报警大概意思是当服务器内存百分比大于80的时候,就进行报警,并且通过labels标签关联team:node (这里team=node是在我们alertmanager里面配置的接收器,默认是default),并且报警内容添加主机和当前内存使用率
接下来我们访问prometheus,点击alerts,就可以看到我们添加的NodeMemoryUsage
我这里将脚本改成>50
image_1demkpnda19d7osa1tac143n9oc3t.png-116.4kB
等待1分钟后
prometheus进入了等待PENDING状态
image_1deobr2fibqq1uon10amn081no457.png-265.2kB
当前值已经大于我们设置的50%,现在已经出发报警
image_1deobt30u1kig1cp8qrp1etm12e55k.png-180.8kB
邮件内容如下
image_1deocf7s415ujfic1djdgfp189d61.png-158.2kB

alertManager Ui界面

我们可以在邮件内容中看到包含View in AlertManager的链接,这是alertmanager自带的Ui界面。我们可以使用NodePort进行访问
这里需要修改一下prometheus的service

cat >>prometeheus-svc.yaml <<EOF
apiVersion: v1
kind: Service
metadata:
  name: prometheus
  namespace: kube-system
  labels:
    app: prometheus
spec:
  selector:
    app: prometheus
  type: NodePort
  ports:
    - name: web
      port: 9090
      targetPort: http
    - name: alertmanager
      port: 9093
      targetPort: 9093
EOF

如果前面也是按照我的文档操作的,可以在prometheus后面添加一个svc端口接口

    - name: alertmanager
      port: 9093
      targetPort: 9093

我们查看一下node-port端口

[root@abcdocker prometheus]# kubectl get svc -n kube-system |grep prometheus
prometheus             NodePort    10.96.163.206            9090:32567/TCP,9093:31212/TCP   73s

访问alertmanager端口为9093=31212 (集群任一节点访问即可)
image_1deouu439g621t271e609dk17hb6u.png-217.9kB
在上面的图片,我们可以看到IP为82.139一直在报警,如果不想接收这个IP报警。可以点击Slience
image_1deova3411hbn1ms5bf77t7k327b.png-122.6kB
注意Prometheus有8小时时区问题
这时候报警匹配为82.139的IP,在2个小时内。不进行报警,我们点击创建就可以。在Comment输入提交内容就可以了
image_1deovl01017ou1gqf1u15egek5n85.png-95.7kB
这里可以直接编辑,或者直接让它过期
image_1deovm0b3riqf5l1ch11pqebnj8i.png-128kB
这里我们已经看不到报警内容了
image_1dep1b3s61b2ls6pl71r6d59u8v.png-40.7kB
点击Silences可以看到被禁用的监控
image_1dep1bh4bdfiqbn1qfo1f00jmc9c.png-51.9kB

相关文章:

  1. Kubernetes 1.14 二进制集群安装
  2. Kubenetes 1.13.5 集群二进制安装
  3. Kuerbernetes 1.11 集群二进制安装
  4. Prometheus Operator 监控k8s组件

相关文章

对接alertmanager创建钉钉卡片(1)
手把手教你搭建OpenFalcon监控系统
无需任何魔法即可使用 Ansible 的神奇变量“hostvars”
openobseve HA本地单集群模式
基于k8s上loggie/vector/openobserve日志收集
openobseve单节点和查询语法

发布评论