Metrics 是可观测性的三大支柱之一,它的核心是:
用结构化的数值型数据,持续记录系统状态,用于告警、趋势分析、容量预测。
业内的数据模型几乎都对齐 OpenTelemetry(OTel)与 Prometheus 标准。
面试官一般期待你回答:
- Metrics 的三类模型是什么?
- 为什么要这样设计?
- Label、时间序列、Sample 是怎么构造的?
- Counter / Gauge / Histogram / Summary 区别?
- Push、Pull 模型以及存储结构?
下面完整拆解。
OpenTelemetry + Prometheus 的 Metrics 数据模型由 3 个核心组成:
- Metric(指标):一类业务指标,例如 http_request_total
- Time Series(时间序列):一个 Metric + 一组标签
- Sample(样本点):某个时间点的数值
一句话:
Metric + Labels → 一个 Time Series → 存储若干 Samples,他们一起构成完整的 Metrics 数据模型。
示例:
Metric: http_requests_total
Labels: method="GET", handler="/api/v1/order"
一个唯一时间序列:
http_requests_total{method="GET", handler="/api/v1/order"}
Sample:
( timestamp=1712148091000, value=342 )
在 Prometheus / OpenTelemetry 中,所有 Metrics 可以归为四大类:
- 单调递增
- 只能增加不能减少
- 常用于统计次数、累计量
例子:
- 总请求数
- 总错误数
- 总用户注册数
数据模型:
counter:
name: http_requests_total
value: 120392
- 可增可减
- 表示某一时刻的状态
例子:
- 当前 goroutine 数量
- 当前内存使用量
- Redis 连接数
数据模型:
gauge:
name: cpu_usage
value: 72.5
用于测分布的指标,如延迟、包大小等。
结构:
- buckets(多个桶)
- count(总数量)
- sum(总和)
示例:
http_request_duration_seconds_bucket{le="0.1"} 1390
http_request_duration_seconds_bucket{le="0.3"} 2345
http_request_duration_seconds_sum 532.1
http_request_duration_seconds_count 2895
Histogram 是最常用的延迟指标模型。
用于客户端直接计算 p99/p95 的分布。
但:
- 不可聚合(分布不能 merge)
- 大规模生产推荐 Histogram + server-side quantile
数据模型:
summary:
quantile=0.9 value=33ms
quantile=0.99 value=70ms
下面是 Prometheus 的完整模型:
表示指标类型:
http_requests_total
go_goroutines
process_cpu_seconds_total
有命名规范(如 _total, _count, _bucket 等)。
Labels 是 Metrics 的“维度”,扩展时间序列。
例如:
method="GET"
status="200"
region="us-east-1"
每一种 Label 组合会产生 一个新的时间序列。
例如:
http_requests_total{method="GET", status="200"} → 一条 TimeSeries
http_requests_total{method="POST", status="500"} → 另一条 TimeSeries
**标签爆炸问题(cardinality explosion)**是 Metrics 最大的陷阱。
定义为:
MetricName + LabelSet
例如:
http_requests_total{method="GET", status="200"}
这是一条“唯一的时间序列”。
一个时间点的测量数据。
结构:
timestamp(int64)
value(float64)
Prometheus 存储的就是所有 TimeSeries 的 Sample。
面试加分点:设计哲学。
Time Series 数据可高度压缩:
- 单条 Series 只有两列(timestamp, value)
- 存储引擎(TSDB)压缩率极高
聚合维度可自由组合:
sum by (method) (http_requests_total)
avg(rate(http_request_duration_seconds[5m]))
Sample 是不可变的 append-only data: 不需要更新,只需要 append。
Prometheus 主动拉取:
/metrics
优点:统一发现、自动采集、减少压力。
Agent/SDK 将 Metrics 主动 push 到 Collector。
云原生下常用架构:
App → OTEL SDK → Collector → Prometheus/Tempo/Grafana Cloud
未来标准: OpenMetrics(基于 Prometheus,但更通用) 被 CNCF 广泛支持。
数据模型:
## TYPE http_requests_total counter
http_requests_total{method="GET"} 1234 1712148091000
“Metrics 的数据模型由三个核心概念组成: Metric(指标定义)、TimeSeries(指标+标签的唯一组合)、Sample(某个时间点的值)。
常用类型有四种:
- Counter:递增,用于累计值。
- Gauge:可增可减,用于当前状态。
- Histogram:用于延迟、大小等的分布统计,包含 buckets、count、sum。
- Summary:客户端计算分位数,但不便聚合。
Metrics 使用标签(Label)扩展时间序列,使得 promQL 可以从多维度聚合。 数据通常以 append-only 的方式写入 TSDB,具有高压缩、高性能和强聚合能力。 采集模型有 Pull(Prometheus)和 Push(OpenTelemetry)。 这是现代可观测性体系的基础。”