Skip to content

.

4f3fab3
Select commit
Loading
Failed to load commit list.
Merged

feat(langgraph): Usage attributes on invocation spans #5211

.
4f3fab3
Select commit
Loading
Failed to load commit list.
Cursor / Cursor Bugbot completed Dec 11, 2025 in 3m 48s

Bugbot Review

Bugbot Analysis Progress (3m 51s elapsed)

✅ Gathered PR context (2s)
✅ Analyzed code changes (1s)
✅ Completed bug detection — 2 potential bugs found (3m 43s)
✅ Validation and filtering completed (1s)
✅ Posted analysis results — 2 bugs reported (4s)
✅ Analysis completed successfully (0s)

Final Result: Bugbot completed review and found 2 potential issues

Request ID: serverGenReqId_fd5c2625-3c9e-4602-841c-ec2bdb263302

Details

Bug: Usage data miscounted when PII collection disabled

When should_send_default_pii() is false or include_prompts is false, input_messages remains None. This causes _get_new_messages in _set_response_attributes to return all output messages instead of just the new ones. Since LangGraph state accumulates messages, usage data will include tokens from all messages in the response rather than only the new messages added during this invocation. The input messages need to be parsed unconditionally (at least for _get_new_messages) to correctly calculate usage data regardless of PII settings.

sentry_sdk/integrations/langgraph.py#L184-L204

# Store input messages to later compare with output
input_messages = None
if (
len(args) > 0
and should_send_default_pii()
and integration.include_prompts
):
input_messages = _parse_langgraph_messages(args[0])
if input_messages:
normalized_input_messages = normalize_message_roles(input_messages)
scope = sentry_sdk.get_current_scope()
messages_data = truncate_and_annotate_messages(
normalized_input_messages, span, scope
)
if messages_data is not None:
set_data_normalized(
span,
SPANDATA.GEN_AI_REQUEST_MESSAGES,
messages_data,
unpack=False,
)

sentry_sdk/integrations/langgraph.py#L240-L260

input_messages = None
if (
len(args) > 0
and should_send_default_pii()
and integration.include_prompts
):
input_messages = _parse_langgraph_messages(args[0])
if input_messages:
normalized_input_messages = normalize_message_roles(input_messages)
scope = sentry_sdk.get_current_scope()
messages_data = truncate_and_annotate_messages(
normalized_input_messages, span, scope
)
if messages_data is not None:
set_data_normalized(
span,
SPANDATA.GEN_AI_REQUEST_MESSAGES,
messages_data,
unpack=False,
)

Fix in Cursor Fix in Web


Bug: Usage data miscounted when PII collection disabled

When should_send_default_pii() is false or include_prompts is false, input_messages remains None. This causes _get_new_messages in _set_response_attributes to return all output messages instead of just the new ones. Since LangGraph state accumulates messages, usage data will include tokens from all messages in the response rather than only the new messages added during this invocation. The input messages need to be parsed unconditionally (at least for _get_new_messages) to correctly calculate usage data regardless of PII settings.

sentry_sdk/integrations/langgraph.py#L184-L204

# Store input messages to later compare with output
input_messages = None
if (
len(args) > 0
and should_send_default_pii()
and integration.include_prompts
):
input_messages = _parse_langgraph_messages(args[0])
if input_messages:
normalized_input_messages = normalize_message_roles(input_messages)
scope = sentry_sdk.get_current_scope()
messages_data = truncate_and_annotate_messages(
normalized_input_messages, span, scope
)
if messages_data is not None:
set_data_normalized(
span,
SPANDATA.GEN_AI_REQUEST_MESSAGES,
messages_data,
unpack=False,
)

sentry_sdk/integrations/langgraph.py#L240-L260

input_messages = None
if (
len(args) > 0
and should_send_default_pii()
and integration.include_prompts
):
input_messages = _parse_langgraph_messages(args[0])
if input_messages:
normalized_input_messages = normalize_message_roles(input_messages)
scope = sentry_sdk.get_current_scope()
messages_data = truncate_and_annotate_messages(
normalized_input_messages, span, scope
)
if messages_data is not None:
set_data_normalized(
span,
SPANDATA.GEN_AI_REQUEST_MESSAGES,
messages_data,
unpack=False,
)

Fix in Cursor Fix in Web