Prerequisites: A working FrontMCP server with at least one tool. See Your First Tool if you need to get started.
What You’ll Get
- Automatic spans for every tool call, resource read, auth flow, and HTTP request
- Structured JSON logs with trace correlation (
trace_id,span_id) this.telemetryAPI for custom spans in your tools and plugins- Per-request log aggregation
Step 1: Install
@opentelemetry/api as the only hard dependency (~50KB). OTel SDK packages are optional peers — install only what you need.
Step 2: Enable Observability
Add theobservability field to your @FrontMcp config:
Step 3: Configure a Backend
- Console (Dev)
- OTLP (Any Backend)
- Coralogix
- Datadog
- Logz.io
- Winston
- Pino
See spans printed to your terminal — great for development:
Step 4: Use this.telemetry in Tools
Every execution context (tools, resources, prompts, agents) gets a this.telemetry API when observability is enabled. No imports, no context construction — it just works.
Step 5: Structured Logging
Whenlogging is enabled, every this.logger.info() call produces a structured JSON entry with automatic trace correlation:
Step 6: Request Log Collection
EnablerequestLogs to get a complete aggregated view of each request:
Step 7: Testing with Telemetry
Use the built-in testing utilities to verify your spans:Span Hierarchy
Every request produces a span tree like this:Attributes Reference
MCP Protocol Attributes (interoperable)
| Attribute | Example | Description |
|---|---|---|
mcp.method.name | tools/call | MCP protocol method |
mcp.session.id | a3f8b2c1d4e5f6a7 | Hashed session ID |
mcp.resource.uri | file:///data.txt | Resource URI |
mcp.component.type | tool | Component type: tool, resource, prompt, agent |
mcp.component.key | tool:get_weather | Fully qualified component key |
Standard OTel Attributes
| Attribute | Example | Description |
|---|---|---|
rpc.system | mcp | RPC system identifier |
rpc.service | my-server | Server name |
rpc.method | tools/call | RPC method |
http.request.method | POST | HTTP method |
http.response.status_code | 200 | HTTP status |
enduser.id | client-42 | Client ID from auth token |
enduser.scope | read write admin | OAuth scopes |
FrontMCP Vendor Attributes
| Attribute | Description |
|---|---|
frontmcp.scope.id | Scope identifier |
frontmcp.request.id | Unique request ID |
frontmcp.tool.name | Tool name |
frontmcp.tool.owner | Tool owner class |
frontmcp.flow.name | Flow name (e.g., tools:call-tool) |
frontmcp.transport.type | Transport: legacy-sse, streamable-http |
frontmcp.auth.mode | Auth mode: public, transparent, orchestrated |
frontmcp.session.id_hash | Privacy-safe session hash |
Best Practices
1. Use this.telemetry for custom instrumentation
1. Use this.telemetry for custom instrumentation
Don’t create spans with raw OTel API. Use
this.telemetry.withSpan() or this.telemetry.startSpan() — they automatically inherit the trace context and add base attributes.2. Add events, not child spans, for lightweight markers
2. Add events, not child spans, for lightweight markers
this.telemetry.addEvent('step-done') is cheaper than this.telemetry.startSpan('step'). Use events for milestones, spans for timed operations.3. Redact sensitive fields in structured logs
3. Redact sensitive fields in structured logs
Always configure
redactFields in production: ['password', 'token', 'secret', 'authorization', 'cookie'].4. Use OTLP for vendor integrations
4. Use OTLP for vendor integrations
The
otlp sink type works with all major platforms (Coralogix, Datadog, Logz.io, Grafana). Don’t build vendor-specific integrations.5. Don't over-instrument
5. Don't over-instrument
The auto-instrumentation covers all SDK flows. Only add
this.telemetry spans for your business logic operations (API calls, database queries, complex processing).Next Steps
Telemetry API Reference
Full API docs for TelemetryAccessor, TelemetrySpan, and testing utilities
Rate Limiting
Add rate limiting alongside observability for production readiness