DevOps全链路实战 | 第 12 天:Grafana 看板搭建:K8s 标准面板与自定义业务看板

第 12/19 天

引言

在上一篇文章中,我们通过 kube-prometheus-stack 完成了 Prometheus 的部署,并利用 ServiceMonitor 实现了对 K8s 集群各项指标的自动采集。然而,Prometheus 本身只是一个时序数据库和数据采集引擎——它存储了海量的监控数据,却不擅长将这些数据以直观、美观的方式呈现出来。这正是 Grafana 的用武之地。

Grafana 是目前开源领域最流行的可视化平台之一,支持数十种数据源(Prometheus、InfluxDB、Elasticsearch、Loki 等),拥有庞大的社区仪表板生态。在本篇文章中,我们将在已有的 kube-prometheus-stack 基础上,深入实践 Grafana 看板的搭建:既会导入 K8s 社区标准面板快速获得集群全局视图,又会从零创建自定义业务看板,将 Prometheus 指标转化为对研发和运维真正有价值的洞察。

K8s

核心概念

Grafana 架构与数据流

Grafana 的核心工作流可以概括为三个层次:

  • 数据源(DataSource):Grafana 不自己存储数据,而是通过配置数据源连接后端存储引擎。在我们的场景中,数据源就是 kube-prometheus-stack 部署的 Prometheus 实例。
  • 仪表板(Dashboard):由多个面板(Panel)组成,每个面板绑定一个查询表达式(如 PromQL),以折线图、仪表盘、表格、热力图等形式渲染数据。
  • 变量(Variables):仪表板级别的参数化机制,支持通过下拉框切换 namespace、pod、node 等维度,实现一个看板覆盖多场景的复用能力。

kube-prometheus-stack 内置的 Grafana

在前一天的部署中,kube-prometheus-stack Helm Chart 已经自动集成了 Grafana 组件。我们可以通过以下方式获取 Grafana 的访问凭据:

💻 代码示例

# 获取 Grafana 初始管理员密码(存储在 Secret 中)

kubectl get secret -n monitoring kube-prometheus-stack-grafana

-o jsonpath="{.data.admin-password}" | base64 -d ; echo

 

# 获取 Grafana Service 信息

kubectl get svc -n monitoring | grep grafana

 

# 通过端口转发本地访问(生产环境建议配置 Ingress)

kubectl port-forward -n monitoring svc/kube-prometheus-stack-grafana 3000:80

打开浏览器访问 http://localhost:3000,使用用户名 admin 和上面获取的密码即可登录。此时,Prometheus 数据源已经被 kube-prometheus-stack 自动注入并配置好,无需手动添加。

实战步骤

一、导入 K8s 社区标准面板

Grafana 社区维护了大量高质量的 K8s 监控仪表板,我们可以直接通过 Dashboard ID 导入,而不必从零搭建。以下是几个经典面板:

面板名称 Dashboard ID 适用场景
Kubernetes Cluster Monitoring 315 集群全局资源概览
Kubernetes Pods 6417 Pod 级别 CPU/内存详情
Node Exporter Full 1860 节点主机层指标全貌
CoreDNS 15762 DNS 解析性能监控

方式一:通过 Web UI 导入

  1. 登录 Grafana → 左侧菜单点击 Dashboards → Import
  2. 在 “Import via grafana.com” 输入框中填入 Dashboard ID(如 315)
  3. 点击 Load,选择 Prometheus 数据源
  4. 点击 Import 完成导入

方式二:通过 Grafana API 批量导入

在生产环境中,我们通常希望将看板配置纳入版本管理,实现可重复部署。可以通过 API 脚本化导入:

💻 代码示例

#!/bin/bash

GRAFANA_URL="http://localhost:3000"

GRAFANA_USER="admin"

GRAFANA_PASS="$(kubectl get secret -n monitoring kube-prometheus-stack-grafana -o jsonpath='{.data.admin-password}' | base64 -d)"

 

# 定义要导入的面板 ID 列表

DASHBOARD_IDS=(315 6417 1860 15762)

 

for ID in "${DASHBOARD_IDS[@]}"; do

echo "Importing dashboard $ID…"

# 从 grafana.com 下载面板 JSON

DASHBOARD_JSON=$(curl -sL "https://grafana.com/api/dashboards/${ID}/revisions/latest/download")

# 构造 API 请求体

PAYLOAD=$(jq -n –argjson db "$DASHBOARD_JSON" '{dashboard: $db, overwrite: true}')

# 通过 Grafana HTTP API 导入

curl -s -X POST "${GRAFANA_URL}/api/dashboards/db"

-u "${GRAFANA_USER}:${GRAFANA_PASS}"

-H "Content-Type: application/json"

-d "$PAYLOAD" | jq -r '.title + " => " + (.status // "unknown")'

done

提示:将上述脚本保存为 import-dashboards.sh,后续集群重建时一键恢复所有标准面板。

二、配置 Helm Values 持久化看板

除了手动导入,更推荐的做法是通过 Helm Values 让看板在部署时自动加载。kube-prometheus-stack 的 grafana.dashboards 字段支持定义 ConfigMap 引用的面板:

💻 代码示例

# values-grafana-dashboards.yaml

grafana:

adminPassword: "ChangeMeInProduction!"

persistence:

enabled: true

size: 10Gi

storageClassName: "local-path"

 

# 通过 ConfigMap 预置自定义看板

dashboardProviders:

dashboardproviders.yaml:

apiVersion: 1

providers:

– name: 'custom'

orgId: 1

folder: 'DevOps Custom'

type: file

disableDeletion: false

editable: true

options:

path: /var/lib/grafana/dashboards/custom

 

dashboards:

custom:

k8s-overview:

gnetId: 315

revision: 1

datasource: Prometheus

k8s-pods:

gnetId: 6417

revision: 1

datasource: Prometheus

 

# 额外数据源(如需接入 Loki 日志)

additionalDataSources:

– name: Loki

type: loki

url: http://loki-gateway.monitoring.svc.cluster.local:80

access: proxy

isDefault: false

应用配置:

💻 代码示例

helm upgrade kube-prometheus-stack prometheus-community/kube-prometheus-stack

-n monitoring

-f values-grafana-dashboards.yaml

–reuse-values

三、从零创建自定义业务看板

标准面板覆盖的是基础设施层指标。在实际业务中,我们往往需要监控应用维度的自定义指标——比如 API 请求量、错误率、P99 延迟等。接下来我们从零创建一个业务看板。

3.1 定义看板变量

进入 Grafana → Dashboards → New → New Dashboard,首先配置变量以实现多 namespace 切换:

  • 变量名 namespace,类型 Query,数据源选 Prometheus
  • 查询表达式:label_values(kube_pod_info, namespace)
  • 变量名 pod,类型 Query,查询表达式:label_values(kube_pod_info{namespace=~"$namespace"}, pod)

这样面板的 PromQL 就可以引用 $namespace 和 $pod 实现动态过滤。

3.2 核心业务面板 PromQL

以下是一个典型的微服务业务看板需要覆盖的查询:

💻 代码示例

# 1. API 请求速率(QPS)— 按状态码分类

sum(rate(http_requests_total{namespace="$namespace", pod=~"$pod"}[5m])) by (status_code)

 

# 2. 错误率(5xx 占比)

sum(rate(http_requests_total{namespace="$namespace", status_code=~"5.."}[5m]))

/

sum(rate(http_requests_total{namespace="$namespace"}[5m])) * 100

 

# 3. P99 延迟(使用直方图分位数)

histogram_quantile(0.99,

sum(rate(http_request_duration_seconds_bucket{namespace="$namespace"}[5m])) by (le)

)

 

# 4. Pod CPU 使用率(相对于 Limit)

sum(rate(container_cpu_usage_seconds_total{namespace="$namespace", container!=""}[5m])) by (pod)

/

sum(kube_pod_container_resource_limits{resource="cpu", namespace="$namespace"}) by (pod) * 100

 

# 5. Pod 内存使用量

sum(container_memory_working_set_bytes{namespace="$namespace", container!=""}) by (pod)

3.3 面板布局建议

一个好的业务看板应该遵循”从宏观到微观”的布局原则:

  1. 顶部行(Row):关键 SLI 指标概览——QPS、错误率、P99 延迟,使用 Stat 面板或 Gauge 面板,配阈值着色
  2. 第二行:请求量趋势折线图(按状态码分系列),叠加错误率百分比曲线
  3. 第三行:延迟分布热力图(使用 Heatmap 面板展示 P50/P95/P99 分位)
  4. 底部行:Pod 资源使用明细表格,列出 CPU/内存使用率、重启次数

3.4 导出看板 JSON 纳入 GitOps

看板配置完成后,点击 Dashboard 右上角 Share → Export → View JSON,将 JSON 内容复制保存到 Git 仓库:

💻 代码示例

# 在 GitOps 配置仓库中

mkdir -p manifests/grafana-dashboards/business-api

# 将导出的 JSON 保存为以下文件

# manifests/grafana-dashboards/business-api/business-overview.json

 

# 创建 ConfigMap 将看板挂载到 Grafana

cat > manifests/grafana-dashboards/business-api-configmap.yaml << 'EOF'

apiVersion: v1

kind: ConfigMap

metadata:

name: grafana-dashboard-business

namespace: monitoring

labels:

grafana_dashboard: "1"

data:

business-overview.json: |

{

"title": "Business API Overview",

"schemaVersion": 39,

"templating": { … }

}

EOF

通过给 ConfigMap 打上 grafana_dashboard: "1" 标签,kube-prometheus-stack 中的 Grafana Sidecar 会自动发现并加载该看板,无需重启 Pod。当 Argo CD 同步该 ConfigMap 后,新看板即可在 Grafana 中自动出现——这就是 GitOps 管理监控看板的完整闭环。

常见问题

Q1:Grafana 面板显示 “No data” 怎么排查?

依次检查:(1) 数据源是否正确选择 Prometheus;(2) 在 Prometheus Web UI 中直接执行该 PromQL 确认有数据返回;(3) 检查时间范围选择器是否设置了过短的时间窗口;(4) 确认变量值已正确选择(namespace/pod 不为空);(5) 检查 ServiceMonitor 的 labelSelector 是否匹配到目标 Pod。

Q2:自定义业务指标在 Prometheus 中找不到?

如果业务应用通过 /metrics 暴露了自定义指标但没有被采集,需要检查:(1) Pod 是否有正确的 annotation(prometheus.io/scrape: "true"、prometheus.io/port: "8080");(2) 是否创建了对应的 ServiceMonitor 资源;(3) ServiceMonitor 的 namespaceSelector 和 selector.matchLabels 是否正确匹配。可以通过 kubectl get servicemonitor -A 查看已注册的采集规则。

Q3:Grafana 密码修改后如何持久化?

通过 Helm Values 的 grafana.adminPassword 字段配置后,需要执行 helm upgrade 并删除 Grafana Pod 触发重建(密码在首次启动时写入 Secret 后不再随 Pod 重启改变)。如果希望以后修改密码不丢失,建议配置 grafana.persistence.enabled: true 使用 PVC 持久化 /var/lib/grafana 目录。

Q4:看板变量下拉框加载缓慢?

当集群规模较大时,label_values 查询可能返回大量标签值导致加载缓慢。优化方式:(1) 在查询中使用 =~ 正则过滤范围,如 label_values(kube_pod_info{namespace=~"prod-.*", namespace);(2) 在变量配置中启用 “Multi-value” 并限制 “Include All option”;(3) 在 Prometheus 配置中对高基数标签进行 metric_relabel_configs 裁剪。

总结

今天我们围绕 Grafana 看板搭建展开了系统性的实战:首先通过 Dashboard ID 快速导入 K8s 社区标准面板,获得了集群资源、Pod、节点、DNS 等多维度的开箱即用视图;随后通过 Helm Values 实现了看板配置的持久化和自动化加载;最后从零构建了一个业务级看板,覆盖了 API QPS、错误率、P99 延迟等核心 SLI 指标,并将看板 JSON 纳入 GitOps 管理。

关键要点回顾:

  • 标准面板优先:社区已提供了大量经过验证的 K8s 看板,导入即可用,避免重复造轮子
  • 变量是灵魂:合理使用 $namespace、$pod 等变量,让一个看板覆盖多场景
  • GitOps 管理看板:将看板 JSON 存入 Git 仓库,通过 ConfigMap + Sidecar 自动同步,实现配置即代码
  • 业务指标分层:基础设施指标用标准面板,应用业务指标用自定义面板,两者互补形成完整可观测性视图

有了 Prometheus 采集和 Grafana 可视化,我们已经能看到集群的实时状态。但”看到”只是第一步——当指标异常时,我们需要被主动告知。这正是明天告警体系要解决的问题。

下期预告

第 13 天:告警规则与 Alertmanager:钉钉/邮件通知渠道配置

我们将配置 Prometheus 告警规则(如 Pod CrashLoopBackOff、节点 NotReady、CPU 超阈值等),部署 Alertmanager 并打通钉钉机器人和邮件通知渠道,让异常第一时间触达运维人员。

系列大纲

  1. 全链路架构总览:从代码提交到灰度发布的完整管道设计
  2. K8s 集群与网络基础:kubeadm 离线部署与 Cilium 网络插件
  3. Harbor 私有镜像仓库部署与验证:Helm 安装与镜像推送
  4. GitLab CE 自托管部署:代码仓库与项目管理平台
  5. GitLab Runner 配置:K8s Executor 与 RBAC 权限设置
  6. GitLab CI 流水线搭建:.gitlab-ci.yml 与 Kaniko 无守护进程构建
  7. Harbor 镜像版本管理与 Tag 策略配置
  8. Argo CD 部署与 GitOps 配置仓库创建
  9. CI 与 CD 联动:从代码提交到部署的全自动闭环
  10. SonarQube 代码质量检查:SonarQube 部署与 GitLab CI 集成
  11. Prometheus 部署:kube-prometheus-stack 与 ServiceMonitor 指标采集
  12. Grafana 看板搭建:K8s 标准面板与自定义业务看板(今天)
  13. 告警规则与 Alertmanager:钉钉/邮件通知渠道配置
  14. Argo Rollouts 安装与基础概念:CRD 与 Rollout 资源定义
  15. 金丝雀发布实战:setWeight 流量分割与 pause 步骤
  16. AnalysisTemplate 指标分析与自动回滚机制
  17. 全链路端到端演示:代码提交→构建→代码检查→灰度→监控→告警完整流程
  18. 生产化加固要点:Harbor/GitLab/Argo CD/SonarQube 高可用方案
  19. 供应链安全闭环:Trivy 扫描 + cosign 签名 + Kyverno 验签
微信二维码
© 版权声明
THE END
喜欢就支持一下吧
点赞0 分享
评论 抢沙发
头像 - 恒星
欢迎您留下宝贵的见解!
提交
头像 - 恒星

昵称

取消
昵称表情代码图片快捷回复

    暂无评论内容