Skip to main content

The talker-reasoner pattern for voice agents

Splitting a voice agent across two models lets a fast primary agent keep the conversation moving, while a slower subagent works through the hard reasoning in the background.


Your voice agent needs to do something complex, whether that's researching flight options across three airlines, running a multi-step calculation, or querying a slow enterprise API. In a standard setup the user has to wait until the agent is done: two seconds of waiting, then three, until it starts to feel like a dropped call.

The fix is to stop asking a single model to be both fast and thorough, and to split the work across two of them instead: a latency-optimized model handles every conversational turn, while a slower and more capable model does the reasoning in the background. This is known as subagent delegation, but you'll also see it described as the talker-reasoner pattern or as a fast brain and slow brain architecture.

What is subagent delegationLink to this section

Subagent delegation is an architecture in which two LLMs with distinct roles work on the same conversation: one handles realtime interaction with the user, and the other performs the kind of reasoning that would take far too long to finish inside a single conversational turn.

ComponentRoleTypical model choice
Primary agentHandles every conversational turn. Listens, responds, keeps the user engaged, and decides when to delegate.Latency-optimized, such as google/gemma-4-31b-it
SubagentRuns in the background with its own chat context. Performs open-ended analysis, multi-step research, or planning.Reasoning-optimized, such as google/gemini-3.1-pro

The two are connected by an async tool. The primary agent calls that tool, which acknowledges the request immediately and releases the conversation, so the subagent's result can arrive later as a follow-up reply once it's ready.

The important consequence is that the primary agent never blocks, even when the user's request needs deep reasoning or a slow tool call, because blocking means the user has to wait. Delegating that work to a subagent means the user hears continuous speech throughout, and it leaves the primary agent free to take on another task while the subagent is still thinking.

How it worksLink to this section

Consider a research assistant that gets asked the following question: "How would switching our delivery fleet to electric vans change our operating costs over five years?"

A single agent would spend several seconds reasoning through vehicle costs, energy prices, maintenance, and residual values before it said a single word, and all of that time would essentially ignore the user. With a subagent handling the analysis instead, the flow looks like this:

StepPrimary agentSubagent
1Recognizes that the question needs real analysis and calls its analyze tool. The tool's first progress update releases the conversation, so the agent says it's looking into it and carries on.Receives the question in a focused context of its own and starts reasoning.
2Keeps talking. Answers unrelated questions, asks clarifying ones, and voices periodic filler speech during silent stretches. Its instructions forbid guessing at the delegated question.Still reasoning. The conversation history never reaches it, so the primary agent's turns stay cheap.
3Delivers the finished analysis as a follow-up reply once it's idle, naming the question it answers.Idle, ready for the next delegation.

For the full implementation, including a worked example in both Python and Node.js, see the documentation on delegating to a reasoning model.

When to use itLink to this section

Use subagent delegation when:

  • Long-running background work, such as deep research or multi-step planning which would otherwise leave the user waiting for seconds at a time.
  • A reasoning model adds real value to the answer, but its latency would break the conversation if the user had to wait for it.
  • Coaching and advisory agents need to sustain an empathetic conversation while forming a complex model of the user and their goals.
  • "Let me think about that" is a natural thing for the agent to say, and it has clarifying questions or useful context to offer while the subagent works.

When to avoid itLink to this section

Skip it when:

  • The answer has to be verified before it's spoken, as with pricing or medical guidance. A user doesn't think of these as research topics, so a brief pause while the agent confirms the answer is more appropriate than delegating in the background.
  • A single fast model is sufficient. If one model can handle the reasoning inside your latency budget, splitting the work across two of them adds complexity for no benefit.
  • The primary agent can't fill the time meaningfully. If the agent has nothing useful to say while the subagent works, the user ends up listening to filler instead of silence, which isn't much of an improvement.
  • Interactions are very short. If your calls typically last less than 30 seconds, the subagent may never finish its work before the conversation is over.

Implementing it with LiveKitLink to this section

In the Agents framework, the primary agent is an ordinary Agent running on a fast model, and the subagent is a separate LLM instance that you call through the standalone LLM interface with a chat context of its own. The only thing joining the two is an async function tool.

The subagent delegation guide has the complete implementation in both Python and Node.js, along with comparisons to the other agent patterns and best practices.

Give it a try and let us know what you're building.

Related