首页 > 解决方案 > Aspnetcore 健康检查降级状态被忽略

问题描述

我在 MSDN 网站上发布的信息之后学习了 HealthChecks:https ://docs.microsoft.com/en-us/aspnet/core/host-and-deploy/health-checks?view=aspnetcore-5.0#register-健康检查服务

下面的代码片段告诉如果不健康的检查返回,我可以通过说它已降级来覆盖该值。

services.AddHealthChecks()
    .AddCheck<ExampleHealthCheck>(
        "example_health_check",
        failureStatus: HealthStatus.Degraded,
        tags: new[] { "example" });

所以我用这个实现尝试了这个,假设我会得到一个降级的结果而不是一个不健康的结果:

public class Startup
{
    public Startup(IConfiguration configuration)
    {
        Configuration = configuration;
    }
    public IConfiguration Configuration { get; }
    public void ConfigureServices(IServiceCollection services)
    {
        services.AddHealthChecks().AddCheck<ExampleHealthCheck>("ExampleHealthCheck", failureStatus: HealthStatus.Degraded);
    }
    public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
    {
        app.UseRouting();
        app.UseEndpoints(endpoints =>
        {
            endpoints.MapHealthChecks("/health");
        });
    }
}
internal class ExampleHealthCheck : IHealthCheck
{
    public Task<HealthCheckResult> CheckHealthAsync(HealthCheckContext context, CancellationToken cancellationToken = default(CancellationToken))
    {
        return Task.FromResult(HealthCheckResult.Unhealthy("An unhealthy result."));
    }
}

有人可以解释为什么这不起作用或我哪里弄错了吗?

标签: c#asp.net-corehealth-check

解决方案


这很令人困惑,因为您希望 HealthCheck 自动返回您在failureStatus属性上定义的结果,但您的 HealthCheck 显式返回Unhealthy

如果你看一下GitHub 上AddHealthCheck<T>的方法,你会看到只创建了一个.HealthCheckRegistration

public static IHealthChecksBuilder AddCheck(
            this IHealthChecksBuilder builder,
            string name,
            IHealthCheck instance,
            HealthStatus? failureStatus = null,
            IEnumerable<string>? tags = null,
            TimeSpan? timeout = null)
        {
            if (builder == null)
            {
                throw new ArgumentNullException(nameof(builder));
            }

            if (name == null)
            {
                throw new ArgumentNullException(nameof(name));
            }

            if (instance == null)
            {
                throw new ArgumentNullException(nameof(instance));
            }

            return builder.Add(new HealthCheckRegistration(name, instance, failureStatus, tags, timeout));
        }

该对象随后在您的运行状况检查的上下文中传递。然后,您可以读取失败时预期的 failureStatus,然后HealthCheckResult从中返回一个。在您的情况下,这将返回Degraded

public class Startup
{
    public Startup(IConfiguration configuration)
    {
        Configuration = configuration;
    }
    public IConfiguration Configuration { get; }
    public void ConfigureServices(IServiceCollection services)
    {
        services.AddHealthChecks().AddCheck<ExampleHealthCheck>("ExampleHealthCheck", failureStatus: HealthStatus.Degraded);
    }
    public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
    {
        app.UseRouting();
        app.UseEndpoints(endpoints =>
        {
            endpoints.MapHealthChecks("/health");
        });
    }
}

internal class ExampleHealthCheck : IHealthCheck
{
   public Task<HealthCheckResult> CheckHealthAsync(HealthCheckContext context, CancellationToken cancellationToken = default(CancellationToken))
   {
      return Task.FromResult(new HealthCheckResult(context.Registration.FailureStatus));
   }
}

推荐阅读