Description
Background and Motivation
.NET 8 added support for metrics to ASP.NET Core. The most commonly used metric is http.server.request.duration
, which captures request duration along with many other tags.
Today this metric is always captured, however there are situations where it is useful to disable collection. For example, system endpoints such as health checks and Prometheus scraping. These system endpoints are regularly polled and can distort expected results for people who want metrics to reflect true application usage.
There is high customer interest in solving this issue: #50654
Proposed API
There are two ways to specify metrics are disabled. The first is statically, per-endpoint, using metadata.
Assembly Microsoft.AspNetCore.Http.Abstractions
:
namespace Microsoft.AspNetCore.Http.Metadata;
+ public interface IDisableHttpMetricsMetadata
+ {
+ }
Assembly Microsoft.AspNetCore.Http.Extensions
:
namespace Microsoft.AspNetCore.Http;
+ public sealed class DisableHttpMetricsAttribute : Attribute, IDisableHttpMetricsMetadata
+ {
+ }
+ public static class HttpMetricsEndpointConventionBuilderExtensions
+ {
+ public static IEndpointConventionBuilder DisableHttpMetrics(this IEndpointConventionBuilder builder);
+ }
The second is dynamically disabling, per-request, using a feature.
namespace Microsoft.AspNetCore.Http.Features;
public interface IHttpMetricsTagsFeature
{
+ // This is a DIM property added to an existing interface.
+ // It's not ideal, but I don't think it is worth adding a new interface.
+ // I believe with a DIM property, setting it does nothing, and it will always return false. This is fine.
+ public bool MetricsDisabled { get; set; }
}
Usage Examples
Controller:
public class SystemController
{
[DisableHttpMetrics]
public IActionResult HealthCheck()
{
// ...
}
}
Minimal API:
app.MapPrometheusScrapingEndpoint().DisableHttpMetrics();
Dynamically:
app.Use(async (context, next) =>
{
// Disable metrics 50% of the time.
if (Random.Shared.Next(0, 10) % 2 == 0)
{
context.Features.GetRequiredFeature<IHttpMetricsTagsFeature>().MetricsDisabled = true;
}
await next.Invoke();
});
Alternative Designs
Add a dedicated feature, e.g. IHttpMetricsDisableFeature
, that would allow requests (or middleware) to decide whether to disable metrics dynamically.