MCP
MCP connects A3S Code sessions to external tool servers. A stdio server can be
added to a live session, inspected, called through its registered tools, and
removed. Tools from a server are registered into the session and named
mcp__<server>__<tool>.
Add A Server
Use the object-shaped addMcp(...) API for new code. It maps directly to the
core McpServerConfig shape and avoids the positional overload's argument
ordering.
Python exposes the object-shaped API as session.add_mcp({...}).
addMcpServer(...) / add_mcp_server(...) and
addMcpServerConfig(...) / add_mcp_server_config(...) remain compatibility
aliases.
For remote servers, use a nested transport object with type: 'http' or
type: 'streamable-http'. Supply credentials from the host environment or a
secret manager, and validate the server before relying on it in production docs
or release notes.
Inspect And Remove
Ownership And Session Isolation
MCP capability discovery and live mutation have different owners:
- The agent-global manager owns servers loaded from global configuration.
- A manager supplied through Rust
SessionOptionsis an inherited, read-only capability source for that session. - Every built session owns a new private manager for live
addMcpandremoveMcpServeroperations.
Session assembly reads tool definitions from inherited sources without merging session configuration back into those managers. A locally added server can override an inherited server with the same fully qualified tool names, but only inside that session. Removing the local server reveals the inherited tools again. It does not unregister, disconnect, or otherwise mutate the global or host-owned source, and sibling sessions remain unchanged.
Delegated child agents receive the ordered capability sources so they can call
the same MCP tools without taking ownership. session.close() disconnects only
the private manager's servers. agent.close() and disconnectIdleMcp(...)
remain responsible for the agent-global manager.
For Rust, a host-supplied MCP source requires async session construction so discovery happens without blocking:
Idle Disconnect
A connected stdio MCP server holds resources — file descriptors and a
background worker — even while it sits idle. In a long-lived cluster session
those quiet servers accumulate. disconnectIdleMcp reaps them on demand: it
disconnects every global MCP server whose
last activity is older than the threshold (or that has no recorded activity),
releasing the FDs and workers, while keeping each server's registered
config.
This is an agent-level method (it operates only on the agent's global MCP manager,
backed by McpManager::disconnect_idle(threshold_ms)). It returns the list of
disconnected server names.
Rust hosts call Agent::disconnect_idle_mcp(threshold_ms) directly.
Hosts running thousands of long-lived sessions should call this periodically
from a sweeper (e.g. every 60s with a 5-min threshold). Disconnect does not
reconnect lazily: a later tool call on a disconnected server fails with
MCP server not connected: <name> until the host reconnects it. Calling
syncGlobalMcpServers(...) / sync_global_mcp_servers(...) /
SyncGlobalMCPServers(...) with the full server list reconnects every enabled
server that is not connected; entries omitted from the list are removed.
Disconnect also purges orphan timestamps: a touch()-without-connect entry
(recorded for a server that was never actually connected) is swept on each
disconnect_idle call so the activity map cannot grow unbounded over a
long-running manager's lifetime.
Security
Treat external tool servers as privileged integrations and keep secrets in environment variables.