Monitoring & KQL Troubleshooting
Observe AI workloads with OpenTelemetry, Application Insights, Log Analytics and KQL: traces, tables, queries, dashboards, workbooks and alerts.
What this covers
The observability half of the secure/monitor domain is end-to-end visibility into distributed AI apps: instrument with OpenTelemetry, export to Azure Monitor Application Insights, store in a Log Analytics workspace, and analyze with KQL, dashboards, workbooks and alerts. This guide is the one-page summary; the deep notes live in the learning path Observe and troubleshoot apps on Azure.
Exam weight: Secure, monitor, and troubleshoot Azure solutions (20–25%)
Skills measured
- "Trace distributed systems by using OpenTelemetry SDKs"
- "Write KQL queries to analyze logs and metrics"
Key concepts
Definitions
| Term | Definition |
|---|---|
| OpenTelemetry | Vendor-neutral API/SDK for traces, metrics and logs |
| Azure Monitor | Azure's observability platform (metrics, logs, alerts, workbooks) |
| Application Insights | APM feature for app requests, dependencies, exceptions, traces |
| Log Analytics workspace | Shared log store queried with KQL |
| KQL | Kusto Query Language: pipeline queries over tables |
| OperationId | Correlation ID for one end-to-end request (= OTel trace ID) |
| Custom dimensions | Dynamic properties from span attributes (customDimensions classic, Properties workspace) |
| Workbook | Interactive parameterized analysis report |
| Action group | Notification and automation targets for alert rules |
Vocabulary (OTel to Azure)
| OpenTelemetry | Application Insights |
|---|---|
| Trace | Operation (OperationId / operation_Id) |
| SERVER / CONSUMER span | Request row (AppRequests) |
| CLIENT / PRODUCER / INTERNAL span | Dependency row (AppDependencies) |
| Attributes | Properties / customDimensions |
service.name | Cloud role (AppRoleName / cloud_RoleName) |
| Context propagation | Distributed tracing (traceparent) |
Standard tables
| Workspace table | Classic name | Contents |
|---|---|---|
AppRequests | requests | Incoming requests |
AppDependencies | dependencies | Outbound HTTP / DB / queue calls and internal spans |
AppTraces | traces | Log messages |
AppExceptions | exceptions | Exceptions |
AppMetrics | customMetrics | Custom metrics |
Classic names work when you query from the Application Insights resource; App* names when you query the workspace. Tables are pre-created; you never define them.
How it works
App (OTel SDK) → Azure Monitor exporter → Application Insights
→ Log Analytics tables → KQL / dashboards / alertsHands-on
Azure CLI
Create a workspace and a workspace-based Application Insights resource:
az monitor log-analytics workspace create \
--resource-group <resource-group> \
--workspace-name <workspace-name> \
--location eastus
az monitor app-insights component create \
--app <app-insights-name> \
--location eastus \
--resource-group <resource-group> \
--workspace <workspace-name>Python
Quick instrumentation:
from azure.monitor.opentelemetry import configure_azure_monitor
from opentelemetry import trace
configure_azure_monitor() # reads APPLICATIONINSIGHTS_CONNECTION_STRING
tracer = trace.get_tracer(__name__)
with tracer.start_as_current_span("generate_embedding") as span:
span.set_attribute("gen_ai.model", "text-embedding-3-large")
embedding = model.embed(text)KQL
Failures and P95 per hour for embedding requests:
AppRequests
| where TimeGenerated > ago(24h)
| where Name has "embed"
| summarize
count(),
Failures = countif(Success == false),
P95 = percentile(DurationMs, 95)
by bin(TimeGenerated, 1h)
| order by TimeGenerated descFull trace for one operation (Type = source table):
union AppRequests, AppDependencies, AppTraces, AppExceptions
| where OperationId == "abc123def456"
| project TimeGenerated, Type, Name, Message, DurationMs
| order by TimeGenerated ascExam traps
| Need | Choose |
|---|---|
| Instrument Python quickly | azure-monitor-opentelemetry + configure_azure_monitor() |
| Queue consumer joins the producer's trace | extract() context + SpanKind.CONSUMER |
| Control ingestion cost | Sampling (rate limited default, or fixed percentage) |
| Correlate rows of one request | OperationId |
| At-a-glance team health | Azure dashboard |
| Interactive investigation with parameters | Workbook |
| Alert on custom attribute or percentile | Log search alert |
| Alert without a known threshold | Smart detection |
Quick review
- Distro package (
azure-monitor-opentelemetry) configures exporter + auto-instrumentation in one call. - Spans map to
AppRequests/AppDependencies; attributes toProperties/customDimensions. - Tables such as
AppExceptionsare pre-created. - Debug with
OperationIdacross aunionof App* tables. - Use
countiffor error rate andpercentilefor latency. - Alert on error rate, P95 latency and dependency failures via metric or log search rules.
Practice
Practice: OpenTelemetry questions · Practice: KQL questions
Related study path topics:
- Explore OpenTelemetry and its role in observability
- Add the OpenTelemetry SDK to an application
- Configure spans and traces
- Export telemetry to Azure Monitor
- Debug distributed flows with trace data
- Write basic KQL queries
- Explore logs for errors and performance
- Build dashboards for app telemetry
- Create workbooks for interactive analysis
- Set alerts for app failures and anomalies