Skip to content

[bot] Anthropic: MCP connector tool calls (mcp_tool_use/mcp_tool_result) are silently dropped from tool spans #797

Description

@braintrust-bot

Summary

Anthropic's MCP connector feature (tools=[{"type": "mcp_toolset", ...}] on client.messages.create(), gated by the mcp-client-2025-11-20 beta header) returns mcp_tool_use and mcp_tool_result content blocks when Claude calls a remote MCP server's tools. The repo's Anthropic tracing does not recognize mcp_tool_use as a tool call at all, so:

  • MCP tool calls are never captured into a span (no input, no tool name, no call metadata).
  • MCP tool results are still detected (because the result-type check is suffix-based) but are logged as orphaned spans with no call context, since the corresponding call was never registered.

This is a correctness gap, not just missing-coverage: half of each MCP tool exchange is dropped and the other half is logged incompletely/incorrectly.

What is missing

In py/src/braintrust/integrations/anthropic/tracing.py:

_SERVER_TOOL_USE_TYPE = "server_tool_use"          # line 1337

def _is_server_tool_result_type(item_type: Any) -> bool:   # line 1340
    return isinstance(item_type, str) and item_type.endswith("_tool_result") and item_type != "tool_result"

_log_server_tool_spans (line 1455) pairs calls and results by walking response content:

item_type = item.get("type")
if item_type == _SERVER_TOOL_USE_TYPE:      # line 1470 — only matches "server_tool_use"
    ...
    continue

if not _is_server_tool_result_type(item_type):   # line 1481
    continue
  • The call-side check only matches the literal string "server_tool_use" (used for built-in server tools like web search / code execution). It does not match "mcp_tool_use", so mcp_tool_use blocks fall through the loop entirely and are never added to calls_by_id.
  • The result-side check (_is_server_tool_result_type) matches anything ending in _tool_result except the literal tool_result, so mcp_tool_result does pass this check — but since no matching call was ever registered, it's appended as (None, item), producing a tool span with output only and no input/tool name.

Separately, _MANAGED_AGENTS_CALL_TYPES (line 905) does include "agent.mcp_tool_use" — but that's the distinct, agent.-prefixed type used by the Managed Agents API (client.beta.agents/client.beta.sessions), not the plain mcp_tool_use/mcp_tool_result types returned by the standard Messages API's MCP connector.

Braintrust docs status: unclear / not_found

The Anthropic integration page mentions mcp_servers exactly once, as one of many request parameters captured in span metadata for the Go SDK's request-param list. It does not mention mcp_toolset, mcp_tool_use, or mcp_tool_result anywhere, and does not document any tool-span behavior specific to the MCP connector for any language. The only documented span-splitting for server-side tools is generic ("server-side tool calls ... appear as child tool spans"), described for the Java SDK, and is not confirmed to apply to MCP connector blocks specifically.

Upstream sources

  • Anthropic MCP connector docs: https://platform.claude.com/docs/en/agents-and-tools/mcp-connector — confirms the mcp_toolset tool type, the mcp-client-2025-11-20 beta header, and the exact response content block types "mcp_tool_use" and "mcp_tool_result" (example response blocks shown verbatim in the "How MCP connector tool calls work" section).

Local repo files inspected

  • py/src/braintrust/integrations/anthropic/tracing.py (full file, 1627 lines) — specifically _SERVER_TOOL_USE_TYPE (line 1337), _is_server_tool_result_type (line 1340), _log_server_tool_spans (line 1455), _MANAGED_AGENTS_CALL_TYPES (line 905)
  • py/src/braintrust/integrations/anthropic/integration.py
  • py/src/braintrust/integrations/anthropic/patchers.py

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions