文档原链接:Metrics Data Model
Overview
OpenTelemetry的metrics 数据模型由一组协议规范和语义约定组成,用于传输预聚合的指标时间序列数据。
1.旨在从现有系统导入数据以及将数据导出到现有系统,以及支持内部 OpenTelemetry 用例,以从span或logs生成指标。
2. 流行的现有metrics数据格式可以明确地转换为 OpenTelemetry metrics数据模型,而不会损失语义或保真度。因为明确指定了 Prometheus 和 Statsd 展示格式的转换。
3. 数据模型指定了许多在收集路径上使用的保留语义的数据转换,支持灵活的系统配置。该模型通过选择累积和增量传输来支持可靠性和无状态控制。该模型通过空间和时间重新聚合支持成本控制。
Events => Data Stream => Timeseries
OTLP Metrics 协议被设计为传输metrics数据的标准。为了描述该数据的预期用途以及相关的语义,OpenTelemetry metrics数据流类型将链接到一个框架,该框架包含一个关于 Metrics API 和离散输入值的高级模型,以及一个定义时间序列和离散输出值的低级模型。模型之间的关系如下图所示。
该协议旨在满足 OpenCensus Metrics 系统的要求,特别是满足其 Metrics Views 的概念。特别是为了满足其 Metrics Views 的概念。通过支持收集路径上的数据转换,在 OpenTelemetry Metrics 数据模型中完成视图。
OpenTelemetry 确定了三种保留语义的 metrics 数据转换,这些转换可用于构建metrics 收集系统作为控制成本、可靠性和资源分配的方法。OpenTelemetry Metrics 数据模型旨在支持这些转换,既可以在数据生成时在 SDK 内进行,也可以作为 OpenTelemetry 收集器内的重新处理阶段进行。这些转变是:
1.时间重新聚合:以高频收集的指标可以重新聚合为更长的间隔,从而允许预先计算或使用低分辨率时间序列来代替原始指标数据。
2.空间重新聚合:使用不需要的属性生成的指标可以重新聚合为具有较少属性的指标。
3.Delta-to-Cumulative:以 Delta 临时性输入和输出的指标减轻了客户端保持高基数状态的负担。增量的使用允许下游服务承担转换为累积时间序列的成本,或者放弃成本并直接计算费率。
OpenTelemetry Metrics 数据流的设计使得这些转换可以自动应用于相同类型的流,但须满足下述条件:
每个 OTLP 数据流都有一个内在的可分解聚合函数,使其在语义上得到明确定义,可以跨时间和空间属性合并数据点。
每个 OTLP 数据点还有两个有意义的时间戳,与内在聚合相结合,使得可以对模型的每个基本点进行标准的metric数据转换,同时确保结果具有预期的含义。
与 OpenCensus Metrics 一样,只需选择聚合间隔和所需属性,即可将指标数据转换为一个或多个视图。通过配置不同的视图,可以将一串 OTLP 数据转换为多个时间序列输出,并且所需的视图处理可以在 SDK 内部应用,也可以由外部收集器应用。
Example Use-cases
指标数据模型是围绕一系列“核心”用例设计的。虽然此列表并不详尽,但它代表了 OTel 指标使用的范围和广度。
- 对于有状态客户端、无状态服务器,OTel SDK 使用累积时间性(cumulative temporality),将 10 秒的变化值导出到单个 OTel collector;
- Collector 将原始数据传递到 OTLP 目标地址
- Collector在不更改属性的情况下重新聚合为更长的间隔
- Collector 重新聚合成几个不同的视图 ( views ),每个视图都有可用属性的子集,导出到相同的目的地 - 对于无状态客户端、有状态服务器,OTel SDK 使用增量时间性(delta temporality),将 10 秒的变化值导出到单个 OTel collector;
- Collector 重新聚合为 60 秒的变化值
- Collector 将增量转换为累积时间性(converts delta to cumulative temporality) - OTel SDK 将 10 秒变化值(例如 CPU、请求延迟)和 15 分钟变化之(例如室温)导出到单个 OTel Collector。Collector 将带有或不带有聚合的数据流向上游导出。
- 许多本地运行的 OTel SDK 都导出 10 秒的变化值,每个报告给单个(本地)OTel 收集器
- Collector 重新聚合为 60 秒的变化值
- Collector 重新聚合以消除各个 SDK 的身份(例如不同的 service.instance.id 值)
- Collector 导出到 OTLP 目标地址 - OTel Collector池 接收 OTLP 并导出 Prometheus 远程写入
- Collector 将服务发现与指标资源结合起来
- Collector 计算“up”,陈旧标记 (英文: Collector computes “up”, staleness marker)
- Collector 应用独特的外部标签 - OTel Collector 接收 Statsd 并导出 OTLP
- 具有增量临时性(delta temporality):无状态Collector
- 具有累积临时性 (cumulative temporality):有状态Collector - OTel SDK直接导出到第三方后端
Model Details
OpenTelemetry 将metrics 分为三个交互模型:
1.事件模型(Event model),表示仪器(instrumentation )如何报告指标数据。
2.时间序列模型( Timeseries model),表示后端如何存储指标数据
3.OTEL数据模型(OpenTelemetry Protocol data model),即指标流模型(Metric Stream Model),定义 OpenTeLemetry 协议 (OTLP),表示如何在事件模型和时间序列存储之间操作和传输指标数据流(metric data streams)。
事件模型 -Event Model
事件模型是数据记录发生的地方。它的基础由Instruments 组成,Instruments (仪器)用于通过事件记录数据观察。然后,这些原始事件在发送到其他系统之前以某种方式进行转换。OpenTelemetry 指标的设计使得可以以不同的方式使用相同的 instrument 和 events 来生成metrics流。
尽管观测事件可以直接报告给后端,但实际上这是不可行的,因为可观测系统中使用的数据量巨大,并且可用于遥测收集目的的网络/CPU 资源有限。最好的例子是直方图指标,其中原始事件以压缩格式而不是单个时间序列记录。
注意:上图显示了一台仪器如何将事件转换为多种类型的指标流。对于何时以及如何执行此操作有一些注意事项和细微差别。指标 API 规范中概述了仪器和指标配置。
虽然 OpenTelemetry 在如何将仪器转换为指标流方面提供了灵活性,但仪器的定义使得可以提供合理的默认映射。API 规范中详细介绍了确切的 OpenTelemetry 仪器。
时间序列模型-Timeseries Model
在一个低级别指标数据模型中,时间序列由由多个元数据属性组成的实体定义:
- 指标名称
- 属性(维度)
- 点的值类型(整数、浮点等)
- 测量单位
每个时间序列的主要数据都是有序的(时间戳,值)点,具有以下值类型之一:
- Counter -计数器(单调、累积)
- Gauge -测量
- Histogram - 直方图
- Exponential Histogram - 指数直方图
我们关心的是知道点值何时被定义,而不是隐式或显式不存在。增量数据点的metric stream定义时间间隔值,而不是时间点值。要准确定义数据的存在和不存在,就需要进一步发展这些模型之间的对应关系。
OTEL数据模型-OpenTelemetry Protocol data model
OpenTelemetry协议(OTLP)数据模型由指标数据流组成。这些流又由指标数据点(metric data points)组成。指标数据流可以直接转换为时间序列。
指标流被分组为单独的Metric
对象,通过以下方式标识:
- 原始
Resource
属性 - 检测
Scope
(例如,检测库名称、版本) - 指标流的
name
包括name
,该Metric
对象由以下属性定义:
- 数据点类型(例如
Sum
,Gauge
,Histogram
ExponentialHistogram
,Summary
) - 指标流的
unit
- 指标流的
description
- 内在数据点属性(如果适用):
AggregationTemporality
,Monotonic
数据点类型、unit
和内在属性被认为是识别的,而description
字段本质上是明确不识别的。
特定点的外在属性不被视为识别;这些包括但不限于:
Histogram
数据点的桶边界- 数据点的规模或桶计数
ExponentialHistogram
。
该 Metric
对象包含各个流,由属性 Attributes
集合标识。在各个流中,点由一两个时间戳标识,详细信息因数据点类型而异。
在某些数据点类型(例如,Sum
和 Gauge
)内,数值点值允许存在变化;在这种情况下,相关的变化(即浮点与整数)不被认为是识别的。
OTEL数据模型:生产者建议(Producer recommendations)
生产者应防止具有相同资源(Resource)和范围属性(Scope)的给定名称存在多个指标标识。生产者应该聚合相同指标对象的数据作为基本功能,因此,多个指标(Metric)的出现被认为是“语义错误”,通常需要在某个地方发生重复的冲突仪器注册。
生产者也许能够修复问题,具体取决于他们是 SDK 还是下游处理器:
- 如果潜在冲突涉及非识别属性(即
description
),则生产者应该选择较长的字符串。 - 如果潜在冲突涉及相似但不同的单位(例如“ms”和“s”),则实现可以转换单位以避免语义错误;否则,实现应该通知用户语义错误并传递冲突的数据。
- 如果潜在冲突涉及
AggregationTemporality
属性,则实现可以使用累积到增量或增量到累积转换来转换时间性;否则,实现应该通知用户语义错误并传递冲突的数据。 - 一般来说,对于涉及标识属性(即除 之外的所有属性
description
)的潜在冲突,生产者应该通知用户语义错误并传递冲突数据。
当 OpenTelemetry API 的实现内部发生此类语义错误时,会假定存在固定Resource
值。因此,实现 OpenTelemetry API 的 SDK 拥有有关重复仪器注册冲突来源的完整信息,有时能够帮助用户避免语义错误。具体细节请参见SDK规范
OTEL数据模型:消费者建议(Consumer recommendations)
Metric
消费者可以拒绝包含语义错误的 OpenTelemetry Metrics 数据(即给定name
、 Resource
和的多个身份Scope
)。
尽管这个主题值得关注,但 OpenTelemetry 并未指定任何向最终用户传达此类结果的方法。
点种类(Point kinds )
Metric数据流可以使用这些基本点类型之一,所有这些基本点类型都满足上述要求,这意味着它们为同类点定义了可分解的聚合函数(也称为“自然合并”函数)
基本点类型有:
比较 OTLP 指标数据流和时间序列数据模型,OTLP 不会将其点类型 1:1 映射到时间序列点。
在 OTLP 中,求和点(Sum Point)可以表示单调计数或非单调计数。这意味着当总和是单调时,OTLP 总和被转换为时间序列计数器(Timeseries Counter),或者当总和不单调时被转换为计量器(Gauge)。
具体来说,在 OpenTelemetry 中,Sums 总是有一个聚合函数,您可以通过加法进行组合。因此,对于 OpenTelemetry 中的非单调和,我们可以通过加法(自然地)进行聚合。在时间序列模型中,您不能假设任何特定的 Gauge 都是总和,因此默认聚合不会是加法。
除了 OTLP 中使用的核心点类型之外,还有专为与现有metrics格式兼容而设计的数据类型。
Metric points
Sums
Sum 由以下部分组成:
- 增量或累积的聚合临时性。(An Aggregation Temporality of delta or cumulative.)
- 表示 Sum 是否单调的标志 。一般情况下,假设 sum 正在增加.
- 对于增量单调和(delta monotonic sums),这意味着读者应该期望非负值。
- 对于累积单调和(cumulative monotonic sums),这意味着读者应该期望不小于先前值的值。 - 一组数据点(data points),每个数据点包含:
- 一组独立的 name-value 属性值对。
-(start, end]
,用于计算 Sum 的时间窗口。 时间间隔包括结束时间,时间是自 1970 年 1 月 1 日 00:00:00 UTC 以来的 UNIX 纪元时间(以纳秒为单位)。还有可选的一组 examplars (see Exemplars)。
聚合时间性(aggregation temporality)用于理解计算 Sum 的过程。当聚合时间性为“delta”时,我们期望指标流的时间窗口没有重叠,例如:
而累积聚合时间性(cumulative aggregation temporality)则是,我们期望导出自 `start` 以来的全部总和(full sum)(通常 `start ` 意味着进程/应用程序启动时刻):
在各种使用场景中,使用 Delta 与 Cumulative aggregation 之间存在各种权衡,例如:
- Detecting process restarts
- Calculating rates
- Push vs. Pull based metric reporting
OTLP 支持这两种模型,并允许 API、SDK 和用户确定适合其用例的最佳权衡。
Gauge
OTLP 中的Gauge 表示给定时间的采样值。 Gauge流包括:
- 一组数据点(data points),每个数据点包含:
- 一组独立的 name-value 属性值对。
- 采样值(例如当前CPU温度)
- 值进行采样时的时间戳 (time_unix_nano
)
- 可选)时间戳 (start_time_unix_nano
),最能代表可以记录测量的第一个可能时刻。这通常设置为指标收集系统启动时的时间戳。
- 可选的一组 examplars (see Exemplars)。
在 OTLP 中,Gauge 流中的点表示给定时间窗口的最后采样事件。
在此示例中,我们可以看到我们使用 Gauge 采样的基础时间序列。虽然事件模型可以在给定的指标报告间隔内多次采样,但通过 OTLP 在指标流中仅报告最后一个值。
Gauge 不提供聚合语义,而是在执行时间对齐或调整分辨率等操作时使用“最后一个样本值”。
可以通过转换为直方图 `histograms` 或其他指标类型来聚合Gauge。这些操作默认情况下不执行,需要用户直接配置。
Histogram
也称直方图,其度量数据点以压缩格式传达大量记录的测量结果。直方图将一组事件捆绑为多个群体,并提供总体事件计数和所有事件的总和。
直方图由以下部分组成:
- 增量或累积的聚合临时性。(An Aggregation Temporality of delta or cumulative.)
- 一组数据点(data points),每个数据点包含:
- 一组独立的 name-value 属性值对。
- (start, end]时间窗口。 时间间隔包括结束时间,时间是自 1970 年 1 月 1 日 00:00:00 UTC 以来的 UNIX 纪元时间(以纳秒为单位)。
- 直方图中点总数的计数(count)
- 直方图中所有值的总和(sum)
- (可选)直方图中所有值的最小值 (min)。
- (可选)直方图中所有值的最大值(max)
- (可选)一系列桶,具有:明确的边界值。这些值表示存储桶(buckets)的下限和上限,以及是否将给定的观察结果记录在该存储桶中。这些桶包含观测值的个数。
与 Sums 一样,直方图也定义聚合时间性。上图表示 Delta 时间性,其中累积的事件计数在报告后重置为零,并发生新的聚合。另一方面,累积继续聚合事件,并使用新的开始时间进行重置。
聚合时间性也对 min 和max 字段有影响。最小值和最大值对于 Delta 时间性更有用,因为随着记录更多事件,累积最小值和最大值表示的值将稳定。
此外,可以将最小值和最大值从 Delta 转换为 Cumulative,但不能从 Cumulative 转换为 Delta。从 Cumulative 转换为 Delta 时,可以删除最小值和最大值,或者使用其他表示形式(例如gauge)来捕获最小值和最大值。
桶的数量是可选的。没有桶的直方图仅根据总和和计数来传达总体,并且可以解释为具有单桶覆盖的直方图(-Inf,+Inf)