我目前正在将OpenTelemeter集成到一个DotNet项目中,并且正在使用Prometheus Exporter在/v1/metrics路径上公开我的指标.鉴于该项目目前正在开发中,我们预计该系统提供的指标将发生重大变化.我们正在寻找一种方法来同时在不同的端点路径上导出不同版本的指标,例如/v2/metrics、/v3/metrics等.

这是正在讨论的代码部分:

    services.AddOpenTelemetry()
        .WithMetrics(opts => opts
            .SetResourceBuilder(ResourceBuilder.CreateDefault().AddService("rrfc"))
            .AddMeter(TelemetryUnit.CALL_TELEMETRY_METER)
            .AddPrometheusExporter(opt =>
            {
                opt.ScrapeEndpointPath = "/v1/metrics";
            }));
    
    app.UseOpenTelemetryPrometheusScrapingEndpoint();

有没有办法用不同的SCrapeEndpoint路径选项配置多个Prometheus导出器,并在同一项目中使用它们?或者,还有其他方法来实现这一目标吗?如有任何帮助或指导,将不胜感激.先谢谢你.

What I have already tried:

我曾try 添加另一个具有不同刮擦端点的普罗米修斯导出器,但将始终使用最后一个.

推荐答案

如您所见,最后配置的导出器将获胜.WithMetricsdoc comments表示:

注意:这是安全的,可以由库作者多次调用. 将按顺序应用每个已注册的配置操作.

与使用扩展方法不同,您需要手动实例化两个独立的MetricProvider,并如下所示擦除端点:

var meterProvider1 = Sdk.CreateMeterProviderBuilder()
    .SetResourceBuilder(ResourceBuilder.CreateDefault().AddService("rrfc"))
    .AddMeter(TelemetryUnit.CALL_TELEMETRY_METER)
    .AddPrometheusExporter("v1 metrics", opt =>
    {
        opt.ScrapeEndpointPath = "/v1/metrics";
    }, name: "v1 metrics");

var meterProvider2 = Sdk.CreateMeterProviderBuilder()
    .SetResourceBuilder(ResourceBuilder.CreateDefault().AddService("rrfc"))
    .AddMeter(TelemetryUnit.CALL_TELEMETRY_METER)
    .AddPrometheusExporter("v2 metrics", opt =>
    {
        opt.ScrapeEndpointPath = "/v2/metrics";
    });

app.UseOpenTelemetryPrometheusScrapingEndpoint(meterProvider1, null, null, null, "v1 metrics");
app.UseOpenTelemetryPrometheusScrapingEndpoint(meterProvider2, null, null, null, "v2 metrics");

如果为Looking at the implementation,则将null传递给Path参数将导致在使用命名选项时查找导出器选项以检索配置的导出器路径.

手动创建多个MeterProvider实例意味着要弄清楚如何管理它们的生命周期.WithMetrics扩展方法通过连接到.NET依赖项注入框架来实现这一点.

根据doc commentsCreateMeterProviderBuilder的州:

创建一个MeterProviderBuilder,用于构建 A MeterProvider.在典型的应用程序中,单个 MeterProvider在应用程序启动时创建并释放 在应用程序关闭时.重要的是要确保提供者不是 处置得太早了.

一种快速的解决方案是将这两个MeterProvider个实例注册为单例,如下所示:

services.AddSingleton(meterProvider1);
services.AddSingleton(meterProvider2);

当应用程序终止时,这应该会正确地处理这两个实例.

.net相关问答推荐

为什么 PropertyInfo.SetValue 在此示例中不起作用以及如何使其起作用?

Azure SignalR 和微服务

信号量的多线程问题

在 ASP.NET MVC 中我可以在哪里放置自定义类?

是否可以像 WebView 一样在 Windows 窗体中嵌入 Gecko 或 Webkit?

ASP.NET MVC:隐藏字段值不会使用 HtmlHelper.Hidden 呈现

extern 在 C# 中是如何工作的?

Automapper:使用 ReverseMap() 和 ForMember() 进行双向映射

如何在 WPF 中创建/制作圆角按钮?

什么是编组?当某些东西被编组时会发生什么?

C# 中基于接口编程的运算符重载

基于多个字符分隔符拆分字符串

找不到 Assert.Fail 和 Assert.Pass 或等效项

日期时间是什么意思?在 C# 中是什么意思?

如何在可取消的异步/等待中处理 TransactionScope?

如何在 WebBrowser 控件中注入 Javascript?

使用没有catch块的try-finally块

在 IIS 中访问 .svc 文件时出现 HTTP 404

如何使用匿名方法返回值?

泛型类的静态成员是否与特定实例相关联?