feat(mcp): load MCP servers asynchronously at startup

Boot MCP servers (npx/uvx) on a background thread instead of blocking
agent init. Built-in tools serve traffic immediately while MCP comes
online; each new agent reads whatever is ready at creation time.
Idempotent via _mcp_loaded flag — concurrent sessions never re-fork
subprocesses. Per-server failures are isolated and warmup is triggered
in app.py so loading overlaps with channel startup.
This commit is contained in:
zhayujie
2026-05-08 15:22:42 +08:00
parent 9a09e057d6
commit 307769b949
5 changed files with 133 additions and 27 deletions

View File

@@ -383,12 +383,16 @@ class AgentInitializer:
except Exception as e:
logger.warning(f"[AgentInitializer] Failed to load tool {tool_name}: {e}")
# Add MCP tools
for mcp_tool in tool_manager._mcp_tool_instances.values():
tools.append(mcp_tool)
if tool_manager._mcp_tool_instances and session_id is None:
logger.info(f"[AgentInitializer] Added {len(tool_manager._mcp_tool_instances)} MCP tool(s): "
f"{list(tool_manager._mcp_tool_instances.keys())}")
# Add MCP tools (snapshot to avoid races with the background loader)
mcp_tools_snapshot = list(tool_manager._mcp_tool_instances.items())
if mcp_tools_snapshot:
for _, mcp_tool in mcp_tools_snapshot:
tools.append(mcp_tool)
if session_id is None:
names = [name for name, _ in mcp_tools_snapshot]
logger.info(
f"[AgentInitializer] Added {len(names)} MCP tool(s): {names}"
)
# Add memory tools
if memory_tools: