Notatka
Dostęp do tej strony wymaga autoryzacji. Może spróbować zalogować się lub zmienić katalogi.
Dostęp do tej strony wymaga autoryzacji. Możesz spróbować zmienić katalogi.
Przez Glenn Condron i Juergen Gutsch
Note
Nie jest to najnowsza wersja tego artykułu. Aby zapoznać się z aktualną wersją, zobacz artykuł w wersji .NET 10.
Warning
Ta wersja ASP.NET Core nie jest już obsługiwana. Aby uzyskać więcej informacji, zobacz zasady pomocy technicznej platformy .NET i platformy .NET Core. Aby zapoznać się z aktualną wersją, zobacz artykuł w wersji .NET 10.
ASP.NET Core oferuje middleware sprawdzania kondycji oraz biblioteki do raportowania kondycji składników infrastruktury aplikacji.
Testy kondycji są udostępniane przez aplikację jako punkty końcowe HTTP. Punkty końcowe kontroli kondycji można skonfigurować dla różnych scenariuszy monitorowania w czasie rzeczywistym:
- Sondy kondycji mogą być używane przez koordynatorów kontenerów i moduły równoważenia obciążenia w celu sprawdzenia stanu aplikacji. Na przykład orkiestrator kontenerów może reagować na niepowodzenie sprawdzania kondycji, zatrzymując wdrożenie stopniowe lub ponownie uruchamiając kontener. Moduł równoważenia obciążenia może reagować na problemy z aplikacją przez przekierowanie ruchu z wadliwego wystąpienia do wystąpienia działającego poprawnie.
- Użycie pamięci, dysku i innych zasobów serwera fizycznego można monitorować pod kątem stanu dobrej kondycji.
- Testy kondycji mogą testować zależności aplikacji, takie jak bazy danych i zewnętrzne punkty końcowe usługi, w celu potwierdzenia dostępności i normalnego działania.
Testy kondycji są zwykle używane z zewnętrzną usługą monitorowania lub koordynatorem kontenerów w celu sprawdzenia stanu aplikacji. Przed dodaniem kontroli kondycji do aplikacji zdecyduj, który system monitorowania ma być używany. System monitorowania określa, jakie typy testów zdrowia należy utworzyć i jak skonfigurować ich punkty końcowe.
Podstawowa sonda kondycji
W przypadku wielu aplikacji podstawowa konfiguracja sondy kondycji, która zgłasza dostępność aplikacji do przetwarzania żądań (statusu działania) jest wystarczająca do ustalenia stanu aplikacji.
Podstawowa konfiguracja rejestruje usługi monitorowania stanu i wywołuje middleware do kontroli stanu zdrowia, aby odpowiedzieć na adresie URL odpowiedzią zdrowotną. Domyślnie żadne konkretne kontrole kondycji nie są rejestrowane w celu przetestowania żadnej konkretnej zależności lub podsystemu. Aplikacja jest uważana za w dobrej kondycji, jeśli może odpowiadać pod adresem URL punktu końcowego zdrowia. Domyślny zapisujący odpowiedzi zapisuje HealthStatus jako odpowiedź w postaci zwykłego tekstu do klienta. Parametr HealthStatus jest HealthStatus.Healthy, HealthStatus.Degraded lub HealthStatus.Unhealthy.
Zarejestruj usługi sprawdzania kondycji w AddHealthChecks w Program.cs. Utwórz punkt końcowy kontroli kondycji, wywołując polecenie MapHealthChecks.
Poniższy przykład tworzy punkt końcowy kontroli kondycji: /healthz.
var builder = WebApplication.CreateBuilder(args);
builder.Services.AddHealthChecks();
var app = builder.Build();
app.MapHealthChecks("/healthz");
app.Run();
Doker HEALTHCHECK
Platforma Docker zawiera wbudowaną HEALTHCHECK dyrektywę, której można użyć do sprawdzenia stanu aplikacji korzystającej z podstawowej konfiguracji kontroli kondycji:
HEALTHCHECK CMD curl --fail http://localhost:5000/healthz || exit 1
W poprzednim przykładzie użyto curl do wysłania żądania HTTP do punktu końcowego sprawdzania kondycji na /healthz.
curl nie jest uwzględniana w obrazach kontenerów systemu Linux platformy .NET, ale można ją dodać, instalując wymagany pakiet w pliku Dockerfile. Kontenery korzystające z obrazów opartych na systemie Alpine Linux mogą używać dołączonego wget zamiast curl.
Tworzenie kontroli kondycji
Tworzenie kontroli kondycji przez zaimplementowanie interfejsu IHealthCheck . Metoda CheckHealthAsync zwraca wartość HealthCheckResult , która wskazuje kondycję jako Healthy, Degradedlub Unhealthy. Wynik jest zapisywany jako odpowiedź w postaci zwykłego tekstu z konfigurowalnym kodem stanu. Zobacz sekcję Opcje sprawdzania kondycji .
HealthCheckResult może również zwracać opcjonalne pary klucz-wartość.
W poniższym przykładzie pokazano układ kontroli kondycji:
public class SampleHealthCheck : IHealthCheck
{
public Task<HealthCheckResult> CheckHealthAsync(
HealthCheckContext context, CancellationToken cancellationToken = default)
{
var isHealthy = true;
// ...
if (isHealthy)
{
return Task.FromResult(
HealthCheckResult.Healthy("A healthy result."));
}
return Task.FromResult(
new HealthCheckResult(
context.Registration.FailureStatus, "An unhealthy result."));
}
}
Logika kontroli kondycji jest umieszczana w metodzie CheckHealthAsync . W poprzednim przykładzie ustawiono tymczasową zmienną isHealthy, na wartość true. Jeśli wartość parametru isHealthy jest ustawiona na false, zwracany jest stan HealthCheckRegistration.FailureStatus.
Jeśli CheckHealthAsync podczas sprawdzania wystąpi wyjątek, zostanie zwrócony nowy HealthReportEntry z ustawioną HealthReportEntry.Status na FailureStatus. Ten stan jest definiowany przez AddCheck (zobacz sekcję Rejestrowanie usług sprawdzania kondycji) i zawiera wewnętrzny wyjątek, który spowodował niepowodzenie sprawdzania. Parametr Description jest ustawiony na komunikat wyjątku.
Rejestrowanie usług kontroli kondycji
Aby zarejestrować usługę sprawdzania kondycji, wywołaj AddCheck w Program.cs:
builder.Services.AddHealthChecks()
.AddCheck<SampleHealthCheck>("Sample");
Przeciążenie AddCheck pokazane w poniższym przykładzie ustawia stan błędu (HealthStatus) w celu raportowania, gdy kontrola kondycji zgłasza błąd. Jeśli stan niepowodzenia jest ustawiony na null (wartość domyślna), HealthStatus.Unhealthy jest zgłaszany. To przeciążenie jest przydatnym scenariuszem dla autorów bibliotek, gdzie status awarii wskazywany przez bibliotekę jest wymuszany przez aplikację, gdy wystąpi błąd w sprawdzaniu kondycji, o ile implementacja sprawdzania kondycji respektuje to ustawienie.
Tagi mogą służyć do filtrowania kontroli kondycji. Tagi są opisane w sekcji Filtrowanie kontroli kondycji systemu.
builder.Services.AddHealthChecks()
.AddCheck<SampleHealthCheck>(
"Sample",
failureStatus: HealthStatus.Degraded,
tags: new[] { "sample" });
AddCheck może również wykonać funkcję lambda. W poniższym przykładzie sprawdzanie kondycji zawsze zwraca zdrowy wynik.
builder.Services.AddHealthChecks()
.AddCheck("Sample", () => HealthCheckResult.Healthy("A healthy result."));
Wywołaj metodę AddTypeActivatedCheck , aby przekazać argumenty do implementacji kontroli kondycji. W poniższym przykładzie kontrola kondycji aktywowana typem akceptuje liczbę całkowitą i ciąg w konstruktorze:
public class SampleHealthCheckWithArgs : IHealthCheck
{
private readonly int _arg1;
private readonly string _arg2;
public SampleHealthCheckWithArgs(int arg1, string arg2)
=> (_arg1, _arg2) = (arg1, arg2);
public Task<HealthCheckResult> CheckHealthAsync(
HealthCheckContext context, CancellationToken cancellationToken = default)
{
// ...
return Task.FromResult(HealthCheckResult.Healthy("A healthy result."));
}
}
Aby zarejestrować poprzednią kontrolę kondycji, wywołaj metodę AddTypeActivatedCheck za pomocą liczby całkowitej i ciągu przekazanego jako argumenty:
builder.Services.AddHealthChecks()
.AddTypeActivatedCheck<SampleHealthCheckWithArgs>(
"Sample",
failureStatus: HealthStatus.Degraded,
tags: new[] { "sample" },
args: new object[] { 1, "Arg" });
Zastosuj trasowanie kontroli zdrowia
W Program.cs wywołaj MapHealthChecks na budowniczym punktu końcowego z adresem URL punktu końcowego lub ścieżką względną:
app.MapHealthChecks("/healthz");
Wymagaj hosta
Wywołaj RequireHost , aby określić co najmniej jednego dozwolonego hosta dla endpointu kontroli kondycji. Użyj formatu Unicode, a nie punycode dla hostów i możesz dołączyć port. Jeśli nie podasz kolekcji, zostanie zaakceptowany każdy host.
app.MapHealthChecks("/healthz")
.RequireHost("www.contoso.com:5001");
Aby ograniczyć punkt końcowy kontroli kondycji do odpowiadania tylko na określonym porcie, określ port w wywołaniu metody RequireHost. Zazwyczaj użyj tego podejścia w środowisku kontenera, aby uwidocznić port na potrzeby usług monitorowania:
app.MapHealthChecks("/healthz")
.RequireHost("*:5001");
Warning
Interfejs API opierający się na nagłówku Host, tak jak HttpRequest.Host oraz RequireHost, podlega potencjalnemu fałszowaniu przez klientów.
Aby zapobiec fałszowaniu hostów i portów, użyj jednej z następujących metod:
- Użyj HttpContext.Connection (ConnectionInfo.LocalPort), gdzie sprawdzane są porty.
- Zastosowanie filtrowania hostów.
Aby zapobiec fałszowaniu portu przez nieautoryzowanych klientów, wywołaj metodę RequireAuthorization:
app.MapHealthChecks("/healthz")
.RequireHost("*:5001")
.RequireAuthorization();
Aby uzyskać więcej informacji, zobacz Dopasowywanie hostów w trasach za pomocą elementu RequireHost.
Wymagaj autoryzacji
Wywołaj polecenie RequireAuthorization , aby uruchomić oprogramowanie pośredniczące autoryzacji w punkcie końcowym żądania sprawdzania kondycji. Przeciążenie RequireAuthorization akceptuje co najmniej jedną zasady autoryzacji. Jeśli nie podano zasad, są używane domyślne zasady autoryzacji:
app.MapHealthChecks("/healthz")
.RequireAuthorization();
Włącz żądania Cross-Origin (CORS)
Mimo że ręczne uruchamianie kontroli kondycji z przeglądarki nie jest typowym scenariuszem, oprogramowanie pośredniczące CORS można włączyć poprzez wywołanie RequireCors na punktach końcowych kontroli kondycji. Przeciążenie RequireCors akceptuje delegata konstruktora zasad CORS (CorsPolicyBuilder) lub nazwę zasad. Aby uzyskać więcej informacji, zobacz Włączanie żądań między źródłami (CORS) w ASP.NET Core.
Opcje kontroli kondycji
HealthCheckOptions umożliwia dostosowanie zachowania kontroli kondycji:
- Kontrole kondycji filtrów
- Dostosowywanie kodu stanu HTTP
- Blokowanie nagłówków pamięci podręcznej
- Dostosowywanie danych wyjściowych
Filtrowanie sprawdzania kondycji
Domyślnie oprogramowanie pośredniczące sprawdzania kondycji uruchamia wszystkie zarejestrowane kontrole kondycji. Aby uruchomić podzbiór testów kondycji, podaj funkcję, która zwraca wartość logiczną jako argument opcji Predicate.
Poniższy przykład filtruje kontrole zdrowotne, tak aby uruchamiane były tylko te oznaczone tagiem sample.
app.MapHealthChecks("/healthz", new HealthCheckOptions
{
Predicate = healthCheck => healthCheck.Tags.Contains("sample")
});
Dostosowywanie kodu stanu HTTP
Użyj ResultStatusCodes do dostosowywania mapowania stanu kondycji na kody stanu HTTP. Następujące StatusCodes przypisania są wartościami domyślnymi używanymi przez middleware. Zmień wartości kodu stanu, aby spełnić wymagania:
app.MapHealthChecks("/healthz", new HealthCheckOptions
{
ResultStatusCodes =
{
[HealthStatus.Healthy] = StatusCodes.Status200OK,
[HealthStatus.Degraded] = StatusCodes.Status200OK,
[HealthStatus.Unhealthy] = StatusCodes.Status503ServiceUnavailable
}
});
Tłumienie nagłówków pamięci podręcznej
AllowCachingResponses kontroluje, czy middleware do sprawdzania kondycji dodaje nagłówki HTTP do odpowiedzi z sondy, aby zapobiec buforowaniu odpowiedzi. Jeśli wartość to false (wartość domyślna), oprogramowanie pośredniczące ustawia lub zastępuje nagłówki Cache-Control, Expires i Pragma, aby zapobiec buforowaniu odpowiedzi. Jeśli wartość to true, oprogramowanie pośredniczące nie modyfikuje nagłówków pamięci podręcznej odpowiedzi:
app.MapHealthChecks("/healthz", new HealthCheckOptions
{
AllowCachingResponses = true
});
Dostosowywanie danych wyjściowych
Aby dostosować dane wyjściowe raportu kontroli kondycji, ustaw HealthCheckOptions.ResponseWriter właściwość na delegata, który zapisuje odpowiedź:
app.MapHealthChecks("/healthz", new HealthCheckOptions
{
ResponseWriter = WriteResponse
});
Domyślny delegat zapisuje minimalną odpowiedź w postaci czystego tekstu z wartością ciągu HealthReport.Status. Poniższy delegat niestandardowy zwraca niestandardową odpowiedź JSON przy użyciu polecenia System.Text.Json:
private static Task WriteResponse(HttpContext context, HealthReport healthReport)
{
context.Response.ContentType = "application/json; charset=utf-8";
var options = new JsonWriterOptions { Indented = true };
using var memoryStream = new MemoryStream();
using (var jsonWriter = new Utf8JsonWriter(memoryStream, options))
{
jsonWriter.WriteStartObject();
jsonWriter.WriteString("status", healthReport.Status.ToString());
jsonWriter.WriteStartObject("results");
foreach (var healthReportEntry in healthReport.Entries)
{
jsonWriter.WriteStartObject(healthReportEntry.Key);
jsonWriter.WriteString("status",
healthReportEntry.Value.Status.ToString());
jsonWriter.WriteString("description",
healthReportEntry.Value.Description);
jsonWriter.WriteStartObject("data");
foreach (var item in healthReportEntry.Value.Data)
{
jsonWriter.WritePropertyName(item.Key);
JsonSerializer.Serialize(jsonWriter, item.Value,
item.Value?.GetType() ?? typeof(object));
}
jsonWriter.WriteEndObject();
jsonWriter.WriteEndObject();
}
jsonWriter.WriteEndObject();
jsonWriter.WriteEndObject();
}
return context.Response.WriteAsync(
Encoding.UTF8.GetString(memoryStream.ToArray()));
}
Interfejs API sprawdzania kondycji nie zapewnia wbudowanej obsługi złożonych formatów zwracanych JSON, ponieważ format jest specyficzny dla wybranego systemu monitorowania. Dostosuj odpowiedź w poprzednich przykładach zgodnie z potrzebami. Aby uzyskać więcej informacji na temat serializacji JSON za pomocą System.Text.Json, zobacz Jak serializować i deserializować JSON na platformie .NET.
Sonda bazy danych
Kontrola kondycji może określić zapytanie bazy danych do uruchomienia jako test logiczny, aby wskazać, czy baza danych odpowiada normalnie.
AspNetCore.Diagnostics.HealthChecks, biblioteka sprawdzania kondycji dla aplikacji ASP.NET Core zawiera kontrolę kondycji uruchamianą względem bazy danych programu SQL Server.
AspNetCore.Diagnostics.HealthChecks
SELECT 1 Wykonuje zapytanie względem bazy danych, aby potwierdzić, że połączenie z bazą danych jest w dobrej kondycji.
Warning
Podczas sprawdzania połączenia z bazą danych przy użyciu zapytania wybierz zapytanie, które szybko zwraca. Podejście do zapytania powoduje przeciążenie bazy danych i obniżenie wydajności. W większości przypadków uruchomienie zapytania testowego nie jest konieczne. Wystarczy nawiązać pomyślne połączenie z bazą danych. Jeśli okaże się, że konieczne jest uruchomienie zapytania, wybierz proste zapytanie SELECT, takie jak SELECT 1.
Aby użyć tej kontroli kondycji programu SQL Server, dołącz odwołanie do AspNetCore.HealthChecks.SqlServer pakietu NuGet. Poniższy przykład rejestruje kontrolę kondycji programu SQL Server:
var conStr = builder.Configuration.GetConnectionString("DefaultConnection");
if (string.IsNullOrEmpty(conStr))
{
throw new InvalidOperationException(
"Could not find a connection string named 'DefaultConnection'.");
}
builder.Services.AddHealthChecks()
.AddSqlServer(conStr);
Note
Firma Microsoft nie utrzymuje ani nie wspiera AspNetCore.Diagnostics.HealthChecks.
Sonda DbContext w Entity Framework Core
Sprawdzanie DbContext potwierdza, że aplikacja może komunikować się z bazą danych skonfigurowaną dla elementu EF CoreDbContext. Aplikacje, które obsługują DbContext weryfikację:
- Użyj platformy Entity Framework (EF) Core.
- Dołącz odniesienie do pakietu NuGet
Microsoft.Extensions.Diagnostics.HealthChecks.EntityFrameworkCore.
AddDbContextCheck rejestruje kontrolę kondycji dla elementu DbContext. Element DbContext jest dostarczany do metody jako TContext. Przeciążenie jest dostępne do skonfigurowania stanu niepowodzenia, tagów i niestandardowego zapytania testowego.
Domyślnie:
- Wywołuje
DbContextHealthCheckmetodę EF CoreCanConnectAsync. Możesz dostosować operację wykonywaną podczas kontroli kondycji przy użyciuAddDbContextCheckprzeciążeń metod. - Nazwa sprawdzania kondycji to nazwa typu
TContext.
Poniższy przykład rejestruje element DbContext i skojarzony element DbContextHealthCheck:
builder.Services.AddDbContext<SampleDbContext>(options =>
options.UseSqlServer(
builder.Configuration.GetConnectionString("DefaultConnection")));
builder.Services.AddHealthChecks()
.AddDbContextCheck<SampleDbContext>();
Oddzielne sondy gotowości i żywotności
W niektórych scenariuszach hostingu użyj pary kontroli kondycji, aby odróżnić dwa stany aplikacji:
- Gotowość wskazuje, czy aplikacja działa normalnie, ale nie jest gotowa do odbierania żądań.
- Liveness wskazuje, czy aplikacja uległa awarii i musi zostać ponownie uruchomiona.
Rozważmy następujący przykład: Aplikacja musi pobrać duży plik konfiguracji, zanim będzie gotowa do przetwarzania żądań. Nie chcesz ponownie uruchamiać aplikacji, jeśli początkowe pobieranie nie powiedzie się, ponieważ aplikacja może ponowić próbę pobrania pliku kilka razy. Użyj sondy liveness, aby opisać stan żywotności procesu, nie są uruchamiane żadne inne kontrole. Chcesz również uniemożliwić wysyłanie żądań do aplikacji przed pomyślnym pobraniem pliku konfiguracji. Użyj sondy gotowości, aby wskazać stan "nie jest gotowy", dopóki pobieranie się nie powiedzie, a aplikacja będzie gotowa do odbierania żądań.
Następujące zadanie w tle symuluje proces uruchamiania, który trwa około 15 sekund. Po zakończeniu zadania zadanie ustawia StartupHealthCheck.StartupCompleted właściwość na true:
public class StartupBackgroundService : BackgroundService
{
private readonly StartupHealthCheck _healthCheck;
public StartupBackgroundService(StartupHealthCheck healthCheck)
=> _healthCheck = healthCheck;
protected override async Task ExecuteAsync(CancellationToken stoppingToken)
{
// Simulate the effect of a long-running task.
await Task.Delay(TimeSpan.FromSeconds(15), stoppingToken);
_healthCheck.StartupCompleted = true;
}
}
Ten StartupHealthCheck raportuje ukończenie długotrwałego zadania uruchamiania i ujawnia właściwość StartupCompleted, którą ustawia usługa w tle.
public class StartupHealthCheck : IHealthCheck
{
private volatile bool _isReady;
public bool StartupCompleted
{
get => _isReady;
set => _isReady = value;
}
public Task<HealthCheckResult> CheckHealthAsync(
HealthCheckContext context, CancellationToken cancellationToken = default)
{
if (StartupCompleted)
{
return Task.FromResult(HealthCheckResult.Healthy("The startup task has completed."));
}
return Task.FromResult(HealthCheckResult.Unhealthy("That startup task is still running."));
}
}
Zarejestruj kontrolę kondycji przy użyciu AddCheck w Program.cs, włącznie z usługą hostowaną. Ponieważ hostowana usługa ustawia właściwość na badanie stanu zdrowia, zarejestruj także badanie stanu zdrowia w kontenerze usługi jako singleton.
builder.Services.AddHostedService<StartupBackgroundService>();
builder.Services.AddSingleton<StartupHealthCheck>();
builder.Services.AddHealthChecks()
.AddCheck<StartupHealthCheck>(
"Startup",
tags: new[] { "ready" });
Aby utworzyć dwa różne punkty końcowe kontroli kondycji, wywołaj MapHealthChecks dwa razy.
app.MapHealthChecks("/healthz/ready", new HealthCheckOptions
{
Predicate = healthCheck => healthCheck.Tags.Contains("ready")
});
app.MapHealthChecks("/healthz/live", new HealthCheckOptions
{
Predicate = _ => false
});
W poprzednim przykładzie są tworzone następujące punkty końcowe sprawdzania kondycji:
-
/healthz/readyw celu sprawdzenia gotowości. Sprawdzanie gotowości ogranicza kontrole kondycji do tych oznaczonych tagiemready. -
/healthz/livew celu sprawdzenia żywotności. Sprawdzanie żywotności filtruje wszystkie kontrole kondycji, zwracającfalsew delegacie HealthCheckOptions.Predicate. Aby uzyskać więcej informacji na temat filtrowania kontroli kondycji, zobacz Filtrowanie kontroli kondycji w tym artykule.
Zanim zadanie uruchamiania zostanie ukończone, punkt końcowy /healthz/ready zgłasza stan Unhealthy. Po zakończeniu zadania uruchamiania ten punkt końcowy zgłasza stan Healthy. Punkt końcowy /healthz/live wyklucza wszystkie sprawdzania i raportuje stan Healthy dla wszystkich wywołań.
Przykład rozwiązania Kubernetes
Korzystanie z oddzielnych testów gotowości i dostępności jest przydatne w środowisku, takim jak Kubernetes. Na platformie Kubernetes może być konieczne uruchomienie czasochłonnych zadań podczas rozruchu, zanim aplikacja będzie mogła zaakceptować żądania, takich jak test dostępności podstawowej bazy danych. Korzystając z oddzielnych testów, koordynator może określić, czy aplikacja działa, ale nie jest jeszcze gotowa, czy nie można uruchomić aplikacji. Aby uzyskać więcej informacji na temat sond gotowości i kondycji na platformie Kubernetes, zobacz Konfigurowanie sond kondycji i gotowości w dokumentacji platformy Kubernetes.
W poniższym przykładzie pokazano konfigurację sondy gotowości Kubernetes:
spec:
template:
spec:
readinessProbe:
# an http probe
httpGet:
path: /healthz/ready
port: 80
# length of time to wait for a pod to initialize
# after pod startup, before applying health checking
initialDelaySeconds: 30
timeoutSeconds: 1
ports:
- containerPort: 80
Rozpowszechnianie biblioteki kontroli kondycji
Aby rozpowszechnić kontrolę stanu zdrowia jako bibliotekę:
Napisz kontrolę kondycji, która implementuje IHealthCheck interfejs jako klasę autonomiczną. Klasa może polegać na iniekcji zależności (DI), aktywacji typu i nazwanych opcjach uzyskiwania dostępu do danych konfiguracji.
Napisz metodę rozszerzenia z parametrami, które aplikacja, która korzysta, wywołuje w swojej metodzie
Program.cs. Rozważmy następujące przykładowe sprawdzanie kondycji, które akceptujearg1iarg2jako parametry konstruktora:public SampleHealthCheckWithArgs(int arg1, string arg2) => (_arg1, _arg2) = (arg1, arg2);Powyższy podpis wskazuje, że kontrola kondycji wymaga niestandardowych danych do przetwarzania logiki sondy sprawdzania kondycji. Dane są przekazywane delegatowi, który jest używany do utworzenia instancji sprawdzenia kondycji, gdy sprawdzenie kondycji jest zarejestrowane za pomocą metody rozszerzenia. W poniższym przykładzie obiekt wywołujący określa:
-
arg1: punkt danych typu liczbowego całkowitego dla sprawdzania stanu zdrowia. -
arg2: argument ciągu dla sprawdzania kondycji. -
name: opcjonalna nazwa sprawdzania kondycji. Jeślinullzostanie użyta wartość domyślna. -
failureStatus: opcjonalny HealthStatuselement , który jest zgłaszany dla stanu błędu. Jeślinull, HealthStatus.Unhealthy jest używany. -
tags: opcjonalnaIEnumerable<string>kolekcja tagów.
public static class SampleHealthCheckBuilderExtensions { private const string DefaultName = "Sample"; public static IHealthChecksBuilder AddSampleHealthCheck( this IHealthChecksBuilder healthChecksBuilder, int arg1, string arg2, string? name = null, HealthStatus? failureStatus = null, IEnumerable<string>? tags = default) { return healthChecksBuilder.Add( new HealthCheckRegistration( name ?? DefaultName, _ => new SampleHealthCheckWithArgs(arg1, arg2), failureStatus, tags)); } }-
Wydawca kontroli kondycji
Po dodaniu elementu IHealthCheckPublisher do kontenera usługi system monitorowania kondycji okresowo wykonuje sprawdzanie kondycji i wywołuje PublishAsync z wynikiem. Ten proces jest przydatny w scenariuszu systemu monitorowania stanu zdrowia opartym na zasadzie wypychania, który oczekuje, że każdy proces będzie okresowo wywoływał system monitorowania w celu określenia stanu zdrowia.
HealthCheckPublisherOptions pozwól ustawić następujące ustawienia:
- Delay: początkowe opóźnienie po uruchomieniu aplikacji przed wykonaniem IHealthCheckPublisher wystąpień. Opóźnienie odbywa się raz podczas uruchamiania i nie ma zastosowania do późniejszych iteracji. Wartość domyślna to pięć sekund.
- Period: okres IHealthCheckPublisher wykonywania. Wartość domyślna to 30 sekund.
-
Predicate: Jeśli Predicate jest
null(wartość domyślna), usługa wydawcy testów kondycji uruchamia wszystkie zarejestrowane testy kondycji. Aby uruchomić podzbiór kontroli kondycji, podaj funkcję, która filtruje zestaw testów. Predykat jest obliczany w każdym okresie. - Timeout: limit czasu na wykonywanie kontroli kondycji dla wszystkich IHealthCheckPublisher wystąpień. Użyj polecenia InfiniteTimeSpan , aby wykonać bez limitu czasu. Wartość domyślna to 30 sekund.
W poniższym przykładzie pokazano układ wydawcy zdrowotnego.
public class SampleHealthCheckPublisher : IHealthCheckPublisher
{
public Task PublishAsync(HealthReport report, CancellationToken cancellationToken)
{
if (report.Status == HealthStatus.Healthy)
{
// ...
}
else
{
// ...
}
return Task.CompletedTask;
}
}
Klasa HealthCheckPublisherOptions udostępnia właściwości służące do konfigurowania zachowania publikatora sprawdzania kondycji systemu.
W poniższym przykładzie wydawca kontroli kondycji jest rejestrowany jako singleton i konfiguruje HealthCheckPublisherOptions element:
builder.Services.Configure<HealthCheckPublisherOptions>(options =>
{
options.Delay = TimeSpan.FromSeconds(2);
options.Predicate = healthCheck => healthCheck.Tags.Contains("sample");
});
builder.Services.AddSingleton<IHealthCheckPublisher, SampleHealthCheckPublisher>();
AspNetCore.Diagnostics.HealthChecks:
- Zawiera wydawców dla kilku systemów, w tym Application Insights.
- Nie jest obsługiwany ani utrzymywany przez firmę Microsoft.
Indywidualne kontrole kondycji
Można ustawić Delay i Period indywidualnie na każdym HealthCheckRegistration. Ustaw te wartości, gdy chcesz uruchomić niektóre kontrole kondycji z inną szybkością niż okres ustawiony w pliku HealthCheckPublisherOptions.
Poniższy kod ustawia wartości Delay i Period dla elementu SampleHealthCheck1:
var builder = WebApplication.CreateBuilder(args);
builder.Services.AddHealthChecks()
.Add(new HealthCheckRegistration(
name: "SampleHealthCheck1",
instance: new SampleHealthCheck(),
failureStatus: null,
tags: null,
timeout: default)
{
Delay = TimeSpan.FromSeconds(40),
Period = TimeSpan.FromSeconds(30)
});
var app = builder.Build();
app.MapHealthChecks("/healthz");
app.Run();
Wstrzykiwanie zależności i kontrole kondycji
Można zastosować iniekcję zależności, aby wykorzystać instancję określonego Type wewnątrz klasy monitorującej stan zdrowia. Wstrzykiwanie zależności może być przydatne do wstrzykiwania opcji lub konfiguracji globalnej do kontroli kondycji. Używanie wstrzykiwania zależności nie jest typowym scenariuszem konfigurowania kontroli kondycji. Zwykle każde sprawdzenie kondycji jest dość specyficzne dla rzeczywistego testu i jest konfigurowane przy użyciu metod rozszerzeń IHealthChecksBuilder.
W poniższym przykładzie pokazano przykładową kontrolę kondycji, która pobiera obiekt konfiguracji za pośrednictwem iniekcji zależności:
public class SampleHealthCheckWithDI : IHealthCheck
{
private readonly SampleHealthCheckWithDiConfig _config;
public SampleHealthCheckWithDI(SampleHealthCheckWithDiConfig config)
=> _config = config;
public Task<HealthCheckResult> CheckHealthAsync(
HealthCheckContext context, CancellationToken cancellationToken = default)
{
var isHealthy = true;
// use _config ...
if (isHealthy)
{
return Task.FromResult(
HealthCheckResult.Healthy("A healthy result."));
}
return Task.FromResult(
new HealthCheckResult(
context.Registration.FailureStatus, "An unhealthy result."));
}
}
Element SampleHealthCheckWithDiConfig oraz sprawdzanie kondycji należy dodać do kontenera usługi :
builder.Services.AddSingleton<SampleHealthCheckWithDiConfig>(new SampleHealthCheckWithDiConfig
{
BaseUriToCheck = new Uri("https://sample.contoso.com/api/")
});
builder.Services.AddHealthChecks()
.AddCheck<SampleHealthCheckWithDI>(
"With Dependency Injection",
tags: new[] { "inject" });
UseHealthChecks vs MapHealthChecks
Kontrole stanu zdrowia można umożliwić dostęp osobom dzwoniącym na dwa sposoby:
- UseHealthChecks rejestruje oprogramowanie pośredniczące do obsługi żądań kontroli kondycji w potoku oprogramowania pośredniczącego.
- MapHealthChecks rejestruje punkt końcowy kontroli kondycji. Punkt końcowy jest zgodny i wykonywany wraz z innymi punktami końcowymi w aplikacji.
Zamiast korzystać z MapHealthChecks, można użyć pośredniego oprogramowania obsługującego punkty końcowe, takiego jak autoryzacja, co pozwala uzyskać bardziej precyzyjną kontrolę nad polityką dopasowywania.
UseHealthChecks Używając zamiast MapHealthChecks, można kontrolować dokładnie, gdzie testy kondycji są uruchamiane w potoku oprogramowania pośredniczącego.
- Przerywa potok, gdy żądanie jest zgodne z punktem końcowym sprawdzania kondycji. Krótkie spięcie jest często pożądane, ponieważ pozwala uniknąć niepotrzebnej pracy, takiej jak logowanie oraz inne elementy pośredniczące.
- Służy głównie do konfigurowania middleware monitorowania stanu w potoku.
- Może dopasować dowolną ścieżkę na porcie używając
nulllub pustegoPathString. Umożliwia wykonanie kontroli zdrowia dla każdego żądania kierowanego do określonego portu. - Kod źródłowy
MapHealthChecks Pozwala:
- Kończenie potoku, gdy żądanie jest zgodne z punktem końcowym sprawdzania kondycji, wywołując metodę ShortCircuit. Na przykład
app.MapHealthChecks("/healthz").ShortCircuit();. Aby uzyskać więcej informacji, zobacz Oprogramowanie pośredniczące zwarcie po routingu. - Mapowanie określonych tras lub punktów końcowych na potrzeby kontroli kondycji.
- Dostosowanie adresu URL lub ścieżki, w której jest dostępny punkt końcowy sprawdzania kondycji.
- Mapowanie wielu punktów końcowych kontroli kondycji z różnymi trasami lub konfiguracjami. Obsługa wielu punktów końcowych:
- Włącza oddzielne punkty końcowe dla różnych typów testów kondycji lub składników.
- Służy do rozróżniania różnych aspektów kondycji aplikacji lub stosowania określonych konfiguracji do podzbiorów kontroli kondycji.
- Kod źródłowy
Dodatkowe zasoby
Note
Ten artykuł został częściowo utworzony z pomocą sztucznej inteligencji. Przed opublikowaniem autor przejrzał i poprawił zawartość zgodnie z potrzebą. Zapoznaj się z naszymi zasadami korzystania z zawartości generowanej za pośrednictwem AI w usłudze Microsoft Learn.
ASP.NET Core oferuje middleware sprawdzania kondycji oraz biblioteki do raportowania kondycji składników infrastruktury aplikacji.
Testy kondycji są udostępniane przez aplikację jako punkty końcowe HTTP. Punkty końcowe kontroli kondycji można skonfigurować dla różnych scenariuszy monitorowania w czasie rzeczywistym:
- Sondy kondycji mogą być używane przez koordynatorów kontenerów i moduły równoważenia obciążenia w celu sprawdzenia stanu aplikacji. Na przykład orkiestrator kontenerów może reagować na niepowodzenie sprawdzania kondycji, zatrzymując wdrożenie stopniowe lub ponownie uruchamiając kontener. Moduł równoważenia obciążenia może reagować na problemy z aplikacją przez przekierowanie ruchu z wadliwego wystąpienia do wystąpienia działającego poprawnie.
- Użycie pamięci, dysku i innych zasobów serwera fizycznego można monitorować pod kątem stanu dobrej kondycji.
- Testy kondycji mogą testować zależności aplikacji, takie jak bazy danych i zewnętrzne punkty końcowe usługi, w celu potwierdzenia dostępności i normalnego działania.
Wyświetl lub pobierz przykładowy kod (jak pobrać)
Przykładowa aplikacja zawiera przykłady scenariuszy opisanych w tym artykule. Aby uruchomić przykładową aplikację dla danego scenariusza, użyj polecenia dotnet run z folderu projektu w powłoce poleceń. Zobacz plik przykładowej README.md aplikacji i opisy scenariuszy w tym artykule, aby uzyskać szczegółowe informacje na temat korzystania z przykładowej aplikacji.
Prerequisites
Testy kondycji są zwykle używane z zewnętrzną usługą monitorowania lub koordynatorem kontenerów w celu sprawdzenia stanu aplikacji. Przed dodaniem kontroli kondycji do aplikacji zdecyduj, który system monitorowania ma być używany. System monitorowania określa, jakie typy testów zdrowia należy utworzyć i jak skonfigurować ich punkty końcowe.
Pakiet Microsoft.AspNetCore.Diagnostics.HealthChecks jest przywoływany niejawnie dla aplikacji ASP.NET Core. Aby uruchomić kontrole kondycji przy użyciu programu Entity Framework Core, dodaj odwołanie do Microsoft.Extensions.Diagnostics.HealthChecks.EntityFrameworkCore pakietu.
Przykładowa aplikacja udostępnia kod uruchamiania w celu zademonstrowania kontroli kondycji dla kilku scenariuszy. Scenariusz sondy bazy danych sprawdza stan połączenia z bazą danych przy użyciu AspNetCore.Diagnostics.HealthChecks. Scenariusz sondy DbContext sprawdza bazę danych przy użyciu . Aby zapoznać się ze scenariuszami bazy danych, przykładowa aplikacja:
- Tworzy bazę danych i udostępnia jej parametry połączenia w
appsettings.jsonpliku. - Zawiera następujące odwołania do pakietów w pliku projektu:
Note
AspNetCore.Diagnostics.HealthChecks nie jest obsługiwany ani wspierany przez firmę Microsoft.
Inny scenariusz kontroli kondycji demonstruje, jak filtrować te kontrole przez port zarządzania. Przykładowa aplikacja wymaga utworzenia pliku zawierającego Properties/launchSettings.json adres URL zarządzania i port zarządzania. Aby uzyskać więcej informacji, zobacz sekcję Filtruj według portów .
Podstawowa sonda kondycji
W przypadku wielu aplikacji podstawowa konfiguracja sondy kondycji, która zgłasza dostępność aplikacji do przetwarzania żądań (statusu działania) jest wystarczająca do ustalenia stanu aplikacji.
Podstawowa konfiguracja rejestruje usługi monitorowania stanu i wywołuje middleware do kontroli stanu zdrowia, aby odpowiedzieć na adresie URL odpowiedzią zdrowotną. Domyślnie żadne konkretne kontrole kondycji nie są rejestrowane w celu przetestowania żadnej konkretnej zależności lub podsystemu. Aplikacja jest uważana za w dobrej kondycji, jeśli może odpowiadać pod adresem URL punktu końcowego zdrowia. Domyślny składnik zapisu odpowiedzi zapisuje stan (HealthStatus) jako odpowiedź w postaci zwykłego tekstu z powrotem do klienta, wskazując stan HealthStatus.Healthy, HealthStatus.Degraded lub HealthStatus.Unhealthy.
Zarejestruj usługi sprawdzania kondycji w AddHealthChecks w Startup.ConfigureServices. Utwórz punkt końcowy kontroli kondycji, wywołując MapHealthChecks w Startup.Configure.
W przykładowej aplikacji punkt końcowy sprawdzania kondycji jest tworzony pod adresem /health (BasicStartup.cs):
public class BasicStartup
{
public void ConfigureServices(IServiceCollection services)
{
services.AddHealthChecks();
}
public void Configure(IApplicationBuilder app)
{
app.UseRouting();
app.UseEndpoints(endpoints =>
{
endpoints.MapHealthChecks("/health");
});
}
}
Aby uruchomić podstawowy scenariusz konfiguracji przy użyciu przykładowej aplikacji, wykonaj następujące polecenie z folderu projektu w powłoce poleceń:
dotnet run --scenario basic
Przykład platformy Docker
Platforma Docker oferuje wbudowaną HEALTHCHECK dyrektywę, która może służyć do sprawdzania stanu aplikacji korzystającej z podstawowej konfiguracji kontroli kondycji:
HEALTHCHECK CMD curl --fail http://localhost:5000/health || exit
Tworzenie kontroli kondycji
Testy kondycji są tworzone przez zaimplementowanie interfejsu IHealthCheck . Metoda CheckHealthAsync zwraca wartość HealthCheckResult , która wskazuje kondycję jako Healthy, Degradedlub Unhealthy. Wynik jest zapisywany jako odpowiedź w postaci zwykłego tekstu z konfigurowalnym kodem stanu (konfiguracja jest opisana w sekcji Opcje sprawdzania kondycji).
HealthCheckResult może również zwracać opcjonalne pary klucz-wartość.
Poniższa ExampleHealthCheck klasa demonstruje układ kontroli kondycji. Logika kontroli kondycji jest umieszczana w metodzie CheckHealthAsync . W poniższym przykładzie ustawiono fikcyjną zmienną , healthCheckResultHealthyna true. Jeśli wartość parametru healthCheckResultHealthy jest ustawiona na false, zwracany jest stan HealthCheckRegistration.FailureStatus.
public class ExampleHealthCheck : IHealthCheck
{
public Task<HealthCheckResult> CheckHealthAsync(
HealthCheckContext context,
CancellationToken cancellationToken = default(CancellationToken))
{
var healthCheckResultHealthy = true;
if (healthCheckResultHealthy)
{
return Task.FromResult(
HealthCheckResult.Healthy("A healthy result."));
}
return Task.FromResult(
new HealthCheckResult(context.Registration.FailureStatus,
"An unhealthy result."));
}
}
Jeśli w trakcie sprawdzania CheckHealthAsync zostanie zgłoszony wyjątek, nowy HealthReportEntry zostaje zwrócony z ustawionym na FailureStatusHealthReportEntry.Status, który jest zdefiniowany przez AddCheck (zobacz sekcję Usługi sprawdzania kondycji rejestru), i zawiera wewnętrzny wyjątek, który początkowo spowodował błąd sprawdzania. Parametr Description jest ustawiony na komunikat wyjątku.
Rejestrowanie usług kontroli kondycji
Typ ExampleHealthCheck jest dodawany do usług sprawdzania kondycji przy użyciu AddCheck w pliku Startup.ConfigureServices.
services.AddHealthChecks()
.AddCheck<ExampleHealthCheck>("example_health_check");
Przeciążenie AddCheck pokazane w poniższym przykładzie ustawia stan błędu (HealthStatus) w celu raportowania, gdy kontrola kondycji zgłasza błąd. Jeśli stan niepowodzenia jest ustawiony na null (wartość domyślna), HealthStatus.Unhealthy jest zgłaszany. To przeciążenie jest przydatnym scenariuszem dla autorów bibliotek, gdzie status awarii wskazywany przez bibliotekę jest wymuszany przez aplikację, gdy wystąpi błąd w sprawdzaniu kondycji, o ile implementacja sprawdzania kondycji respektuje to ustawienie.
Tagi mogą służyć do filtrowania kontroli kondycji (opisanych dalej w sekcji Filtr kontroli kondycji).
services.AddHealthChecks()
.AddCheck<ExampleHealthCheck>(
"example_health_check",
failureStatus: HealthStatus.Degraded,
tags: new[] { "example" });
AddCheck może również wykonać funkcję lambda. W poniższym przykładzie nazwa kontroli kondycji jest określona jako Example i sprawdzanie zawsze zwraca stan dobrej kondycji:
services.AddHealthChecks()
.AddCheck("Example", () =>
HealthCheckResult.Healthy("Example is OK!"), tags: new[] { "example" });
Wywołaj metodę AddTypeActivatedCheck , aby przekazać argumenty do implementacji kontroli kondycji. W poniższym przykładzie TestHealthCheckWithArgs akceptuje liczbę całkowitą i ciąg do użycia, gdy CheckHealthAsync jest wywoływany:
private class TestHealthCheckWithArgs : IHealthCheck
{
public TestHealthCheckWithArgs(int i, string s)
{
I = i;
S = s;
}
public int I { get; set; }
public string S { get; set; }
public Task<HealthCheckResult> CheckHealthAsync(HealthCheckContext context,
CancellationToken cancellationToken = default)
{
...
}
}
TestHealthCheckWithArgs jest rejestrowany przez wywołanie AddTypeActivatedCheck za pomocą liczby całkowitej i ciągu przekazanego do implementacji:
services.AddHealthChecks()
.AddTypeActivatedCheck<TestHealthCheckWithArgs>(
"test",
failureStatus: HealthStatus.Degraded,
tags: new[] { "example" },
args: new object[] { 5, "string" });
Zastosuj trasowanie kontroli zdrowia
W Startup.Configure wywołaj MapHealthChecks na budowniczym punktu końcowego z adresem URL punktu końcowego lub ścieżką względną:
app.UseEndpoints(endpoints =>
{
endpoints.MapHealthChecks("/health");
});
Wymagaj hosta
Wywołaj RequireHost , aby określić co najmniej jednego dozwolonego hosta dla endpointu kontroli kondycji. Hosty powinny być unicode, a nie punycode i mogą zawierać port. Jeśli kolekcja nie zostanie dostarczona, zaakceptowany zostanie dowolny host.
app.UseEndpoints(endpoints =>
{
endpoints.MapHealthChecks("/health").RequireHost("www.contoso.com:5001");
});
Aby uzyskać więcej informacji, zobacz sekcję Filtruj według portów .
Wymagaj autoryzacji
Wywołaj polecenie RequireAuthorization , aby uruchomić oprogramowanie pośredniczące autoryzacji w punkcie końcowym żądania sprawdzania kondycji. Przeciążenie RequireAuthorization akceptuje co najmniej jedną zasady autoryzacji. Jeśli nie podano zasad, są używane domyślne zasady autoryzacji.
app.UseEndpoints(endpoints =>
{
endpoints.MapHealthChecks("/health").RequireAuthorization();
});
Włącz żądania Cross-Origin (CORS)
Mimo że ręczne uruchamianie kontroli kondycji z przeglądarki nie jest typowym scenariuszem użycia, oprogramowanie pośredniczące CORS można włączyć przez wywołanie RequireCors punktów końcowych kontroli kondycji. Przeciążenie RequireCors akceptuje delegata budującego zasady CORS (CorsPolicyBuilder) lub nazwę zasad. Jeśli nie podano zasad, zostanie użyta domyślna zasada CORS. Aby uzyskać więcej informacji, zobacz Włączanie żądań między źródłami (CORS) w ASP.NET Core.
Opcje kontroli kondycji
HealthCheckOptions umożliwia dostosowanie zachowania kontroli kondycji:
- Kontrole kondycji filtrów
- Dostosowywanie kodu stanu HTTP
- Blokowanie nagłówków pamięci podręcznej
- Dostosowywanie danych wyjściowych
Filtrowanie sprawdzania kondycji
Domyślnie middleware do kontroli kondycji uruchamia wszystkie zarejestrowane testy zdrowia. Aby uruchomić podzbiór testów kondycji, podaj funkcję, która zwraca wartość logiczną jako argument opcji Predicate. W poniższym przykładzie Bar sprawdzanie kondycji jest filtrowane według tagu (bar_tag) w instrukcji warunkowej funkcji, gdzie true jest zwracana tylko wtedy, gdy właściwość Tags sprawdzania kondycji odpowiada foo_tag albo baz_tag.
W pliku Startup.ConfigureServices:
services.AddHealthChecks()
.AddCheck("Foo", () =>
HealthCheckResult.Healthy("Foo is OK!"), tags: new[] { "foo_tag" })
.AddCheck("Bar", () =>
HealthCheckResult.Unhealthy("Bar is unhealthy!"), tags: new[] { "bar_tag" })
.AddCheck("Baz", () =>
HealthCheckResult.Healthy("Baz is OK!"), tags: new[] { "baz_tag" });
W Startup.Configure, Predicate filtruje sprawdzanie kondycji 'Bar'. Wykonaj tylko polecenia Foo i Baz:
app.UseEndpoints(endpoints =>
{
endpoints.MapHealthChecks("/health", new HealthCheckOptions()
{
Predicate = (check) => check.Tags.Contains("foo_tag") ||
check.Tags.Contains("baz_tag")
});
});
Dostosowywanie kodu stanu HTTP
Użyj ResultStatusCodes do dostosowywania mapowania stanu kondycji na kody stanu HTTP. Następujące StatusCodes przypisania są wartościami domyślnymi używanymi przez middleware. Zmień wartości kodu stanu, aby spełniały twoje wymagania.
W pliku Startup.Configure:
app.UseEndpoints(endpoints =>
{
endpoints.MapHealthChecks("/health", new HealthCheckOptions()
{
ResultStatusCodes =
{
[HealthStatus.Healthy] = StatusCodes.Status200OK,
[HealthStatus.Degraded] = StatusCodes.Status200OK,
[HealthStatus.Unhealthy] = StatusCodes.Status503ServiceUnavailable
}
});
});
Tłumienie nagłówków pamięci podręcznej
AllowCachingResponses kontroluje, czy middleware do sprawdzania kondycji dodaje nagłówki HTTP do odpowiedzi z sondy, aby zapobiec buforowaniu odpowiedzi. Jeśli wartość to false (wartość domyślna), oprogramowanie pośredniczące ustawia lub zastępuje nagłówki Cache-Control, Expires i Pragma, aby zapobiec buforowaniu odpowiedzi. Jeśli wartość to true, oprogramowanie pośredniczące nie modyfikuje nagłówków pamięci podręcznej odpowiedzi.
W pliku Startup.Configure:
app.UseEndpoints(endpoints =>
{
endpoints.MapHealthChecks("/health", new HealthCheckOptions()
{
AllowCachingResponses = true
});
});
Dostosowywanie danych wyjściowych
W Startup.Configurepliku ustaw opcję delegata HealthCheckOptions.ResponseWriter na potrzeby pisania odpowiedzi:
app.UseEndpoints(endpoints =>
{
endpoints.MapHealthChecks("/health", new HealthCheckOptions()
{
ResponseWriter = WriteResponse
});
});
Domyślny delegat zapisuje minimalną odpowiedź w postaci czystego tekstu z wartością ciągu HealthReport.Status. Następujący delegat niestandardowy zwraca niestandardową odpowiedź JSON.
Pierwszy przykład z przykładowej aplikacji pokazuje, jak używać polecenia System.Text.Json:
private static Task WriteResponse(HttpContext context, HealthReport result)
{
context.Response.ContentType = "application/json; charset=utf-8";
var options = new JsonWriterOptions
{
Indented = true
};
using (var stream = new MemoryStream())
{
using (var writer = new Utf8JsonWriter(stream, options))
{
writer.WriteStartObject();
writer.WriteString("status", result.Status.ToString());
writer.WriteStartObject("results");
foreach (var entry in result.Entries)
{
writer.WriteStartObject(entry.Key);
writer.WriteString("status", entry.Value.Status.ToString());
writer.WriteString("description", entry.Value.Description);
writer.WriteStartObject("data");
foreach (var item in entry.Value.Data)
{
writer.WritePropertyName(item.Key);
JsonSerializer.Serialize(
writer, item.Value, item.Value?.GetType() ??
typeof(object));
}
writer.WriteEndObject();
writer.WriteEndObject();
}
writer.WriteEndObject();
writer.WriteEndObject();
}
var json = Encoding.UTF8.GetString(stream.ToArray());
return context.Response.WriteAsync(json);
}
}
W drugim przykładzie pokazano, jak używać polecenia Newtonsoft.Json:
private static Task WriteResponse(HttpContext context, HealthReport result)
{
context.Response.ContentType = "application/json";
var json = new JObject(
new JProperty("status", result.Status.ToString()),
new JProperty("results", new JObject(result.Entries.Select(pair =>
new JProperty(pair.Key, new JObject(
new JProperty("status", pair.Value.Status.ToString()),
new JProperty("description", pair.Value.Description),
new JProperty("data", new JObject(pair.Value.Data.Select(
p => new JProperty(p.Key, p.Value))))))))));
return context.Response.WriteAsync(
json.ToString(Formatting.Indented));
}
W przykładowej aplikacji oznacz jako komentarz dyrektywę
Interfejs API sprawdzania kondycji nie zapewnia wbudowanej obsługi złożonych formatów zwracanych JSON, ponieważ format jest specyficzny dla wybranego systemu monitorowania. Dostosuj odpowiedź w poprzednich przykładach zgodnie z potrzebami. Aby uzyskać więcej informacji na temat serializacji JSON za pomocą System.Text.Json, zobacz Jak serializować i deserializować JSON na platformie .NET.
Sonda bazy danych
Kontrola kondycji może określić zapytanie bazy danych do uruchomienia jako test logiczny, aby wskazać, czy baza danych odpowiada normalnie.
Przykładowa aplikacja używa AspNetCore.Diagnostics.HealthChecksbiblioteki kontroli kondycji dla aplikacji ASP.NET Core do uruchamiania kontroli kondycji bazy danych programu SQL Server.
AspNetCore.Diagnostics.HealthChecks
SELECT 1 Wykonuje zapytanie względem bazy danych, aby potwierdzić, że połączenie z bazą danych jest w dobrej kondycji.
Warning
Podczas sprawdzania połączenia bazy danych z zapytaniem wybierz zapytanie, które szybko zwraca. Podejście do zapytania powoduje przeciążenie bazy danych i obniżenie wydajności. W większości przypadków uruchomienie zapytania testowego nie jest konieczne. Wystarczy nawiązać pomyślne połączenie z bazą danych. Jeśli okaże się, że konieczne jest uruchomienie zapytania, wybierz proste zapytanie SELECT, takie jak SELECT 1.
Dołącz odwołanie do pakietu AspNetCore.HealthChecks.SqlServer.
Podaj prawidłowy ciąg połączenia z bazą danych w pliku appsettings.json aplikacji przykładowej. Aplikacja używa bazy danych programu SQL Server o nazwie HealthCheckSample:
{
"ConnectionStrings": {
"DefaultConnection": "Server=(localdb)\\MSSQLLocalDB;Database=HealthCheckSample;Trusted_Connection=True;MultipleActiveResultSets=true;ConnectRetryCount=0"
},
"Logging": {
"LogLevel": {
"Default": "Information",
"Microsoft": "Warning",
"Microsoft.Hosting.Lifetime": "Information"
},
"Console": {
"IncludeScopes": "true"
}
},
"AllowedHosts": "*"
}
Zarejestruj usługi sprawdzania kondycji w AddHealthChecks w Startup.ConfigureServices. Przykładowa aplikacja wywołuje metodę AddSqlServer z parametrem połączenia bazy danych (DbHealthStartup.cs):
services.AddHealthChecks()
.AddSqlServer(Configuration["ConnectionStrings:DefaultConnection"]);
Punkt końcowy kontroli kondycji jest tworzony przez wywołanie metody MapHealthChecks w pliku Startup.Configure:
app.UseEndpoints(endpoints =>
{
endpoints.MapHealthChecks("/health");
}
Aby uruchomić scenariusz sondy bazy danych przy użyciu przykładowej aplikacji, wykonaj następujące polecenie z folderu projektu w oknie wiersza polecenia:
dotnet run --scenario db
Note
AspNetCore.Diagnostics.HealthChecks nie jest obsługiwany ani wspierany przez firmę Microsoft.
Sonda DbContext w Entity Framework Core
Sprawdzanie DbContext potwierdza, że aplikacja może komunikować się z bazą danych skonfigurowaną dla elementu EF CoreDbContext. Sprawdzanie DbContext jest obsługiwane w aplikacjach, które:
- Użyj platformy Entity Framework (EF) Core.
- Dołącz odwołanie do pakietu
Microsoft.Extensions.Diagnostics.HealthChecks.EntityFrameworkCore.
AddDbContextCheck<TContext> rejestruje kontrolę kondycji dla elementu DbContext. Metoda otrzymuje DbContext jako TContext. Przeciążenie jest dostępne do skonfigurowania stanu niepowodzenia, tagów i niestandardowego zapytania testowego.
Domyślnie:
- Wywołuje
DbContextHealthCheckmetodę EF CoreCanConnectAsync. Możesz dostosować operację uruchamianą podczas sprawdzania kondycji, używając przeciążeń metodyAddDbContextCheck. - Nazwa sprawdzania kondycji to nazwa typu
TContext.
W przykładowej aplikacji AppDbContext jest dostarczana do AddDbContextCheck i zarejestrowana jako usługa w Startup.ConfigureServices (DbContextHealthStartup.cs):
services.AddHealthChecks()
.AddDbContextCheck<AppDbContext>();
services.AddDbContext<AppDbContext>(options =>
{
options.UseSqlServer(
Configuration["ConnectionStrings:DefaultConnection"]);
});
Punkt końcowy kontroli kondycji jest tworzony przez wywołanie metody MapHealthChecks w pliku Startup.Configure:
app.UseEndpoints(endpoints =>
{
endpoints.MapHealthChecks("/health");
}
Aby uruchomić DbContext scenariusz sondowania przy użyciu przykładowej aplikacji, upewnij się, że baza danych określona przez parametry połączenia nie istnieje w wystąpieniu programu SQL Server. Jeśli baza danych istnieje, usuń ją.
Wykonaj następujące polecenie z folderu projektu w powłoce poleceń:
dotnet run --scenario dbcontext
Po uruchomieniu aplikacji sprawdź stan kondycji, wysyłając żądanie do punktu końcowego /health w przeglądarce. Baza danych i AppDbContext nie istnieją, dlatego aplikacja udostępnia następującą odpowiedź:
Unhealthy
Uruchom aplikację przykładową, aby utworzyć bazę danych. Prześlij żądanie do /createdatabase. Aplikacja odpowiada:
Creating the database...
Done!
Navigate to /health to see the health status.
Prześlij żądanie do punktu końcowego /health . Baza danych i kontekst istnieją, więc aplikacja odpowiada:
Healthy
Uruchom przykładową aplikację w celu usunięcia bazy danych. Prześlij żądanie do /deletedatabase. Aplikacja odpowiada:
Deleting the database...
Done!
Navigate to /health to see the health status.
Prześlij żądanie do punktu końcowego /health . Aplikacja zapewnia niezdrową odpowiedź.
Unhealthy
Oddzielne sondy gotowości i żywotności
W niektórych scenariuszach hostingu para kontroli kondycji służy do rozróżniania dwóch stanów aplikacji:
- Gotowość wskazuje, czy aplikacja działa normalnie, ale nie jest gotowa do odbierania żądań.
- Liveness wskazuje, czy aplikacja uległa awarii i musi zostać ponownie uruchomiona.
Rozważmy następujący przykład: Aplikacja musi pobrać duży plik konfiguracji, zanim będzie gotowa do przetwarzania żądań. Nie chcemy, aby aplikacja została ponownie uruchomiona, jeśli początkowe pobieranie nie powiedzie się, ponieważ aplikacja może ponowić próbę pobrania pliku kilka razy. Używamy sondy żywotności procesu do opisania żywotności procesu, nie są uruchamiane żadne inne testy. Chcemy również uniemożliwić wysyłanie żądań do aplikacji przed pomyślnym pobraniem pliku konfiguracji. Używamy sondy gotowości, aby wskazać stan "niegotowości", dopóki pobieranie nie zakończy się sukcesem, a aplikacja będzie gotowa do odbierania żądań.
Przykładowa aplikacja zawiera kontrolę kondycji, aby zgłosić ukończenie długotrwałego zadania uruchamiania w usłudze hostowanej. Właściwość StartupHostedServiceHealthCheck udostępnia atrybut StartupTaskCompleted, który hostowana usługa może ustawić na true po zakończeniu długotrwałego zadania (StartupHostedServiceHealthCheck.cs):
public class StartupHostedServiceHealthCheck : IHealthCheck
{
private volatile bool _startupTaskCompleted = false;
public string Name => "slow_dependency_check";
public bool StartupTaskCompleted
{
get => _startupTaskCompleted;
set => _startupTaskCompleted = value;
}
public Task<HealthCheckResult> CheckHealthAsync(
HealthCheckContext context,
CancellationToken cancellationToken = default(CancellationToken))
{
if (StartupTaskCompleted)
{
return Task.FromResult(
HealthCheckResult.Healthy("The startup task is finished."));
}
return Task.FromResult(
HealthCheckResult.Unhealthy("The startup task is still running."));
}
}
Długotrwałe zadanie w tle jest uruchamiane przez usługę hostowaną (Services/StartupHostedService). Na zakończenie zadania StartupHostedServiceHealthCheck.StartupTaskCompleted jest ustawione na true:
public class StartupHostedService : IHostedService, IDisposable
{
private readonly int _delaySeconds = 15;
private readonly ILogger _logger;
private readonly StartupHostedServiceHealthCheck _startupHostedServiceHealthCheck;
public StartupHostedService(ILogger<StartupHostedService> logger,
StartupHostedServiceHealthCheck startupHostedServiceHealthCheck)
{
_logger = logger;
_startupHostedServiceHealthCheck = startupHostedServiceHealthCheck;
}
public Task StartAsync(CancellationToken cancellationToken)
{
_logger.LogInformation("Startup Background Service is starting.");
// Simulate the effect of a long-running startup task.
Task.Run(async () =>
{
await Task.Delay(_delaySeconds * 1000);
_startupHostedServiceHealthCheck.StartupTaskCompleted = true;
_logger.LogInformation("Startup Background Service has started.");
});
return Task.CompletedTask;
}
public Task StopAsync(CancellationToken cancellationToken)
{
_logger.LogInformation("Startup Background Service is stopping.");
return Task.CompletedTask;
}
public void Dispose()
{
}
}
Kontrola kondycji jest zarejestrowana AddCheck razem Startup.ConfigureServices z hostowaną usługą. Ponieważ hostowana usługa musi ustawić właściwość sprawdzania kondycji, kontrola kondycji jest również zarejestrowana w kontenerze usługi (LivenessProbeStartup.cs):
services.AddHostedService<StartupHostedService>();
services.AddSingleton<StartupHostedServiceHealthCheck>();
services.AddHealthChecks()
.AddCheck<StartupHostedServiceHealthCheck>(
"hosted_service_startup",
failureStatus: HealthStatus.Degraded,
tags: new[] { "ready" });
services.Configure<HealthCheckPublisherOptions>(options =>
{
options.Delay = TimeSpan.FromSeconds(2);
options.Predicate = (check) => check.Tags.Contains("ready");
});
services.AddSingleton<IHealthCheckPublisher, ReadinessPublisher>();
Punkt końcowy sprawdzania kondycji jest tworzony przez wywołanie metody MapHealthChecks w pliku Startup.Configure. W przykładowej aplikacji punkty końcowe sprawdzania kondycji są tworzone pod adresem:
-
/health/readyw celu sprawdzenia gotowości. Test gotowości filtruje testy kondycji do sprawdzania kondycji za pomocą taguready. -
/health/livew celu sprawdzenia żywotności. Sprawdzenie żywotności filtrujeStartupHostedServiceHealthCheckpoprzez zwróceniefalsewHealthCheckOptions.Predicate(aby uzyskać więcej informacji, zobacz Filtrowanie kontroli kondycji)
W poniższym przykładowym kodzie:
- Sprawdzanie gotowości używa wszystkich zarejestrowanych testów z etykietą "ready".
- Element
Predicatewyklucza wszystkie kontrole i zwraca wartość 200-OK.
app.UseEndpoints(endpoints =>
{
endpoints.MapHealthChecks("/health/ready", new HealthCheckOptions()
{
Predicate = (check) => check.Tags.Contains("ready"),
});
endpoints.MapHealthChecks("/health/live", new HealthCheckOptions()
{
Predicate = (_) => false
});
}
Aby uruchomić scenariusz konfiguracji gotowości/dostępności przy użyciu aplikacji przykładowej, wykonaj następujące polecenie z folderu projektu w wierszu poleceń.
dotnet run --scenario liveness
W przeglądarce przejdź /health/ready kilka razy, aż minie 15 sekund. Raporty kontroli stanu Unhealthy przez pierwsze 15 sekund. Po 15 sekundach punkt końcowy zgłasza Healthy, co odzwierciedla ukończenie długotrwałego zadania przez hostowaną usługę.
W tym przykładzie zostanie również utworzony program Health Check Publisher (IHealthCheckPublisher implementacja), który uruchamia pierwszą kontrolę gotowości z dwusekundowym opóźnieniem. Aby uzyskać więcej informacji, zobacz sekcję Health Check Publisher.
Przykład rozwiązania Kubernetes
Korzystanie z oddzielnych testów gotowości i dostępności jest przydatne w środowisku, takim jak Kubernetes. Na platformie Kubernetes aplikacja może być wymagana do wykonywania czasochłonnej pracy podczas uruchamiania przed zaakceptowaniem żądań, takich jak test dostępności bazowej bazy danych. Użycie oddzielnych kontroli umożliwia orkiestratorowi rozróżnienie, czy aplikacja działa, ale nie jest jeszcze gotowa, czy nie można uruchomić aplikacji. Aby uzyskać więcej informacji na temat sond gotowości i kondycji na platformie Kubernetes, zobacz Konfigurowanie sond kondycji i gotowości w dokumentacji platformy Kubernetes.
W poniższym przykładzie pokazano konfigurację sondy gotowości Kubernetes:
spec:
template:
spec:
readinessProbe:
# an http probe
httpGet:
path: /health/ready
port: 80
# length of time to wait for a pod to initialize
# after pod startup, before applying health checking
initialDelaySeconds: 30
timeoutSeconds: 1
ports:
- containerPort: 80
Sonda oparta na metryce z niestandardowym modułem zapisywania odpowiedzi
Przykładowa aplikacja demonstruje kontrolę kondycji pamięci z niestandardowym modułem zapisywania odpowiedzi.
MemoryHealthCheck zgłasza stan obniżonej wydajności, jeśli aplikacja używa więcej niż określony próg pamięci (1 GB w przykładowej aplikacji). Moduł HealthCheckResult zawiera informacje dotyczące Garbage Colletor (GC) dla aplikacji (MemoryHealthCheck.cs):
public class MemoryHealthCheck : IHealthCheck
{
private readonly IOptionsMonitor<MemoryCheckOptions> _options;
public MemoryHealthCheck(IOptionsMonitor<MemoryCheckOptions> options)
{
_options = options;
}
public string Name => "memory_check";
public Task<HealthCheckResult> CheckHealthAsync(
HealthCheckContext context,
CancellationToken cancellationToken = default(CancellationToken))
{
var options = _options.Get(context.Registration.Name);
// Include GC information in the reported diagnostics.
var allocated = GC.GetTotalMemory(forceFullCollection: false);
var data = new Dictionary<string, object>()
{
{ "AllocatedBytes", allocated },
{ "Gen0Collections", GC.CollectionCount(0) },
{ "Gen1Collections", GC.CollectionCount(1) },
{ "Gen2Collections", GC.CollectionCount(2) },
};
var status = (allocated < options.Threshold) ?
HealthStatus.Healthy : context.Registration.FailureStatus;
return Task.FromResult(new HealthCheckResult(
status,
description: "Reports degraded status if allocated bytes " +
$">= {options.Threshold} bytes.",
exception: null,
data: data));
}
}
Zarejestruj usługi sprawdzania kondycji w AddHealthChecks w Startup.ConfigureServices. Zamiast włączać kontrolę kondycji przez przekazanie jej do AddCheck, MemoryHealthCheck jest rejestrowany jako usługa. Wszystkie IHealthCheck zarejestrowane usługi są dostępne dla usług kontroli kondycji i oprogramowania pośredniczącego. Zalecamy zarejestrowanie usług kontroli kondycji jako usług Singleton.
W CustomWriterStartup.cs przykładowej aplikacji:
services.AddHealthChecks()
.AddMemoryHealthCheck("memory");
Punkt końcowy sprawdzania kondycji jest tworzony przez wywołanie metody MapHealthChecks w pliku Startup.Configure. Delegat WriteResponse jest dostarczany do ResponseWriter właściwości w celu wyprowadzenia niestandardowej odpowiedzi JSON po wykonaniu sprawdzania kondycji:
app.UseEndpoints(endpoints =>
{
endpoints.MapHealthChecks("/health", new HealthCheckOptions()
{
ResponseWriter = WriteResponse
});
}
Delegat WriteResponse formatuje CompositeHealthCheckResult na obiekt JSON i zwraca wynik JSON dla odpowiedzi na kontrolę zdrowia. Aby uzyskać więcej informacji, zobacz sekcję Dostosowywanie danych wyjściowych .
Aby uruchomić sondę opartą na metrykach z niestandardowymi danymi wyjściowymi modułu zapisywania odpowiedzi przy użyciu przykładowej aplikacji, wykonaj następujące polecenie z folderu projektu w powłoce poleceń:
dotnet run --scenario writer
Note
AspNetCore.Diagnostics.HealthChecks obejmuje scenariusze sprawdzania kondycji oparte na metrykach, w tym przechowywanie dysku i testy żywotności maksymalnej wartości.
AspNetCore.Diagnostics.HealthChecks nie jest obsługiwany ani wspierany przez firmę Microsoft.
Filtruj według portu
Wywołaj RequireHost na MapHealthChecks ze wzorcem URL, który określa port, aby ograniczyć żądania kontroli kondycji do wskazanego portu. Takie podejście jest zwykle używane w środowisku kontenera do uwidaczniania portu na potrzeby usług monitorowania.
Przykładowa aplikacja konfiguruje port przy użyciu dostawcy konfiguracji zmiennych środowiskowych. Port jest ustawiany w launchSettings.json pliku i przekazywany do dostawcy konfiguracji za pośrednictwem zmiennej środowiskowej. Należy również skonfigurować serwer do nasłuchiwania żądań na porcie zarządzania.
Aby użyć przykładowej aplikacji do zademonstrowania konfiguracji portu zarządzania, utwórz launchSettings.json plik w folderze Properties .
Następujący Properties/launchSettings.json plik w przykładowej aplikacji nie jest uwzględniony w plikach projektu przykładowej aplikacji i należy go utworzyć ręcznie:
{
"profiles": {
"SampleApp": {
"commandName": "Project",
"commandLineArgs": "",
"launchBrowser": true,
"environmentVariables": {
"ASPNETCORE_ENVIRONMENT": "Development",
"ASPNETCORE_URLS": "http://localhost:5000/;http://localhost:5001/",
"ASPNETCORE_MANAGEMENTPORT": "5001"
},
"applicationUrl": "http://localhost:5000/"
}
}
}
Zarejestruj usługi sprawdzania kondycji w AddHealthChecks w Startup.ConfigureServices. Utwórz punkt końcowy kontroli kondycji, wywołując MapHealthChecks w Startup.Configure.
W przykładowej aplikacji wywołanie RequireHost na punkcie końcowym w Startup.Configure określa port zarządzania na podstawie konfiguracji:
endpoints.MapHealthChecks("/health")
.RequireHost($"*:{Configuration["ManagementPort"]}");
Punkty końcowe są tworzone w przykładowej aplikacji w programie Startup.Configure. W poniższym przykładowym kodzie:
- Sprawdzanie gotowości używa wszystkich zarejestrowanych testów z etykietą "ready".
- Element
Predicatewyklucza wszystkie kontrole i zwraca wartość 200-OK.
app.UseEndpoints(endpoints =>
{
endpoints.MapHealthChecks("/health/ready", new HealthCheckOptions()
{
Predicate = (check) => check.Tags.Contains("ready"),
});
endpoints.MapHealthChecks("/health/live", new HealthCheckOptions()
{
Predicate = (_) => false
});
}
Note
Możesz uniknąć tworzenia launchSettings.json pliku w przykładowej aplikacji, ustawiając jawnie port zarządzania w kodzie. W Program.cs, gdzie utworzono HostBuilder, dodaj wywołanie do ListenAnyIP i podaj punkt końcowy portu zarządzania aplikacją. W Configure pliku ManagementPortStartup.cs określ port zarządzania za pomocą RequireHost polecenia :
Program.cs:
return new HostBuilder()
.ConfigureWebHostDefaults(webBuilder =>
{
webBuilder.UseKestrel()
.ConfigureKestrel(serverOptions =>
{
serverOptions.ListenAnyIP(5001);
})
.UseStartup(startupType);
})
.Build();
ManagementPortStartup.cs:
app.UseEndpoints(endpoints =>
{
endpoints.MapHealthChecks("/health").RequireHost("*:5001");
});
Aby uruchomić scenariusz konfiguracji portu zarządzania przy użyciu przykładowej aplikacji, wykonaj następujące polecenie z folderu projektu w powłoce poleceń:
dotnet run --scenario port
Rozpowszechnianie biblioteki kontroli kondycji
Aby rozpowszechnić kontrolę stanu zdrowia jako bibliotekę:
Napisz kontrolę kondycji, która implementuje IHealthCheck interfejs jako klasę autonomiczną. Klasa może polegać na iniekcji zależności (DI), aktywacji typu i nazwanych opcjach uzyskiwania dostępu do danych konfiguracji.
W logice kontroli stanu komponentu
CheckHealthAsync:-
data1idata2są używane w metodzie do uruchamiania logiki sprawdzania kondycji sondy. -
AccessViolationExceptionjest obsługiwane.
W przypadku AccessViolationExceptionFailureStatus jest zwracany z parametrem HealthCheckResult, aby umożliwić użytkownikom skonfigurowanie stanu awarii kontroli kondycji.
using System; using System.Threading; using System.Threading.Tasks; using Microsoft.Extensions.Diagnostics.HealthChecks; namespace SampleApp { public class ExampleHealthCheck : IHealthCheck { private readonly string _data1; private readonly int? _data2; public ExampleHealthCheck(string data1, int? data2) { _data1 = data1 ?? throw new ArgumentNullException(nameof(data1)); _data2 = data2 ?? throw new ArgumentNullException(nameof(data2)); } public async Task<HealthCheckResult> CheckHealthAsync( HealthCheckContext context, CancellationToken cancellationToken) { try { return HealthCheckResult.Healthy(); } catch (AccessViolationException ex) { return new HealthCheckResult( context.Registration.FailureStatus, description: "An access violation occurred during the check.", exception: ex, data: null); } } } }-
Napisz metodę rozszerzenia z parametrami, które aplikacja, która korzysta, wywołuje w swojej metodzie
Startup.Configure. W poniższym przykładzie przyjęto założenie następującego podpisu metody kontroli kondycji:ExampleHealthCheck(string, string, int )Powyższy podpis wskazuje, że
ExampleHealthCheckwymaga dodatkowych danych do przetwarzania logiki sondy sprawdzania kondycji. Dane są przekazywane delegatowi, który jest używany do utworzenia instancji sprawdzenia kondycji, gdy sprawdzenie kondycji jest zarejestrowane za pomocą metody rozszerzenia. W poniższym przykładzie wywołujący określa wartość opcjonalną:- nazwa sprawdzenia kondycji (
name).nullJeśliexample_health_checkparametr jest używany. - punkt danych tekstowych dla sprawdzenia kondycji (
data1). - Punkt danych całkowitych dla kontroli stanu (
data2). Jeślinull,1jest używany. - stan błędu (HealthStatus). Wartość domyślna to
null. Jeślinull, zgłaszany jest HealthStatus.Unhealthy jako status błędu. - tagi (
IEnumerable<string>).
using System.Collections.Generic; using Microsoft.Extensions.Diagnostics.HealthChecks; public static class ExampleHealthCheckBuilderExtensions { const string DefaultName = "example_health_check"; public static IHealthChecksBuilder AddExampleHealthCheck( this IHealthChecksBuilder builder, string name = default, string data1, int data2 = 1, HealthStatus? failureStatus = default, IEnumerable<string> tags = default) { return builder.Add(new HealthCheckRegistration( name ?? DefaultName, sp => new ExampleHealthCheck(data1, data2), failureStatus, tags)); } }- nazwa sprawdzenia kondycji (
Wydawca kontroli kondycji
Po dodaniu elementu IHealthCheckPublisher do kontenera usługi system monitorowania kondycji okresowo wykonuje sprawdzanie kondycji i wywołuje PublishAsync z wynikiem. Jest to przydatne w scenariuszu systemu monitorowania stanu opartym na podejściu bazującym na przesyłaniu, który oczekuje, że każdy proces będzie okresowo wywoływać system monitorowania w celu oceny stanu.
Interfejs IHealthCheckPublisher ma jedną metodę:
Task PublishAsync(HealthReport report, CancellationToken cancellationToken);
HealthCheckPublisherOptions pozwala na ustawienie:
- Delay: początkowe opóźnienie zastosowane po uruchomieniu aplikacji przed wykonaniem IHealthCheckPublisher wystąpień. Opóźnienie jest stosowane raz podczas uruchamiania i nie ma zastosowania do kolejnych iteracji. Wartość domyślna to pięć sekund.
- Period: okres IHealthCheckPublisher wykonywania. Wartość domyślna to 30 sekund.
-
Predicate: Jeśli Predicate jest
null(wartość domyślna), usługa wydawcy testów kondycji uruchamia wszystkie zarejestrowane testy kondycji. Aby uruchomić podzbiór kontroli kondycji, podaj funkcję, która filtruje zestaw testów. Predykat jest obliczany w każdym okresie. - Timeout: limit czasu na wykonywanie kontroli kondycji dla wszystkich IHealthCheckPublisher wystąpień. Użyj polecenia InfiniteTimeSpan , aby wykonać bez limitu czasu. Wartość domyślna to 30 sekund.
W przykładowej aplikacji ReadinessPublisher jest implementacją IHealthCheckPublisher . Stan kontroli kondycji jest rejestrowany dla każdego sprawdzenia na poziomie dziennika:
- Informacje (LogInformation), jeśli stan kontroli kondycji to Healthy.
- Błąd (LogError), jeśli stan to Degraded lub Unhealthy.
public class ReadinessPublisher : IHealthCheckPublisher
{
private readonly ILogger _logger;
public ReadinessPublisher(ILogger<ReadinessPublisher> logger)
{
_logger = logger;
}
// The following example is for demonstration purposes only. Health Checks
// Middleware already logs health checks results. A real-world readiness
// check in a production app might perform a set of more expensive or
// time-consuming checks to determine if other resources are responding
// properly.
public Task PublishAsync(HealthReport report,
CancellationToken cancellationToken)
{
if (report.Status == HealthStatus.Healthy)
{
_logger.LogInformation("{Timestamp} Readiness Probe Status: {Result}",
DateTime.UtcNow, report.Status);
}
else
{
_logger.LogError("{Timestamp} Readiness Probe Status: {Result}",
DateTime.UtcNow, report.Status);
}
cancellationToken.ThrowIfCancellationRequested();
return Task.CompletedTask;
}
}
W przykładzie LivenessProbeStartup przykładowej aplikacji StartupHostedService test gotowości ma dwie sekundy opóźnienia przed uruchomieniem i wykonuje sprawdzanie co 30 sekund. Aby aktywować implementacjęIHealthCheckPublisher, przykład rejestruje ReadinessPublisher jako usługę pojedynczą w kontenerze DI:
services.AddHostedService<StartupHostedService>();
services.AddSingleton<StartupHostedServiceHealthCheck>();
services.AddHealthChecks()
.AddCheck<StartupHostedServiceHealthCheck>(
"hosted_service_startup",
failureStatus: HealthStatus.Degraded,
tags: new[] { "ready" });
services.Configure<HealthCheckPublisherOptions>(options =>
{
options.Delay = TimeSpan.FromSeconds(2);
options.Predicate = (check) => check.Tags.Contains("ready");
});
services.AddSingleton<IHealthCheckPublisher, ReadinessPublisher>();
Note
AspNetCore.Diagnostics.HealthChecks zawiera wydawców dla kilku systemów, w tym Application Insights.
AspNetCore.Diagnostics.HealthChecks nie jest obsługiwany ani wspierany przez firmę Microsoft.
Ogranicz kontrole zdrowotne za pomocą MapWhen
Użyj polecenia MapWhen , aby warunkowo rozgałęzić potok żądania dla punktów końcowych sprawdzania kondycji.
W poniższym przykładzie MapWhen rozgałęzia potok żądań, aby aktywować oprogramowanie pośredniczące do sprawdzania kondycji, jeśli zostanie odebrane żądanie GET dla punktu końcowego api/HealthCheck.
app.MapWhen(
context => context.Request.Method == HttpMethod.Get.Method &&
context.Request.Path.StartsWith("/api/HealthCheck"),
builder => builder.UseHealthChecks());
app.UseEndpoints(endpoints =>
{
endpoints.MapRazorPages();
});
Aby uzyskać więcej informacji, zobacz Oprogramowanie pośredniczące ASP.NET Core.
ASP.NET Core oferuje middleware sprawdzania kondycji oraz biblioteki do raportowania kondycji składników infrastruktury aplikacji.
Testy kondycji są udostępniane przez aplikację jako punkty końcowe HTTP. Punkty końcowe kontroli kondycji można skonfigurować dla różnych scenariuszy monitorowania w czasie rzeczywistym:
- Sondy kondycji mogą być używane przez koordynatorów kontenerów i moduły równoważenia obciążenia w celu sprawdzenia stanu aplikacji. Na przykład orkiestrator kontenerów może reagować na niepowodzenie sprawdzania kondycji, zatrzymując wdrożenie stopniowe lub ponownie uruchamiając kontener. Moduł równoważenia obciążenia może reagować na problemy z aplikacją przez przekierowanie ruchu z wadliwego wystąpienia do wystąpienia działającego poprawnie.
- Użycie pamięci, dysku i innych zasobów serwera fizycznego można monitorować pod kątem stanu dobrej kondycji.
- Testy kondycji mogą testować zależności aplikacji, takie jak bazy danych i zewnętrzne punkty końcowe usługi, w celu potwierdzenia dostępności i normalnego działania.
Wyświetl lub pobierz przykładowy kod (jak pobrać)
Przykładowa aplikacja zawiera przykłady scenariuszy opisanych w tym artykule. Aby uruchomić przykładową aplikację dla danego scenariusza, użyj polecenia dotnet run z folderu projektu w powłoce poleceń. Zobacz plik przykładowej README.md aplikacji i opisy scenariuszy w tym artykule, aby uzyskać szczegółowe informacje na temat korzystania z przykładowej aplikacji.
Prerequisites
Testy kondycji są zwykle używane z zewnętrzną usługą monitorowania lub koordynatorem kontenerów w celu sprawdzenia stanu aplikacji. Przed dodaniem kontroli kondycji do aplikacji zdecyduj, który system monitorowania ma być używany. System monitorowania określa, jakie typy testów zdrowia należy utworzyć i jak skonfigurować ich punkty końcowe.
Pakiet Microsoft.AspNetCore.Diagnostics.HealthChecks jest przywoływany niejawnie dla aplikacji ASP.NET Core. Aby uruchomić kontrole kondycji przy użyciu programu Entity Framework Core, dodaj odwołanie do Microsoft.Extensions.Diagnostics.HealthChecks.EntityFrameworkCore pakietu.
Przykładowa aplikacja udostępnia kod uruchamiania w celu zademonstrowania kontroli kondycji dla kilku scenariuszy. Scenariusz sondy bazy danych sprawdza stan połączenia z bazą danych przy użyciu AspNetCore.Diagnostics.HealthChecks. Scenariusz sondy DbContext sprawdza bazę danych przy użyciu . Aby zapoznać się ze scenariuszami bazy danych, przykładowa aplikacja:
- Tworzy bazę danych i udostępnia jej parametry połączenia w
appsettings.jsonpliku. - Zawiera następujące odwołania do pakietów w pliku projektu:
Note
AspNetCore.Diagnostics.HealthChecks nie jest obsługiwany ani wspierany przez firmę Microsoft.
Inny scenariusz kontroli kondycji demonstruje, jak filtrować te kontrole przez port zarządzania. Przykładowa aplikacja wymaga utworzenia pliku zawierającego Properties/launchSettings.json adres URL zarządzania i port zarządzania. Aby uzyskać więcej informacji, zobacz sekcję Filtruj według portów .
Podstawowa sonda kondycji
W przypadku wielu aplikacji podstawowa konfiguracja sondy kondycji, która zgłasza dostępność aplikacji do przetwarzania żądań (statusu działania) jest wystarczająca do ustalenia stanu aplikacji.
Podstawowa konfiguracja rejestruje usługi monitorowania stanu i wywołuje middleware do kontroli stanu zdrowia, aby odpowiedzieć na adresie URL odpowiedzią zdrowotną. Domyślnie żadne konkretne kontrole kondycji nie są rejestrowane w celu przetestowania żadnej konkretnej zależności lub podsystemu. Aplikacja jest uważana za w dobrej kondycji, jeśli może odpowiadać pod adresem URL punktu końcowego zdrowia. Domyślny składnik zapisu odpowiedzi zapisuje stan (HealthStatus) jako odpowiedź w postaci zwykłego tekstu z powrotem do klienta, wskazując stan HealthStatus.Healthy, HealthStatus.Degraded lub HealthStatus.Unhealthy.
Zarejestruj usługi sprawdzania kondycji w AddHealthChecks w Startup.ConfigureServices. Utwórz punkt końcowy kontroli kondycji, wywołując MapHealthChecks w Startup.Configure.
W przykładowej aplikacji punkt końcowy sprawdzania kondycji jest tworzony pod adresem /health (BasicStartup.cs):
public class BasicStartup
{
public void ConfigureServices(IServiceCollection services)
{
services.AddHealthChecks();
}
public void Configure(IApplicationBuilder app)
{
app.UseRouting();
app.UseEndpoints(endpoints =>
{
endpoints.MapHealthChecks("/health");
});
}
}
Aby uruchomić podstawowy scenariusz konfiguracji przy użyciu przykładowej aplikacji, wykonaj następujące polecenie z folderu projektu w powłoce poleceń:
dotnet run --scenario basic
Przykład platformy Docker
Platforma Docker oferuje wbudowaną HEALTHCHECK dyrektywę, która może służyć do sprawdzania stanu aplikacji korzystającej z podstawowej konfiguracji kontroli kondycji:
HEALTHCHECK CMD curl --fail http://localhost:5000/health || exit
Tworzenie kontroli kondycji
Testy kondycji są tworzone przez zaimplementowanie interfejsu IHealthCheck . Metoda CheckHealthAsync zwraca wartość HealthCheckResult , która wskazuje kondycję jako Healthy, Degradedlub Unhealthy. Wynik jest zapisywany jako odpowiedź w postaci zwykłego tekstu z konfigurowalnym kodem stanu (konfiguracja jest opisana w sekcji Opcje sprawdzania kondycji).
HealthCheckResult może również zwracać opcjonalne pary klucz-wartość.
Poniższa ExampleHealthCheck klasa demonstruje układ kontroli kondycji. Logika kontroli kondycji jest umieszczana w metodzie CheckHealthAsync . W poniższym przykładzie ustawiono fikcyjną zmienną , healthCheckResultHealthyna true. Jeśli wartość parametru healthCheckResultHealthy jest ustawiona na false, zwracany jest stan HealthCheckResult.Unhealthy.
public class ExampleHealthCheck : IHealthCheck
{
public Task<HealthCheckResult> CheckHealthAsync(
HealthCheckContext context,
CancellationToken cancellationToken = default(CancellationToken))
{
var healthCheckResultHealthy = true;
if (healthCheckResultHealthy)
{
return Task.FromResult(
HealthCheckResult.Healthy("A healthy result."));
}
return Task.FromResult(
HealthCheckResult.Unhealthy("An unhealthy result."));
}
}
Rejestrowanie usług kontroli kondycji
Typ ExampleHealthCheck jest dodawany do usług sprawdzania kondycji przy użyciu AddCheck w pliku Startup.ConfigureServices.
services.AddHealthChecks()
.AddCheck<ExampleHealthCheck>("example_health_check");
Przeciążenie AddCheck pokazane w poniższym przykładzie ustawia stan błędu (HealthStatus) w celu raportowania, gdy kontrola kondycji zgłasza błąd. Jeśli stan niepowodzenia jest ustawiony na null (wartość domyślna), HealthStatus.Unhealthy jest zgłaszany. To przeciążenie jest przydatnym scenariuszem dla autorów bibliotek, gdzie status awarii wskazywany przez bibliotekę jest wymuszany przez aplikację, gdy wystąpi błąd w sprawdzaniu kondycji, o ile implementacja sprawdzania kondycji respektuje to ustawienie.
Tagi mogą służyć do filtrowania kontroli kondycji (opisanych dalej w sekcji Filtr kontroli kondycji).
services.AddHealthChecks()
.AddCheck<ExampleHealthCheck>(
"example_health_check",
failureStatus: HealthStatus.Degraded,
tags: new[] { "example" });
AddCheck może również wykonać funkcję lambda. W poniższym przykładzie nazwa kontroli kondycji jest określona jako Example i sprawdzanie zawsze zwraca stan dobrej kondycji:
services.AddHealthChecks()
.AddCheck("Example", () =>
HealthCheckResult.Healthy("Example is OK!"), tags: new[] { "example" });
Wywołaj metodę AddTypeActivatedCheck , aby przekazać argumenty do implementacji kontroli kondycji. W poniższym przykładzie TestHealthCheckWithArgs akceptuje liczbę całkowitą i ciąg do użycia, gdy CheckHealthAsync jest wywoływany:
private class TestHealthCheckWithArgs : IHealthCheck
{
public TestHealthCheckWithArgs(int i, string s)
{
I = i;
S = s;
}
public int I { get; set; }
public string S { get; set; }
public Task<HealthCheckResult> CheckHealthAsync(HealthCheckContext context,
CancellationToken cancellationToken = default)
{
...
}
}
TestHealthCheckWithArgs jest rejestrowany przez wywołanie AddTypeActivatedCheck za pomocą liczby całkowitej i ciągu przekazanego do implementacji:
services.AddHealthChecks()
.AddTypeActivatedCheck<TestHealthCheckWithArgs>(
"test",
failureStatus: HealthStatus.Degraded,
tags: new[] { "example" },
args: new object[] { 5, "string" });
Zastosuj trasowanie kontroli zdrowia
W Startup.Configure wywołaj MapHealthChecks na budowniczym punktu końcowego z adresem URL punktu końcowego lub ścieżką względną:
app.UseEndpoints(endpoints =>
{
endpoints.MapHealthChecks("/health");
});
Wymagaj hosta
Wywołaj RequireHost , aby określić co najmniej jednego dozwolonego hosta dla endpointu kontroli kondycji. Hosty powinny być unicode, a nie punycode i mogą zawierać port. Jeśli kolekcja nie zostanie dostarczona, zaakceptowany zostanie dowolny host.
app.UseEndpoints(endpoints =>
{
endpoints.MapHealthChecks("/health").RequireHost("www.contoso.com:5001");
});
Aby uzyskać więcej informacji, zobacz sekcję Filtruj według portów .
Wymagaj autoryzacji
Wywołaj polecenie RequireAuthorization , aby uruchomić oprogramowanie pośredniczące autoryzacji w punkcie końcowym żądania sprawdzania kondycji. Przeciążenie RequireAuthorization akceptuje co najmniej jedną zasady autoryzacji. Jeśli nie podano zasad, są używane domyślne zasady autoryzacji.
app.UseEndpoints(endpoints =>
{
endpoints.MapHealthChecks("/health").RequireAuthorization();
});
Włącz żądania Cross-Origin (CORS)
Mimo że ręczne uruchamianie kontroli kondycji z przeglądarki nie jest typowym scenariuszem użycia, oprogramowanie pośredniczące CORS można włączyć przez wywołanie RequireCors punktów końcowych kontroli kondycji. Przeciążenie RequireCors akceptuje delegata budującego zasady CORS (CorsPolicyBuilder) lub nazwę zasad. Jeśli nie podano zasad, zostanie użyta domyślna zasada CORS. Aby uzyskać więcej informacji, zobacz Włączanie żądań między źródłami (CORS) w ASP.NET Core.
Opcje kontroli kondycji
HealthCheckOptions umożliwia dostosowanie zachowania kontroli kondycji:
- Kontrole kondycji filtrów
- Dostosowywanie kodu stanu HTTP
- Blokowanie nagłówków pamięci podręcznej
- Dostosowywanie danych wyjściowych
Filtrowanie sprawdzania kondycji
Domyślnie middleware do kontroli kondycji uruchamia wszystkie zarejestrowane testy zdrowia. Aby uruchomić podzbiór testów kondycji, podaj funkcję, która zwraca wartość logiczną jako argument opcji Predicate. W poniższym przykładzie Bar sprawdzanie kondycji jest filtrowane według tagu (bar_tag) w instrukcji warunkowej funkcji, gdzie true jest zwracana tylko wtedy, gdy właściwość Tags sprawdzania kondycji odpowiada foo_tag albo baz_tag.
W pliku Startup.ConfigureServices:
services.AddHealthChecks()
.AddCheck("Foo", () =>
HealthCheckResult.Healthy("Foo is OK!"), tags: new[] { "foo_tag" })
.AddCheck("Bar", () =>
HealthCheckResult.Unhealthy("Bar is unhealthy!"), tags: new[] { "bar_tag" })
.AddCheck("Baz", () =>
HealthCheckResult.Healthy("Baz is OK!"), tags: new[] { "baz_tag" });
W Startup.Configure, Predicate filtruje sprawdzanie kondycji 'Bar'. Wykonaj tylko polecenia Foo i Baz:
app.UseEndpoints(endpoints =>
{
endpoints.MapHealthChecks("/health", new HealthCheckOptions()
{
Predicate = (check) => check.Tags.Contains("foo_tag") ||
check.Tags.Contains("baz_tag")
});
});
Dostosowywanie kodu stanu HTTP
Użyj ResultStatusCodes do dostosowywania mapowania stanu kondycji na kody stanu HTTP. Następujące StatusCodes przypisania są wartościami domyślnymi używanymi przez middleware. Zmień wartości kodu stanu, aby spełniały twoje wymagania.
W pliku Startup.Configure:
app.UseEndpoints(endpoints =>
{
endpoints.MapHealthChecks("/health", new HealthCheckOptions()
{
ResultStatusCodes =
{
[HealthStatus.Healthy] = StatusCodes.Status200OK,
[HealthStatus.Degraded] = StatusCodes.Status200OK,
[HealthStatus.Unhealthy] = StatusCodes.Status503ServiceUnavailable
}
});
});
Tłumienie nagłówków pamięci podręcznej
AllowCachingResponses kontroluje, czy middleware do sprawdzania kondycji dodaje nagłówki HTTP do odpowiedzi z sondy, aby zapobiec buforowaniu odpowiedzi. Jeśli wartość to false (wartość domyślna), oprogramowanie pośredniczące ustawia lub zastępuje nagłówki Cache-Control, Expires i Pragma, aby zapobiec buforowaniu odpowiedzi. Jeśli wartość to true, oprogramowanie pośredniczące nie modyfikuje nagłówków pamięci podręcznej odpowiedzi.
W pliku Startup.Configure:
app.UseEndpoints(endpoints =>
{
endpoints.MapHealthChecks("/health", new HealthCheckOptions()
{
AllowCachingResponses = true
});
});
Dostosowywanie danych wyjściowych
W Startup.Configurepliku ustaw opcję delegata HealthCheckOptions.ResponseWriter na potrzeby pisania odpowiedzi:
app.UseEndpoints(endpoints =>
{
endpoints.MapHealthChecks("/health", new HealthCheckOptions()
{
ResponseWriter = WriteResponse
});
});
Domyślny delegat zapisuje minimalną odpowiedź w postaci czystego tekstu z wartością ciągu HealthReport.Status. Następujący delegat niestandardowy zwraca niestandardową odpowiedź JSON.
Pierwszy przykład z przykładowej aplikacji pokazuje, jak używać polecenia System.Text.Json:
private static Task WriteResponse(HttpContext context, HealthReport result)
{
context.Response.ContentType = "application/json; charset=utf-8";
var options = new JsonWriterOptions
{
Indented = true
};
using (var stream = new MemoryStream())
{
using (var writer = new Utf8JsonWriter(stream, options))
{
writer.WriteStartObject();
writer.WriteString("status", result.Status.ToString());
writer.WriteStartObject("results");
foreach (var entry in result.Entries)
{
writer.WriteStartObject(entry.Key);
writer.WriteString("status", entry.Value.Status.ToString());
writer.WriteString("description", entry.Value.Description);
writer.WriteStartObject("data");
foreach (var item in entry.Value.Data)
{
writer.WritePropertyName(item.Key);
JsonSerializer.Serialize(
writer, item.Value, item.Value?.GetType() ??
typeof(object));
}
writer.WriteEndObject();
writer.WriteEndObject();
}
writer.WriteEndObject();
writer.WriteEndObject();
}
var json = Encoding.UTF8.GetString(stream.ToArray());
return context.Response.WriteAsync(json);
}
}
W drugim przykładzie pokazano, jak używać pliku Newtonsoft.Json:
private static Task WriteResponse(HttpContext context, HealthReport result)
{
context.Response.ContentType = "application/json";
var json = new JObject(
new JProperty("status", result.Status.ToString()),
new JProperty("results", new JObject(result.Entries.Select(pair =>
new JProperty(pair.Key, new JObject(
new JProperty("status", pair.Value.Status.ToString()),
new JProperty("description", pair.Value.Description),
new JProperty("data", new JObject(pair.Value.Data.Select(
p => new JProperty(p.Key, p.Value))))))))));
return context.Response.WriteAsync(
json.ToString(Formatting.Indented));
}
W przykładowej aplikacji oznacz jako komentarz dyrektywę
Interfejs API sprawdzania kondycji nie zapewnia wbudowanej obsługi złożonych formatów zwracanych JSON, ponieważ format jest specyficzny dla wybranego systemu monitorowania. Dostosuj odpowiedź w poprzednich przykładach zgodnie z potrzebami. Aby uzyskać więcej informacji na temat serializacji JSON za pomocą System.Text.Json, zobacz Jak serializować i deserializować JSON na platformie .NET.
Sonda bazy danych
Kontrola kondycji może określić zapytanie bazy danych do uruchomienia jako test logiczny, aby wskazać, czy baza danych odpowiada normalnie.
Przykładowa aplikacja używa AspNetCore.Diagnostics.HealthChecksbiblioteki kontroli kondycji dla aplikacji ASP.NET Core do uruchamiania kontroli kondycji bazy danych programu SQL Server.
AspNetCore.Diagnostics.HealthChecks
SELECT 1 Wykonuje zapytanie względem bazy danych, aby potwierdzić, że połączenie z bazą danych jest w dobrej kondycji.
Warning
Podczas sprawdzania połączenia bazy danych z zapytaniem wybierz zapytanie, które szybko zwraca. Podejście do zapytania powoduje przeciążenie bazy danych i obniżenie wydajności. W większości przypadków uruchomienie zapytania testowego nie jest konieczne. Wystarczy nawiązać pomyślne połączenie z bazą danych. Jeśli okaże się, że konieczne jest uruchomienie zapytania, wybierz proste zapytanie SELECT, takie jak SELECT 1.
Dołącz odwołanie do pakietu AspNetCore.HealthChecks.SqlServer.
Podaj prawidłowy ciąg połączenia z bazą danych w pliku appsettings.json aplikacji przykładowej. Aplikacja używa bazy danych programu SQL Server o nazwie HealthCheckSample:
{
"ConnectionStrings": {
"DefaultConnection": "Server=(localdb)\\MSSQLLocalDB;Database=HealthCheckSample;Trusted_Connection=True;MultipleActiveResultSets=true;ConnectRetryCount=0"
},
"Logging": {
"LogLevel": {
"Default": "Information",
"Microsoft": "Warning",
"Microsoft.Hosting.Lifetime": "Information"
},
"Console": {
"IncludeScopes": "true"
}
},
"AllowedHosts": "*"
}
Zarejestruj usługi sprawdzania kondycji w AddHealthChecks w Startup.ConfigureServices. Przykładowa aplikacja wywołuje metodę AddSqlServer z parametrem połączenia bazy danych (DbHealthStartup.cs):
services.AddHealthChecks()
.AddSqlServer(Configuration["ConnectionStrings:DefaultConnection"]);
Punkt końcowy kontroli kondycji jest tworzony przez wywołanie metody MapHealthChecks w pliku Startup.Configure:
app.UseEndpoints(endpoints =>
{
endpoints.MapHealthChecks("/health");
}
Aby uruchomić scenariusz sondy bazy danych przy użyciu przykładowej aplikacji, wykonaj następujące polecenie z folderu projektu w oknie wiersza polecenia:
dotnet run --scenario db
Note
AspNetCore.Diagnostics.HealthChecks nie jest obsługiwany ani wspierany przez firmę Microsoft.
Sonda DbContext w Entity Framework Core
Sprawdzanie DbContext potwierdza, że aplikacja może komunikować się z bazą danych skonfigurowaną dla elementu EF CoreDbContext. Sprawdzanie DbContext jest obsługiwane w aplikacjach, które:
- Użyj platformy Entity Framework (EF) Core.
- Dołącz odwołanie do pakietu
Microsoft.Extensions.Diagnostics.HealthChecks.EntityFrameworkCore.
AddDbContextCheck<TContext> rejestruje kontrolę kondycji dla elementu DbContext. Metoda otrzymuje DbContext jako TContext. Przeciążenie jest dostępne do skonfigurowania stanu niepowodzenia, tagów i niestandardowego zapytania testowego.
Domyślnie:
- Wywołuje
DbContextHealthCheckmetodę EF CoreCanConnectAsync. Możesz dostosować operację uruchamianą podczas sprawdzania kondycji, używając przeciążeń metodyAddDbContextCheck. - Nazwa sprawdzania kondycji to nazwa typu
TContext.
W przykładowej aplikacji AppDbContext jest dostarczana do AddDbContextCheck i zarejestrowana jako usługa w Startup.ConfigureServices (DbContextHealthStartup.cs):
services.AddHealthChecks()
.AddDbContextCheck<AppDbContext>();
services.AddDbContext<AppDbContext>(options =>
{
options.UseSqlServer(
Configuration["ConnectionStrings:DefaultConnection"]);
});
Punkt końcowy kontroli kondycji jest tworzony przez wywołanie metody MapHealthChecks w pliku Startup.Configure:
app.UseEndpoints(endpoints =>
{
endpoints.MapHealthChecks("/health");
}
Aby uruchomić DbContext scenariusz sondowania przy użyciu przykładowej aplikacji, upewnij się, że baza danych określona przez parametry połączenia nie istnieje w wystąpieniu programu SQL Server. Jeśli baza danych istnieje, usuń ją.
Wykonaj następujące polecenie z folderu projektu w powłoce poleceń:
dotnet run --scenario dbcontext
Po uruchomieniu aplikacji sprawdź stan kondycji, wysyłając żądanie do punktu końcowego /health w przeglądarce. Baza danych i AppDbContext nie istnieją, dlatego aplikacja udostępnia następującą odpowiedź:
Unhealthy
Uruchom aplikację przykładową, aby utworzyć bazę danych. Prześlij żądanie do /createdatabase. Aplikacja odpowiada:
Creating the database...
Done!
Navigate to /health to see the health status.
Prześlij żądanie do punktu końcowego /health . Baza danych i kontekst istnieją, więc aplikacja odpowiada:
Healthy
Uruchom przykładową aplikację w celu usunięcia bazy danych. Prześlij żądanie do /deletedatabase. Aplikacja odpowiada:
Deleting the database...
Done!
Navigate to /health to see the health status.
Prześlij żądanie do punktu końcowego /health . Aplikacja zapewnia niezdrową odpowiedź.
Unhealthy
Oddzielne sondy gotowości i żywotności
W niektórych scenariuszach hostingu para kontroli kondycji służy do rozróżniania dwóch stanów aplikacji:
- Gotowość wskazuje, czy aplikacja działa normalnie, ale nie jest gotowa do odbierania żądań.
- Liveness wskazuje, czy aplikacja uległa awarii i musi zostać ponownie uruchomiona.
Rozważmy następujący przykład: Aplikacja musi pobrać duży plik konfiguracji, zanim będzie gotowa do przetwarzania żądań. Nie chcemy, aby aplikacja została ponownie uruchomiona, jeśli początkowe pobieranie nie powiedzie się, ponieważ aplikacja może ponowić próbę pobrania pliku kilka razy. Używamy sondy żywotności procesu do opisania żywotności procesu, nie są uruchamiane żadne inne testy. Chcemy również uniemożliwić wysyłanie żądań do aplikacji przed pomyślnym pobraniem pliku konfiguracji. Używamy sondy gotowości, aby wskazać stan "niegotowości", dopóki pobieranie nie zakończy się sukcesem, a aplikacja będzie gotowa do odbierania żądań.
Przykładowa aplikacja zawiera kontrolę kondycji, aby zgłosić ukończenie długotrwałego zadania uruchamiania w usłudze hostowanej. Właściwość StartupHostedServiceHealthCheck udostępnia atrybut StartupTaskCompleted, który hostowana usługa może ustawić na true po zakończeniu długotrwałego zadania (StartupHostedServiceHealthCheck.cs):
public class StartupHostedServiceHealthCheck : IHealthCheck
{
private volatile bool _startupTaskCompleted = false;
public string Name => "slow_dependency_check";
public bool StartupTaskCompleted
{
get => _startupTaskCompleted;
set => _startupTaskCompleted = value;
}
public Task<HealthCheckResult> CheckHealthAsync(
HealthCheckContext context,
CancellationToken cancellationToken = default(CancellationToken))
{
if (StartupTaskCompleted)
{
return Task.FromResult(
HealthCheckResult.Healthy("The startup task is finished."));
}
return Task.FromResult(
HealthCheckResult.Unhealthy("The startup task is still running."));
}
}
Długotrwałe zadanie w tle jest uruchamiane przez usługę hostowaną (Services/StartupHostedService). Na zakończenie zadania StartupHostedServiceHealthCheck.StartupTaskCompleted jest ustawione na true:
public class StartupHostedService : IHostedService, IDisposable
{
private readonly int _delaySeconds = 15;
private readonly ILogger _logger;
private readonly StartupHostedServiceHealthCheck _startupHostedServiceHealthCheck;
public StartupHostedService(ILogger<StartupHostedService> logger,
StartupHostedServiceHealthCheck startupHostedServiceHealthCheck)
{
_logger = logger;
_startupHostedServiceHealthCheck = startupHostedServiceHealthCheck;
}
public Task StartAsync(CancellationToken cancellationToken)
{
_logger.LogInformation("Startup Background Service is starting.");
// Simulate the effect of a long-running startup task.
Task.Run(async () =>
{
await Task.Delay(_delaySeconds * 1000);
_startupHostedServiceHealthCheck.StartupTaskCompleted = true;
_logger.LogInformation("Startup Background Service has started.");
});
return Task.CompletedTask;
}
public Task StopAsync(CancellationToken cancellationToken)
{
_logger.LogInformation("Startup Background Service is stopping.");
return Task.CompletedTask;
}
public void Dispose()
{
}
}
Kontrola kondycji jest zarejestrowana AddCheck razem Startup.ConfigureServices z hostowaną usługą. Ponieważ hostowana usługa musi ustawić właściwość sprawdzania kondycji, kontrola kondycji jest również zarejestrowana w kontenerze usługi (LivenessProbeStartup.cs):
services.AddHostedService<StartupHostedService>();
services.AddSingleton<StartupHostedServiceHealthCheck>();
services.AddHealthChecks()
.AddCheck<StartupHostedServiceHealthCheck>(
"hosted_service_startup",
failureStatus: HealthStatus.Degraded,
tags: new[] { "ready" });
services.Configure<HealthCheckPublisherOptions>(options =>
{
options.Delay = TimeSpan.FromSeconds(2);
options.Predicate = (check) => check.Tags.Contains("ready");
});
services.AddSingleton<IHealthCheckPublisher, ReadinessPublisher>();
Punkt końcowy sprawdzania kondycji jest tworzony przez wywołanie metody MapHealthChecks w pliku Startup.Configure. W przykładowej aplikacji punkty końcowe sprawdzania kondycji są tworzone pod adresem:
-
/health/readyw celu sprawdzenia gotowości. Test gotowości filtruje testy kondycji do sprawdzania kondycji za pomocą taguready. -
/health/livew celu sprawdzenia żywotności. Sprawdzenie żywotności filtrujeStartupHostedServiceHealthCheckpoprzez zwróceniefalsewHealthCheckOptions.Predicate(aby uzyskać więcej informacji, zobacz Filtrowanie kontroli kondycji)
W poniższym przykładowym kodzie:
- Sprawdzanie gotowości używa wszystkich zarejestrowanych testów z etykietą "ready".
- Element
Predicatewyklucza wszystkie kontrole i zwraca wartość 200-OK.
app.UseEndpoints(endpoints =>
{
endpoints.MapHealthChecks("/health/ready", new HealthCheckOptions()
{
Predicate = (check) => check.Tags.Contains("ready"),
});
endpoints.MapHealthChecks("/health/live", new HealthCheckOptions()
{
Predicate = (_) => false
});
}
Aby uruchomić scenariusz konfiguracji gotowości/dostępności przy użyciu aplikacji przykładowej, wykonaj następujące polecenie z folderu projektu w wierszu poleceń.
dotnet run --scenario liveness
W przeglądarce przejdź /health/ready kilka razy, aż minie 15 sekund. Raporty kontroli stanu Unhealthy przez pierwsze 15 sekund. Po 15 sekundach punkt końcowy zgłasza Healthy, co odzwierciedla ukończenie długotrwałego zadania przez hostowaną usługę.
W tym przykładzie zostanie również utworzony program Health Check Publisher (IHealthCheckPublisher implementacja), który uruchamia pierwszą kontrolę gotowości z dwusekundowym opóźnieniem. Aby uzyskać więcej informacji, zobacz sekcję Health Check Publisher.
Przykład rozwiązania Kubernetes
Korzystanie z oddzielnych testów gotowości i dostępności jest przydatne w środowisku, takim jak Kubernetes. Na platformie Kubernetes aplikacja może być wymagana do wykonywania czasochłonnej pracy podczas uruchamiania przed zaakceptowaniem żądań, takich jak test dostępności bazowej bazy danych. Użycie oddzielnych kontroli umożliwia orkiestratorowi rozróżnienie, czy aplikacja działa, ale nie jest jeszcze gotowa, czy nie można uruchomić aplikacji. Aby uzyskać więcej informacji na temat sond gotowości i kondycji na platformie Kubernetes, zobacz Konfigurowanie sond kondycji i gotowości w dokumentacji platformy Kubernetes.
W poniższym przykładzie pokazano konfigurację sondy gotowości Kubernetes:
spec:
template:
spec:
readinessProbe:
# an http probe
httpGet:
path: /health/ready
port: 80
# length of time to wait for a pod to initialize
# after pod startup, before applying health checking
initialDelaySeconds: 30
timeoutSeconds: 1
ports:
- containerPort: 80
Sonda oparta na metryce z niestandardowym modułem zapisywania odpowiedzi
Przykładowa aplikacja demonstruje kontrolę kondycji pamięci z niestandardowym modułem zapisywania odpowiedzi.
MemoryHealthCheck zgłasza stan obniżonej wydajności, jeśli aplikacja używa więcej niż określony próg pamięci (1 GB w przykładowej aplikacji). Moduł HealthCheckResult zawiera informacje dotyczące Garbage Colletor (GC) dla aplikacji (MemoryHealthCheck.cs):
public class MemoryHealthCheck : IHealthCheck
{
private readonly IOptionsMonitor<MemoryCheckOptions> _options;
public MemoryHealthCheck(IOptionsMonitor<MemoryCheckOptions> options)
{
_options = options;
}
public string Name => "memory_check";
public Task<HealthCheckResult> CheckHealthAsync(
HealthCheckContext context,
CancellationToken cancellationToken = default(CancellationToken))
{
var options = _options.Get(context.Registration.Name);
// Include GC information in the reported diagnostics.
var allocated = GC.GetTotalMemory(forceFullCollection: false);
var data = new Dictionary<string, object>()
{
{ "AllocatedBytes", allocated },
{ "Gen0Collections", GC.CollectionCount(0) },
{ "Gen1Collections", GC.CollectionCount(1) },
{ "Gen2Collections", GC.CollectionCount(2) },
};
var status = (allocated < options.Threshold) ?
HealthStatus.Healthy : context.Registration.FailureStatus;
return Task.FromResult(new HealthCheckResult(
status,
description: "Reports degraded status if allocated bytes " +
$">= {options.Threshold} bytes.",
exception: null,
data: data));
}
}
Zarejestruj usługi sprawdzania kondycji w AddHealthChecks w Startup.ConfigureServices. Zamiast włączać kontrolę kondycji przez przekazanie jej do AddCheck, MemoryHealthCheck jest rejestrowany jako usługa. Wszystkie IHealthCheck zarejestrowane usługi są dostępne dla usług kontroli kondycji i oprogramowania pośredniczącego. Zalecamy zarejestrowanie usług kontroli kondycji jako usług Singleton.
W CustomWriterStartup.cs przykładowej aplikacji:
services.AddHealthChecks()
.AddMemoryHealthCheck("memory");
Punkt końcowy sprawdzania kondycji jest tworzony przez wywołanie metody MapHealthChecks w pliku Startup.Configure. Delegat WriteResponse jest dostarczany do ResponseWriter właściwości w celu wyprowadzenia niestandardowej odpowiedzi JSON po wykonaniu sprawdzania kondycji:
app.UseEndpoints(endpoints =>
{
endpoints.MapHealthChecks("/health", new HealthCheckOptions()
{
ResponseWriter = WriteResponse
});
}
Delegat WriteResponse formatuje CompositeHealthCheckResult na obiekt JSON i zwraca wynik JSON dla odpowiedzi na kontrolę zdrowia. Aby uzyskać więcej informacji, zobacz sekcję Dostosowywanie danych wyjściowych .
Aby uruchomić sondę opartą na metrykach z niestandardowymi danymi wyjściowymi modułu zapisywania odpowiedzi przy użyciu przykładowej aplikacji, wykonaj następujące polecenie z folderu projektu w powłoce poleceń:
dotnet run --scenario writer
Note
AspNetCore.Diagnostics.HealthChecks obejmuje scenariusze sprawdzania kondycji oparte na metrykach, w tym przechowywanie dysku i testy żywotności maksymalnej wartości.
AspNetCore.Diagnostics.HealthChecks nie jest obsługiwany ani wspierany przez firmę Microsoft.
Filtruj według portu
Wywołaj RequireHost na MapHealthChecks ze wzorcem URL, który określa port, aby ograniczyć żądania kontroli kondycji do wskazanego portu. Takie podejście jest zwykle używane w środowisku kontenera do uwidaczniania portu na potrzeby usług monitorowania.
Przykładowa aplikacja konfiguruje port przy użyciu dostawcy konfiguracji zmiennych środowiskowych. Port jest ustawiany w launchSettings.json pliku i przekazywany do dostawcy konfiguracji za pośrednictwem zmiennej środowiskowej. Należy również skonfigurować serwer do nasłuchiwania żądań na porcie zarządzania.
Aby użyć przykładowej aplikacji do zademonstrowania konfiguracji portu zarządzania, utwórz launchSettings.json plik w folderze Properties .
Następujący Properties/launchSettings.json plik w przykładowej aplikacji nie jest uwzględniony w plikach projektu przykładowej aplikacji i należy go utworzyć ręcznie:
{
"profiles": {
"SampleApp": {
"commandName": "Project",
"commandLineArgs": "",
"launchBrowser": true,
"environmentVariables": {
"ASPNETCORE_ENVIRONMENT": "Development",
"ASPNETCORE_URLS": "http://localhost:5000/;http://localhost:5001/",
"ASPNETCORE_MANAGEMENTPORT": "5001"
},
"applicationUrl": "http://localhost:5000/"
}
}
}
Zarejestruj usługi sprawdzania kondycji w AddHealthChecks w Startup.ConfigureServices. Utwórz punkt końcowy kontroli kondycji, wywołując MapHealthChecks w Startup.Configure.
W przykładowej aplikacji wywołanie RequireHost na punkcie końcowym w Startup.Configure określa port zarządzania na podstawie konfiguracji:
endpoints.MapHealthChecks("/health")
.RequireHost($"*:{Configuration["ManagementPort"]}");
Punkty końcowe są tworzone w przykładowej aplikacji w programie Startup.Configure. W poniższym przykładowym kodzie:
- Sprawdzanie gotowości używa wszystkich zarejestrowanych testów z etykietą "ready".
- Element
Predicatewyklucza wszystkie kontrole i zwraca wartość 200-OK.
app.UseEndpoints(endpoints =>
{
endpoints.MapHealthChecks("/health/ready", new HealthCheckOptions()
{
Predicate = (check) => check.Tags.Contains("ready"),
});
endpoints.MapHealthChecks("/health/live", new HealthCheckOptions()
{
Predicate = (_) => false
});
}
Note
Możesz uniknąć tworzenia launchSettings.json pliku w przykładowej aplikacji, ustawiając jawnie port zarządzania w kodzie. W Program.cs, gdzie utworzono HostBuilder, dodaj wywołanie do ListenAnyIP i podaj punkt końcowy portu zarządzania aplikacją. W Configure pliku ManagementPortStartup.cs określ port zarządzania za pomocą RequireHost polecenia :
Program.cs:
return new HostBuilder()
.ConfigureWebHostDefaults(webBuilder =>
{
webBuilder.UseKestrel()
.ConfigureKestrel(serverOptions =>
{
serverOptions.ListenAnyIP(5001);
})
.UseStartup(startupType);
})
.Build();
ManagementPortStartup.cs:
app.UseEndpoints(endpoints =>
{
endpoints.MapHealthChecks("/health").RequireHost("*:5001");
});
Aby uruchomić scenariusz konfiguracji portu zarządzania przy użyciu przykładowej aplikacji, wykonaj następujące polecenie z folderu projektu w powłoce poleceń:
dotnet run --scenario port
Rozpowszechnianie biblioteki kontroli kondycji
Aby rozpowszechnić kontrolę stanu zdrowia jako bibliotekę:
Napisz kontrolę kondycji, która implementuje IHealthCheck interfejs jako klasę autonomiczną. Klasa może polegać na iniekcji zależności (DI), aktywacji typu i nazwanych opcjach uzyskiwania dostępu do danych konfiguracji.
W logice kontroli stanu komponentu
CheckHealthAsync:-
data1idata2są używane w metodzie do uruchamiania logiki sprawdzania kondycji sondy. -
AccessViolationExceptionjest obsługiwane.
W przypadku AccessViolationExceptionFailureStatus jest zwracany z parametrem HealthCheckResult, aby umożliwić użytkownikom skonfigurowanie stanu awarii kontroli kondycji.
using System; using System.Threading; using System.Threading.Tasks; using Microsoft.Extensions.Diagnostics.HealthChecks; namespace SampleApp { public class ExampleHealthCheck : IHealthCheck { private readonly string _data1; private readonly int? _data2; public ExampleHealthCheck(string data1, int? data2) { _data1 = data1 ?? throw new ArgumentNullException(nameof(data1)); _data2 = data2 ?? throw new ArgumentNullException(nameof(data2)); } public async Task<HealthCheckResult> CheckHealthAsync( HealthCheckContext context, CancellationToken cancellationToken) { try { return HealthCheckResult.Healthy(); } catch (AccessViolationException ex) { return new HealthCheckResult( context.Registration.FailureStatus, description: "An access violation occurred during the check.", exception: ex, data: null); } } } }-
Napisz metodę rozszerzenia z parametrami, które aplikacja, która korzysta, wywołuje w swojej metodzie
Startup.Configure. W poniższym przykładzie przyjęto założenie następującego podpisu metody kontroli kondycji:ExampleHealthCheck(string, string, int )Powyższy podpis wskazuje, że
ExampleHealthCheckwymaga dodatkowych danych do przetwarzania logiki sondy sprawdzania kondycji. Dane są przekazywane delegatowi, który jest używany do utworzenia instancji sprawdzenia kondycji, gdy sprawdzenie kondycji jest zarejestrowane za pomocą metody rozszerzenia. W poniższym przykładzie wywołujący określa wartość opcjonalną:- nazwa sprawdzenia kondycji (
name). Jeślinull,example_health_checkjest używany. - punkt danych tekstowych dla sprawdzenia kondycji (
data1). - Punkt danych całkowitych dla kontroli stanu (
data2). Jeślinull,1jest używany. - stan błędu (HealthStatus). Wartość domyślna to
null. Jeślinull, zgłaszany jest HealthStatus.Unhealthy jako status błędu. - tagi (
IEnumerable<string>).
using System.Collections.Generic; using Microsoft.Extensions.Diagnostics.HealthChecks; public static class ExampleHealthCheckBuilderExtensions { const string DefaultName = "example_health_check"; public static IHealthChecksBuilder AddExampleHealthCheck( this IHealthChecksBuilder builder, string name = default, string data1, int data2 = 1, HealthStatus? failureStatus = default, IEnumerable<string> tags = default) { return builder.Add(new HealthCheckRegistration( name ?? DefaultName, sp => new ExampleHealthCheck(data1, data2), failureStatus, tags)); } }- nazwa sprawdzenia kondycji (
Wydawca kontroli kondycji
Po dodaniu elementu IHealthCheckPublisher do kontenera usługi system monitorowania kondycji okresowo wykonuje sprawdzanie kondycji i wywołuje PublishAsync z wynikiem. Jest to przydatne w scenariuszu systemu monitorowania stanu opartym na podejściu bazującym na przesyłaniu, który oczekuje, że każdy proces będzie okresowo wywoływać system monitorowania w celu oceny stanu.
Interfejs IHealthCheckPublisher ma jedną metodę:
Task PublishAsync(HealthReport report, CancellationToken cancellationToken);
HealthCheckPublisherOptions pozwala na ustawienie:
- Delay: początkowe opóźnienie zastosowane po uruchomieniu aplikacji przed wykonaniem IHealthCheckPublisher wystąpień. Opóźnienie jest stosowane raz podczas uruchamiania i nie ma zastosowania do kolejnych iteracji. Wartość domyślna to pięć sekund.
- Period: okres IHealthCheckPublisher wykonywania. Wartość domyślna to 30 sekund.
-
Predicate: Jeśli Predicate jest
null(wartość domyślna), usługa wydawcy testów kondycji uruchamia wszystkie zarejestrowane testy kondycji. Aby uruchomić podzbiór kontroli kondycji, podaj funkcję, która filtruje zestaw testów. Predykat jest obliczany w każdym okresie. - Timeout: limit czasu na wykonywanie kontroli kondycji dla wszystkich IHealthCheckPublisher wystąpień. Użyj polecenia InfiniteTimeSpan , aby wykonać bez limitu czasu. Wartość domyślna to 30 sekund.
W przykładowej aplikacji ReadinessPublisher jest implementacją IHealthCheckPublisher . Stan kontroli kondycji jest rejestrowany dla każdego sprawdzenia na poziomie dziennika:
- Informacje (LogInformation), jeśli stan kontroli kondycji to Healthy.
- Błąd (LogError), jeśli stan to Degraded lub Unhealthy.
public class ReadinessPublisher : IHealthCheckPublisher
{
private readonly ILogger _logger;
public ReadinessPublisher(ILogger<ReadinessPublisher> logger)
{
_logger = logger;
}
// The following example is for demonstration purposes only. Health Checks
// Middleware already logs health checks results. A real-world readiness
// check in a production app might perform a set of more expensive or
// time-consuming checks to determine if other resources are responding
// properly.
public Task PublishAsync(HealthReport report,
CancellationToken cancellationToken)
{
if (report.Status == HealthStatus.Healthy)
{
_logger.LogInformation("{Timestamp} Readiness Probe Status: {Result}",
DateTime.UtcNow, report.Status);
}
else
{
_logger.LogError("{Timestamp} Readiness Probe Status: {Result}",
DateTime.UtcNow, report.Status);
}
cancellationToken.ThrowIfCancellationRequested();
return Task.CompletedTask;
}
}
W przykładzie LivenessProbeStartup przykładowej aplikacji StartupHostedService test gotowości ma dwie sekundy opóźnienia przed uruchomieniem i wykonuje sprawdzanie co 30 sekund. Aby aktywować implementacjęIHealthCheckPublisher, przykład rejestruje ReadinessPublisher jako usługę pojedynczą w kontenerze DI:
services.AddHostedService<StartupHostedService>();
services.AddSingleton<StartupHostedServiceHealthCheck>();
services.AddHealthChecks()
.AddCheck<StartupHostedServiceHealthCheck>(
"hosted_service_startup",
failureStatus: HealthStatus.Degraded,
tags: new[] { "ready" });
services.Configure<HealthCheckPublisherOptions>(options =>
{
options.Delay = TimeSpan.FromSeconds(2);
options.Predicate = (check) => check.Tags.Contains("ready");
});
services.AddSingleton<IHealthCheckPublisher, ReadinessPublisher>();
Note
AspNetCore.Diagnostics.HealthChecks zawiera wydawców dla kilku systemów, w tym Application Insights.
AspNetCore.Diagnostics.HealthChecks nie jest obsługiwany ani wspierany przez firmę Microsoft.
Ogranicz kontrole zdrowotne za pomocą MapWhen
Użyj polecenia MapWhen , aby warunkowo rozgałęzić potok żądania dla punktów końcowych sprawdzania kondycji.
W poniższym przykładzie MapWhen rozgałęzia potok żądań, aby aktywować oprogramowanie pośredniczące do sprawdzania kondycji, jeśli zostanie odebrane żądanie GET dla punktu końcowego api/HealthCheck.
app.MapWhen(
context => context.Request.Method == HttpMethod.Get.Method &&
context.Request.Path.StartsWith("/api/HealthCheck"),
builder => builder.UseHealthChecks());
app.UseEndpoints(endpoints =>
{
endpoints.MapRazorPages();
});
Aby uzyskać więcej informacji, zobacz Oprogramowanie pośredniczące ASP.NET Core.
ASP.NET Core oferuje middleware sprawdzania kondycji oraz biblioteki do raportowania kondycji składników infrastruktury aplikacji.
Testy kondycji są udostępniane przez aplikację jako punkty końcowe HTTP. Punkty końcowe kontroli kondycji można skonfigurować dla różnych scenariuszy monitorowania w czasie rzeczywistym:
- Sondy kondycji mogą być używane przez koordynatorów kontenerów i moduły równoważenia obciążenia w celu sprawdzenia stanu aplikacji. Na przykład orkiestrator kontenerów może reagować na niepowodzenie sprawdzania kondycji, zatrzymując wdrożenie stopniowe lub ponownie uruchamiając kontener. Moduł równoważenia obciążenia może reagować na problemy z aplikacją przez przekierowanie ruchu z wadliwego wystąpienia do wystąpienia działającego poprawnie.
- Użycie pamięci, dysku i innych zasobów serwera fizycznego można monitorować pod kątem stanu dobrej kondycji.
- Testy kondycji mogą testować zależności aplikacji, takie jak bazy danych i zewnętrzne punkty końcowe usługi, w celu potwierdzenia dostępności i normalnego działania.
Testy kondycji są zwykle używane z zewnętrzną usługą monitorowania lub koordynatorem kontenerów w celu sprawdzenia stanu aplikacji. Przed dodaniem kontroli kondycji do aplikacji zdecyduj, który system monitorowania ma być używany. System monitorowania określa, jakie typy testów zdrowia należy utworzyć i jak skonfigurować ich punkty końcowe.
Podstawowa sonda kondycji
W przypadku wielu aplikacji podstawowa konfiguracja sondy kondycji, która zgłasza dostępność aplikacji do przetwarzania żądań (statusu działania) jest wystarczająca do ustalenia stanu aplikacji.
Podstawowa konfiguracja rejestruje usługi monitorowania stanu i wywołuje middleware do kontroli stanu zdrowia, aby odpowiedzieć na adresie URL odpowiedzią zdrowotną. Domyślnie żadne konkretne kontrole kondycji nie są rejestrowane w celu przetestowania żadnej konkretnej zależności lub podsystemu. Aplikacja jest uważana za w dobrej kondycji, jeśli może odpowiadać pod adresem URL punktu końcowego zdrowia. Domyślny zapisujący odpowiedzi zapisuje HealthStatus jako odpowiedź w postaci zwykłego tekstu do klienta. Parametr HealthStatus jest HealthStatus.Healthy, HealthStatus.Degraded lub HealthStatus.Unhealthy.
Zarejestruj usługi sprawdzania kondycji w AddHealthChecks w Program.cs. Utwórz punkt końcowy kontroli kondycji, wywołując polecenie MapHealthChecks.
Poniższy przykład tworzy punkt końcowy kontroli kondycji: /healthz.
var builder = WebApplication.CreateBuilder(args);
builder.Services.AddHealthChecks();
var app = builder.Build();
app.MapHealthChecks("/healthz");
app.Run();
Doker HEALTHCHECK
Platforma Docker oferuje wbudowaną HEALTHCHECK dyrektywę, która może służyć do sprawdzania stanu aplikacji korzystającej z podstawowej konfiguracji kontroli kondycji:
HEALTHCHECK CMD curl --fail http://localhost:5000/healthz || exit
W poprzednim przykładzie użyto curl do wysłania żądania HTTP do punktu końcowego sprawdzania kondycji na /healthz.
curl nie jest uwzględniana w obrazach kontenerów systemu Linux platformy .NET, ale można ją dodać, instalując wymagany pakiet w pliku Dockerfile. Kontenery korzystające z obrazów opartych na systemie Alpine Linux mogą używać dołączonego wget zamiast curl.
Tworzenie kontroli kondycji
Testy kondycji są tworzone przez zaimplementowanie interfejsu IHealthCheck . Metoda CheckHealthAsync zwraca wartość HealthCheckResult , która wskazuje kondycję jako Healthy, Degradedlub Unhealthy. Wynik jest zapisywany jako odpowiedź w postaci zwykłego tekstu z konfigurowalnym kodem stanu. Konfiguracja została opisana w sekcji Opcje sprawdzania kondycji.
HealthCheckResult może również zwracać opcjonalne pary klucz-wartość.
W poniższym przykładzie pokazano układ kontroli kondycji:
public class SampleHealthCheck : IHealthCheck
{
public Task<HealthCheckResult> CheckHealthAsync(
HealthCheckContext context, CancellationToken cancellationToken = default)
{
var isHealthy = true;
// ...
if (isHealthy)
{
return Task.FromResult(
HealthCheckResult.Healthy("A healthy result."));
}
return Task.FromResult(
new HealthCheckResult(
context.Registration.FailureStatus, "An unhealthy result."));
}
}
Logika kontroli kondycji jest umieszczana w metodzie CheckHealthAsync . W poprzednim przykładzie ustawiono tymczasową zmienną isHealthy, na wartość true. Jeśli wartość parametru isHealthy jest ustawiona na false, zwracany jest stan HealthCheckRegistration.FailureStatus.
Jeśli CheckHealthAsync podczas sprawdzania wystąpi wyjątek, zostanie zwrócony nowy HealthReportEntry z ustawioną HealthReportEntry.Status na FailureStatus. Ten stan jest definiowany przez AddCheck (zobacz sekcję Rejestrowanie usług sprawdzania kondycji) i zawiera wewnętrzny wyjątek, który spowodował niepowodzenie sprawdzania. Parametr Description jest ustawiony na komunikat wyjątku.
Rejestrowanie usług kontroli kondycji
Aby zarejestrować usługę sprawdzania kondycji, wywołaj AddCheck w Program.cs:
builder.Services.AddHealthChecks()
.AddCheck<SampleHealthCheck>("Sample");
Przeciążenie AddCheck pokazane w poniższym przykładzie ustawia stan błędu (HealthStatus) w celu raportowania, gdy kontrola kondycji zgłasza błąd. Jeśli stan niepowodzenia jest ustawiony na null (wartość domyślna), HealthStatus.Unhealthy jest zgłaszany. To przeciążenie jest przydatnym scenariuszem dla autorów bibliotek, gdzie status awarii wskazywany przez bibliotekę jest wymuszany przez aplikację, gdy wystąpi błąd w sprawdzaniu kondycji, o ile implementacja sprawdzania kondycji respektuje to ustawienie.
Tagi mogą służyć do filtrowania kontroli kondycji. Tagi są opisane w sekcji Filtrowanie kontroli kondycji systemu.
builder.Services.AddHealthChecks()
.AddCheck<SampleHealthCheck>(
"Sample",
failureStatus: HealthStatus.Degraded,
tags: new[] { "sample" });
AddCheck może również wykonać funkcję lambda. W poniższym przykładzie sprawdzanie kondycji zawsze zwraca zdrowy wynik.
builder.Services.AddHealthChecks()
.AddCheck("Sample", () => HealthCheckResult.Healthy("A healthy result."));
Wywołaj metodę AddTypeActivatedCheck , aby przekazać argumenty do implementacji kontroli kondycji. W poniższym przykładzie kontrola kondycji aktywowana typem akceptuje liczbę całkowitą i ciąg w konstruktorze:
public class SampleHealthCheckWithArgs : IHealthCheck
{
private readonly int _arg1;
private readonly string _arg2;
public SampleHealthCheckWithArgs(int arg1, string arg2)
=> (_arg1, _arg2) = (arg1, arg2);
public Task<HealthCheckResult> CheckHealthAsync(
HealthCheckContext context, CancellationToken cancellationToken = default)
{
// ...
return Task.FromResult(HealthCheckResult.Healthy("A healthy result."));
}
}
Aby zarejestrować poprzednią kontrolę kondycji, wywołaj metodę AddTypeActivatedCheck za pomocą liczby całkowitej i ciągu przekazanego jako argumenty:
builder.Services.AddHealthChecks()
.AddTypeActivatedCheck<SampleHealthCheckWithArgs>(
"Sample",
failureStatus: HealthStatus.Degraded,
tags: new[] { "sample" },
args: new object[] { 1, "Arg" });
Zastosuj trasowanie kontroli zdrowia
W Program.cs wywołaj MapHealthChecks na budowniczym punktu końcowego z adresem URL punktu końcowego lub ścieżką względną:
app.MapHealthChecks("/healthz");
Wymagaj hosta
Wywołaj RequireHost , aby określić co najmniej jednego dozwolonego hosta dla endpointu kontroli kondycji. Hosty powinny być unicode, a nie punycode i mogą zawierać port. Jeśli kolekcja nie zostanie dostarczona, zostanie zaakceptowany dowolny host.
app.MapHealthChecks("/healthz")
.RequireHost("www.contoso.com:5001");
Aby ograniczyć punkt końcowy kontroli kondycji do odpowiadania tylko na określonym porcie, określ port w wywołaniu metody RequireHost. Takie podejście jest zwykle używane w środowisku kontenera do uwidaczniania portu na potrzeby usług monitorowania:
app.MapHealthChecks("/healthz")
.RequireHost("*:5001");
Warning
Interfejs API opierający się na nagłówku Host, tak jak HttpRequest.Host oraz RequireHost, podlega potencjalnemu fałszowaniu przez klientów.
Aby zapobiec fałszowaniu hostów i portów, użyj jednej z następujących metod:
- Użyj HttpContext.Connection (ConnectionInfo.LocalPort), gdzie sprawdzane są porty.
- Zastosowanie filtrowania hostów.
Aby zapobiec fałszowaniu portu przez nieautoryzowanych klientów, wywołaj metodę RequireAuthorization:
app.MapHealthChecks("/healthz")
.RequireHost("*:5001")
.RequireAuthorization();
Aby uzyskać więcej informacji, zobacz Dopasowywanie hostów w trasach za pomocą elementu RequireHost.
Wymagaj autoryzacji
Wywołaj polecenie RequireAuthorization , aby uruchomić oprogramowanie pośredniczące autoryzacji w punkcie końcowym żądania sprawdzania kondycji. Przeciążenie RequireAuthorization akceptuje co najmniej jedną zasady autoryzacji. Jeśli nie podano zasad, są używane domyślne zasady autoryzacji:
app.MapHealthChecks("/healthz")
.RequireAuthorization();
Włącz żądania Cross-Origin (CORS)
Mimo że ręczne uruchamianie kontroli kondycji z przeglądarki nie jest typowym scenariuszem, oprogramowanie pośredniczące CORS można włączyć poprzez wywołanie RequireCors na punktach końcowych kontroli kondycji. Przeciążenie RequireCors akceptuje delegata konstruktora zasad CORS (CorsPolicyBuilder) lub nazwę zasad. Aby uzyskać więcej informacji, zobacz Włączanie żądań między źródłami (CORS) w ASP.NET Core.
Opcje kontroli kondycji
HealthCheckOptions umożliwia dostosowanie zachowania kontroli kondycji:
- Kontrole kondycji filtrów
- Dostosowywanie kodu stanu HTTP
- Blokowanie nagłówków pamięci podręcznej
- Dostosowywanie danych wyjściowych
Filtrowanie sprawdzania kondycji
Domyślnie oprogramowanie pośredniczące sprawdzania kondycji uruchamia wszystkie zarejestrowane kontrole kondycji. Aby uruchomić podzbiór testów kondycji, podaj funkcję, która zwraca wartość logiczną jako argument opcji Predicate.
Poniższy przykład filtruje kontrole zdrowotne, tak aby uruchamiane były tylko te oznaczone tagiem sample.
app.MapHealthChecks("/healthz", new HealthCheckOptions
{
Predicate = healthCheck => healthCheck.Tags.Contains("sample")
});
Dostosowywanie kodu stanu HTTP
Użyj ResultStatusCodes do dostosowywania mapowania stanu kondycji na kody stanu HTTP. Następujące StatusCodes przypisania są wartościami domyślnymi używanymi przez middleware. Zmień wartości kodu stanu, aby spełnić wymagania:
app.MapHealthChecks("/healthz", new HealthCheckOptions
{
ResultStatusCodes =
{
[HealthStatus.Healthy] = StatusCodes.Status200OK,
[HealthStatus.Degraded] = StatusCodes.Status200OK,
[HealthStatus.Unhealthy] = StatusCodes.Status503ServiceUnavailable
}
});
Tłumienie nagłówków pamięci podręcznej
AllowCachingResponses kontroluje, czy middleware do sprawdzania kondycji dodaje nagłówki HTTP do odpowiedzi z sondy, aby zapobiec buforowaniu odpowiedzi. Jeśli wartość to false (wartość domyślna), oprogramowanie pośredniczące ustawia lub zastępuje nagłówki Cache-Control, Expires i Pragma, aby zapobiec buforowaniu odpowiedzi. Jeśli wartość to true, oprogramowanie pośredniczące nie modyfikuje nagłówków pamięci podręcznej odpowiedzi:
app.MapHealthChecks("/healthz", new HealthCheckOptions
{
AllowCachingResponses = true
});
Dostosowywanie danych wyjściowych
Aby dostosować dane wyjściowe raportu kontroli kondycji, ustaw HealthCheckOptions.ResponseWriter właściwość na delegata, który zapisuje odpowiedź:
app.MapHealthChecks("/healthz", new HealthCheckOptions
{
ResponseWriter = WriteResponse
});
Domyślny delegat zapisuje minimalną odpowiedź w postaci czystego tekstu z wartością ciągu HealthReport.Status. Poniższy delegat niestandardowy zwraca niestandardową odpowiedź JSON przy użyciu polecenia System.Text.Json:
private static Task WriteResponse(HttpContext context, HealthReport healthReport)
{
context.Response.ContentType = "application/json; charset=utf-8";
var options = new JsonWriterOptions { Indented = true };
using var memoryStream = new MemoryStream();
using (var jsonWriter = new Utf8JsonWriter(memoryStream, options))
{
jsonWriter.WriteStartObject();
jsonWriter.WriteString("status", healthReport.Status.ToString());
jsonWriter.WriteStartObject("results");
foreach (var healthReportEntry in healthReport.Entries)
{
jsonWriter.WriteStartObject(healthReportEntry.Key);
jsonWriter.WriteString("status",
healthReportEntry.Value.Status.ToString());
jsonWriter.WriteString("description",
healthReportEntry.Value.Description);
jsonWriter.WriteStartObject("data");
foreach (var item in healthReportEntry.Value.Data)
{
jsonWriter.WritePropertyName(item.Key);
JsonSerializer.Serialize(jsonWriter, item.Value,
item.Value?.GetType() ?? typeof(object));
}
jsonWriter.WriteEndObject();
jsonWriter.WriteEndObject();
}
jsonWriter.WriteEndObject();
jsonWriter.WriteEndObject();
}
return context.Response.WriteAsync(
Encoding.UTF8.GetString(memoryStream.ToArray()));
}
Interfejs API sprawdzania kondycji nie zapewnia wbudowanej obsługi złożonych formatów zwracanych JSON, ponieważ format jest specyficzny dla wybranego systemu monitorowania. Dostosuj odpowiedź w poprzednich przykładach zgodnie z potrzebami. Aby uzyskać więcej informacji na temat serializacji JSON za pomocą System.Text.Json, zobacz Jak serializować i deserializować JSON na platformie .NET.
Sonda bazy danych
Kontrola kondycji może określić zapytanie bazy danych do uruchomienia jako test logiczny, aby wskazać, czy baza danych odpowiada normalnie.
AspNetCore.Diagnostics.HealthChecks, biblioteka sprawdzania kondycji dla aplikacji ASP.NET Core zawiera kontrolę kondycji uruchamianą względem bazy danych programu SQL Server.
AspNetCore.Diagnostics.HealthChecks
SELECT 1 Wykonuje zapytanie względem bazy danych, aby potwierdzić, że połączenie z bazą danych jest w dobrej kondycji.
Warning
Podczas sprawdzania połączenia bazy danych z zapytaniem wybierz zapytanie, które szybko zwraca. Podejście do zapytania powoduje przeciążenie bazy danych i obniżenie wydajności. W większości przypadków uruchomienie zapytania testowego nie jest konieczne. Wystarczy nawiązać pomyślne połączenie z bazą danych. Jeśli okaże się, że konieczne jest uruchomienie zapytania, wybierz proste zapytanie SELECT, takie jak SELECT 1.
Aby użyć tej kontroli kondycji programu SQL Server, dołącz odwołanie do AspNetCore.HealthChecks.SqlServer pakietu NuGet. Poniższy przykład rejestruje kontrolę kondycji programu SQL Server:
builder.Services.AddHealthChecks()
.AddSqlServer(
builder.Configuration.GetConnectionString("DefaultConnection"));
Note
AspNetCore.Diagnostics.HealthChecks nie jest obsługiwany ani wspierany przez firmę Microsoft.
Sonda DbContext w Entity Framework Core
Sprawdzanie DbContext potwierdza, że aplikacja może komunikować się z bazą danych skonfigurowaną dla elementu EF CoreDbContext. Sprawdzanie DbContext jest obsługiwane w aplikacjach, które:
- Użyj platformy Entity Framework (EF) Core.
- Dołącz odniesienie do pakietu NuGet
Microsoft.Extensions.Diagnostics.HealthChecks.EntityFrameworkCore.
AddDbContextCheck rejestruje kontrolę kondycji dla elementu DbContext. Element DbContext jest dostarczany do metody jako TContext. Przeciążenie jest dostępne do skonfigurowania stanu niepowodzenia, tagów i niestandardowego zapytania testowego.
Domyślnie:
- Wywołuje
DbContextHealthCheckmetodę EF CoreCanConnectAsync. Możesz dostosować operację uruchamianą podczas sprawdzania kondycji, używając przeciążeń metodyAddDbContextCheck. - Nazwa sprawdzania kondycji to nazwa typu
TContext.
Poniższy przykład rejestruje element DbContext i skojarzony element DbContextHealthCheck:
builder.Services.AddDbContext<SampleDbContext>(options =>
options.UseSqlServer(
builder.Configuration.GetConnectionString("DefaultConnection")));
builder.Services.AddHealthChecks()
.AddDbContextCheck<SampleDbContext>();
Oddzielne sondy gotowości i żywotności
W niektórych scenariuszach hostingu para kontroli kondycji służy do rozróżniania dwóch stanów aplikacji:
- Gotowość wskazuje, czy aplikacja działa normalnie, ale nie jest gotowa do odbierania żądań.
- Liveness wskazuje, czy aplikacja uległa awarii i musi zostać ponownie uruchomiona.
Rozważmy następujący przykład: Aplikacja musi pobrać duży plik konfiguracji, zanim będzie gotowa do przetwarzania żądań. Nie chcemy, aby aplikacja została ponownie uruchomiona, jeśli początkowe pobieranie nie powiedzie się, ponieważ aplikacja może ponowić próbę pobrania pliku kilka razy. Używamy sondy żywotności procesu do opisania żywotności procesu, nie są uruchamiane żadne inne testy. Chcemy również uniemożliwić wysyłanie żądań do aplikacji przed pomyślnym pobraniem pliku konfiguracji. Używamy sondy gotowości, aby wskazać stan "niegotowości", dopóki pobieranie nie zakończy się sukcesem, a aplikacja będzie gotowa do odbierania żądań.
Następujące zadanie w tle symuluje proces uruchamiania, który trwa około 15 sekund. Po zakończeniu zadania zadanie ustawia StartupHealthCheck.StartupCompleted właściwość na true:
public class StartupBackgroundService : BackgroundService
{
private readonly StartupHealthCheck _healthCheck;
public StartupBackgroundService(StartupHealthCheck healthCheck)
=> _healthCheck = healthCheck;
protected override async Task ExecuteAsync(CancellationToken stoppingToken)
{
// Simulate the effect of a long-running task.
await Task.Delay(TimeSpan.FromSeconds(15), stoppingToken);
_healthCheck.StartupCompleted = true;
}
}
StartupHealthCheck informuje o ukończeniu długotrwałego zadania uruchamiania i ujawnia StartupCompleted właściwość ustawioną przez usługę w tle.
public class StartupHealthCheck : IHealthCheck
{
private volatile bool _isReady;
public bool StartupCompleted
{
get => _isReady;
set => _isReady = value;
}
public Task<HealthCheckResult> CheckHealthAsync(
HealthCheckContext context, CancellationToken cancellationToken = default)
{
if (StartupCompleted)
{
return Task.FromResult(HealthCheckResult.Healthy("The startup task has completed."));
}
return Task.FromResult(HealthCheckResult.Unhealthy("That startup task is still running."));
}
}
Kontrola kondycji jest zarejestrowana AddCheck razem Program.cs z hostowaną usługą. Ponieważ hostowana usługa musi ustawić właściwość w sprawdzaniu kondycji, sprawdzanie kondycji jest również zarejestrowane w kontenerze usługi jako singleton.
builder.Services.AddHostedService<StartupBackgroundService>();
builder.Services.AddSingleton<StartupHealthCheck>();
builder.Services.AddHealthChecks()
.AddCheck<StartupHealthCheck>(
"Startup",
tags: new[] { "ready" });
Aby utworzyć dwa różne punkty końcowe kontroli kondycji, wywołaj MapHealthChecks dwa razy.
app.MapHealthChecks("/healthz/ready", new HealthCheckOptions
{
Predicate = healthCheck => healthCheck.Tags.Contains("ready")
});
app.MapHealthChecks("/healthz/live", new HealthCheckOptions
{
Predicate = _ => false
});
W poprzednim przykładzie są tworzone następujące punkty końcowe sprawdzania kondycji:
-
/healthz/readyw celu sprawdzenia gotowości. Sprawdzanie gotowości ogranicza kontrole kondycji do tych oznaczonych tagiemready. -
/healthz/livew celu sprawdzenia żywotności. Sprawdzanie żywotności filtruje wszystkie kontrole kondycji, zwracającfalsew delegacie HealthCheckOptions.Predicate. Aby uzyskać więcej informacji na temat filtrowania kontroli kondycji, zobacz Filtrowanie kontroli kondycji w tym artykule.
Zanim zadanie uruchamiania zostanie ukończone, punkt końcowy /healthz/ready zgłasza stan Unhealthy. Po zakończeniu zadania uruchamiania ten punkt końcowy zgłasza stan Healthy. Punkt końcowy /healthz/live wyklucza wszystkie sprawdzania i raportuje stan Healthy dla wszystkich wywołań.
Przykład rozwiązania Kubernetes
Korzystanie z oddzielnych testów gotowości i dostępności jest przydatne w środowisku, takim jak Kubernetes. Na platformie Kubernetes aplikacja może być wymagana do wykonywania czasochłonnej pracy podczas uruchamiania przed zaakceptowaniem żądań, takich jak test dostępności bazowej bazy danych. Użycie oddzielnych kontroli umożliwia orkiestratorowi rozróżnienie, czy aplikacja działa, ale nie jest jeszcze gotowa, czy nie można uruchomić aplikacji. Aby uzyskać więcej informacji na temat sond gotowości i kondycji na platformie Kubernetes, zobacz Konfigurowanie sond kondycji i gotowości w dokumentacji platformy Kubernetes.
W poniższym przykładzie pokazano konfigurację sondy gotowości Kubernetes:
spec:
template:
spec:
readinessProbe:
# an http probe
httpGet:
path: /healthz/ready
port: 80
# length of time to wait for a pod to initialize
# after pod startup, before applying health checking
initialDelaySeconds: 30
timeoutSeconds: 1
ports:
- containerPort: 80
Rozpowszechnianie biblioteki kontroli kondycji
Aby rozpowszechnić kontrolę stanu zdrowia jako bibliotekę:
Napisz kontrolę kondycji, która implementuje IHealthCheck interfejs jako klasę autonomiczną. Klasa może polegać na iniekcji zależności (DI), aktywacji typu i nazwanych opcjach uzyskiwania dostępu do danych konfiguracji.
Napisz metodę rozszerzenia z parametrami, które aplikacja, która korzysta, wywołuje w swojej metodzie
Program.cs. Rozważmy następujące przykładowe sprawdzanie kondycji, które akceptujearg1iarg2jako parametry konstruktora:public SampleHealthCheckWithArgs(int arg1, string arg2) => (_arg1, _arg2) = (arg1, arg2);Powyższy podpis wskazuje, że kontrola kondycji wymaga niestandardowych danych do przetwarzania logiki sondy sprawdzania kondycji. Dane są przekazywane delegatowi, który jest używany do utworzenia instancji sprawdzenia kondycji, gdy sprawdzenie kondycji jest zarejestrowane za pomocą metody rozszerzenia. W poniższym przykładzie obiekt wywołujący określa:
-
arg1: punkt danych typu liczbowego całkowitego dla sprawdzania stanu zdrowia. -
arg2: argument ciągu dla sprawdzania kondycji. -
name: opcjonalna nazwa sprawdzania kondycji. Jeślinullzostanie użyta wartość domyślna. -
failureStatus: opcjonalny HealthStatuselement , który jest zgłaszany dla stanu błędu. Jeślinull, HealthStatus.Unhealthy jest używany. -
tags: opcjonalnaIEnumerable<string>kolekcja tagów.
public static class SampleHealthCheckBuilderExtensions { private const string DefaultName = "Sample"; public static IHealthChecksBuilder AddSampleHealthCheck( this IHealthChecksBuilder healthChecksBuilder, int arg1, string arg2, string? name = null, HealthStatus? failureStatus = null, IEnumerable<string>? tags = default) { return healthChecksBuilder.Add( new HealthCheckRegistration( name ?? DefaultName, _ => new SampleHealthCheckWithArgs(arg1, arg2), failureStatus, tags)); } }-
Wydawca kontroli kondycji
Po dodaniu elementu IHealthCheckPublisher do kontenera usługi system monitorowania kondycji okresowo wykonuje sprawdzanie kondycji i wywołuje PublishAsync z wynikiem. Ten proces jest przydatny w scenariuszu systemu monitorowania stanu zdrowia opartym na zasadzie wypychania, który oczekuje, że każdy proces będzie okresowo wywoływał system monitorowania w celu określenia stanu zdrowia.
HealthCheckPublisherOptions umożliwia ustawienie następujących opcji:
- Delay: początkowe opóźnienie zastosowane po uruchomieniu aplikacji przed wykonaniem IHealthCheckPublisher wystąpień. Opóźnienie jest stosowane raz podczas uruchamiania i nie ma zastosowania do późniejszych iteracji. Wartość domyślna to pięć sekund.
- Period: okres IHealthCheckPublisher wykonywania. Wartość domyślna to 30 sekund.
-
Predicate: Jeśli Predicate jest
null(wartość domyślna), usługa wydawcy testów kondycji uruchamia wszystkie zarejestrowane testy kondycji. Aby uruchomić podzbiór kontroli kondycji, podaj funkcję, która filtruje zestaw testów. Predykat jest obliczany w każdym okresie. - Timeout: limit czasu na wykonywanie kontroli kondycji dla wszystkich IHealthCheckPublisher wystąpień. Użyj polecenia InfiniteTimeSpan , aby wykonać bez limitu czasu. Wartość domyślna to 30 sekund.
W poniższym przykładzie pokazano układ wydawcy zdrowotnego:
public class SampleHealthCheckPublisher : IHealthCheckPublisher
{
public Task PublishAsync(HealthReport report, CancellationToken cancellationToken)
{
if (report.Status == HealthStatus.Healthy)
{
// ...
}
else
{
// ...
}
return Task.CompletedTask;
}
}
Klasa HealthCheckPublisherOptions udostępnia właściwości służące do konfigurowania zachowania publikatora sprawdzania kondycji systemu.
W poniższym przykładzie wydawca kontroli kondycji jest rejestrowany jako singleton i konfiguruje HealthCheckPublisherOptions element:
builder.Services.Configure<HealthCheckPublisherOptions>(options =>
{
options.Delay = TimeSpan.FromSeconds(2);
options.Predicate = healthCheck => healthCheck.Tags.Contains("sample");
});
builder.Services.AddSingleton<IHealthCheckPublisher, SampleHealthCheckPublisher>();
Note
AspNetCore.Diagnostics.HealthChecks zawiera wydawców dla kilku systemów, w tym Application Insights.
AspNetCore.Diagnostics.HealthChecks nie jest obsługiwany ani wspierany przez firmę Microsoft.
Wstrzykiwanie zależności i kontrole kondycji
Można zastosować iniekcję zależności, aby wykorzystać instancję określonego Type wewnątrz klasy monitorującej stan zdrowia. Wstrzykiwanie zależności może być przydatne do wstrzykiwania opcji lub konfiguracji globalnej do kontroli kondycji. Używanie wstrzykiwania zależności nie jest typowym scenariuszem konfigurowania kontroli kondycji. Zwykle każde sprawdzenie kondycji jest dość specyficzne dla rzeczywistego testu i jest konfigurowane przy użyciu metod rozszerzeń IHealthChecksBuilder.
W poniższym przykładzie pokazano przykładową kontrolę kondycji, która pobiera obiekt konfiguracji za pośrednictwem iniekcji zależności:
public class SampleHealthCheckWithDI : IHealthCheck
{
private readonly SampleHealthCheckWithDiConfig _config;
public SampleHealthCheckWithDI(SampleHealthCheckWithDiConfig config)
=> _config = config;
public Task<HealthCheckResult> CheckHealthAsync(
HealthCheckContext context, CancellationToken cancellationToken = default)
{
var isHealthy = true;
// use _config ...
if (isHealthy)
{
return Task.FromResult(
HealthCheckResult.Healthy("A healthy result."));
}
return Task.FromResult(
new HealthCheckResult(
context.Registration.FailureStatus, "An unhealthy result."));
}
}
Element SampleHealthCheckWithDiConfig oraz sprawdzanie kondycji należy dodać do kontenera usługi :
builder.Services.AddSingleton<SampleHealthCheckWithDiConfig>(new SampleHealthCheckWithDiConfig
{
BaseUriToCheck = new Uri("https://sample.contoso.com/api/")
});
builder.Services.AddHealthChecks()
.AddCheck<SampleHealthCheckWithDI>(
"With Dependency Injection",
tags: new[] { "inject" });
UseHealthChecks vs MapHealthChecks
Istnieją dwa sposoby udostępniania kontroli kondycji obiektom wywołującym:
- UseHealthChecks rejestruje oprogramowanie pośredniczące do obsługi żądań kontroli kondycji w potoku oprogramowania pośredniczącego.
- MapHealthChecks rejestruje punkt końcowy kontroli kondycji. Punkt końcowy jest zgodny i wykonywany wraz z innymi punktami końcowymi w aplikacji.
Zaletą używania MapHealthChecks nad UseHealthChecks jest możliwość korzystania z oprogramowania pośredniczącego świadomego punktów końcowych, takiego jak autoryzacja, oraz posiadanie większej, precyzyjnej kontroli nad zasadami dopasowywania. Główną zaletą używania UseHealthChecks zamiast MapHealthChecks jest precyzyjne kontrolowanie tego, gdzie w potoku middleware są uruchamiane kontrole kondycji.
- Przerywa potok, gdy żądanie jest zgodne z punktem końcowym sprawdzania kondycji. Krótkie spięcie jest często pożądane, ponieważ pozwala uniknąć niepotrzebnej pracy, takiej jak logowanie oraz inne elementy pośredniczące.
- Służy głównie do konfigurowania middleware monitorowania stanu w potoku.
- Może dopasować dowolną ścieżkę na porcie używając
nulllub pustegoPathString. Umożliwia wykonanie kontroli zdrowia dla każdego żądania kierowanego do określonego portu. - Kod źródłowy
MapHealthChecks Pozwala:
- Mapowanie określonych tras lub punktów końcowych na potrzeby kontroli kondycji.
- Dostosowanie adresu URL lub ścieżki, w której jest dostępny punkt końcowy sprawdzania kondycji.
- Mapowanie wielu punktów końcowych kontroli kondycji z różnymi trasami lub konfiguracjami. Obsługa wielu punktów końcowych:
- Włącza oddzielne punkty końcowe dla różnych typów testów kondycji lub składników.
- Służy do rozróżniania różnych aspektów kondycji aplikacji lub stosowania określonych konfiguracji do podzbiorów kontroli kondycji.
- Kod źródłowy
Dodatkowe zasoby
Note
Ten artykuł został częściowo utworzony z pomocą sztucznej inteligencji. Przed opublikowaniem autor przejrzał i poprawił zawartość zgodnie z potrzebą. Zapoznaj się z naszymi zasadami korzystania z zawartości generowanej za pośrednictwem AI w usłudze Microsoft Learn.