4. Kubernetes 存储组件拓扑图构建:使用 kube-state-metrics 与 csi-metrics 暴露存储资源拓扑
在租户配额校准体系中,存储资源拓扑的精确暴露是核心前提。本章将演示如何通过 kube-state-metrics (KSM) 与 csi-metrics 两个组件,构建完整的 Kubernetes 存储资源拓扑图,为后续 Prometheus 采集与配额计算提供结构化数据源。
4.1 存储拓扑数据源对比
KSM 与 csi-metrics 在存储拓扑暴露中扮演互补角色。KSM 提供控制面对象(PVC、PV、StorageClass)的元数据与状态;csi-metrics 则暴露存储后端(卷、快照、容量)的实时指标。下表对比两者的核心差异:
| 维度 | kube-state-metrics | csi-metrics |
|---|---|---|
| 数据来源 | Kubernetes API Server(控制面对象) | CSI Driver Sidecar(存储后端) |
| 暴露对象 | PVC、PV、StorageClass、Namespace | Volume、Snapshot、Capacity、Node |
| 指标类型 | 元数据标签、状态计数、请求量 | 容量字节、使用率、IOPS、延迟 |
| 更新频率 | 依赖 API Watch(秒级) | 依赖 CSI 驱动轮询(分钟级) |
| 租户关联 | 通过 Namespace 标签直接关联 | 通过 VolumeHandle 间接关联 |
| 典型指标 | kube_persistentvolumeclaim_info |
csi_volume_capacity_bytes |
实践建议:KSM 适合做租户存储对象清单与配额基线;csi-metrics 适合做实际使用量校准。两者必须联合使用,才能形成完整的“申请-分配-使用”拓扑链路。
4.2 kube-state-metrics 存储指标暴露
KSM 默认暴露所有 Kubernetes 对象指标。对于存储拓扑,我们需要重点关注以下指标族:
- PVC 相关:
kube_persistentvolumeclaim_info(名称、命名空间、存储类、访问模式)、kube_persistentvolumeclaim_status_phase(Pending/Bound/Lost) - PV 相关:
kube_persistentvolume_info(名称、存储类、回收策略)、kube_persistentvolume_capacity_bytes(容量) - StorageClass 相关:
kube_storageclass_info(名称、Provisioner、参数) - Namespace 相关:
kube_namespace_labels(租户标签)
部署 KSM 时,建议通过 --metric-whitelist 参数仅暴露存储相关指标,减少 Prometheus 采集压力:
kube-state-metrics \
--metric-whitelist="kube_persistentvolumeclaim_.*" \
--metric-whitelist="kube_persistentvolume_.*" \
--metric-whitelist="kube_storageclass_.*" \
--metric-whitelist="kube_namespace_labels"
4.3 csi-metrics 存储后端指标暴露
csi-metrics 是 CSI 规范定义的指标暴露接口,由 CSI Sidecar 容器(csi-external-provisioner、csi-external-attacher、csi-external-resizer)在 :9808 端口提供。核心指标包括:
- 卷容量:
csi_volume_capacity_bytes(按 VolumeHandle 和 Node 维度) - 卷使用率:
csi_volume_used_bytes(实际已用空间) - 快照指标:
csi_snapshot_info(快照名称、源卷、就绪状态) - 节点存储:
csi_node_capacity_bytes(节点总容量与可用容量)
验证 csi-metrics 是否正常工作:
# 假设 CSI 驱动部署在 csi-driver 命名空间
kubectl -n csi-driver port-forward pod/csi-external-provisioner-0 9808:9808
curl http://localhost:9808/metrics | grep csi_volume
注意:并非所有 CSI 驱动都完整实现 csi-metrics 规范。生产环境建议先执行
curl /metrics 确认指标存在,再配置 Prometheus 采集。对于不支持的驱动,可考虑使用 node_exporter 的 filesystem 指标作为替代。
4.4 存储拓扑图构建:从指标到关系
将 KSM 与 csi-metrics 的指标关联起来,形成完整的存储拓扑图。核心关联逻辑如下:
- PVC → PV 绑定:通过
kube_persistentvolumeclaim_info中的volume_name标签关联到kube_persistentvolume_info。 - PV → CSI VolumeHandle:通过
kube_persistentvolume_info中的volume_handle标签关联到csi_volume_capacity_bytes的volume_handle标签。 - PVC → Namespace → 租户:通过
kube_persistentvolumeclaim_info的namespace标签关联到kube_namespace_labels中的租户标签(如tenant_id)。 - PV → StorageClass:通过
kube_persistentvolume_info的storage_class标签关联到kube_storageclass_info。
下图展示了完整的存储拓扑关系:
4.5 Prometheus 采集配置
在 Prometheus 中配置两个采集目标,分别抓取 KSM 与 csi-metrics 指标:
scrape_configs:
# kube-state-metrics 采集
- job_name: 'kube-state-metrics'
kubernetes_sd_configs:
- role: endpoints
namespaces:
names: ['kube-system']
relabel_configs:
- source_labels: [__meta_kubernetes_service_name]
regex: kube-state-metrics
action: keep
- source_labels: [__meta_kubernetes_endpoint_port_name]
regex: http-metrics
action: keep
metric_relabel_configs:
- source_labels: [__name__]
regex: 'kube_(persistentvolumeclaim|persistentvolume|storageclass|namespace).*'
action: keep
# csi-metrics 采集
- job_name: 'csi-metrics'
kubernetes_sd_configs:
- role: pod
namespaces:
names: ['csi-driver']
relabel_configs:
- source_labels: [__meta_kubernetes_pod_label_app]
regex: csi-external-provisioner
action: keep
- source_labels: [__meta_kubernetes_pod_annotation_prometheus_io_port]
regex: '9808'
action: keep
metric_relabel_configs:
- source_labels: [__name__]
regex: 'csi_(volume|snapshot|node).*'
action: keep
4.6 拓扑验证查询
采集完成后,通过 PromQL 验证拓扑关联是否成功:
# 查询租户 A 的所有 PVC 及其绑定的 PV 容量
kube_persistentvolumeclaim_info{namespace="ns-tenant-a"}
* on(volume_name) group_left(storage_class)
kube_persistentvolume_info
* on(volume_name) group_left()
kube_persistentvolume_capacity_bytes
# 查询租户 A 的 CSI 卷实际容量
kube_persistentvolume_info{volume_handle=~".*"}
* on(volume_handle) group_left()
csi_volume_capacity_bytes
关键检查点:如果上述查询返回空结果,请依次排查:① KSM 是否暴露了存储指标;② csi-metrics 端口是否可达;③ volume_handle 标签是否在 PV 对象中正确设置;④ Prometheus relabel 规则是否过滤掉了必要标签。
至此,Kubernetes 存储组件拓扑图构建完成。下一阶段将基于此拓扑图,实现租户存储配额的自动校准与差异分析。