Metric Design 基础:定义、类型与命名规范

在可观测性体系中,Metric(度量指标)是质量门禁卡点的最小数据单元。它是一组带时间戳的数值序列,用于描述系统在某一时刻或某一时间窗口内的状态、行为或性能。只有正确理解 Metric 的本质、分类与命名规则,才能设计出可被门禁卡点准确评估的告警阈值基线。

2.1 什么是 Metric

Metric 是对系统特征进行数值化抽象的结果,通常由以下三要素构成:

要素 说明 示例
Metric Name 指标名称,唯一标识一类度量 http_requests_total
Labels(标签) 键值对维度,用于区分不同实例、方法、状态 method="GET", status="200"
Value(数值) 当前采样点的实际测量值 1024
质量门禁视角:Metric 是门禁卡点的“传感器数据”。没有标准化的 Metric,阈值基线将失去可比较的锚点,门禁判定也会退化为“拍脑袋”规则。

2.2 Metric 的四种核心类型

不同场景需要不同语义的 Metric 类型。以下是生产环境中最常见的四种类型及其适用场景:

类型 语义 典型用途 门禁卡点示例
Counter 只增不减的累计值(重启归零) 请求总数、错误总数、任务完成数 错误率 = 错误 Counter 增量 / 总请求 Counter 增量
Gauge 可增可减的瞬时值 CPU 使用率、内存占用、连接数、队列深度 当前连接数 > 阈值上限时触发告警
Histogram 分桶统计,记录分布与累计计数 请求延迟、响应大小、批处理耗时 P99 延迟 > 500ms 时阻断发布
Summary 分位数预计算,客户端侧聚合 延迟分位数(P50/P90/P99)、吞吐量 P99 延迟基线对比,无需服务端二次计算
选型建议:质量门禁卡点中,Histogram 是最推荐的类型。它既能计算分位数(P99/P95),又能通过 _bucket 指标计算 SLI/SLO 达标率,灵活性远超 Summary。Summary 仅在客户端计算分位数且无法聚合时使用。

2.3 Metric 命名规范

统一的命名规范是团队协作和自动化门禁解析的基础。推荐遵循 Prometheus 命名规范,该规范已被业界广泛采纳:

  • 基础格式:<namespace>_<subsystem>_<metric_name>[_<unit>]
  • 命名规则:
    • 全部使用小写字母 + 下划线(snake_case)
    • Metric Name 必须以字母开头
    • 使用 _total 后缀标识 Counter 类型
    • 使用 _seconds / _bytes / _count 等后缀标识单位
    • Histogram 自动生成 _bucket、_count、_sum 后缀
正确示例 错误示例 说明
api_http_requests_total api.http.requests 禁止使用点号或驼峰
node_cpu_seconds_total node_cpu 缺少单位后缀,语义模糊
db_query_duration_seconds db_query_time 时间类指标必须带 _seconds
http_request_duration_seconds_bucket http_request_bucket Histogram 必须保留 _bucket 后缀
门禁卡点红线:所有接入质量门禁的 Metric 必须通过命名规范校验。不符合规范的指标将被自动拒绝,无法进入基线计算流程。这是保证门禁系统可维护性的第一道防线。

2.4 Metric 类型与命名规范关系图

下图展示了四种 Metric 类型在质量门禁卡点中的典型数据流,以及命名规范如何贯穿始终:

Metric 类型与命名规范在质量门禁中的数据流 应用服务 Counter: _total Gauge: 无后缀 Histogram: _bucket Summary: 预计算分位 命名规范校验 ✓ 小写+下划线 ✓ 单位后缀 ✓ 类型后缀 ✓ 禁止点号/驼峰 ✓ 标签白名单 不通过则拒绝 阈值基线计算 Counter → 速率/错误率 Gauge → 水位/饱和度 Histogram → P99/P95 Summary → 预聚合分位 输出:动态阈值 质量门禁卡点:基线对比 → 通过 / 阻断

2.5 代码示例:Prometheus Client 定义规范 Metric

以下 Go 代码展示了如何按照规范定义四种类型的 Metric,并注入质量门禁所需的标签:

// Counter:请求总数,带 method 和 status 标签
apiRequestTotal = prometheus.NewCounterVec(
    prometheus.CounterOpts{
        Name: "api_http_requests_total",
        Help: "Total number of HTTP requests.",
    },
    []string{"method", "status"},
)

// Gauge:当前活跃连接数
activeConnections = prometheus.NewGauge(
    prometheus.GaugeOpts{
        Name: "api_active_connections",
        Help: "Current number of active connections.",
    },
)

// Histogram:请求延迟,单位秒,分桶 0.1~10
requestDuration = prometheus.NewHistogramVec(
    prometheus.HistogramOpts{
        Name:    "api_request_duration_seconds",
        Help:    "Request latency in seconds.",
        Buckets: []float64{0.1, 0.3, 0.5, 1, 3, 5, 10},
    },
    []string{"method"},
)

// Summary:延迟分位数,客户端预计算
requestLatencySummary = prometheus.NewSummaryVec(
    prometheus.SummaryOpts{
        Name:       "api_request_latency_seconds",
        Help:       "Request latency summary.",
        Objectives: map[float64]float64{0.5: 0.05, 0.9: 0.01, 0.99: 0.001},
    },
    []string{"method"},
)
门禁集成提示:在注册 Metric 时,建议额外注入 service、env、version 等固定标签。这些标签在门禁卡点中用于区分不同服务、环境和版本基线,避免跨环境阈值混淆。