Skip to content

feat: integrate Azure Monitor OTel Profiler + Code Optimizations#288

Merged
BenjaminMichaelis merged 4 commits into
mainfrom
benjaminmichaelis/azure-profiler-planning
May 15, 2026
Merged

feat: integrate Azure Monitor OTel Profiler + Code Optimizations#288
BenjaminMichaelis merged 4 commits into
mainfrom
benjaminmichaelis/azure-profiler-planning

Conversation

@BenjaminMichaelis
Copy link
Copy Markdown
Member

Summary

Integrates Azure Monitor Application Insights Profiler (via the modern OpenTelemetry path) into Microsoft.TryDotNet to enable Code Optimizations insights on the CPU-heavy Roslyn compilation workloads in POST /commands.

What changed

File Change
NuGet.config Added nuget.org source + Azure.Monitor.* / OpenTelemetry.* package source mapping (was blocked by <clear/>)
Directory.Packages.props Pinned Azure.Monitor.OpenTelemetry.AspNetCore 1.5.0 + Azure.Monitor.OpenTelemetry.Profiler 1.0.1-beta.1
src/Microsoft.TryDotNet/Microsoft.TryDotNet.csproj Added two <PackageReference> entries (no version — resolved by CPM)
src/Microsoft.TryDotNet/Program.cs Wired AddOpenTelemetry().UseAzureMonitor().AddAzureMonitorProfiler(); startup warning when connection string missing
src/Microsoft.TryDotNet/appsettings.json Added OTel logging provider section with correct category names

SDK path chosen

Azure Monitor OpenTelemetry Distro (Azure.Monitor.OpenTelemetry.AspNetCore + Azure.Monitor.OpenTelemetry.Profiler) — the canonical modern path. Classic Microsoft.ApplicationInsights.Profiler.AspNetCore was rejected (legacy, not on repo feeds).

Key decisions

  • No BYOS — Code Optimizations does not work with Bring Your Own Storage
  • Runtime image unchanged — SDK image is intentional; CSharpProjectKernel needs full dotnet toolchain
  • Connection string via env var — inject APPLICATIONINSIGHTS_CONNECTION_STRING at deploy time; never baked in
  • CPU trigger (post-deploy, Azure Portal) — 80% / 30s / 15min cooldown; required to capture Roslyn compilation spikes

Post-deploy steps required

  1. Inject APPLICATIONINSIGHTS_CONNECTION_STRING as container env var
  2. Azure Portal → Application Insights → Performance → Profiler → Triggers → CPU (80%, 30s, 15min cooldown)
  3. Confirm startup in container logs: Starting application insights profiler with connection string: ...

Reviewed by

Three agents (Sonnet, Opus 4.6, GPT-5.5) reviewed against all 5 Microsoft Learn docs. All findings addressed. Unanimous approval after fix to profiler logger category in appsettings.json.

- NuGet.config: add nuget.org source + Azure.Monitor.* / OpenTelemetry.* package source mapping
- Directory.Packages.props: pin Azure.Monitor.OpenTelemetry.AspNetCore 1.5.0 and Azure.Monitor.OpenTelemetry.Profiler 1.0.1-beta.1
- Microsoft.TryDotNet.csproj: add PackageReference for both OTel packages
- Program.cs: wire AddOpenTelemetry().UseAzureMonitor().AddAzureMonitorProfiler(); add startup warning for missing connection string
- appsettings.json: suppress OTel log noise (Default=Warning), keep Microsoft.ServiceProfiler=Information for initial validation
Add 'Azure.Monitor.OpenTelemetry.Profiler' category to OpenTelemetry
log provider section. The OTel profiler emits startup/session logs
under 'Azure.Monitor.OpenTelemetry.Profiler.*' (not 'Microsoft.ServiceProfiler'
which is the classic AI SDK category). Without this, profiler startup
confirmation logs were suppressed in Azure Monitor (still visible in
container stdout via the global Default:Information, but not exported).

Keep 'Microsoft.ServiceProfiler' as the README troubleshooting guide
recommends it for internal diagnostics from the underlying profiler agent.
Copilot AI review requested due to automatic review settings May 15, 2026 05:47
Copy link
Copy Markdown

Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR integrates Azure Monitor’s modern OpenTelemetry distro (including the Azure Monitor Profiler) into Microsoft.TryDotNet so CPU-heavy Roslyn compilation workloads (notably POST /commands) can be analyzed via Application Insights Profiler / Code Optimizations.

Changes:

  • Adds Azure Monitor OpenTelemetry distro + Profiler packages via Central Package Management.
  • Wires up AddOpenTelemetry().UseAzureMonitor().AddAzureMonitorProfiler() in Program.cs and emits a startup warning when no AI connection string is present.
  • Updates NuGet restore configuration to include nuget.org and source mapping for Azure Monitor / OpenTelemetry packages; updates logging configuration in appsettings.json.

Reviewed changes

Copilot reviewed 5 out of 5 changed files in this pull request and generated no comments.

Show a summary per file
File Description
src/Microsoft.TryDotNet/Program.cs Registers Azure Monitor OpenTelemetry + Profiler and adds a missing-connection-string startup warning.
src/Microsoft.TryDotNet/Microsoft.TryDotNet.csproj Adds package references for Azure Monitor OpenTelemetry distro + Profiler (versions resolved via CPM).
src/Microsoft.TryDotNet/appsettings.json Adds logging configuration intended to surface profiler-related categories.
NuGet.config Adds nuget.org feed and maps Azure Monitor / OpenTelemetry package IDs to it.
Directory.Packages.props Pins Azure.Monitor.OpenTelemetry.AspNetCore and prerelease Azure.Monitor.OpenTelemetry.Profiler.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

UseAzureMonitor() throws InvalidOperationException when
APPLICATIONINSIGHTS_CONNECTION_STRING is not set, which breaks CI
test runs and local dev environments without Azure Monitor configured.

Wrap the OTel registration in a null/empty check so it's a no-op
when the connection string is absent. The startup warning in Main()
already informs operators when telemetry is inactive.
Copy link
Copy Markdown

Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Copilot reviewed 5 out of 5 changed files in this pull request and generated 1 comment.

Comments suppressed due to low confidence (1)

src/Microsoft.TryDotNet/Program.cs:81

  • This repeats the APPLICATIONINSIGHTS_CONNECTION_STRING lookup already done in Main. Consider caching the value (or passing it into CreateWebApplicationAsync) to avoid duplicate env reads and to keep the conditional/warning consistent.
        if (!string.IsNullOrWhiteSpace(Environment.GetEnvironmentVariable("APPLICATIONINSIGHTS_CONNECTION_STRING")))
        {
            builder.Services.AddOpenTelemetry()
                .UseAzureMonitor()
                .AddAzureMonitorProfiler();
        }

Comment thread src/Microsoft.TryDotNet/Program.cs Outdated
Avoids silent drift if the warning check and OTel guard ever used
different strings. Both callers now use AppInsightsConnectionStringEnvVar.
@BenjaminMichaelis BenjaminMichaelis temporarily deployed to BuildAndUploadImage May 15, 2026 06:13 — with GitHub Actions Inactive
@BenjaminMichaelis BenjaminMichaelis merged commit f42824d into main May 15, 2026
11 checks passed
@BenjaminMichaelis BenjaminMichaelis deleted the benjaminmichaelis/azure-profiler-planning branch May 15, 2026 06:35
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants