48 lines
2.2 KiB
TypeScript
48 lines
2.2 KiB
TypeScript
import { Client } from '@modelcontextprotocol/sdk/client/index.js';
|
|
import { InMemoryTransport } from '@modelcontextprotocol/sdk/inMemory.js';
|
|
import { afterEach, describe, expect, it, vi } from 'vitest';
|
|
import type { RedditBotApiClient } from '../src/mcp/api-client.js';
|
|
import { createRedditBotMcpServer } from '../src/mcp/server.js';
|
|
|
|
describe('RedditBot MCP server', () => {
|
|
const closeables: Array<{ close(): Promise<void> }> = [];
|
|
|
|
afterEach(async () => {
|
|
await Promise.all(closeables.splice(0).map((item) => item.close()));
|
|
});
|
|
|
|
async function connectedClient() {
|
|
const get = vi.fn(async () => ({ status: 'operational' }));
|
|
const post = vi.fn(async () => ({ success: true, running: true }));
|
|
const server = createRedditBotMcpServer({ get, post } as unknown as RedditBotApiClient);
|
|
const client = new Client({ name: 'test-client', version: '1.0.0' });
|
|
const [clientTransport, serverTransport] = InMemoryTransport.createLinkedPair();
|
|
await Promise.all([server.connect(serverTransport), client.connect(clientTransport)]);
|
|
closeables.push(client, server);
|
|
return { client, get, post };
|
|
}
|
|
|
|
it('advertises read, control, and explicit external-send tools', async () => {
|
|
const { client } = await connectedClient();
|
|
const tools = await client.listTools();
|
|
const names = tools.tools.map((tool) => tool.name);
|
|
|
|
expect(names).toEqual(expect.arrayContaining([
|
|
'get_overview', 'list_accounts', 'list_conversations', 'start_bot', 'stop_bot',
|
|
'set_bot_running', 'trigger_sync', 'send_reply', 'start_conversation',
|
|
]));
|
|
expect(tools.tools.find((tool) => tool.name === 'get_overview')?.annotations?.readOnlyHint).toBe(true);
|
|
expect(tools.tools.find((tool) => tool.name === 'send_reply')?.annotations?.destructiveHint).toBe(true);
|
|
});
|
|
|
|
it('routes start and stop tools to the versioned control API', async () => {
|
|
const { client, post } = await connectedClient();
|
|
|
|
await client.callTool({ name: 'start_bot', arguments: {} });
|
|
await client.callTool({ name: 'stop_bot', arguments: {} });
|
|
|
|
expect(post).toHaveBeenNthCalledWith(1, '/api/v1/control/start');
|
|
expect(post).toHaveBeenNthCalledWith(2, '/api/v1/control/stop');
|
|
});
|
|
});
|