Teilen über


Hinzufügen und Ändern von Azure Monitor OpenTelemetry für .NET-, Java-, Node.js- und Python-Anwendungen

Dieses Handbuch enthält Anweisungen zum Integrieren und Anpassen der OpenTelemetry-Instrumentierung (OTel) in Azure Monitor Application Insights.

Weitere Informationen zu OpenTelemetry-Konzepten finden Sie in der OpenTelemetry-Übersicht oder in den Häufig gestellten Fragen zu OpenTelemetry.

Hinweis

Informationen zu Azure-Funktions-Apps finden Sie unter Verwenden von OpenTelemetry mit Azure-Funktionen.

Automatische Datensammlung

Die Distributionen sammeln Daten automatisch durch Bündelung von OpenTelemetry-Instrumentierungsbibliotheken.

Enthaltene Instrumentierungsbibliotheken

Anforderungen

Abhängigkeiten

Protokollierung

  • ILogger

Um die Anzahl der an Azure Monitor gesendeten Protokolle zu reduzieren oder zu erhöhen, konfigurieren Sie die Protokollierung, um die entsprechende Protokollebene festzulegen oder Filter anzuwenden. Sie können beispielsweise auswählen, dass nur die Protokolle Warning und Error an OpenTelemetry/Azure Monitor gesendet werden. OpenTelemetry steuert das Protokollrouting oder die Filterung nicht – Ihre ILogger Konfiguration trifft diese Entscheidungen. Weitere Informationen zum Konfigurieren ILoggerfinden Sie unter Konfigurieren der Protokollierung.

Weitere Informationen zu ILogger finden Sie unter Protokollierung in C# und .NET und unter Codebeispiele.

Fußnoten

  • ¹: Unterstützt das automatische Melden von unbehandelten/nicht erkannten Fehlern
  • ²: Unterstützt OpenTelemetry-Metriken

Hinweis

Die OpenTelemetry-Distributionen von Azure Monitor umfassen eine benutzerdefinierte Zuordnung und Logik, um automatisch Application Insights-Standardmetriken auszugeben.

Tipp

Alle OpenTelemetry-Metriken, unabhängig davon, ob sie automatisch von Instrumentenbibliotheken oder manuell durch benutzerdefinierte Codierung erfasst werden, gelten derzeit für Abrechnungszwecke als „benutzerdefinierte Metriken“ von Application Insights. Weitere Informationen

Hinzufügen einer Community-Instrumentierungsbibliothek

Sie können automatisch mehr Daten sammeln, wenn Sie Instrumentierungsbibliotheken aus der OpenTelemetry-Community einschließen.

Achtung

Community-Instrumentierungsbibliotheken werden von uns nicht unterstützt und wir übernehmen keine Garantie für ihre Qualität. Wenn Sie einen Vorschlag für unsere Distribution machen möchten, posten Sie ihn in unserer Feedback-Community oder geben Sie dort ein Up-Vote ab. Beachten Sie, dass einige auf experimentellen OpenTelemetry-Spezifikationen basieren und möglicherweise zukünftige grundlegende Änderungen einführen.

Verwenden Sie zum Hinzufügen einer Communitybibliothek die Methoden ConfigureOpenTelemetryMeterProvider oder ConfigureOpenTelemetryTracerProvider, nachdem Sie das NuGet-Paket für die Bibliothek hinzugefügt haben.

Im folgenden Beispiel wird veranschaulicht, wie die Laufzeitinstrumentierung hinzugefügt werden kann, um zusätzliche Metriken zu sammeln:

dotnet add package OpenTelemetry.Instrumentation.Runtime 
// Create a new ASP.NET Core web application builder.
var builder = WebApplication.CreateBuilder(args);

// Configure the OpenTelemetry meter provider to add runtime instrumentation.
builder.Services.ConfigureOpenTelemetryMeterProvider((sp, builder) => builder.AddRuntimeInstrumentation());

// Add the Azure Monitor telemetry service to the application.
// This service will collect and send telemetry data to Azure Monitor.
builder.Services.AddOpenTelemetry().UseAzureMonitor();

// Build the ASP.NET Core web application.
var app = builder.Build();

// Start the ASP.NET Core web application.
app.Run();

Erfassen benutzerdefinierter Telemetriedaten

In diesem Abschnitt erfahren Sie, wie Sie benutzerdefinierte Telemetrie aus Ihrer Anwendung erfassen.

Abhängig von Ihrer Sprache und Ihrem Signaltyp gibt es verschiedene Möglichkeiten, benutzerdefinierte Telemetriedaten zu erfassen, darunter:

  • OpenTelemetry-API
  • Sprachspezifische Protokollierung/Metrikbibliotheken
  • Classic API von Application Insights

Die folgende Tabelle stellt die derzeit unterstützten benutzerdefinierten Telemetrietypen dar:

Sprache Benutzerdefinierte Ereignisse Benutzerdefinierte Metriken Abhängigkeiten Ausnahmen Seitenaufrufe Anfragen Ablaufverfolgungen
ASP.NET Core
   OpenTelemetry-API Ja Ja Ja Ja
   ILogger-API Ja
   KI Classic API
Java
   OpenTelemetry-API Ja Ja Ja Ja
   Logback, Log4j, JUL Ja Ja
   Mikrometer-Metriken Ja
   KI Classic API Ja Ja Ja Ja Ja Ja Ja
Node.js
   OpenTelemetry-API Ja Ja Ja Ja
Python
   OpenTelemetry-API Ja Ja Ja Ja
   Python-Protokollierungsmodul Ja
   Ereigniserweiterung Ja Ja

Hinweis

Application Insights Java 3.x und Application Insights Node.js 3.x sammeln Telemetrie aus der klassischen Application Insights-API. Dieses Verhalten vereinfacht Upgrades und unterstützt vorübergehend benutzerdefinierte Telemetrie, bis die OpenTelemetry-API alle benutzerdefinierten Telemetrietypen enthält.

Hinzufügen benutzerdefinierter Metriken

In diesem Zusammenhang bezieht sich der Ausdruck "benutzerdefinierte Metriken" darauf, Ihren Code manuell zu instrumentieren, um zusätzliche Metriken zu erfassen, die über das hinausgehen, was die OpenTelemetry-Instrumentierungs-Bibliotheken automatisch erfassen.

Die OpenTelemetry-API bietet sechs Metrikinstrumente zur Abdeckung verschiedener Metrikszenarien, und Sie müssen beim Visualisieren von Metriken im Metrik-Explorer den richtigen Aggregationstyp auswählen. Diese Anforderung gilt bei Verwendung der OpenTelemetry-Metrik-API zum Senden von Metriken sowie bei Verwendung einer Instrumentierungsbibliothek.

Die folgende Tabelle enthält die empfohlenen Aggregationstypen für die einzelnen OpenTelemetry-Metrikinstrumente:

OpenTelemetry-Instrument Aggregationstyp von Azure Monitor
Zähler Summe
Asynchroner Zähler Summe
Histogramm Minimum, Maximum, Mittelwert, Summe und Anzahl
Asynchrones Messgerät Durchschnitt
UpDownCounter Summe
UpDownCounter (asynchron) Summe

Achtung

Andere Aggregationstypen sind in den meisten Fällen nicht sinnvoll.

Die OpenTelemetry-Spezifikation beschreibt die Instrumente und enthält Verwendungsbeispiele.

Tipp

Das Histogramm ist am vielseitigsten und entspricht am ehesten der Classic API von Application Insights für GetMetric. Azure Monitor vereinfacht das Histogramminstrument derzeit mit unseren fünf unterstützten Aggregationstypen, und Quantile werden demnächst unterstützt. Obwohl weniger vielseitig, wirken sich andere OpenTelemetry-Instrumente weniger auf die Leistung Ihrer Anwendung aus.

Histogrammbeispiel

Der Anwendungsstart muss eine Verbrauchseinheit nach Name abonnieren:

// Create a new ASP.NET Core web application builder.
var builder = WebApplication.CreateBuilder(args);

// Configure the OpenTelemetry meter provider to add a meter named "OTel.AzureMonitor.Demo".
builder.Services.ConfigureOpenTelemetryMeterProvider((sp, builder) => builder.AddMeter("OTel.AzureMonitor.Demo"));

// Add the Azure Monitor telemetry service to the application.
// This service will collect and send telemetry data to Azure Monitor.
builder.Services.AddOpenTelemetry().UseAzureMonitor();

// Build the ASP.NET Core web application.
var app = builder.Build();

// Start the ASP.NET Core web application.
app.Run();

Meter muss mit demselben Namen initialisiert werden:

// Create a new meter named "OTel.AzureMonitor.Demo".
var meter = new Meter("OTel.AzureMonitor.Demo");

// Create a new histogram metric named "FruitSalePrice".
Histogram<long> myFruitSalePrice = meter.CreateHistogram<long>("FruitSalePrice");

// Create a new Random object.
var rand = new Random();

// Record a few random sale prices for apples and lemons, with different colors.
myFruitSalePrice.Record(rand.Next(1, 1000), new("name", "apple"), new("color", "red"));
myFruitSalePrice.Record(rand.Next(1, 1000), new("name", "lemon"), new("color", "yellow"));
myFruitSalePrice.Record(rand.Next(1, 1000), new("name", "lemon"), new("color", "yellow"));
myFruitSalePrice.Record(rand.Next(1, 1000), new("name", "apple"), new("color", "green"));
myFruitSalePrice.Record(rand.Next(1, 1000), new("name", "apple"), new("color", "red"));
myFruitSalePrice.Record(rand.Next(1, 1000), new("name", "lemon"), new("color", "yellow"));

Gegenbeispiel

Der Anwendungsstart muss eine Verbrauchseinheit nach Name abonnieren:

// Create a new ASP.NET Core web application builder.
var builder = WebApplication.CreateBuilder(args);

// Configure the OpenTelemetry meter provider to add a meter named "OTel.AzureMonitor.Demo".
builder.Services.ConfigureOpenTelemetryMeterProvider((sp, builder) => builder.AddMeter("OTel.AzureMonitor.Demo"));

// Add the Azure Monitor telemetry service to the application.
// This service will collect and send telemetry data to Azure Monitor.
builder.Services.AddOpenTelemetry().UseAzureMonitor();

// Build the ASP.NET Core web application.
var app = builder.Build();

// Start the ASP.NET Core web application.
app.Run();

Meter muss mit demselben Namen initialisiert werden:

// Create a new meter named "OTel.AzureMonitor.Demo".
var meter = new Meter("OTel.AzureMonitor.Demo");

// Create a new counter metric named "MyFruitCounter".
Counter<long> myFruitCounter = meter.CreateCounter<long>("MyFruitCounter");

// Record the number of fruits sold, grouped by name and color.
myFruitCounter.Add(1, new("name", "apple"), new("color", "red"));
myFruitCounter.Add(2, new("name", "lemon"), new("color", "yellow"));
myFruitCounter.Add(1, new("name", "lemon"), new("color", "yellow"));
myFruitCounter.Add(2, new("name", "apple"), new("color", "green"));
myFruitCounter.Add(5, new("name", "apple"), new("color", "red"));
myFruitCounter.Add(4, new("name", "lemon"), new("color", "yellow"));

Messgerätbeispiel

Der Anwendungsstart muss eine Verbrauchseinheit nach Name abonnieren:

// Create a new ASP.NET Core web application builder.
var builder = WebApplication.CreateBuilder(args);

// Configure the OpenTelemetry meter provider to add a meter named "OTel.AzureMonitor.Demo".
builder.Services.ConfigureOpenTelemetryMeterProvider((sp, builder) => builder.AddMeter("OTel.AzureMonitor.Demo"));

// Add the Azure Monitor telemetry service to the application.
// This service will collect and send telemetry data to Azure Monitor.
builder.Services.AddOpenTelemetry().UseAzureMonitor();

// Build the ASP.NET Core web application.
var app = builder.Build();

// Start the ASP.NET Core web application.
app.Run();

Meter muss mit demselben Namen initialisiert werden:

// Get the current process.
var process = Process.GetCurrentProcess();

// Create a new meter named "OTel.AzureMonitor.Demo".
var meter = new Meter("OTel.AzureMonitor.Demo");

// Create a new observable gauge metric named "Thread.State".
// This metric will track the state of each thread in the current process.
ObservableGauge<int> myObservableGauge = meter.CreateObservableGauge("Thread.State", () => GetThreadState(process));

private static IEnumerable<Measurement<int>> GetThreadState(Process process)
{
    // Iterate over all threads in the current process.
    foreach (ProcessThread thread in process.Threads)
    {
        // Create a measurement for each thread, including the thread state, process ID, and thread ID.
        yield return new((int)thread.ThreadState, new("ProcessId", process.Id), new("ThreadId", thread.Id));
    }
}

Hinzufügen benutzerdefinierter Ausnahmen

Bestimmte Instrumentierungsbibliotheken melden automatisch Ausnahmen für Application Insights. Möglicherweise möchten Sie jedoch manuell Ausnahmen melden, die über die Berichte von Instrumentierungsbibliotheken hinausgehen. Beispielsweise werden von Ihrem Code erfasste Ausnahmen üblicherweise nicht gemeldet. Unter Umständen empfiehlt es sich, sie zu melden, um in relevanten Umgebungen auf sie aufmerksam zu machen. Hierzu zählen unter anderem der Fehlerabschnitt sowie End-to-End-Transaktionsansichten.

  • Protokollieren einer Ausnahme mithilfe einer Aktivität:

    // Start a new activity named "ExceptionExample".
    using (var activity = activitySource.StartActivity("ExceptionExample"))
    {
        // Try to execute some code.
        try
        {
            throw new Exception("Test exception");
        }
        // If an exception is thrown, catch it and set the activity status to "Error".
        catch (Exception ex)
        {
            activity?.SetStatus(ActivityStatusCode.Error);
            activity?.RecordException(ex);
        }
    }
    
  • Protokollieren einer Ausnahme mithilfe von ILogger:

    // Create a logger using the logger factory. The logger category name is used to filter and route log messages.
    var logger = loggerFactory.CreateLogger(logCategoryName);
    
    // Try to execute some code.
    try
    {
        throw new Exception("Test Exception");
    }
    catch (Exception ex)
    {
        // Log an error message with the exception. The log level is set to "Error" and the event ID is set to 0.
        // The log message includes a template and a parameter. The template will be replaced with the value of the parameter when the log message is written.
        logger.Log(
            logLevel: LogLevel.Error,
            eventId: 0,
            exception: ex,
            message: "Hello {name}.",
            args: new object[] { "World" });
    }
    

Hinzufügen von benutzerdefinierten Spannen

In zwei Szenarien sollten Sie eine benutzerdefinierte Spanne hinzufügen. Erstens, wenn eine Abhängigkeitsanforderung vorhanden ist, die nicht bereits von einer Instrumentierungsbibliothek erfasst wurde. Zweitens, wenn Sie einen Anwendungsprozess als Spanne in der End-to-End-Transaktionsansicht modellieren möchten.

Hinweis

Die Klassen Activity und ActivitySource aus dem System.Diagnostics-Namespace stellen die OpenTelemetry-Konzepte von Span bzw. Tracer dar. Sie erstellen ActivitySource direkt mithilfe des Konstruktors anstelle von mithilfe von TracerProvider. Jede Klasse ActivitySource muss mithilfe von TracerProvider explizit mit AddSource() verbunden werden. Der Fehler liegt daran, dass Teile der OpenTelemetry-Ablaufverfolgungs-API direkt in die .NET-Laufzeit integriert werden. Weitere Informationen finden Sie unter Einführung in die .NET-Ablaufverfolgungs-API für OpenTelemetry.

// Define an activity source named "ActivitySourceName". This activity source will be used to create activities for all requests to the application.
internal static readonly ActivitySource activitySource = new("ActivitySourceName");

// Create an ASP.NET Core application builder.
var builder = WebApplication.CreateBuilder(args);

// Configure the OpenTelemetry tracer provider to add a source named "ActivitySourceName". This will ensure that all activities created by the activity source are traced.
builder.Services.ConfigureOpenTelemetryTracerProvider((sp, builder) => builder.AddSource("ActivitySourceName"));

// Add the Azure Monitor telemetry service to the application. This service will collect and send telemetry data to Azure Monitor.
builder.Services.AddOpenTelemetry().UseAzureMonitor();

// Build the ASP.NET Core application.
var app = builder.Build();

// Map a GET request to the root path ("/") to the specified action.
app.MapGet("/", () =>
{
    // Start a new activity named "CustomActivity". This activity will be traced and the trace data will be sent to Azure Monitor.
    using (var activity = activitySource.StartActivity("CustomActivity"))
    {
        // your code here
    }

    // Return a response message.
    return $"Hello World!";
});

// Start the ASP.NET Core application.
app.Run();

StartActivity ist standardmäßig auf ActivityKind.Internal festgelegt. Sie können jedoch eine beliebige andere ActivityKind angeben. ActivityKind.Client, ActivityKind.Producer und ActivityKind.Internal sind Application Insights-dependencies zugeordnet. ActivityKind.Server und ActivityKind.Consumer sind Application Insights-requests zugeordnet.

Versenden von benutzerdefinierten Ereignissen

Application Insights speichert benutzerdefinierte Ereignisse in der customEvents Tabelle. Eine Möglichkeit, sie zu analysieren, zu filtern und zu visualisieren , besteht darin, die Nutzungserfahrungen von Application Insights zu verwenden.

Wenn Sie die Sammlung clientseitiger Interaktionsereignisse automatisieren möchten, können Sie das Plug-In im JavaScript SDK verwenden.

Benutzerdefinierte Ereignisse befinden sich in der öffentlichen Vorschau und verwenden Azure.Monitor.OpenTelemetry.AspNetCore 1.3.0-beta.3.

Wichtig

Die zusätzlichen Nutzungsbestimmungen für Microsoft Azure-Vorschauen enthalten rechtliche Bedingungen. Sie gelten für diejenigen Azure-Features, die sich in der Beta- oder Vorschauversion befinden oder aber anderweitig noch nicht zur allgemeinen Verfügbarkeit freigegeben sind.

Um eine CustomEvent mit ILogger zu senden, legen Sie das "microsoft.custom_event.name"-Attribut in der Nachrichtenvorlage fest.

// Create a logger factory and configure OpenTelemetry with Azure Monitor
var loggerFactory = LoggerFactory.Create(builder =>
{
    builder
        .AddOpenTelemetry(options =>
        {
            options.AddAzureMonitorLogExporter();
        });
});

// Create a logger for the specified category
var logger = loggerFactory.CreateLogger(logCategoryName);

// Log a custom event with a custom name and additional attribute
// The 'microsoft.custom_event.name' value will be used as the name of the customEvent
logger.LogInformation("{microsoft.custom_event.name} {additional_attrs}", "test-event-name", "val1");

Ändern der Telemetrie

In diesem Abschnitt wird das Ändern von Telemetriedaten erläutert.

Hinzufügen von span-Attributen

Zu diesen Attributen kann das Hinzufügen einer benutzerdefinierten Eigenschaft zu Ihrer Telemetrie gehören. Sie können auch Attribute verwenden, um optionale Felder im Application Insights-Schema festzulegen, z. B. Client-IP.

Hinzufügen einer benutzerdefinierten Eigenschaft zu einem Span-Objekt

Alle Attribute, die Sie Spans hinzufügen, werden als benutzerdefinierte Eigenschaften exportiert. Sie füllen das Feld customDimensions in der Tabelle für Anforderungen, Abhängigkeiten, Spuren oder Ausnahmen aus.

Verwenden Sie zum Hinzufügen von Span-Attributen eine der beiden folgenden Möglichkeiten:

Tipp

Der Vorteil der Verwendung von Optionen, die von Instrumentierungsbibliotheken bereitgestellt werden, wenn sie verfügbar sind, ist, dass der gesamte Kontext verfügbar ist. Dadurch können Benutzer weitere Attribute hinzufügen oder filtern. Mit der Option „anreichern“ in der HttpClient-Instrumentierungsbibliothek erhalten Benutzer beispielsweise Zugriff auf HttpRequestMessage und die HttpResponseMessage selbst. Sie können alles daraus auswählen und als Attribut speichern.

  1. Viele Instrumentierungsbibliotheken bieten eine Anreicherungsoption. Eine Anleitung finden Sie in den Readme-Dateien der einzelnen Instrumentierungsbibliotheken:

  2. Verwenden eines benutzerdefinierten Prozessors:

    Tipp

    Fügen Sie den hier gezeigten Prozessor vor dem Hinzufügen von Azure Monitor hinzu.

    // Create an ASP.NET Core application builder.
    var builder = WebApplication.CreateBuilder(args);
    
    // Configure the OpenTelemetry tracer provider to add a new processor named ActivityEnrichingProcessor.
    builder.Services.ConfigureOpenTelemetryTracerProvider((sp, builder) => builder.AddProcessor(new ActivityEnrichingProcessor()));
    
    // Add the Azure Monitor telemetry service to the application. This service will collect and send telemetry data to Azure Monitor.
    builder.Services.AddOpenTelemetry().UseAzureMonitor();
    
    // Build the ASP.NET Core application.
    var app = builder.Build();
    
    // Start the ASP.NET Core application.
    app.Run();
    

    Fügen Sie Ihrem Projekt ActivityEnrichingProcessor.cs mit dem unten aufgeführten Code hinzu:

    public class ActivityEnrichingProcessor : BaseProcessor<Activity>
    {
        public override void OnEnd(Activity activity)
        {
            // The updated activity will be available to all processors which are called after this processor.
            activity.DisplayName = "Updated-" + activity.DisplayName;
            activity.SetTag("CustomDimension1", "Value1");
            activity.SetTag("CustomDimension2", "Value2");
        }
    }
    

Festlegen der Benutzer-IP

Sie können das Feld client_IP für Requests ausfüllen, indem Sie ein Attribut auf der Spanne festlegen. Application Insights verwendet die IP-Adresse zum Generieren von Benutzerstandortattributen und verwirft sie dann standardmäßig.

Verwenden Sie das Beispiel einer benutzerdefinierten Eigenschaft, ersetzen Sie dabei aber die folgenden Codezeilen in ActivityEnrichingProcessor.cs:

// Add the client IP address to the activity as a tag.
// only applicable in case of activity.Kind == Server
activity.SetTag("client.address", "<IP Address>");

Festlegen der Benutzer-ID oder der authentifizierten Benutzer-ID

Sie können das Feld user_Id oder user_AuthenticatedId für Anforderungen mit Daten auffüllen, indem Sie die folgende Anleitung verwenden. Die Benutzer-ID ist ein anonymer Benutzerbezeichner. Die authentifizierte Benutzer-ID ist ein bekannter Benutzerbezeichner.

Wichtig

Informieren Sie sich über die geltenden Datenschutzgesetze, bevor Sie die authentifizierte Benutzer-ID festlegen.

Verwenden Sie das Beispiel einer benutzerdefinierten Eigenschaft:

// Add the user ID to the activity as a tag, but only if the activity is not null.
activity?.SetTag("enduser.id", "<User Id>");

Hinzufügen von Protokollattributen

OpenTelemetry verwendet den ILogger von .NET. Das Anfügen benutzerdefinierter Dimensionen an Protokolle kann mithilfe einer Nachrichtenvorlage erfolgen.

Abrufen der Ablaufverfolgungs-ID oder Span-ID

Sie können mit den folgenden Schritten die Trace ID und Span ID der derzeit aktiven Span abrufen.

Hinweis

Die Klassen Activity und ActivitySource aus dem System.Diagnostics-Namespace stellen die OpenTelemetry-Konzepte von Span bzw. Tracer dar. Der Fehler liegt daran, dass Teile der OpenTelemetry-Ablaufverfolgungs-API direkt in die .NET-Laufzeit integriert werden. Weitere Informationen finden Sie unter Einführung in die .NET-Ablaufverfolgungs-API für OpenTelemetry.

// Get the current activity.
Activity activity = Activity.Current;
// Get the trace ID of the activity.
string traceId = activity?.TraceId.ToHexString();
// Get the span ID of the activity.
string spanId = activity?.SpanId.ToHexString();

Nächste Schritte