Skip to content

Give agents MCP and extension tools through a tool twin - #120

Merged
mavam merged 2 commits into
mainfrom
topic/tool-twin
Nov 2, 2026
Merged

mavam merged 2 commits into
mainfrom
topic/tool-twin

Conversation

@mavam

@mavam mavam commented Oct 31, 2026 •

Copy link
Copy Markdown
Owner

🔍 Problem

Agents can't use MCP servers or tools from other extensions, such as Webfox's web search. Pi runs those tools only inside its own sessions, it has no durable version of them, and we can't change Pi.

🛠️ Solution

  • Tool twin: pi-agents runs a headless Pi session in the same process with Pi's public SDK (createAgentSession, DefaultResourceLoader, createMcpExtension). It loads only Pi's MCP extension and the packages listed in piAgents.twinExtensions, and shares Pi's mcp.json and sign-ins.
  • Proxies: one durable extension holds a proxy per twin tool, and every agent selects it.
    • MCP tools Pi declares only to codemode stay deferred. Their namespaces feed agents' codemode, and a prompt section lists them, as Pi's mcp_servers section does.
    • Calls run the twin's tool_call hooks first, so MCP waits until the server is ready.
    • A call is replayed after a crash only for tools marked readOnlyHint or idempotentHint.
  • Lifecycle: the twin opens before the harness and waits up to 10 s for servers, so tool calls that resume find their tools. Servers that connect later reach agents at their next request. It is skipped when there's no mcp.json and nothing is shared.
  • Selection: agents now store a { remove } tool filter instead of naming their tools, so twin tools that appear later reach them. Naming a twin tool in an allowlist changes nothing.
  • Docs: the README drops the caution and shows the twin inside pi-agents in the architecture diagram.

💬 Review

  • Stacked on Adopt the next pi-durable: crash-ended runs, continue, turn limits, and windowed views #119. Checked end to end on the published Pi 1.5.0 too: an agent found the Cloudflare docs server and called web_search from one script.
  • Verified end to end against Pi built from upstream main, with your 11 HTTP MCP servers (309 tools) and npm:webfox. An agent found the Cloudflare docs server through the namespace section and answered from it; another called an MCP tool and web_search from one script. Opening the twin took about 0.5 s, plus about 2 s until the servers were ready.
  • The twin's own connections duplicate the session's: one more HTTP session per server, one more child process per stdio server.
  • Known gaps:
    • Agents created before this change keep their named tools and get no twin tools.
    • Servers that extensions register at runtime aren't mirrored.
    • Scripts get the text of results, not structuredContent: pi-durable strictly validates structured output against a declared schema, and Pi doesn't.
    • Twin tools render as generic cards in the attach view.
    • /mcp changes reach agents after a restart.
  • Removing the twin later means deleting src/host/twin*.ts and its call in the harness.

@mavam
mavam marked this pull request as ready for review November 2, 2026 13:12
Base automatically changed from topic/durable-next to main November 2, 2026 13:21
mavam added 2 commits November 2, 2026 14:21
A headless Pi session in the same process loads Pi's own MCP extension and
the packages listed in piAgents.twinExtensions. Every agent selects one
extension of proxies for its tools; tools MCP declares only to codemode stay
deferred, with their namespaces in codemode and a prompt section listing
them. Agents now remove the agent tools they lack instead of naming the
ones they have, so the twin's tools reach them as servers connect.
@mavam
mavam merged commit 0f28383 into main Nov 2, 2026
3 checks passed
@mavam
mavam deleted the topic/tool-twin branch November 2, 2026 13:23
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant