Savra

The Pattern Every Multi-Agent AI System Needs

A zero-tool supervisor routing to specialised agents cut tokens per request from 8,000 to 800 and took throughput from 2 requests a minute to 12. What the pattern is, and what we later learned it costs.

Kash · FounderUpdated Aug 30, 20263 min read
Poster: "One routing pattern" over a soft pastel sky and a "Chapter 1" stamp (The Pattern Every Multi-Agent AI System Needs)
On this page

First written in February 2026, when Savra ran a multi-agent architecture. We have since moved to a single agent with dynamically activated skills, and the reasons are in Don't Go Multi-Agent, and the routing tax this pattern introduces gets its own measurement later in the series. The measurements below are real and so are the later ones; they describe two different moves. This one fixes an agent drowning in tools. The later one fixes what this fix cost us. Both are worth reading in order.

Every AI application starts the same way. One agent, and then a few more tools, and then a few more.

1User → [Single AI agent with 25+ tools] → Response

That works until it very obviously does not, and the accuracy curve past fifteen tools explains why:

Symptom

Cause

8,000+ tokens per request

Tool descriptions eat the context window

1-2 requests a minute

Rate limits, constantly

Wrong tool selected

Too many options to choose between

15+ second latency

Enormous prompts make for slow inference

We hit all four at once.

The supervisor pattern

The fix is to treat the system as a team rather than a Swiss Army knife:

1 ┌─────────────────┐
2 │ SUPERVISOR │
3 │ (router agent) │
4 │ 0 tools │
5 └────────┬────────┘
6
7 ┌───────────────────┼───────────────────┐
8 ▼ ▼ ▼
9┌─────────────────┐ ┌─────────────────┐ ┌─────────────────┐
10│ GENERAL │ │ RESEARCH │ │ CODE │
11│ Company data │ │ Web search │ │ Programming │
12│ 14 tools │ │ 10 tools │ │ 4 tools │
13└─────────────────┘ └─────────────────┘ └─────────────────┘

The load-bearing detail is that the supervisor has zero tools. It makes one decision and returns it:

1class RoutingDecision(BaseModel):
2 agent: Literal["general", "research", "code"]
3 reason: str

No tool definitions means no tool description tokens, so routing costs about a hundred tokens rather than eight thousand. The specialist is loaded only once the decision is made, and it sees only its own tools.

What a routed request looks like

Take "search the web for competitor analysis".

The supervisor reads it and answers the only question it is asked:

1{
2 "agent": "research",
3 "reason": "User needs external web search capabilities"
4}

About 100 tokens, roughly two seconds.

Then the research agent loads, and only the research agent:

1research_tools = [
2 "web_search", # search the internet
3 "crawl_url", # extract page content
4 "search_knowledge_base", # check internal docs
5 # ... 7 more
6]

Around 500 tokens of tool descriptions instead of 8,000 for all 25. The specialist completes the task and streams the response.

The whole mechanism is one dictionary and one lookup:

1AGENT_TOOLS = {
2 "router": [], # 0 tools
3 "general": [...14], # company data
4 "research": [...10], # web search
5 "code": [...4], # programming
6}
7
8def get_tools_for_agent(agent_type: str) -> list:
9 return AGENT_TOOLS.get(agent_type, [])

What it bought

Metric

Before

After

Change

Tokens per request

~8,000

~800

90% lower

Requests per minute

1-2

12-15

10x throughput

Response time

15+ sec

3-5 sec

3x faster

Rate limit errors

Constant

Rare

Stable

Those numbers held up. The system stopped falling over, responses got fast enough to use, and the bill became predictable.

What we would tell you now

Read the table above again and notice what is actually doing the work in it. It is not the supervisor. It is that no single request carries 8,000 tokens of tool descriptions any more.

That distinction took us months to see clearly, and it matters, because the supervisor brings costs of its own that this article did not price:

  • The routing call runs on every request and produces nothing the user sees.
  • A router needs conversation history to route well, so the same context is paid for twice.
  • History split across agents degrades retrieval the moment someone asks a follow-up question.

We eventually kept the dynamic loading and dropped the supervisor, which is a different architecture that gets most of the same win without the routing tax. If you are here because one agent is drowning in tools, this pattern will fix that today. Read the later articles before you decide it is where you should stop.

FAQ

What is the supervisor pattern in a multi-agent system?
A routing agent with no tools of its own that reads the request and names which specialist handles it, costing around a hundred tokens instead of the full tool catalogue.

Why does giving one agent every tool stop working?
Tool descriptions are paid for on every request. At 25 tools that was 8,000 tokens before the user said anything, with rate limits and wrong tool choices following from it.

Does the supervisor pattern have a cost of its own?
Yes. An extra model call per request, conversation context paid for twice, and history fragmented across agents. We later moved back to one agent with dynamic skills.

So is this pattern wrong?
It is a correct fix for one agent drowning in tools. The mistake is treating it as the destination. Keep the dynamic loading, question the router.

Keep reading

See if your brand sounds like itself.

Run the free 90-second Brand Genome audit. No card, just your score.