使用Prometheus监控自定义指标
在使用AOM监控自定义指标中介绍了AOM ICAgent获取负载自定义指标监控数据的方法。您也可以直接在集群中安装Prometheus插件,直接使用Prometheus作为监控平台。
本文将通过一个Nginx应用的示例演示如何使用Prometheus监控自定义指标,步骤如下:
- 安装Prometheus插件
CCE提供了集成Prometheus功能的插件,支持一键安装。
- 访问Prometheus
(可选)为Prometheus绑定LoadBalancer类型的Service,支持从外部访问Prometheus。
- 准备应用
您需要准备一个应用镜像,该应用需要提供监控指标接口供ICAgent采集,且监控数据需要满足Prometheus的规范。
- 监控自定义指标
在集群中使用该应用镜像部署工作负载,将自动上报自定义监控指标至Prometheus。
- 配置自定义指标的采集规则
配置采集规则后,自定义指标会上报至集群metric-server,可用于工作负载弹性伸缩等场景。
- 访问Grafana
从Grafana可视化面板中查看Prometheus的监控数据。
约束与限制
使用Prometheus监控自定义指标时,应用程序需要提供监控指标接口,详情请参见Prometheus监控数据采集说明。
Prometheus监控数据采集说明
Prometheus通过周期性的调用应用程序的监控指标接口(默认为“/metrics”)获取监控数据,应用程序需要提供监控指标接口供Prometheus调用,且监控数据需要满足Prometheus的规范,如下所示。
# TYPE nginx_connections_active gauge nginx_connections_active 2 # TYPE nginx_connections_reading gauge nginx_connections_reading 0
Prometheus提供了各种语言的客户端,客户端具体请参见Prometheus CLIENT LIBRARIES,开发Exporter具体方法请参见WRITING EXPORTERS。Prometheus社区提供丰富的第三方exporter可以直接使用,具体请参见EXPORTERS AND INTEGRATIONS。
访问Prometheus
Prometheus插件安装完成后会在集群中部署一系列工作负载和Service。其中名为prometheus的有状态负载就是Prometheus Server。
您可以创建一个公网LoadBalancer类型Service,这样就可以从外部访问Prometheus。
- 登录CCE控制台,选择一个已安装Prometheus插件的集群,在左侧导航栏中选择“服务发现”。
- 单击右上角“YAML创建”,创建一个公网LoadBalancer类型Service。
apiVersion: v1 kind: Service metadata: name: prom-lb #服务名称,可自定义 namespace: monitoring labels: app: prometheus component: server annotations: kubernetes.io/elb.id: 038ff*** #请替换为集群所在VPC下的ELB实例ID,且ELB实例为公网访问类型 spec: ports: - name: cce-service-0 protocol: TCP port: 88 #服务端口号,可自定义 targetPort: 9090 #Prometheus的默认端口号,无需更改 selector: app: prometheus component: server release: cceaddon-prometheus type: LoadBalancer
- 创建完成后在浏览器访问“负载均衡公网IP地址:服务端口”,访问Prometheus。
- 单击“Status > Targets”,可以查看到Prometheus监控了哪些目标。
准备应用
自行开发的应用程序需要提供监控指标接口供ICAgent采集,且监控数据需要满足Prometheus的规范,详情请参见Prometheus监控数据采集说明。
本文以Nginx为例采集监控数据,Nginx本身有个名叫ngx_http_stub_status_module的模块,这个模块提供了基本的监控功能,通过在nginx.conf的配置可以提供一个对外访问Nginx监控数据的接口。
- 登录一台可连接公网的Linux虚拟机,且要求可执行Docker命令。
- 创建一个nginx.conf文件,如下所示,在http下添加server配置即可让nginx提供对外访问的监控数据的接口。
user nginx; worker_processes auto; error_log /var/log/nginx/error.log warn; pid /var/run/nginx.pid; events { worker_connections 1024; } http { include /etc/nginx/mime.types; default_type application/octet-stream; log_format main '$remote_addr - $remote_user [$time_local] "$request" ' '$status $body_bytes_sent "$http_referer" ' '"$http_user_agent" "$http_x_forwarded_for"'; access_log /var/log/nginx/access.log main; sendfile on; #tcp_nopush on; keepalive_timeout 65; #gzip on; include /etc/nginx/conf.d/*.conf; server { listen 8080; server_name localhost; location /stub_status { stub_status on; access_log off; } } }
- 使用该配置制作一个镜像,创建Dockerfile文件。
vi Dockerfile
Dockerfile文件内容如下所示:FROM nginx:1.21.5-alpine ADD nginx.conf /etc/nginx/nginx.conf EXPOSE 80 CMD ["nginx", "-g", "daemon off;"]
- 使用上面Dockerfile构建镜像并上传到SWR镜像仓库,镜像名称为nginx:exporter。
- 在左侧导航栏选择“我的镜像”,单击右侧“客户端上传”,在弹出的页面中单击“生成临时登录指令”,单击复制登录指令。
- 在集群节点上执行上一步复制的登录指令,登录成功会显示“Login Succeeded”。
- 执行如下命令构建镜像,镜像名称为nginx,版本为exporter。
docker build -t nginx:exporter .
- 为镜像打标签并上传至镜像仓库,其中镜像仓库地址和组织名称请根据实际情况修改。
docker tag nginx:exporter {swr-address}/{group}/nginx:exporter docker push {swr-address}/{group}/nginx:exporter
- 查看应用指标。
- 使用nginx:exporter创建工作负载。
- 登录到容器中,并通过http://<ip_address>:8080/stub_status获取到nginx的监控数据,其中<ip_address>为容器的IP地址,监控数据如下所示。
# curl http://127.0.0.1:8080/stub_status Active connections: 3 server accepts handled requests 146269 146269 212 Reading: 0 Writing: 1 Waiting: 2
监控自定义指标
如上所述的nginx:exporter提供的监控数据,其数据格式并不满足Prometheus的要求,需要将其转换成Prometheus需要的格式,可以使用nginx-prometheus-exporter来转换Nginx的指标,将nginx:exporter和nginx-prometheus-exporter部署到同一个Pod,并在部署时添加如下annotations就可以自动被Prometheus采集监控指标。
kind: Deployment apiVersion: apps/v1 metadata: name: nginx-exporter namespace: default spec: replicas: 1 selector: matchLabels: app: nginx-exporter template: metadata: labels: app: nginx-exporter annotations: prometheus.io/scrape: "true" prometheus.io/port: "9113" prometheus.io/path: "/metrics" prometheus.io/scheme: "http" spec: containers: - name: container-0 image: 'nginx:exporter' # 替换为您上传到SWR的镜像地址 resources: limits: cpu: 250m memory: 512Mi requests: cpu: 250m memory: 512Mi - name: container-1 image: 'nginx/nginx-prometheus-exporter:0.9.0' command: - nginx-prometheus-exporter args: - '-nginx.scrape-uri=http://127.0.0.1:8080/stub_status' imagePullSecrets: - name: default-secret
其中
- prometheus.io/scrape:表示是否需要prometheus采集Pod的监控数据,取值为true。
- prometheus.io/port:表示采集监控数据接口的端口。
- prometheus.io/path:表示采集监控数据接口的URL,如不配置则默认为“/metrics”。
- prometheus.io/scheme:表示采集的协议,值可以填写http或https。
部署应用后,在“Status > Targets”能够发现多了一个9113端口的采集路径的Pod。
在Graph页签下输入nginx,可以看出nginx相关的指标已经在Prometheus中呈现。
配置自定义指标的采集规则
关于采集规则配置详情请参见Metrics Discovery and Presentation Configuration。如您从老版本插件升级至新版,则原有的该配置会被继承,不会丢失。
使用Prometheus监控自定义指标时,应用程序需要提供监控指标接口,详情请参见Prometheus监控数据采集说明。
- 登录CCE控制台,单击集群名称进入集群,在左侧导航栏中选择“配置项与密钥”。
- 切换至“monitoring”命名空间,在“配置项”页签找到user-adapter-config配置项(历史版本插件中该配置项的名称为adapter-config),并单击“更新”。
图1 更新配置项
- 在“配置数据”中单击config.yaml对应的“编辑”按钮,在rules字段下添加自定义指标采集规则。修改完成后单击“确定”保存配置。
如果您需要增加多个采集规则,可在rules字段下添加多个配置,关于采集规则配置详情请参见Metrics Discovery and Presentation Configuration。
针对本示例中的nginx:export应用,自定义采集规则示例如下:rules: - seriesQuery: '{__name__=~"^nginx_.*",container!="POD",namespace!="",pod!=""}' resources: overrides: namespace: resource: namespace pod: resource: pod name: matches: (.*) metricsQuery: 'sum(<<.Series>>{<<.LabelMatchers>>,container!="POD"}) by (<<.GroupBy>>)'
上述示例仅针对本示例中的nginx:export应用,如需采集自定义指标请根据官方指导自行添加或修改规则。
图2 修改配置数据
- 重新部署monitoring命名空间下的custom-metrics-apiserver工作负载。
图3 重新部署custom-metrics-apiserver
- 等custom-metrics-apiserver工作负载成功运行,在创建HPA策略时,即可选择nginx:export应用上报的自定义指标。详情请参见HPA策略。
图4 使用自定义指标创建HPA策略
访问Grafana
Prometheus插件同时安装了Grafana(一款开源可视化工具),并且与Prometheus进行了对接。您可以创建一个公网LoadBalancer类型Service,这样就可以从公网访问Grafana,从Grafana中看到Prometheus的监控数据。
单击访问地址,访问Grafana,选择合适的DashBoard,即可以查到相应的聚合内容。
- 登录CCE控制台,选择一个已安装Prometheus插件的集群,在左侧导航栏中选择“服务发现”。
- 单击右上角“YAML创建”,为Grafana创建一个公网LoadBalancer类型Service。
apiVersion: v1 kind: Service metadata: name: grafana-lb #服务名称,可自定义 namespace: monitoring labels: app: grafana annotations: kubernetes.io/elb.id: 038ff*** #请替换为集群所在VPC下的ELB实例ID,且ELB实例为公网访问类型 spec: ports: - name: cce-service-0 protocol: TCP port: 80 #服务端口号,可自定义 targetPort: 3000 #Grafana的默认端口号,无需更改 selector: app: grafana type: LoadBalancer
- 创建完成后在浏览器访问“负载均衡公网IP地址:服务端口”,访问Grafana并选择合适的DashBoard,即可以查到相应的聚合内容。
附录:Grafana数据持久化
如果Grafana数据没有持久化,Grafana容器重启会导致数据丢失。您可以给Grafana容器挂载云存储,从而实现Grafana数据持久化。
- 请参见通过kubectl连接集群,使用kubectl连接Grafana所在集群。
- 创建云硬盘存储PVC。
apiVersion: v1 kind: PersistentVolumeClaim metadata: name: grafana-pvc namespace: monitoring annotations: everest.io/disk-volume-type: SSD labels: failure-domain.beta.kubernetes.io/region: ae-ad-1 failure-domain.beta.kubernetes.io/zone: spec: accessModes: - ReadWriteOnce resources: requests: storage: 10Gi storageClassName: csi-disk
云硬盘必须与Grafana所在节点在同一个可用区,否则无法挂载。
- failure-domain.beta.kubernetes.io/region:云硬盘所在的区域。
- failure-domain.beta.kubernetes.io/zone:云硬盘所在的AZ。
- storage:云硬盘大小,请根据需要选择。
您还可以在CCE控制台创建云硬盘存储,具体方法请参见通过控制台自动创建云硬盘存储。
- 修改Grafana工作负载配置,挂载云硬盘。
kubectl edit deploy grafana -n monitoring
在YAML文件中给容器添加云硬盘挂载,如下所示。其中PVC名称必须与2中名称一致,挂载路径必须为“/var/lib/grafana”。
另外必须修改grafana负载的升级策略,最大Pod数量为1。
... template: spec: volumes: - name: cce-pvc-grafana persistentVolumeClaim: claimName: grafana-pvc ... containers: - volumeMounts: - name: cce-pvc-grafana mountPath: /var/lib/grafana ... strategy: type: RollingUpdate rollingUpdate: maxUnavailable: 1 maxSurge: 1
修改完成后保存配置,Grafana负载会升级并挂载云硬盘。