MCP Tools
Purpose and Scope
Model Context Protocol, or MCP, is the standard LlamaIndex uses when an agent needs to reach tools and data sources that are exposed by an external MCP server instead of by local Python functions. In practical terms, MCP tools let a LlamaIndex agent treat remote capabilities as structured callable tools. This is useful when the capability already exists outside the application process, when a team wants a language-neutral service boundary, or when tools must be shared by multiple agent hosts rather than embedded directly in one Python runtime.
The LlamaIndex repository separates this support into two layers. The integration package provides an MCP client that can connect to a server using the MCP Python client transports and authentication helpers. The core package defines the general tool contract that agents consume, including tool metadata, JSON parameter schemas, and tool outputs. Keeping those layers distinct lets MCP remain an integration option while preserving the same agent-facing shape used by function tools, query-engine tools, and other tool specs. Sources: llama-index-integrations/tools/llama-index-tools-mcp/llama_index/tools/mcp/client.py, llama-index-core/llama_index/core/tools/types.py
Relevant Source Files
llama-index-integrations/tools/llama-index-tools-mcp/llama_index/tools/mcp/client.py- Implements the MCP client integration, including transport selection, streaming log handling, OAuth token storage, and theBasicMCPClientclass built on the MCPClientSession.docs/api_reference/api_reference/tools/index.md- Defines the generated API reference entry for the core tool types exposed fromllama_index.core.tools.types.llama-index-core/llama_index/core/tools/types.py- Defines the shared tool abstractions and data structures that agents use, includingToolMetadata,ToolOutput,BaseTool,AsyncBaseTool, and adapter support.
System-to-Code Mapping
An MCP server exposes capabilities through a protocol connection; LlamaIndex needs to turn those capabilities into agent-usable tools. The integration source imports MCP client primitives such as ClientSession, stdio_client, sse_client, streamable_http_client, StdioServerParameters, OAuth support, and MCP protocol types. That tells you the client is responsible for connecting to different MCP server styles, maintaining a session, and handling protocol-level content. The same file imports LlamaIndex ChatMessage, TextBlock, and ImageBlock, which indicates that MCP interactions can be bridged into the message and content-block model used elsewhere in LlamaIndex applications. Sources: llama-index-integrations/tools/llama-index-tools-mcp/llama_index/tools/mcp/client.py
The core tool file is the contract that makes those external capabilities usable by agents. ToolMetadata records a tool description, optional name, optional Pydantic function schema, and a return_direct flag. Its get_parameters_dict() method produces the JSON-schema-like parameter dictionary that function-calling models need, and to_openai_tool() wraps the sanitized name, description, and parameters in the OpenAI tool format. This matters for MCP because a remote tool is only useful to an agent after its name, description, inputs, and output handling can be presented through the same interface as any local tool. Sources: llama-index-core/llama_index/core/tools/types.py
Execution Flow
A typical MCP tool flow starts with choosing the server endpoint or command. BasicMCPClient accepts a command_or_url, optional command arguments and environment variables for stdio servers, HTTP timeouts, optional OAuth authentication, optional sampling callback support, headers for HTTP transports, an optional tool-call log callback, and an optional httpx.AsyncClient. The integration also includes enable_sse(), a helper that detects Server-Sent Events endpoints by checking for transport=sse, a path ending in /sse, or /sse/ inside the URL path. That small helper is an important operational detail: the client can infer whether a URL should use the SSE transport rather than treating every URL the same way. Sources: llama-index-integrations/tools/llama-index-tools-mcp/llama_index/tools/mcp/client.py
Once the connection exists, tool execution follows the same loop used by LlamaIndex agents: the agent sends user input and chat history to the LLM with available tool schemas; the model either answers directly or selects one or more tools; tool results are appended to the conversation; and the model is invoked again with the updated context. MCP changes where the tool implementation lives, not the high-level control loop. That distinction is useful when designing systems: local Python functions are simplest for application-specific logic, while MCP is better for service-backed capabilities, shared data access, or tools owned by another process or platform.
API Components
| Component | Source-level role | Notes |
|---|---|---|
BasicMCPClient | MCP session client | Connects to an MCP server through command or URL inputs and supports stdio, SSE, streamable HTTP, OAuth, headers, timeouts, sampling, logging, and custom HTTP clients. |
enable_sse(command_or_url: str) -> bool | Transport helper | Detects SSE endpoints from query parameters and URL paths. |
DefaultInMemoryTokenStorage | OAuth token storage | Implements MCP TokenStorage with in-memory tokens and client information; appropriate as a default but not durable across restarts. |
StreamingHandler | Logging bridge | Sends formatted log records to a callback and can append streamed text content events. |
ToolMetadata | Core schema metadata | Provides names, descriptions, Pydantic input schemas, parameter dictionaries, and OpenAI-compatible tool definitions. |
ToolOutput | Core result model | Carries content blocks, tool name, raw input, raw output, error state, and an optional private exception. |
The generated tool API index explicitly publishes AsyncBaseTool, BaseToolAsyncAdapter, BaseTool, ToolMetadata, and ToolOutput from the core tool types module. For MCP users, those names are the stable reference points to understand what an agent expects from any tool-like object. The MCP client can be viewed as an integration that speaks the external protocol, while these core classes describe the internal shape that LlamaIndex agents, workflows, and adapters can reason about. Sources: docs/api_reference/api_reference/tools/index.md, llama-index-core/llama_index/core/tools/types.py
Implementation Details and Constraints
The in-memory OAuth storage is intentionally simple. DefaultInMemoryTokenStorage keeps an optional OAuthToken and optional OAuthClientInformationFull on the object and exposes asynchronous getters and setters for both. That design is convenient for examples and ephemeral processes, but it should not be confused with production credential persistence. If an MCP server requires OAuth and the application must survive restarts, the storage object is the extension point where durable, encrypted, or environment-specific token storage should replace the default. Sources: llama-index-integrations/tools/llama-index-tools-mcp/llama_index/tools/mcp/client.py
Tool schema quality is another important constraint. ToolMetadata.to_openai_tool() enforces a maximum description length unless skip_length_check is set, and it sanitizes names to match function-name requirements by replacing unsupported characters. If a remote MCP tool has a verbose description or a name generated from an incompatible source, the LlamaIndex tool layer is where those model-facing constraints become visible. Developers should treat descriptions and parameter schemas as part of the runtime interface, not as incidental documentation, because they directly affect tool selection and argument generation. Sources: llama-index-core/llama_index/core/tools/types.py
Minimal Usage Pattern
Install the MCP tools integration package alongside the core and model integrations your agent needs. Then create a client for the server command or URL, discover or wrap the server capabilities as tools according to the integration guide, and pass those tools to a workflow-based agent such as FunctionAgent. The shape is the same as local tool usage: the agent receives a list of tools plus an LLM, and the runtime decides when to invoke the external capability. The operational difference is that connection setup, authentication, and transport behavior now belong to the MCP client boundary.
from llama_index.tools.mcp import BasicMCPClient
client = BasicMCPClient(
command_or_url="https://example.com/mcp/sse",
timeout=30,
sse_read_timeout=300,
headers={"Authorization": "Bearer ..."},
)Use local Python tools when the callable belongs entirely to the application and can run safely in-process. Use MCP when the tool is already hosted, should be shared across hosts, needs protocol-level interoperability, or represents external services such as databases, APIs, or hosted document-processing capabilities. After connection, keep the agent-facing design discipline the same: concise names, accurate descriptions, strict input schemas, and explicit error behavior produce better tool calling than broad or ambiguous interfaces.
Next Steps
Read the general tools page next if you need the shared contract behind BaseTool, AsyncBaseTool, ToolMetadata, and ToolOutput. Then read the agents pages to see how tool schemas participate in the function-calling loop. If your MCP use case involves long-running conversations, pair this page with sessions and streaming: sessions explain where state lives across turns, while streaming explains how partial model or tool output can be surfaced to users while the agent is still running.