test(core): add unit tests for subagent MCP tool isolation

Unit tests added:
1. Tool Registry Filtering: Verified that main registry hides all '__agent__' prefixed tools.
2. Subagent Tool Inheritance: Verified that agents correctly filter out other agents' MCP tools while retaining their own.
Verified with vitest in packages/core.
This commit is contained in:
Akhilesh Kumar
2026-03-11 20:52:52 +00:00
parent 5a020e7720
commit b132791cd2
2 changed files with 75 additions and 0 deletions
@@ -2510,5 +2510,49 @@ describe('LocalAgentExecutor', () => {
mcpServers['test-server'],
);
});
it('should filter out other agents MCP tools when inheriting tools from parent registry', async () => {
const parentMcpTool1 = new DiscoveredMCPTool(
{} as unknown as CallableTool,
'__agent__OtherAgent__server1',
'tool1',
'desc1',
{},
mockConfig.getMessageBus(),
);
const parentMcpTool2 = new DiscoveredMCPTool(
{} as unknown as CallableTool,
'__agent__TestAgent__server2',
'tool2',
'desc2',
{},
mockConfig.getMessageBus(),
);
parentToolRegistry.registerTool(parentMcpTool1);
parentToolRegistry.registerTool(parentMcpTool2);
const definition = createTestDefinition();
definition.toolConfig = undefined; // trigger inheritance
vi.spyOn(mockConfig, 'getMcpClientManager').mockReturnValue({
maybeDiscoverMcpServer: vi.fn(),
} as unknown as ReturnType<typeof mockConfig.getMcpClientManager>);
const executor = await LocalAgentExecutor.create(
definition,
mockConfig,
onActivity,
);
const agentTools = (
executor as unknown as { toolRegistry: ToolRegistry }
).toolRegistry.getAllToolNames();
expect(agentTools).toContain(parentMcpTool2.asFullyQualifiedTool().name);
expect(agentTools).not.toContain(
parentMcpTool1.asFullyQualifiedTool().name,
);
});
});
});
@@ -284,6 +284,37 @@ describe('ToolRegistry', () => {
});
});
describe('subagent MCP tools filtering', () => {
it('should hide __agent__ prefixed tools when isMainRegistry is true', async () => {
const mainRegistry = new ToolRegistry(config, mockMessageBus, true);
const subagentRegistry = new ToolRegistry(config, mockMessageBus, false);
const mcpTool = createMCPTool(
'__agent__TestAgent__myServer',
'my-tool',
'description',
);
vi.spyOn(mcpTool, 'getSchema').mockReturnValue({
name: 'my_tool',
description: 'description',
} as unknown as FunctionDeclaration);
mainRegistry.registerTool(mcpTool);
subagentRegistry.registerTool(mcpTool);
const mainDeclarations =
mainRegistry.getFunctionDeclarations('test-model');
const subagentDeclarations =
subagentRegistry.getFunctionDeclarations('test-model');
expect(mainDeclarations.length).toBe(0);
expect(subagentDeclarations.length).toBe(1);
expect(subagentDeclarations[0].name).toBe(
'mcp___agent__TestAgent__myServer_my-tool',
);
});
});
describe('excluded tools', () => {
const simpleTool = new MockTool({
name: 'tool-a',