CI/CD 可观测性
为了帮助管理员监控 CI/CD 平台并对其进行故障排除,并帮助开发人员提高 CI/CD 管道的速度和可靠性,Elastic Observability 提供了持续集成和持续交付 (CI/CD) 流程的可见性。
为了在管道上提供监控仪表板、警报和根本原因分析,Elastic 与最流行的 CI/CD 平台的社区合作,使用 OpenTelemetry 检测工具。
CI/CD 可观测性架构
使用 APM 服务器,将所有 OpenTelemetry 原生 CI/CD 观测工具直接连接到 Elastic Observability。
使用 Elastic 构建 CI/CD 可观测性的架构
更高级的 CI/CD 可观测性架构包括部署在边缘(靠近 CI/CD 工具)的 OpenTelemetry 收集器。该架构提供以下特性:
- CI/CD 工具和收集器之间的低延迟特别有利于像 otel-cli 这样的临时工具。
- 除了 Elastic Observability 之外,还能够将可观测性信号路由到多个后端。
使用 Elastic 实现 CI/CD 可观测性的高级架构
CI/CD 管理员的可观测性
Elastic Observability 允许 CI/CD 管理员监控 CI/CD 平台并对其进行故障排除并检测异常情况。
CI/CD 平台监控和告警
Elastic Observability 通过提供 CI 系统的 KPI 仪表板来帮助 CI/CD 管理员监控他们的平台。
Jenkins 运行状况仪表板提供有关构建执行、失败、构建代理的配置、活动和空闲的worker或 JVM 运行状况的见解。
Jenkins KPIs in Elastic Observability
Jenkins Provisioning KPIs in Elastic Observability
Elastic Observability 中的 Jenkins JVM 健康指标
CI/CD 平台故障排除
CI/CD 管理员在快速排除平台问题时需要评估异常的影响,无论是排除一个管道故障,还是影响更多管道,甚至整个 CI/CD 平台的更严重的问题。
Elastic Observability 通过将管道执行可视化为分布式跟踪,以及在任何维度上对管道执行进行切片和切块以评估中断的性质和影响的能力,从而能够对 CI 平台中断进行故障排除。
在下图中,Jenkins CI 构建失败,其异常报告为错误。选择这些错误中的任何一个以查看特定信息。
该案例中,错误与意外停止的 CI Agent有关的。
Elastic Observability 中的 Jenkins 管道构建错误
错误概览屏幕提供 捕获的CI 构建异常的高级视图。类似的错误被分组以快速查看哪些错误正在影响您的服务并允许您采取行动来纠正它们。
Elastic Observability 中的 Jenkins 作业和管道错误
将 CI 管道执行编制为 Elastic Observability 中的跟踪
开发人员的可观测性
开发团队需要不断优化他们不断变化的 CI/CD 管道,以提高其可靠性,同时追求更快的管道。将管道可视化为分布式跟踪有助于记录正在发生的事情并提高性能和可靠性(不稳定的测试和管道)。
通过将 OpenTelemetry 与许多流行的 CI/CD 和 DevOps 工具(如 Maven 或 Ansible)集成,Elastic Observability 通过提供对 CI/CD 管道执行的深入见解来解决这些问题。
CI/CD 管道可见性
在 Elastic Observability 中将 CI/CD 管道可视化为分布式跟踪,提供所有管道的事件和运行状况指标。
Elastic Observability 中的 APM 服务视图提供了所有已埋点的 CI/CD 服务的视图,其中包含有关其 KPI 的见解。
Elastic Observability 中的 Jenkins 服务总览
服务页面按管道分解,并展示各自的运行状况和性能指标,为您的 CI/CD 工作流提供更详细的见解。要快速查看哪些管道遇到的错误最多、执行最频繁或最慢,您可以对列表进行排序和筛选。
Elastic Observability 中的 Jenkins 服务
单个管道可见性
确定要排除故障的管道后,您可以深入了解其性能随时间推移的更多详细信息。管道摘要(特定的管道对应特定的Transaction)显示管道的各个构建和作业(构建和作业对应Trace)中的持续时间和故障率的细分,以发现减速或故障。
Elastic Observability 中 Jenkins 管道的性能概述
管道和传统作业是自动被埋点的。如果您发现构建缓慢或失败并且需要了解正在发生的事情,您可以深入到构建的跟踪视图以查找持续时间长或错误的作业。然后,您可以深入研究细节以了解错误的来源。
Jenkins 管道构建为 Elastic Observability 中的跟踪
要进一步调查,您可以查看以Labels的方式添加到构建中的上下文详细信息。
Elastic Observability 中 Jenkins 管道执行的上下文属性
在 Elastic 中存储 Jenkins 管道日志
Jenkins 管道日志可以通过 OpenTelemetry 协议 (OTLP) 发送,与管道构建和 Jenkins 健康指标一起存储在可观测性后端中。将日志存储在可观测性后端有几个好处,包括:
- 将所有的可观测性数据进行统一的存储,更利于我们实现Jenkins实例的全观测性、监控、警报和故障排除。
- 更好的构建可追溯性和长期存储,因此您可以更轻松地审核软件交付生命周期。
- 通过大大减少存储在 Jenkins 中的数据量并限制 Jenkins 在存储大量构建历史时众所周知的文件系统性能挑战,从而提高 Jenkins 的可扩展性和可靠性。
要求和配置
在 Elastic 中存储 Jenkins 管道日志需要:
- Elastic Observability 8.1 或更高版本。
- 可以从Jenkins Agents上访问Jenkins OpenTelemetry Plugin上配置的OpenTelemetry协议端点(即不要指定一个localhost OTLP端点,除非OpenTelemetry收集器与Jenkins Agents部署在同一台主机上)。
- 使用 OpenTelemetry 收集器时,除了跟踪和指标管道之外 ,还设置日志管道
在 Elastic 中存储管道日志:
- 访问到 Jenkins 的配置页面,导航到OpenTelemetry部分。
- 设置OTLP 端点。
- 使用Add Visualization Observability Backend下拉菜单选择Elastic Observability选项。
- 设置Kibana base URL。
- 单击高级按钮以选择存储集成策略。在 Elastic Observability 中存储管道日志有两种选择: - 在 Elastic 中存储管道日志并在 Elastic 或 Jenkins 中查看日志,这意味着您可以在 Jenkins UI 中按需查看存储在 Elastic 中的日志。 - 将管道日志存储在 Elastic 中,并仅在 Elastic 中查看日志,这意味着日志将不再通过 Jenkins UI 可见。 建议配置为选项一,在 Elastic 或 Jenkins 查看日志,因为它通过继续在 Jenkins UI 中呈现日志并允许您验证 Elasticsearch 设置来提供更无缝的用户体验。
在 Kibana 和 Jenkins 中可视化日志
Jenkins OpenTelemetry 插件在 Elasticsearch 中提供管道日志存储,同时使您能够在 Kibana 中可视化日志并继续通过 Jenkins 管道构建控制台显示它们。
这种更高级的设置需要将 Jenkins 控制器连接到 Elasticsearch,并且需要对logs-apm.app
以及最好对该索引模板的ILM策略(默认是logs-apm.app_logs-default_policy
策略)的Metadata具有读取权限。使用“Validate Elasticsearch configuration”来验证设置。
用于在 Elastic 中存储管道日志并在 Elastic 和 Jenkins 中可视化日志的架构
仅在 Kibana 中可视化日志
仅在 Kibana 中可视化日志涉及更简单的设置,不需要从 Jenkins 控制器访问 Elasticsearch。这是因为 Jenkins 管道构建控制台显示了指向 Kibana 日志可视化的超链接,而不是在 Jenkins UI 中显示日志。
用于在 Elastic 中存储管道日志并在 Elastic 中专门显示日志的架构
埋码 CI/CD 管道
观察 CI/CD 管道是通过埋码不同的 CI/CD 和 DevOps 工具来实现的。Elastic 与开源社区合作,利用 OpenTelemetry 提供最佳覆盖范围。
Jenkins
安装 OpenTelemetry 插件
- 在 Jenkins UI 上,转到Manage Jenkins > Manage Plugins。
- 单击Available选项卡,然后搜索OpenTelemetry。
- 选择OpenTelemetry复选框,然后单击Download now and install after restart。 要验证插件是否已安装,请单击Installed选项卡,然后搜索OpenTelemetry Plugin。
配置 OpenTelemetry Plugin
OpenTelemetry 插件需要配置为向 OpenTelemetry 服务报告数据。此外,您还需要 OpenTelemetry 服务的端点、身份验证类型和访问凭证。
- 在 Jenkins UI 上,转到Manage Jenkins > Configure System。
- 转到 OpenTelemetry 插件部分。
- 使用 Elastic APM 服务器 URL 和 APM 服务器身份验证配置您的 OpenTelemetry 端点和身份验证: - 如果使用 Elastic APM secret令牌授权,请选择Bearer Authentication Token,并将令牌添加为 Jenkins secret文本凭证。 在这里插入图片描述
- 如果使用 Elastic API Key 授权,请定义Header Authentications:
- Header name::`"Authorization"`
- Header value:一个秘密文本凭证,值为`"ApiKey an_api_key"`(`an_api_key`是密钥的值)
- 转到Add Visualisation Observability Backend并输入Kibana的地址。
- 最后,还有其他设置需要配置:
- 用于通信的端点证书。
- 发送到 OpenTelemetry 服务的服务名称和服务命名空间。
- 超时和批处理时间。
- 您可能希望从发送的数据中省略的任何步骤。
注意:您可以将 OpenTelemetry 配置导出为环境变量,以便与其他工具(如 otel-cli、Ansible Otel 插件等)一起使用。如果启用此选项,请考虑您可能会在控制台输出中公开credentials。
要了解有关 Jenkins 与 Elastic Observability 集成的更多信息,请参阅OpenTelemetry。
在 Kibana 中安装 Jenkins Bashboard
开箱即用的 Kibana 仪表板有助于可视化 CI/CD 平台的一些指标。
使用Import API或 Kibana UI,您可以安装与 7.12 或更高版本兼容的仪表板 。
例如,您可以按照以下步骤操作:
- 在 Kibana UI 中导入仪表板
- 新仪表板现在可以使用:
Kibana 中的 Jenkins 仪表板
Maven
Maven OpenTelemetry 扩展集成提供对所有 Maven 构建的全面可见性。该扩展为每个构建和性能指标生成跟踪,以帮助您了解哪些 Maven 目标或 Maven 子模块运行最多、失败的频率以及完成所需的时间。
来自CI管道(Jenkins作业或管道)的上下文传播通过符合W3C Trace Context规范的TRACEPARENT
和TRACESTATE
环境变量传递给Maven构建。因此,CI平台上发生的一切也会显示在跟踪中。
您可以使用Maven OpenTelemetry 扩展配置您的 Maven 项目。例如,您可以将以下代码段添加到您的 pom.xml 文件中:
代码语言:html复制<project>
...
<build>
<extensions>
<extension>
<groupId>io.opentelemetry.contrib</groupId>
<artifactId>opentelemetry-maven-extension</artifactId>
<version>1.12.0-alpha</version>
</extension>
</extensions>
</build>
</project>
现在你可以通过将配置细节作为环境变量传递,触发将Maven构建报告性能数据发送到Elastic Observability:
代码语言:shell复制export OTEL_EXPORTER_OTLP_ENDPOINT = "https://elastic-apm-server.example.com:8200"
export OTEL_EXPORTER_OTLP_HEADERS = "Authorization=Bearer an_apm_secret_token"
export OTEL_TRACES_EXPORTER = "otlp"
mvn verify
您也可以使用 Maven 命令行参数-Dmaven.ext.class.path=...
来埋点 Maven 构建,而无需修改 pom.xml 文件
export OTEL_EXPORTER_OTLP_ENDPOINT = "https://elastic-apm-server.example.com:8200"
export OTEL_EXPORTER_OTLP_HEADERS = "Authorization=Bearer an_apm_secret_token"
export OTEL_TRACES_EXPORTER = "otlp"
mvn -Dmaven.ext.class.path=path/to/opentelemetry-maven-extension.jar verify
您还可以从 CI 平台触发 Maven 构建,并在 Elastic Observability 中可视化端到端管道执行,包括 CI 管道和 Maven 构建的详细步骤。
用Jenkins调用Maven构建时,没有必要使用环境变量来配置Maven构建(OTEL_EXPORTER_OTLP_ENDPOINT...
),而是依靠Jenkins将OpenTelemetry配置注入环境变量的能力。。有关更多详细信息,请参阅安装 OpenTelemetry 插件。
执行 Maven 构建的 Jenkins 管道
要了解更多信息,请参阅Maven 构建与 Elastic Observability 的集成。
Ansible
Ansible OpenTelemetry 插件集成提供对所有 Ansible Playbook的可见性。该插件会为每次运行和性能指标生成跟踪,以帮助您了解哪些 Ansible 任务或角色运行最多、失败的频率以及完成所需的时间。
您可以使用Ansible OpenTelemetry 回调插件配置您的 Ansible playbook 。需要安装 Opentelemetry python 库并按照示例部分中的说明配置回调。
来自 Jenkins 作业或管道的上下文传播被传递到 Ansible 运行。因此,CI 中发生的所有事情也会显示在跟踪中。
对 Ansible playbook的可见性
此集成提供开箱即用的服务地图,其中包含连接到 Ansible Playbook 的所有服务。所有这些功能可以帮助你快速、直观地评估你在配置和持续部署中使用的服务。
使用 Ansible 插件检测的 Jenkins 管道执行的 ServiceMap 视图
Otel cli
otel-cli是一个用于发送 OpenTelemetry 跟踪的命令行工具,如果在没有其他隐式集成的情况下需要显式地埋码您的脚本,这将非常有用。
使用 otel-cli 包装器,您可以配置以 shell、make 或其他脚本语言实现的构建脚本。例如,使用 otel-cli 检测下面的 Makefile 有助于将每个目标中的每个命令可视化为跨度。
代码语言:shell复制# see https://blog.container-solutions.com/tagging-docker-images-the-right-way
NAME := acmecorp/foo
TAG := $$(git log -1 --pretty=%!H(MISSING))
IMG := ${NAME}:${TAG}
LATEST := ${NAME}:latest
build:
@otel-cli exec
--name 'docker build'
docker build -t ${IMG} .
@otel-cli exec
--name 'docker tag'
docker tag ${IMG} ${LATEST}
push:
@otel-cli exec
--name 'docker push'
--attrs "http.url=https://docker.elastic.dev"
docker push ${NAME}
login:
@otel-cli exec
--name 'docker login'
--attrs 'rpc.system=grpc'
docker login -u ${DOCKER_USER} -p ${DOCKER_PASS}
要调用使用 otel-cli 进行跟踪的 shell 脚本:
代码语言:javascript复制export OTEL_EXPORTER_OTLP_ENDPOINT = "elastic-apm-server.example.com:8200"
export OTEL_EXPORTER_OTLP_HEADERS = "Authorization=Bearer an_apm_secret_token"
export OTEL_TRACES_EXPORTER = "otlp"
make login build push
Jenkins 构建中包含使用 otel-cli 埋点的 Makefile的执行
使用 otel-cli 埋点的 Jenkins 管道执行的 ServiceMap 视图
Pytest-otel
pytest-otel是一个 pytest 插件,用于将 Python 测试结果作为 OpenTelemetry 跟踪发送。测试跟踪可帮助您了解测试执行、检测瓶颈并跨时间比较测试执行以检测不当行为和问题。
来自 CI 管道(Jenkins 作业或管道)的上下文传播通过TRACEPARENT
.
OTEL_EXPORTER_OTLP_ENDPOINT=https://elastic-apm-server.example.com:8200
OTEL_EXPORTER_OTLP_HEADERS="authorization=Bearer an_apm_secret_token"
OTEL_SERVICE_NAME=pytest_otel
pytest --otel-session-name='My_Test_cases'
Pytest 测试的可见性
Concourse CI
要配置 Concourse CI 以发送跟踪,请参阅跟踪文档。在 Concourse 配置中,您只需要定义CONCOURSE_TRACING_OTLP_ADDRESS
和CONCOURSE_TRACING_OTLP_HEADERS
。
CONCOURSE_TRACING_OTLP_ADDRESS=elastic-apm-server.example.com:8200
CONCOURSE_TRACING_OTLP_HEADERS=Authorization=Bearer your-secret-token
支持上下文传播;因此,您可以从上述集成中受益。
配置 Concourse CI 跟踪后,Concourse CI 管道执行将可在 Elastic Observability 中观测。
Elastic Observability 中的 Concourse CI 管道执行
Concourse CI 不通过 OpenTelemetry 报告健康指标。但是,您可以使用 OpenTelemetry Collector Span Metrics Processor 将管道执行跟踪导出为 KPI 指标,例如吞吐量和管道的错误率。
从部署管道检查服务运行状况
在部署管道中集成自动化服务健康检查对于端到端部署自动化至关重要,这对于提高部署频率至关重要。
Elastic Observability 暴露 HTTP API 以检查服务的运行状况。您可以将这些 API 集成到部署管道中,以验证新部署实例的行为,并根据运行状况自动继续部署或回滚。
以下示例显示了一个金丝雀部署管道,该管道利用Elastic的health check HTTP APIs来自动进行质量检查,然后再从金丝雀推广到整个实例集的部署。
通过调用KIBANA_URL/internal/apm/services
API执行健康检查,将新部署实例上的服务的交易错误率与阈值进行比较。向调用传递以下参数。:
start
和end
: 使用ISO-8601格式的时间间隔(例如“2021-09-01T13:24:12Z”,UTC 时间)kuery
:用于过滤服务名称,例如,正在部署的新版本,将范围缩小到金丝雀实例。例子service.name:"MY_SERVICE_NAME" AND service.version:"1.2.3"
environment
:部署金丝雀实例的环境。比如:production
。
要定义时间范围,使用start
和end
参数。这些参数是ISO-8601格式的日期。要想只查询一个服务,在参数kuery
中组合一个过滤器,然后用表达式`service.name:MY_SERVICE_NAME
and service.version: SERVICE_VERSION来过滤服务。最后通过传递
environment参数来应用一个环境过滤器。要选择所有环境,使用
ENVIRONMENT_ALL`。
API 调用需要身份验证。我们建议使用 API Token 进行身份验证。
API 可能会发生变化,针对持续交付用例优化的稳定 API 即将发布。
代码语言:python代码运行次数:0复制def check_service_health(service_name, service_version, error_rate_threshold, kibana_url, api_token):
now = datetime.now()
five_minutes_ago = now - timedelta(minutes=5)
params = {
"start": five_minutes_ago.strftime("%Y-%m-%dT%H:%M:%SZ"),
"end": now.strftime("%Y-%m-%dT%H:%M:%SZ"),
"kuery": "service.name:{} and service.version:{}".format(service_name, service_version),
"environment": "ENVIRONMENT_ALL"
}
url = "{}/internal/apm/services?{}".format(kibana_url, urllib.parse.urlencode(params))
req = urllib.request.Request(url=url, headers={"Authorization": "Bearer {}".format(api_token)})
with urllib.request.urlopen(req) as response:
body = response.read().decode("utf8")
obj = json.loads(body)
if len(obj['items']) > 0 and obj['items'][0].transactionErrorRate > error_rate_threshold:
raise Exception("Error rate for service {} is higher than threshold {}, current value is {}".format(service_name, error_rate_threshold, obj['items'][0].transactionErrorRate))