.NET CORE 接入 OpenTelemetry 收集指标、链路跟踪数据
1. OpenTelemetry简介
OpenTelemetry(简称 OTel)是一个开源的云原生观测框架,由 Cloud Native Computing Foundation(CNCF)维护。它的目标是提供一套标准化的工具、API 和 SDK,帮助开发者收集、生成和管理应用程序的遥测数据(如指标、日志、分布式追踪等),从而实现对系统运行状态的全面观测。
2. OpenTelemetry 能做什么?
统一观测数据标准:
标准化了指标(Metrics)、日志(Logs)和分布式追踪(Traces)的格式(如 OTLP 协议),解决多工具数据格式不兼容的问题。
分布式追踪(Distributed Tracing):
跟踪请求在微服务架构中的完整流转路径,记录每个服务的耗时、状态和依赖关系。
帮助定位性能瓶颈(例如:哪个服务导致请求延迟?)。
指标(Metrics)收集:
自动采集系统性能指标(如 CPU 使用率、请求吞吐量、错误率等),也支持自定义业务指标。
与 Prometheus、Grafana 等监控工具无缝集成。
日志(Logs)集成:
将日志与追踪和指标关联,提供更完整的上下文(例如:某条错误日志对应的请求链路)。
灵活的导出与集成:
支持将数据导出到多种后端系统(如 Jaeger、Zipkin、Prometheus、Elasticsearch、Datadog 等),无需修改代码即可切换观测平台。
自动代码插桩(Auto-Instrumentation):
对常见框架(如 HTTP 服务、数据库驱动)自动注入观测代码,减少手动插桩的工作量。
3. OpenTelemetry Clinet 接入
创建项目并引用相关OpenTelemetry包,使用正确的提供程序配置 OpenTelemetry
<Project Sdk="Microsoft.NET.Sdk.Web">
<PropertyGroup>
<TargetFramework>net8.0</TargetFramework>
<Nullable>enable</Nullable>
<ImplicitUsings>enable</ImplicitUsings>
</PropertyGroup>
<ItemGroup>
<PackageReference Include="Newtonsoft.Json" Version="13.0.3" />
<PackageReference Include="OpenTelemetry.Exporter.Console" Version="1.11.2" />
<PackageReference Include="OpenTelemetry.Exporter.OpenTelemetryProtocol" Version="1.11.2" />
<PackageReference Include="OpenTelemetry.Exporter.Prometheus.AspNetCore" Version="1.11.2-beta.1" />
<PackageReference Include="OpenTelemetry.Extensions.Hosting" Version="1.11.2" />
<PackageReference Include="OpenTelemetry.Instrumentation.AspNetCore" Version="1.11.1" />
<PackageReference Include="OpenTelemetry.Instrumentation.Http" Version="1.11.1" />
<PackageReference Include="OpenTelemetry.Instrumentation.Runtime" Version="1.11.1" />
<PackageReference Include="Swashbuckle.AspNetCore" Version="7.3.1" />
</ItemGroup>
<ItemGroup>
<PackageReference Include="Newtonsoft.Json" Version="13.0.3" />
<PackageReference Include="Swashbuckle.AspNetCore" Version="7.3.1" />
</ItemGroup>
</Project>配置 OpenTelemetry 用于向 OpenTelemetry 服务端发送Tracing、Metrics、Logging 数据
using OpenTelemetry.Instrumentation.AspNetCore;
using OpenTelemetry.Logs;
using OpenTelemetry.Metrics;
using OpenTelemetry.Resources;
using OpenTelemetry.Trace;
using Otlp.AspNetCore;
var appBuilder = WebApplication.CreateBuilder(args);
// 创建一个服务来公开ActivitySource,并创建用于手动检测的Metric Instruments
appBuilder.Services.AddSingleton<Instrumentation>();
// 清除WebApplication主机使用的默认日志记录提供程序
appBuilder.Logging.ClearProviders();
// 使用自动启动配置OpenTetry日志记录、指标和跟踪
// 从OpenTetry添加OpenTetry扩展。扩展。群众或部队的集合
appBuilder.Services.AddOpenTelemetry()
.ConfigureResource(r => r
.AddService(
serviceName: appBuilder.Configuration.GetValue("ServiceName", defaultValue: "otel-test")!,
serviceVersion: typeof(Program).Assembly.GetName().Version?.ToString() ?? "unknown",
serviceInstanceId: Environment.MachineName))
.WithTracing(builder =>
{
// Tracing
// 确保TracerProvider订阅了任何自定义ActivitySource。
builder
.AddSource(Instrumentation.ActivitySourceName)
.SetSampler(new AlwaysOnSampler())
.AddHttpClientInstrumentation()
.AddAspNetCoreInstrumentation();
// 对AspNetCore检测选项使用IConfiguration绑定。
appBuilder.Services.Configure<AspNetCoreTraceInstrumentationOptions>(appBuilder.Configuration.GetSection("AspNetCoreInstrumentation"));
builder.AddOtlpExporter(otlpOptions =>
{
// 直接将IConfiguration用于Otlp导出器端点选项
otlpOptions.Endpoint = new Uri(appBuilder.Configuration.GetValue("Otlp:Endpoint", defaultValue: "http://localhost:4317"));
});
})
.WithMetrics(builder =>
{
// Metrics
// 确保MeterProvider订阅任何自定义指标。
builder
.AddMeter(Instrumentation.MeterName)
.SetExemplarFilter(ExemplarFilterType.TraceBased)
.AddRuntimeInstrumentation()
.AddHttpClientInstrumentation()
.AddAspNetCoreInstrumentation();
builder.AddOtlpExporter(otlpOptions =>
{
// 直接将IConfiguration用于Otlp导出器端点选项。
otlpOptions.Endpoint = new Uri(appBuilder.Configuration.GetValue("Otlp:Endpoint", defaultValue: "http://localhost:4317")!);
});
})
.WithLogging(builder =>
{
// Logging
builder.AddConsoleExporter();
builder.AddOtlpExporter(otlpOptions =>
{
// 直接将IConfiguration用于Otlp导出器端点选项。
otlpOptions.Endpoint = new Uri(appBuilder.Configuration.GetValue("Otlp:Endpoint", defaultValue: "http://localhost:4317"));
});
});
appBuilder.Services.AddControllers();
appBuilder.Services.AddEndpointsApiExplorer();
appBuilder.Services.AddSwaggerGen();
var app = appBuilder.Build();
if (app.Environment.IsDevelopment())
{
app.UseSwagger();
app.UseSwaggerUI();
}
app.UseHttpsRedirection();
app.UseAuthorization();
app.MapControllers();
app.Run();OpenTelemetry .NET Client , 详细介绍如何接入并举例进行参考
4. 官方资料
5. OpenTelemetry Collector 使用和安装
OpenTelemetry Collector 接收跟踪、指标和日志,处理遥测数据,并将其导出到使用其组件的各种可观察性后端,如:Jaeger
OpenTelemetry Collector 配置问卷参考:
receivers:
otlp:
protocols:
grpc:
endpoint: 0.0.0.0:4317
http:
endpoint: 0.0.0.0:4318
processors:
batch:
exporters:
otlp/jaeger:
endpoint: 10.0.12.10:4317
tls:
insecure: true
prometheus:
endpoint: 0.0.0.0:8889
service:
pipelines:
traces:
receivers: [otlp]
processors: []
exporters: [otlp/jaeger]
metrics:
receivers: [otlp]
processors: []
exporters: [prometheus]exporters.prometheus.endpoint=0.0.0.0:8889,对应prometheus采集地址=http://服务器节点:8889/metare;
exporters.otlp/jaeger.endpoint=10.0.12.10:4317,对映Jaeger 链路数据采集器地址
6. prometheus安装和使用
配置文件参考
global:
scrape_interval: 15s # Set the scrape interval to every 15 seconds. Default is every 1 minute.
evaluation_interval: 15s # Evaluate rules every 15 seconds. The default is every 1 minute.
# scrape_timeout is set to the global default (10s).
# Alertmanager configuration
alerting:
alertmanagers:
- static_configs:
- targets:
# - alertmanager:9093
# Load rules once and periodically evaluate them according to the global 'evaluation_interval'.
rule_files:
# - "first_rules.yml"
# - "second_rules.yml"
scrape_configs:
# prometheus
- job_name: prometheus
static_configs:
- targets: ['10.0.12.10:9090']
# prometheus-mysqld-exporter
- job_name: mysql
metrics_path: /probe
params:
auth_module: [client]
static_configs:
- targets:
# All mysql hostnames or unix sockets to monitor.
- 10.0.12.10:3306
relabel_configs:
- source_labels: [__address__]
target_label: __param_target
- source_labels: [__param_target]
target_label: instance
- target_label: __address__
# The mysqld_exporter host:port
replacement: 10.0.12.10:9104
# opentelemetry-metrics
- job_name: opentelemetry
metrics_path: /metrics
static_configs:
- targets:
- 10.0.12.10:8889

7. Jaeger安装和使用
OpenTelemetry Collector 接收跟踪的数据会被 OpenTelemetry Collector 发送至 jaeger ,用于在jaeger 展示链路数据

8. Grafana安装和使用
运行 Grafana Docker 镜像
