编译时指标源生成

.NET 的计量基础结构旨在为新式 .NET 应用程序提供高度可用且高性能的计量解决方案。

若要使用源生成的计量,请创建一个类,用于定义代码可以生成的指标的名称和维度。 然后,使用 partial 方法签名创建类。

源代码生成器自动生成代码,该代码公开了强类型的计量类型和方法,你可以调用这些类型和方法来记录度量值。 生成的方法采用高效形式实现,与传统的计量解决方案相比,这降低了计算开销。

立即开始

若要开始,请安装 📦 Microsoft.Extensions.Telemetry.Abstractions NuGet 包:

dotnet add package Microsoft.Extensions.Telemetry.Abstractions

有关详细信息,请参阅 dotnet add package管理 .NET 应用程序中的包依赖项

泛型属性

泛型属性需要 C# 11 或更高版本。 对于 C# 10 或更早版本,请改用非泛型属性。

以下示例演示声明三个指标的类。 这些方法用属性标记,并声明为 staticpartial。 代码生成器在生成时运行,并提供这些方法的实现以及随附的类型。

internal class MetricConstants
{
    public const string EnvironmentName = "env";
    public const string Region = "region";
    public const string RequestName = "requestName";
    public const string RequestStatus = "requestStatus";
}

以下代码演示如何将生成器与基元类型配合使用:

using System.Diagnostics.Metrics;
using Microsoft.Extensions.Diagnostics.Metrics;

namespace MetricsGen;

internal static partial class Metric
{
    // an explicit metric name is given
    [Histogram<long>("requestName", "duration", Name = "MyCustomMetricName")]
    public static partial Latency CreateLatency(Meter meter);

    // no explicit metric name given, it is auto-generated from the method name
    [Counter<int>(
        MetricConstants.EnvironmentName,
        MetricConstants.Region,
        MetricConstants.RequestName,
        MetricConstants.RequestStatus)]
    public static partial TotalCount CreateTotalCount(Meter meter);

    [Counter<int>]
    public static partial TotalFailures CreateTotalFailures(this Meter meter);
}

上一个声明自动返回以下内容:

  • Latency 带有Record方法的类
  • 包含 Add 方法的 TotalCount
  • 包含 Add 方法的 TotalFailures 类。

这些属性指示每个指标使用的维度集。 生成的类型的签名如下所示:

internal class TotalCount
{
    public void Add(int value, object? env, object? region, object? requestName, object? requestStatus)
}

internal TotalFailures
{
    public void Add(int value)
}

internal class Latency
{
    public void Record(long value, object? requestName, object? duration);
}

特性中指定的维度已转换为 Add 参数和 Record 方法。 然后使用生成的方法创建这些类型的实例。 创建实例后,可以调用 AddRecord 注册指标值,如以下示例所示:

internal class MyClass
{
    // these variable are for example purposes, the dimensions values should depend on your business logic.
    private string envName = "envValue";
    private string regionName = "regionValue";
    private string requestName = "requestNameValue";
    private string status = "requestStatusValue";
    private string duration = "1:00:00";

    private readonly Latency _latencyMetric;
    private readonly TotalCount _totalCountMetric;
    private readonly TotalFailures _totalFailuresMetric;

    public MyClass(Meter meter)
    {
        // Create metric instances using the source-generated factory methods
        _latencyMetric = Metric.CreateLatency(meter);
        _totalCountMetric = Metric.CreateTotalCount(meter);
        // This syntax is available since `CreateTotalFailures` is defined as an extension method
        _totalFailuresMetric = meter.CreateTotalFailures();
    }

    public void ReportSampleRequestCount()
    {
        // method logic ...

        // Invoke Add on the counter and pass the dimension values you need.
        _totalCountMetric.Add(1, envName, regionName, requestName, status);
    }

    public void ReportSampleLatency()
    {
        // method logic ...

        // Invoke Record on the histogram and pass the dimension values you need.
        _latencyMetric.Record(1, requestName, duration);
    }

    public void ReportSampleFailuresCount()
    {
        // method logic ...

        // Invoke Add on the counter and pass the dimension values you need.
        _totalFailuresMetric.Add(1);
    }
}

指标方法要求

指标方法受以下限制:

  • 它们必须是 public static partial
  • 返回类型必须是唯一的。
  • 它们的名称不得以下划线开头。
  • 其参数名称不得以下划线开头。
  • 其第一个参数必须是 Meter 类型。 指标方法受以下限制:

另请参阅

有关支持的指标的详细信息,请参阅 工具类型 ,了解如何选择在不同情况下要使用的检测器。