Udostępnij przez


Przykład: użycie OpenTelemetry z OTLP i autonomicznym pulpitem nawigacyjnym Aspire

Ten artykuł jest jedną z serii przykładów ilustrujących możliwość obserwowania platformy .NET za pomocą technologii OpenTelemetry.

Oprócz bycia standardową częścią Aspire, pulpit nawigacyjny Aspire jest dostępny jako samodzielny kontener Docker, który zapewnia punkt końcowy OTLP do wysyłania danych telemetrycznych. Dashboard wizualizuje logi, metryki i ślady. Korzystanie z pulpitu nawigacyjnego w ten sposób nie ma zależności od Aspire i wizualizuje dane telemetryczne z dowolnej aplikacji wysyłającej dane telemetryczne za pośrednictwem OTLP. Działa równie dobrze w przypadku aplikacji napisanych w języku Java, GoLang lub Python, pod warunkiem, że mogą wysyłać dane telemetryczne do punktu końcowego OTLP.

Korzystanie z Aspire Dashboard wymaga mniej kroków konfiguracji i ustawień niż korzystanie z rozwiązań typu open source, takich jak Prometheus, Grafana i Jaeger. Jednak w przeciwieństwie do tych narzędzi pulpit nawigacyjny Aspirator jest przeznaczony jako narzędzie do wizualizacji dla deweloperów, a nie do monitorowania produkcyjnego.

1. Tworzenie projektu

Utwórz prosty projekt internetowego interfejsu API, korzystając z szablonu ASP.NET Core Empty w programie Visual Studio lub następującego polecenia CLI platformy .NET:

dotnet new web

2. Dodawanie metryk i definicji działań

Poniższy kod definiuje nową metrykę (greetings.count) dla liczby wywołań interfejsu API i nowego źródła działań (Otel.Example).

// Custom metrics for the application
var greeterMeter = new Meter("OTel.Example", "1.0.0");
var countGreetings = greeterMeter.CreateCounter<int>("greetings.count", description: "Counts the number of greetings");

// Custom ActivitySource for the application
var greeterActivitySource = new ActivitySource("OTel.Example");

3. Tworzenie punktu końcowego interfejsu API

Wstaw następujący kod między builder.Build(); i app.Run()

app.MapGet("/", SendGreeting);

Wstaw następującą funkcję w dolnej części pliku:

async Task<string> SendGreeting(ILogger<Program> logger)
{
    // Create a new Activity scoped to the method
    using var activity = greeterActivitySource.StartActivity("GreeterActivity");

    // Log a message
    logger.LogInformation("Sending greeting");

    // Increment the custom counter
    countGreetings.Add(1);

    // Add a tag to the Activity
    activity?.SetTag("greeting", "Hello World!");

    return "Hello World!";
}

Uwaga

Definicja punktu końcowego nie używa żadnych elementów specyficznych dla funkcji OpenTelemetry. Używa on interfejsów API platformy .NET do obserwowalności.

4. Odwołaj się do pakietów OpenTelemetry

Użyj Menedżer pakietów NuGet lub wiersza polecenia, aby dodać następujące pakiety NuGet:

  <ItemGroup>
    <PackageReference Include="OpenTelemetry.Exporter.OpenTelemetryProtocol" Version="1.9.0" />
    <PackageReference Include="OpenTelemetry.Extensions.Hosting" Version="1.9.0" />
    <PackageReference Include="OpenTelemetry.Instrumentation.AspNetCore" Version="1.9.0" />
    <PackageReference Include="OpenTelemetry.Instrumentation.Http" Version="1.9.0" />
  </ItemGroup>

Uwaga

Użyj najnowszych wersji, ponieważ interfejsy API OTel stale ewoluują.

5. Konfigurowanie biblioteki OpenTelemetry przy użyciu odpowiednich dostawców

Wstaw następujący kod przed :builder.Build();

// Setup logging to be exported via OpenTelemetry
builder.Logging.AddOpenTelemetry(logging =>
{
    logging.IncludeFormattedMessage = true;
    logging.IncludeScopes = true;
});

var otel = builder.Services.AddOpenTelemetry();

// Add Metrics for ASP.NET Core and our custom metrics and export via OTLP
otel.WithMetrics(metrics =>
{
    // Metrics provider from OpenTelemetry
    metrics.AddAspNetCoreInstrumentation();
    //Our custom metrics
    metrics.AddMeter(greeterMeter.Name);
    // Metrics provides by ASP.NET Core in .NET 8
    metrics.AddMeter("Microsoft.AspNetCore.Hosting");
    metrics.AddMeter("Microsoft.AspNetCore.Server.Kestrel");
});

// Add Tracing for ASP.NET Core and our custom ActivitySource and export via OTLP
otel.WithTracing(tracing =>
{
    tracing.AddAspNetCoreInstrumentation();
    tracing.AddHttpClientInstrumentation();
    tracing.AddSource(greeterActivitySource.Name);
});

// Export OpenTelemetry data via OTLP, using env vars for the configuration
var OtlpEndpoint = builder.Configuration["OTEL_EXPORTER_OTLP_ENDPOINT"];
if (OtlpEndpoint != null)
{
    otel.UseOtlpExporter();
}

Ten kod konfiguruje usługę OpenTelemetry z różnymi źródłami telemetrii:

  • Dodaje dostawcę OTel do usługi ILogger w celu zbierania rekordów dzienników.
  • Konfiguruje metryki, rejestrując dostawców instrumentacji i mierniki dla ASP.NET oraz nasz własny miernik.
  • Konfiguruje śledzenie, rejestrując dostawców instrumentacji oraz nasze niestandardowe ActivitySource.

Następnie rejestruje eksportera OTLP przy użyciu zmiennych środowiskowych do jego konfiguracji.

6. Konfigurowanie zmiennych środowiskowych OTLP

Eksporter OTLP można skonfigurować za pośrednictwem interfejsów API w kodzie, ale częściej konfiguruje go za pomocą zmiennych środowiskowych. Dodaj następujące elementy do AppSettings.Development.json

"OTEL_EXPORTER_OTLP_ENDPOINT": "http://localhost:4317",
"OTEL_SERVICE_NAME": "OTLP-Example"

Możesz dodać dodatkowe zmienne środowiskowe dla .NET eksportera OTLP lub typowe zmienne OTel, takie jak do definiowania OTEL_RESOURCE_ATTRIBUTES.

Uwaga

Częstym błędem jest mieszanie plików AppSettings.json i AppSettings.Development.json. Jeśli ten ostatni jest obecny, będzie używany podczas F5 z programu Visual Studio, a wszystkie ustawienia w AppSettings.json zostaną zignorowane.

7. Uruchom kontener Pulpitu nawigacyjnego Aspire

Użyj docker do pobrania i uruchomienia kontenera pulpitu nawigacyjnego.

docker run --rm -it `
-p 18888:18888 `
-p 4317:18889 `
--name aspire-dashboard `
mcr.microsoft.com/dotnet/aspire-dashboard:latest

Dane wyświetlane na pulpicie nawigacyjnym mogą być poufne. Domyślnie pulpit nawigacyjny jest zabezpieczony przy użyciu uwierzytelniania, które wymaga tokenu do zalogowania. Token jest wyświetlany w wynikowych danych wyjściowych podczas uruchamiania kontenera.

Panel AspireAspire DashboardAspire Dashboardpulpit nawigacyjny

Skopiuj wyświetlony adres URL, zastąp 0.0.0.0 ciągiem localhost, na przykład http://localhost:18888/login?t=123456780abcdef123456780, i otwórz go w przeglądarce. Możesz również wkleić klucz po /login?t= wyświetleniu okna dialogowego logowania. Token zmienia się za każdym razem, gdy uruchamiasz kontener.

8. Uruchamianie projektu

Uruchom projekt, a następnie uzyskaj dostęp do interfejsu API za pomocą przeglądarki lub narzędzia curl.

curl -k http://localhost:7275

Za każdym razem, gdy wywołujesz stronę, zwiększa licznik liczby wykonanych powitań.

8.1 Dane wyjściowe dziennika

Instrukcje rejestrowania z kodu są wyświetlane za pomocą ILogger. Domyślnie dostawca konsoli jest włączony, aby dane wyjściowe były kierowane do konsoli.

Istnieje kilka opcji, w jaki sposób dzienniki mogą być wyprowadzane z platformy .NET.

  • Dane wyjściowe stdout i stderr są przekierowywane do plików dziennika przez systemy kontenerowe, takie jak Kubernetes.
  • Korzystanie z bibliotek rejestrowania, które integrują się z aplikacją ILogger. Biblioteki te obejmują Serilog i NLog.
  • Używanie dostawców rejestrowania dla technologii OTel, takich jak OTLP. Sekcja logowania w kodzie z kroku 5 dodaje dostawcę OTel.

Dzienniki są wyświetlane w konsoli jako dzienniki ustrukturyzowane — wszystkie właściwości ustawione w komunikacie dziennika są wyodrębniane jako pola w zapisie dziennika.

Dzienniki na niezależnym pulpicie nawigacyjnym

8.2 Wyświetlanie metryk

Panel Aspire pokazuje metryki dla poszczególnych zasobów (zasób według OTel to sposób mówienia o źródłach danych telemetrycznych, takich jak proces). Po wybraniu zasobu pulpit nawigacyjny wylicza każdą metrykę, która została wysłana do punktu końcowego OTLP przez zasób. Lista metryk jest dynamiczna i jest aktualizowana w miarę odbierania nowych metryk.

Metryki na autonomicznym pulpicie nawigacyjnym

Widok metryk zależy od typu używanej metryki:

  • Liczniki są wyświetlane bezpośrednio.
  • Histogramy, które śledzą wartość na żądanie, takie jak okres czasu lub bajty wysyłane na żądanie, są zbierane w serii kubełków. Pulpit nawigacyjny grafuje percentyle P50, P90 i P99. Wyniki histogramu mogą zawierać przykłady, które są poszczególnymi punktami danych wraz z identyfikatorem trace/spanId dla tego żądania. Są one wyświetlane jako kropki na grafie. Wybranie tego elementu spowoduje przejście do odpowiedniego śladu, aby zobaczyć, co doprowadziło do uzyskania tej wartości. Jest to przydatne w przypadku diagnozowania wartości odstających.
  • Metryki mogą zawierać wymiary, które są parami klucz/wartość skojarzonymi z poszczególnymi wartościami. Wartości są agregowane na wymiar. Korzystając z rozwijanych list w widoku, możesz filtrować wyniki, aby przyjrzeć się określonym aspektom, takim jak tylko zapytania GET, lub dla określonej ścieżki URL w ASP.NET.

8.3 Przeglądanie procesu śledzenia

Widok śledzenia zawiera listę śladów. Każdy ślad jest zestawem działań, które mają ten sam identyfikator traceId. Praca jest śledzona za pomocą zakresów, które reprezentują jednostkę pracy. Przetwarzanie żądania ASP.NET powoduje utworzenie odcinka czasowego. Tworzenie żądania HttpClient jest czasem trwania operacji. Śledząc element nadrzędny zakresu, można zwizualizować hierarchię zakresów. Zbierając zakresy z każdego zasobu (procesu), można śledzić pracę wykonywaną w ramach serii usług. Żądania HTTP mają nagłówek, który jest używany do przekazywania traceId i nadrzędnego spanId do następnej usługi. Każdy zasób musi zbierać dane telemetryczne i wysyłać je do tego samego modułu zbierającego. Następnie będzie agregować i przedstawiać hierarchię zakresów.

Ślady na samodzielnym panelu sterowania

Na pulpicie nawigacyjnym jest wyświetlana lista śladów z informacjami podsumowującymi. Za każdym razem, gdy są widoczne nowe identyfikatory traceId, otrzymują wiersz w tabeli. Kliknięcie opcji "Wyświetl" spowoduje wyświetlenie wszystkich zakresów w śladu.

Elementy w autonomicznym pulpicie nawigacyjnym

Wybranie zakresu pokazuje jego szczegóły, w tym wszystkie właściwości zakresu, takie jak greeting tag ustawiony w kroku 3.