diff --git a/packages/self-modification/repository-plugin/tests/repository-plugin.spec.ts b/packages/self-modification/repository-plugin/tests/repository-plugin.spec.ts index 40ae773e55..26b739677a 100644 --- a/packages/self-modification/repository-plugin/tests/repository-plugin.spec.ts +++ b/packages/self-modification/repository-plugin/tests/repository-plugin.spec.ts @@ -261,6 +261,60 @@ describe('prepared repository plugin Loader composition', () => { await ctx.fiber.dispose() }) + it('mounts and removes tools discovered from a repository MCP server', async () => { + const root = await temporaryDirectory('mcp-loader-success') + const server = join(root, 'mcp-server.mjs') + await writeFile(server, [ + "import { createInterface } from 'node:readline'", + 'const lines = createInterface({ input: process.stdin })', + 'for await (const line of lines) {', + ' const request = JSON.parse(line)', + " if (!('id' in request)) continue", + ' let result', + " if (request.method === 'initialize') {", + ' result = {', + ' protocolVersion: request.params.protocolVersion,', + ' capabilities: { tools: {} },', + " serverInfo: { name: 'repository-fixture', version: '0.0.0' },", + ' }', + " } else if (request.method === 'tools/list') {", + ' result = {', + ' tools: [{', + " name: 'proof',", + " description: 'Repository MCP proof.',", + " inputSchema: { type: 'object', properties: {} },", + ' }],', + ' }', + ' } else {', + ' result = {}', + ' }', + " process.stdout.write(`${JSON.stringify({ jsonrpc: '2.0', id: request.id, result })}\\n`)", + '}', + '', + ].join('\n')) + await writeFile(join(root, '.mcp.json'), JSON.stringify({ + mcpServers: { online: { command: process.execPath, args: [server] } }, + })) + const directory = await writePlugin(root, 'mcp-loader-success-fixture', { mcpServers: '../.mcp.json' }) + await RepositoryPlugin.prepareDshPlugin(directory) + + const ctx = new Context() + ctx.baseUrl = pathToFileURL(directory).href + '/' + await ctx.plugin(Loader) + await ctx.plugin(SystemPrompt) + await ctx.plugin(ToolRegistry) + await ctx.plugin(RepositoryPlugin) + const id = await ctx.loader.create({ + name: pathToFileURL(join(directory, RepositoryPlugin.PREPARED_ENTRY_FILENAME)).href, + }) + await ctx.loader.await() + expect(ctx.tools.get('mcp__online__proof')).toBeDefined() + + await ctx.loader.remove(id) + expect(ctx.tools.get('mcp__online__proof')).toBeUndefined() + await ctx.fiber.dispose() + }) + it('fails an MCP repository plugin load when its declared server cannot connect', async () => { const root = await temporaryDirectory('mcp-loader') await writeFile(join(root, '.mcp.json'), JSON.stringify({