路由器 架构中,路由步骤对输入进行分类并将其定向到专门的 智能体 。当您有不同的 垂直领域 ——需要各自智能体的独立知识域时,这很有用。

主要特点

  • 路由器分解查询
  • 零个或多个专门的智能体被并行调用
  • 结果被综合成连贯的响应

何时使用

当您有不同的垂直领域(需要各自智能体的独立知识域)、需要并行查询多个来源并希望将结果综合成组合响应时,请使用路由器模式。

基本实现

路由器对查询进行分类并将其定向到适当的智能体。使用 Command 进行单智能体路由,或使用 Send 进行到多个智能体的并行扇出。
Use Command to route to a single specialized agent:
import { Command } from "@langchain/langgraph";

interface ClassificationResult {
  query: string;
  agent: string;
}

function classifyQuery(query: string): ClassificationResult {
  // Use LLM to classify query and determine the appropriate agent
  // Classification logic here
  ...
}

function routeQuery(state: typeof State.State) {
  const classification = classifyQuery(state.query);

  // Route to the selected agent
  return new Command({ goto: classification.agent });
}
For a complete implementation, see the tutorial below.

Tutorial: Build a multi-source knowledge base with routing

Build a router that queries GitHub, Notion, and Slack in parallel, then synthesizes results into a coherent answer. Covers state definition, specialized agents, parallel execution with Send , and result synthesis.

Stateless vs. stateful

Two approaches:

Stateless

Each request is routed independently—no memory between calls. For multi-turn conversations, see Stateful routers .
Router vs. Subagents : Both patterns can dispatch work to multiple agents, but they differ in how routing decisions are made:
  • Router : A dedicated routing step (often a single LLM call or rule-based logic) that classifies the input and dispatches to agents. The router itself typically doesn’t maintain conversation history or perform multi-turn orchestration—it’s a preprocessing step.
  • Subagents : An main supervisor agent dynamically decides which subagents to call as part of an ongoing conversation. The main agent maintains context, can call multiple subagents across turns, and orchestrates complex multi-step workflows.
Use a router when you have clear input categories and want deterministic or lightweight classification. Use a supervisor when you need flexible, conversation-aware orchestration where the LLM decides what to do next based on evolving context.

Stateful

For multi-turn conversations, you need to maintain context across invocations.

Tool wrapper

The simplest approach: wrap the stateless router as a tool that a conversational agent can call. The conversational agent handles memory and context; the router stays stateless. This avoids the complexity of managing conversation history across multiple parallel agents.
const searchDocs = tool(
  async ({ query }) => {
    const result = await workflow.invoke({ query });  
    return result.finalAnswer;
  },
  {
    name: "search_docs",
    description: "Search across multiple documentation sources",
    schema: z.object({
      query: z.string().describe("The search query")
    })
  }
);

// Conversational agent uses the router as a tool
const conversationalAgent = createAgent({
  model,
  tools: [searchDocs],
  prompt: "You are a helpful assistant. Use search_docs to answer questions."
});

Full persistence

If you need the router itself to maintain state, use persistence to store message history. When routing to an agent, fetch previous messages from state and selectively include them in the agent’s context—this is a lever for context engineering .
Stateful routers require custom history management. If the router switches between agents across turns, conversations may not feel fluid to end users when agents have different tones or prompts. With parallel invocation, you’ll need to maintain history at the router level (inputs and synthesized outputs) and leverage this history in routing logic. Consider the handoffs pattern or subagents pattern instead—both provide clearer semantics for multi-turn conversations.

Connect these docs to Claude, VSCode, and more via MCP for real-time answers.