声明式配置之旅:为何忽略健康检查端点进行追踪耗时五年
在过去几年中,Java OpenTelemetry 最持久且最受欢迎的功能请求之一是能够有效地 丢弃健康检查端点的 Span – 或其他低价值、高成本的端点。这个问题早在 2020 年 8 月就已提出,但一个全面的解决方案却出奇地难以找到。为什么解决这个看似简单的问题需要我们花费五年的时间?答案在于 OpenTelemetry 配置系统的基本原则以及通往更健壮、更灵活的方法的历程:声明式配置。
从一开始,OpenTelemetry 就依赖环境变量进行配置,这一选择是出于它们在各种语言中普遍可用且易于解析的考虑。然而,随着对更复杂配置用例的需求不断增长,简单的基于字符串的环境变量的局限性变得越来越明显,使得高级配置变得繁琐且难以管理。
引入声明式配置,这是一个强大的演进,它利用 YAML 文件来定义 OpenTelemetry 设置。这一转变允许从任何树形结构的数据源读取数据,从根本上改变了我们处理复杂配置的方式。在本文中,我们将探讨声明式配置如何为过去的挑战提供优雅的解决方案,并以 Java 中健康检查排除等实际用例来展示其即时影响。
入门
配置文件是语言无关的,因此一旦创建了一个文件,就可以将其用于所有 SDK。唯一的例外是具有特定语言名称的参数,这些参数仅与该语言相关(例如,instrumentation/development.java.spring_batch 参数)。请记住,声明式配置是 **实验性** 的,因此事物仍可能发生变化。
以下示例是一个基本的配置文件,可供您入门。
file_format: '1.0-rc.1'
resource:
attributes_list: ${OTEL_RESOURCE_ATTRIBUTES}
detection/development:
detectors:
- service: # will add "service.instance.id" and "service.name" from OTEL_SERVICE_NAME
propagator:
composite:
- tracecontext:
- baggage:
tracer_provider:
processors:
- batch:
exporter:
otlp_http:
endpoint: ${OTEL_EXPORTER_OTLP_TRACES_ENDPOINT:-https://:4318/v1/traces}
meter_provider:
readers:
- periodic:
exporter:
otlp_http:
endpoint: ${OTEL_EXPORTER_OTLP_METRICS_ENDPOINT:-https://:4318/v1/metrics}
logger_provider:
processors:
- batch:
exporter:
otlp_http:
endpoint: ${OTEL_EXPORTER_OTLP_LOGS_ENDPOINT:-https://:4318/v1/logs}
您所要做的就是在应用程序中传递 OTEL_EXPERIMENTAL_CONFIG_FILE=/path/to/otel-config.yaml 以激活实验性声明式配置选项。在撰写本文时,此变量仅在 Java 代理和 JavaScript 中有效。
Java 中的声明式配置
现在让我们看一下声明式配置在 Java 生态系统中的更广泛实现。作为该领域的先驱语言,Java Agent 2.21+ 现在已完全支持声明式配置,大多数插桩和功能已可正常使用。我们正在努力在 2026 年期间整合剩余的功能,您可以在 项目看板 上跟踪我们的进展,并查看 尚未支持的功能列表。
根据您是首次开始还是从使用环境变量迁移,有一些资源可以利用。
- 上一节中的基本(语言无关)配置文件示例是您不需要任何进一步自定义时最快的入门方法。
- 该 迁移配置文件 将旧的环境变量映射到 YAML 架构,允许已使用环境变量配置工作负载的用户进行直接替换。
- 该 完整配置文件(“厨房水槽”)展示了整个架构,并带有注释。这对于希望查看所有可用选项及其默认值的用户很有用。
以上所有文件均适用于支持声明式配置的任何语言。
此外,Java Agent 有许多特定于设置的配置,这些配置会放入您配置文件中的 instrumentation 部分。例如,如果您在应用程序中具有系统属性 otel.instrumentation.spring-batch.experimental.chunk.new-trace,则可以通过移除 otel.instrumentation 前缀,在 . 处拆分并将 - 转换为 _ 来创建声明式配置文件。
file_format: '1.0-rc.1'
# ...
instrumentation/development:
java:
spring_batch:
experimental:
chunk:
new_trace: true
有了此配置,开发人员可以继续像往常一样使用其 Java 插桩,将遥测数据发送到他们选择的可观察性后端。此外,声明式配置文件提供了扩展和添加更多参数的灵活性,从而可以对可观察性设置进行高度定制和细致的控制。
健康检查排除
如引言中所述,Java 社区中最受欢迎的功能请求之一是能够排除健康检查(或其他不重要或嘈杂的资源)以生成追踪。
为此,您需要在 tracer_provider 配置中添加一个新的 sampler 块,如下所示。
file_format: '1.0-rc.1'
# ... the rest of the configuration ....
tracer_provider:
# Configure sampling to exclude health check endpoints.
sampler:
rule_based_routing:
fallback_sampler:
always_on:
span_kind: SERVER
rules:
# Action to take when the rule matches. Must be DROP or RECORD_AND_SAMPLE.
- action: DROP
# The span attribute to match against.
attribute: url.path
# The pattern to compare the span attribute to.
pattern: /actuator.*
# ... the rest of the tracer_provider configuration ...
有关可用选项的更多详细信息,请参阅 Java sampler 文档。
亲自尝试
- 保存 完整配置
- 使用
-Dotel.experimental.config.file=/path/to/otel-config.yaml运行 Java Agent。
可用性
阅读声明式配置后,您可能想知道它在哪里可用以及如何开始使用它。您可以在 文档 中找到有关如何开始以及支持哪些语言的指南。在撰写本文时,Java 已完全兼容,PHP、JavaScript 和 Go 部分兼容。要查看最新状态,请检查 兼容性矩阵 或 语言实现跟踪问题。
Java
如前所述,Java 中的声明式配置是实验性的但已可使用。使用我们之前讨论的示例来设置新配置。如果您有任何问题或反馈,请在 CNCF Slack 的 #otel-java 频道中联系我们。
致其他语言维护者:创建适配声明式配置设置和环境变量的通用接口桥接模块很有用。对于 Java 来说,这就是 声明式配置桥。
JavaScript
JavaScript SDK 中的实现目前正在开发中。已创建一个名为 opentelemetry-configuration 的新包,它同时处理环境变量和声明式配置。通过这种方法,用户在环境变量和配置文件之间切换时无需更改其插桩,因为新包会处理它并为这两种情况返回相同的配置模型。目前,此配置包正在添加到其他插桩包中,以便它们可以利用声明式配置。如果您有任何问题,请在 CNCF Slack 的 #otel-js 频道中联系我们。
PHP
PHP 实现部分兼容,您可以通过 从配置文件初始化 来开始使用它。如需帮助或反馈,请在 CNCF Slack 的 #otel-php 频道中联系我们。
Go
Go 语言有一个声明式配置的 部分实现。每个支持的架构版本都有其相应的包目录。例如,导入 go.opentelemetry.io/contrib/otelconf/v0.3.0 会为您提供支持配置架构 0.3.0 版本。您可以在 包索引 中找到所有可用版本。如果您对如何使用它有疑问,请在 CNCF Slack 的 #otel-go 频道中联系我们。
历程
那么,为什么我们花了五年时间才忽略追踪中的健康检查端点呢?
声明式配置的历程,以及随之而来的健康检查排除的解决方案,凸显了 OpenTelemetry 的一个核心理念:通过严谨的规范构建可持续的解决方案。
从一开始,OpenTelemetry 对环境变量的依赖,虽然普遍可用,但对于高级配置来说,其复杂性却日益增加。最终不允许添加新的环境变量,这留下了一个需要更强大解决方案来填补的空白。
正如我们在本篇博文中介绍的那样,它的替代品是声明式配置。制定和商定精确的语法和语义是一个耗时且有时令人筋疲力尽的过程。例如,我们讨论了关于如何嵌入环境变量的几个提议,直到我们想出了使用 ${OTEL_EXPORTER_OTLP_ENDPOINT:-https://:4318} 的当前解决方案。
这个过程是 OpenTelemetry 社区如何运作的一个有力案例研究。它证明了建立共识、促进协作以及引入重大新功能并推动其在不同项目中的实现所需的集体努力。
声明式配置的未来展望?
声明式配置的旅程远未结束。我们当前的重点是扩大语言支持,这对于确保开发人员无论使用何种工具都能从声明式方法的优势中受益至关重要。
在我们继续开发和完善这些功能的过程中,我们非常关注用户反馈。我们鼓励您开始试验当前的实现,并积极沟通任何缺失的功能、痛点或需要改进的领域。这种协作方法将帮助我们确定开发工作的优先级,并确保我们构建的解决方案真正满足社区的需求。您可以通过 CNCF Slack 的 #otel-config-file 频道分享您的反馈或疑问。
除了提供反馈,还有其他方式可以参与并为声明式配置的增长做出贡献。每个 OpenTelemetry SDK 都有一个专门负责其实现的 特别兴趣小组 (SIG)。加入这些 SIG 提供了一个直接了解开发当前状态、参与讨论并识别贡献机会的途径。无论是通过代码贡献、文档增强,还是仅仅分享您的经验,每一次贡献都有助于推进声明式配置生态系统。您的积极参与是培养强大而通用的现代应用程序开发工具集的关键。
我们希望听到您的声音!
附加资源
要了解有关声明式配置工作的更多信息,以下是一些额外的资源供您探索: