Skip to main content
The LangChainAdapter converts MCP tools into DynamicStructuredTool instances from @langchain/core. The resulting array is compatible with any LangChain agent constructor that accepts a tools parameter, including createReactAgent from LangGraph.

Installation

npm install @mcp-ts/sdk @langchain/core zod
zod is a required peer dependency. The adapter uses it to convert MCP JSON Schema definitions into Zod schemas that LangChain expects.

Quick start

import { MultiSessionClient } from '@mcp-ts/sdk/server';
import { LangChainAdapter } from '@mcp-ts/sdk/adapters/langchain';

const client = new MultiSessionClient('user_123');
await client.connect();

const tools = await LangChainAdapter.getTools(client);

API reference

new LangChainAdapter(client, options?)

Creates an adapter instance. Dependencies (@langchain/core and zod) are loaded lazily on the first call to getTools().
ParameterTypeDescription
clientMCPClient | MultiSessionClientThe MCP client to source tools from.
optionsLangChainAdapterOptionsOptional configuration (see below).

adapter.getTools()

Fetches the tool list from all connected MCP servers and returns a Promise<StructuredTool[]>. Each tool is an instance of DynamicStructuredTool with:
  • name<prefix>_<toolName> (e.g., abcd1234_web_search)
  • description — the MCP tool’s description
  • schema — a Zod schema derived from the tool’s JSON Schema input definition
  • func — an async function that calls client.callTool(toolName, args)
When the underlying client is not connected, getTools() returns an empty array [] instead of throwing.

LangChainAdapter.getTools(client, options?) (static)

A convenience wrapper that creates a LangChainAdapter and immediately calls getTools().
const tools = await LangChainAdapter.getTools(client, { simplifyErrors: true });

LangChainAdapterOptions

FieldTypeDefaultDescription
prefixstringServer ID (8 chars)Namespace prefix prepended to every tool name.
simplifyErrorsbooleanfalseWhen true, catches errors in func and returns "Error: <message>" as a string instead of throwing. Useful when you want the LLM to see the error and recover.
toolRouterToolRouterUse a ToolRouter for intelligent tool filtering. Exposes only meta-tools to reduce context usage.

Complete agent example

The following example wires MCP tools into a LangGraph ReAct agent and runs a query.
import { MultiSessionClient } from '@mcp-ts/sdk/server';
import { LangChainAdapter } from '@mcp-ts/sdk/adapters/langchain';
import { createReactAgent } from '@langchain/langgraph/prebuilt';
import { ChatOpenAI } from '@langchain/openai';
import { HumanMessage } from '@langchain/core/messages';

const client = new MultiSessionClient('user_123');
await client.connect();

const tools = await LangChainAdapter.getTools(client);

const llm = new ChatOpenAI({
  model: 'gpt-4o',
  temperature: 0,
});

const agent = createReactAgent({ llm, tools });

const result = await agent.invoke({
  messages: [new HumanMessage('Find the latest changelog for TypeScript 5.5')],
});

console.log(result.messages.at(-1)?.content);

Simplified error messages

By default, errors thrown inside a tool’s func propagate as exceptions and can interrupt agent execution. Set simplifyErrors: true to catch errors and return them as plain strings — the LLM can then read the error and decide how to proceed.
const tools = await LangChainAdapter.getTools(client, { simplifyErrors: true });
// On error, func returns: "Error: connection timeout" instead of throwing
Enable simplifyErrors when building multi-step agents where a single tool failure should not abort the entire chain. The LLM will see the error message and can try an alternative approach.

Tool naming

Tool names follow the pattern <prefix>_<toolName>. The prefix defaults to the first eight characters of the server ID with hyphens removed.
abcd1234_web_search
abcd1234_read_file
Pass an explicit prefix to control the namespace:
const tools = await LangChainAdapter.getTools(client, { prefix: 'search' });
// search_web_search, search_read_file, …

Using with MultiSessionClient

When you pass a MultiSessionClient, the adapter fetches tools from every connected server concurrently and returns a flat array. Servers that fail to respond are logged and skipped.
import { MultiSessionClient } from '@mcp-ts/sdk/server';
import { LangChainAdapter } from '@mcp-ts/sdk/adapters/langchain';

const client = new MultiSessionClient('user_123');
await client.connect();

// Fetches tools from all connected servers in parallel
const tools = await LangChainAdapter.getTools(client);

Reducing context with ToolRouter

Supply a ToolRouter to expose only meta-tools when you have a large number of MCP tools and want to reduce the prompt size.
import { LangChainAdapter } from '@mcp-ts/sdk/adapters/langchain';
import { ToolRouter } from '@mcp-ts/sdk/shared';

const router = new ToolRouter(client, { strategy: 'search' });
const tools = await LangChainAdapter.getTools(client, { toolRouter: router });