如何为Prometheus的Kubernetes服务发现指标添加集群名称标签?
给Kubernetes集群指标添加自定义cluster-name标签的正确姿势
看起来你遇到的问题核心是relabel规则的触发条件不满足,导致新标签没被成功注入。我来帮你梳理下正确的配置方式和可能的问题点:
一、最简单的正确配置(添加固定集群标签)
如果只是想给某个Kubernetes集群的所有指标统一加上cluster-name="abcde"标签,完全不需要依赖任何K8s元标签(比如__meta_kubernetes_namespace),直接用无source_labels的replace动作即可。配置示例如下:
scrape_configs: - job_name: 'kubernetes-cluster-abcde' # 建议命名为对应集群的专属job kubernetes_sd_configs: - role: node # 根据你的采集需求,这里也可以是pod/service/endpoint等 relabel_configs: # 注入自定义集群标签,直接设置固定值 - action: replace target_label: cluster-name replacement: abcde # 替换成你的集群名称 # 保留你之前生效的domainname修改规则 - source_labels: [__meta_kubernetes_node_name] action: replace target_label: domainname replacement: '$1.example.com'
二、为什么你之前的配置没生效?
你之前用了source_labels: [__meta_kubernetes_namespace],这个规则的问题在于:
- 如果你采集的是node角色的指标,Prometheus的K8s服务发现不会给node目标添加
__meta_kubernetes_namespace元标签(因为node不属于任何namespace)。此时source_labels指定的标签不存在,relabel的replace动作会被直接跳过,自然不会生成cluster-name标签。 - 即使是采集pod/service,也可能存在某些特殊资源没有namespace标签的情况,导致规则无法触发。
三、验证配置是否生效的步骤
配置完成后,可以通过以下方式快速确认:
- 用
promtool check config prometheus.yml检查配置文件是否有语法错误。 - 访问Prometheus的
/targets页面,查看对应job的目标是否已经带上了cluster-name标签。 - 执行查询
container_cpu_usage_seconds_total{cluster-name="abcde"},看是否能返回对应集群的指标数据。
四、进阶:多集群场景的批量标签管理
如果你管理多个K8s集群,不想每个job都硬编码集群名称,可以结合file_sd_configs来批量注入标签:
- 创建一个
clusters.json文件,内容如下:
[ { "targets": ["kubernetes-apiserver-abcde:6443"], "labels": { "cluster-name": "abcde", "api_server": "https://kubernetes-apiserver-abcde:6443" } }, { "targets": ["kubernetes-apiserver-xyz:6443"], "labels": { "cluster-name": "xyz", "api_server": "https://kubernetes-apiserver-xyz:6443" } } ]
- 在Prometheus配置中引用这个文件并传递标签:
scrape_configs: - job_name: 'kubernetes-multi-cluster' file_sd_configs: - files: ['clusters.json'] kubernetes_sd_configs: - role: node api_server: '{{ .labels.api_server }}' tls_config: insecure_skip_verify: true # 根据实际集群的TLS配置调整 relabel_configs: - source_labels: [__meta_file_sd_label_cluster-name] action: replace target_label: cluster-name
这样就能批量管理多个集群的标签,不用重复编写相似的配置块。
内容的提问来源于stack exchange,提问作者Sathish Kumar




