From 074529e5a076d3e8c6dd93cd8c0df4abb3db8e96 Mon Sep 17 00:00:00 2001 From: wuweng Date: Thu, 2 Oct 2025 08:21:11 -0700 Subject: [PATCH] .NET: dotnet sample for OTEL -> Application Insights + Grafana (#1083) * Add Azure Monitor OpenTelemetry Exporter to AgentOpenTelemetry sample * Update README to include Application Insights setup and Grafana dashboard links * Update dotnet/samples/GettingStarted/AgentOpenTelemetry/README.md Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com> --------- Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com> --- dotnet/Directory.Packages.props | 1 + .../AgentOpenTelemetry.csproj | 1 + .../AgentOpenTelemetry/Program.cs | 21 +++++++++++++---- .../AgentOpenTelemetry/README.md | 23 +++++++++++++++++-- 4 files changed, 40 insertions(+), 6 deletions(-) diff --git a/dotnet/Directory.Packages.props b/dotnet/Directory.Packages.props index 3e22804bae..16e7efe391 100644 --- a/dotnet/Directory.Packages.props +++ b/dotnet/Directory.Packages.props @@ -19,6 +19,7 @@ + diff --git a/dotnet/samples/GettingStarted/AgentOpenTelemetry/AgentOpenTelemetry.csproj b/dotnet/samples/GettingStarted/AgentOpenTelemetry/AgentOpenTelemetry.csproj index 9c063be86c..f9b7b3da2a 100644 --- a/dotnet/samples/GettingStarted/AgentOpenTelemetry/AgentOpenTelemetry.csproj +++ b/dotnet/samples/GettingStarted/AgentOpenTelemetry/AgentOpenTelemetry.csproj @@ -11,6 +11,7 @@ + diff --git a/dotnet/samples/GettingStarted/AgentOpenTelemetry/Program.cs b/dotnet/samples/GettingStarted/AgentOpenTelemetry/Program.cs index b835f4ce12..5edfcf53d9 100644 --- a/dotnet/samples/GettingStarted/AgentOpenTelemetry/Program.cs +++ b/dotnet/samples/GettingStarted/AgentOpenTelemetry/Program.cs @@ -5,6 +5,7 @@ using System.Diagnostics; using System.Diagnostics.Metrics; using Azure.AI.OpenAI; using Azure.Identity; +using Azure.Monitor.OpenTelemetry.Exporter; using Microsoft.Agents.AI; using Microsoft.Extensions.AI; using Microsoft.Extensions.DependencyInjection; @@ -23,6 +24,8 @@ const string ServiceName = "AgentOpenTelemetry"; // Configure OpenTelemetry for Aspire dashboard var otlpEndpoint = Environment.GetEnvironmentVariable("OTEL_EXPORTER_OTLP_ENDPOINT") ?? "http://localhost:4318"; +var applicationInsightsConnectionString = Environment.GetEnvironmentVariable("APPLICATIONINSIGHTS_CONNECTION_STRING"); + // Create a resource to identify this service var resource = ResourceBuilder.CreateDefault() .AddService(ServiceName, serviceVersion: "1.0.0") @@ -34,13 +37,19 @@ var resource = ResourceBuilder.CreateDefault() .Build(); // Setup tracing with resource -using var tracerProvider = Sdk.CreateTracerProviderBuilder() +var tracerProviderBuilder = Sdk.CreateTracerProviderBuilder() .SetResourceBuilder(ResourceBuilder.CreateDefault().AddService(ServiceName, serviceVersion: "1.0.0")) .AddSource(SourceName) // Our custom activity source .AddSource("*Microsoft.Agents.AI") // Agent Framework telemetry .AddHttpClientInstrumentation() // Capture HTTP calls to OpenAI - .AddOtlpExporter(options => options.Endpoint = new Uri(otlpEndpoint)) - .Build(); + .AddOtlpExporter(options => options.Endpoint = new Uri(otlpEndpoint)); + +if (!string.IsNullOrWhiteSpace(applicationInsightsConnectionString)) +{ + tracerProviderBuilder.AddAzureMonitorTraceExporter(options => options.ConnectionString = applicationInsightsConnectionString); +} + +using var tracerProvider = tracerProviderBuilder.Build(); // Setup metrics with resource and instrument name filtering using var meterProvider = Sdk.CreateMeterProviderBuilder() @@ -60,6 +69,10 @@ serviceCollection.AddLogging(loggingBuilder => loggingBuilder { options.SetResourceBuilder(ResourceBuilder.CreateDefault().AddService(ServiceName, serviceVersion: "1.0.0")); options.AddOtlpExporter(otlpOptions => otlpOptions.Endpoint = new Uri(otlpEndpoint)); + if (!string.IsNullOrWhiteSpace(applicationInsightsConnectionString)) + { + options.AddAzureMonitorLogExporter(options => options.ConnectionString = applicationInsightsConnectionString); + } options.IncludeScopes = true; options.IncludeFormattedMessage = true; })); @@ -85,7 +98,7 @@ Console.WriteLine(""" """); var endpoint = Environment.GetEnvironmentVariable("AZURE_OPENAI_ENDPOINT") ?? throw new InvalidOperationException("AZURE_OPENAI_ENDPOINT environment variable is not set."); -var deploymentName = System.Environment.GetEnvironmentVariable("AZURE_OPENAI_DEPLOYMENT_NAME") ?? "gpt-4o-mini"; +var deploymentName = Environment.GetEnvironmentVariable("AZURE_OPENAI_DEPLOYMENT_NAME") ?? "gpt-4o-mini"; // Log application startup appLogger.LogInformation("OpenTelemetry Aspire Demo application started"); diff --git a/dotnet/samples/GettingStarted/AgentOpenTelemetry/README.md b/dotnet/samples/GettingStarted/AgentOpenTelemetry/README.md index 884132baa7..3542bf5b30 100644 --- a/dotnet/samples/GettingStarted/AgentOpenTelemetry/README.md +++ b/dotnet/samples/GettingStarted/AgentOpenTelemetry/README.md @@ -4,10 +4,11 @@ This demo showcases the integration of OpenTelemetry with the Microsoft Agent Fr ## Overview -The demo consists of two main components: +The demo consists of three main components: 1. **Aspire Dashboard** - Provides a web-based interface to visualize OpenTelemetry data 2. **Console Application** - An interactive console application that demonstrates agent interactions with proper OpenTelemetry instrumentation +3. **[Optional] Application Insights** - When the agent is deployed to a production environment, Application Insights can be used to monitor the agent performance. ## Architecture @@ -25,6 +26,7 @@ graph TD - Azure OpenAI service endpoint and deployment configured - Azure CLI installed and authenticated (for Azure credential authentication) - Docker installed (for running Aspire Dashboard) +- [Optional] Application Insights and Grafana ## Configuration @@ -37,6 +39,12 @@ $env:AZURE_OPENAI_DEPLOYMENT_NAME="gpt-4o-mini" # Optional, defaults to gpt-4o- **Note**: This demo uses Azure CLI credentials for authentication. Make sure you're logged in with `az login` and have access to the Azure OpenAI resource. +### [Optional] Application Insights Setup +Set the following environment variables: +```powershell +$env:APPLICATIONINSIGHTS_CONNECTION_STRING="InstrumentationKey=XXXX;IngestionEndpoint=https://XXXX.applicationinsights.azure.com/;LiveEndpoint=https://XXXXX.livediagnostics.monitor.azure.com/;ApplicationId=XXXXX" +``` + ## Running the Demo ### Quick Start (Using Script) @@ -108,7 +116,7 @@ You: - Metrics in the **Metrics** tab showing token usage and duration - Logs in the **Structured Logs** tab with detailed information -## Viewing Telemetry Data +## Viewing Telemetry Data in Aspire Dashboard ### Traces 1. In the Aspire Dashboard, navigate to the **Traces** tab @@ -130,6 +138,17 @@ You: 2. Filter by the console application to see detailed logs 3. Logs include information about user inputs, agent responses, and any errors +## [Optional] View Application Insights data in Grafana +Besides the Aspire Dashboard and the Application Insights native UI, you can also use Grafana to visualize the telemetry data in Application Insights. There are two tailored dashboards for you to get started quickly: + +### Agent Overview dashboard +Grafana Dashboard Gallery link: +![Agent Overview dashboard](https://github.com/Azure/azure-managed-grafana/raw/main/samples/assets/grafana-af-agent.gif) + +### Workflow Overview dashboard +Grafana Dashboard Gallery link: +![Workflow Overview dashboard](https://github.com/Azure/azure-managed-grafana/raw/main/samples/assets/grafana-af-workflow.gif) + ## Key Features Demonstrated ### OpenTelemetry Integration