Repository navigation
fix: put each turn's spans in one Langfuse trace - #243
Conversation
A turn produced three unrelated Langfuse traces: the runtime's agent-request span, the Pydantic AI agent run (which carries the prompt, tool and usage data) and an agent-setup span without the session id. The runner starts agent-request without making it current, so nothing was parented to it, and agent-setup ran before any trace existed. The request trace's span is now made current for the turn, in the same way its propagated attributes already were, while it is still ended manually for async generator shutdown. create_span no longer starts a trace of its own when none is current; the setup time it recorded is now agent_setup_ms on the request trace. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
|
No actionable comments were generated in the recent review. 🎉 ℹ️ Recent review info⚙️ Run configuration
📒 Files selected for processing (3)
Included review availability: This review used your included allowance. Your plan provides up to 1 included review per hour; 0 remain after this review. 📝 WalkthroughWalkthroughRequest tracing now includes rounded agent setup duration metadata. Manual request observations are made current in OpenTelemetry until the request context exits. Span creation returns a no-op handle when no trace ID is current. ChangesRequest tracing
Priority: ⬇️ Low Estimated code review effort: 2 (Simple) | ~10 minutes Change: Bug fix Sequence Diagram(s)sequenceDiagram
participant create_request_trace
participant OpenTelemetry
participant create_span
create_request_trace->>OpenTelemetry: Make the request observation span current
create_span->>OpenTelemetry: Create a nested span under the current span
create_request_trace->>OpenTelemetry: Exit the span context and restore the prior current span
Merge Risk: ⚪ Minimal · up to This change groups each turn's spans under one trace and adds setup timing to the trace metadata. No actionable merge-blocking risk was found. Security Architecture ReviewSecurity architecture risk: 🔵 Low · up to The change primarily consolidates existing telemetry rather than expanding access permissions, tool capabilities or data collection. The normal streaming path preserves turn isolation, but exceptional shutdown and tracing-library failure behavior are not fully validated. Retained concerns Security review detailsSecurity Blast Radius
Trust Boundaries and Controls
Resilience and Maintainability Implications
Hardening Proposals
🚥 Pre-merge checks | ✅ 4 | ❌ 1❌ Failed checks (1 warning)
✅ Passed checks (4 passed)
✨ Finishing Touches 💡 1📝 Generate docstrings 💡
🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
|
@coderabbitai review |
✅ Action performedReview finished.
|
Part of #83
Problem
With Langfuse tracing enabled, one turn produced three unrelated traces:
agent-request, the runtime's own span, with the session id;invoke_agentand itschatspans from Pydantic AI, with the session id and all prompt, tool and usage data, but not underagent-request;agent-setup, a root of its own, without the session id.The runner opens
agent-requestwithset_current_observation=False, so the async generator never attaches an OpenTelemetry context it cannot detach at shutdown. Nothing was parented to it, andagent-setupran before any trace existed.Change
create_request_trace(set_current_observation=False)now makes the request span current for the turn. It is attached in the same way and place as the Langfuse propagated attributes (session, tags, metadata), which already spanned the turn'syields. The observation is still ended manually.create_spanyields a no-op when no trace is current, instead of starting a trace of its own without the session. The setup time thatagent-setuprecorded is nowagent_setup_msin the request trace's metadata.No API, event, configuration or schema change. The runtime
trace_idonassistant:final_responseis unchanged.Verification
create_runtimewithFunctionModel, Langfuse writing to an in-memory OpenTelemetry exporter and no network. Before: three trace ids. After: one trace id, withagent-requestas root andinvoke_agent→chatbeneath it, all with the session id, and no context-detach errors.create_spandoes nothing without a current trace. Both fail ondevelop.make checkfrom a clean copy without.env: 3012 passed, 1 skipped (needs Postgres); Ruff and format clean.tests/compatibility: 204 passed.Review
Independent review before opening: Codex
gpt-6-astra, high effort, separate read-only context, 1 round, 0 findings (it read the diff and ran the tracing tests). CodeRabbit follows on this PR.🤖 Generated with Claude Code
Summary by CodeRabbit