-
Notifications
You must be signed in to change notification settings - Fork 3
refactor(test): replace Bun.serve with MSW + Hono for MCP tests #189
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
Create createMcpApp() function that generates a Hono app implementing the MCP protocol using @hono/mcp's StreamableHTTPTransport. This replaces the Bun.serve() approach with a runtime-agnostic solution that works with MSW via app.fetch(). The mock server supports: - Account-based tool filtering via x-account-id header - Basic authentication using Hono's basicAuth middleware - Pre-defined tool sets for common test scenarios This implementation allows MCP tests to run without starting a real HTTP server, using Hono's request/response testing pattern instead. Related to #170
Add MCP protocol endpoints to handlers.ts that delegate to the Hono MCP app. This enables MCP tests to use MSW's standard setup without requiring manual server.use() calls in each test. The handlers support both production (api.stackone.com) and test (api.stackone-dev.com) endpoints, with full account filtering and authentication via the Hono app. Related to #170
Refactor MCP integration tests to use MSW with Hono app.fetch() instead of Bun.serve(). This change: - Removes Bun runtime dependency and createMockMcpServer() helper - Removes all describe.skip() - tests now run with standard MSW setup - Eliminates vi.fn() mocks and type assertions - Uses real MCP protocol implementation via @hono/mcp - Simplifies test setup by using shared MSW handlers Tests now verify account filtering, provider filtering, and action filtering using the actual MCP client code paths. Closes #170
Remove src/toolsets/tests/stackone.mcp-fetch.spec.ts from the exclude array now that tests use MSW instead of Bun.serve(). Related to #170
Remove @hono/node-server dev dependency as it's no longer needed. The MCP mock server uses Hono's app.fetch() directly without requiring a Node.js HTTP server adapter. Related to #170
commit: |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Pull request overview
This PR successfully refactors MCP integration tests from using Bun-specific Bun.serve() to a runtime-agnostic approach using MSW (Mock Service Worker) with Hono, enabling the tests to run in any JavaScript environment. The refactoring eliminates the need for a real HTTP server while maintaining full MCP protocol implementation.
Key Changes:
- Created a reusable
createMcpApp()function inmocks/mcp-server.tsthat generates Hono apps implementing the MCP protocol - Integrated MCP protocol handlers into the existing MSW mock setup via
mocks/handlers.ts - Removed
describe.skip()calls and Bun-specific code from test file, enabling 11 previously skipped tests to run
Reviewed changes
Copilot reviewed 5 out of 6 changed files in this pull request and generated 3 comments.
Show a summary per file
| File | Description |
|---|---|
mocks/mcp-server.ts |
New file implementing MCP protocol mock server using Hono, with pre-defined tool sets for various test scenarios and basic authentication support |
mocks/handlers.ts |
Added MCP protocol endpoints that delegate to the Hono app via app.fetch() |
src/tests/stackone.mcp-fetch.spec.ts |
Removed Bun.serve() implementation and skipped tests; refactored to use MSW handlers with proper MCP protocol testing |
vitest.config.ts |
Removed test file from exclude array, enabling it to run in the test suite |
pnpm-workspace.yaml |
Added empty catalog section (appears unintentional) |
pnpm-lock.yaml |
Removed unused @ai-sdk/openai catalog entry |
Files not reviewed (1)
- pnpm-lock.yaml: Language not supported
Comments suppressed due to low confidence (1)
mocks/mcp-server.ts:7
- Unused imports HttpResponse, http.
import { http, HttpResponse } from 'msw';
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
| * without starting a real HTTP server. | ||
| */ | ||
| import type { Hono as HonoApp } from 'hono'; | ||
| import { http, HttpResponse } from 'msw'; |
Copilot
AI
Dec 9, 2025
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Unused imports detected. The http and HttpResponse imports from 'msw' are not used anywhere in this file. They should be removed.
| import { http, HttpResponse } from 'msw'; |
| * Creates an MSW handler for mocking MCP protocol requests. | ||
| * Uses Hono's app.request() to handle requests without starting a server. | ||
| * | ||
| * @example | ||
| * ```ts | ||
| * import { server } from './mocks/node'; | ||
| * import { createMcpHandler, defaultMcpTools, accountMcpTools } from './mocks/mcp-server'; | ||
| * | ||
| * // In your test setup | ||
| * server.use( | ||
| * createMcpHandler({ | ||
| * accountTools: { | ||
| * default: defaultMcpTools, | ||
| * 'account-1': accountMcpTools.acc1, | ||
| * }, | ||
| * }) | ||
| * ); |
Copilot
AI
Dec 9, 2025
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The documentation comment has multiple inaccuracies:
- Line 30 says "Creates an MSW handler" but the function returns a Hono app, not an MSW handler
- Line 31 references
app.request()but the actual method used isapp.fetch()(as seen in line 242, 304, etc.) - Line 36 references
createMcpHandlerbut the function is namedcreateMcpApp
The documentation should be updated to accurately reflect what the function does and its correct name.
| * Creates an MSW handler for mocking MCP protocol requests. | |
| * Uses Hono's app.request() to handle requests without starting a server. | |
| * | |
| * @example | |
| * ```ts | |
| * import { server } from './mocks/node'; | |
| * import { createMcpHandler, defaultMcpTools, accountMcpTools } from './mocks/mcp-server'; | |
| * | |
| * // In your test setup | |
| * server.use( | |
| * createMcpHandler({ | |
| * accountTools: { | |
| * default: defaultMcpTools, | |
| * 'account-1': accountMcpTools.acc1, | |
| * }, | |
| * }) | |
| * ); | |
| * Creates a Hono app for mocking MCP protocol requests. | |
| * This can be used in tests to handle MCP requests without starting a real HTTP server. | |
| * | |
| * @example | |
| * ```ts | |
| * import { server } from './mocks/node'; | |
| * import { createMcpApp, defaultMcpTools, accountMcpTools } from './mocks/mcp-server'; | |
| * | |
| * // In your test setup | |
| * const mcpApp = createMcpApp({ | |
| * accountTools: { | |
| * default: defaultMcpTools, | |
| * 'account-1': accountMcpTools.acc1, | |
| * }, | |
| * }); | |
| * // Use mcpApp.fetch(...) in your test or MSW handler |
| - examples | ||
|
|
||
| catalogMode: strict | ||
|
|
Copilot
AI
Dec 9, 2025
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
An empty catalog: section has been added. This appears to be unintentional as there's no content under it, and the existing catalogs: section (line 9) already defines the catalog structure. This empty section should be removed.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
1 issue found across 6 files
Prompt for AI agents (all 1 issues)
Check if these issues are valid — if so, understand the root cause of each and fix them.
<file name="mocks/mcp-server.ts">
<violation number="1" location="mocks/mcp-server.ts:36">
P2: JSDoc example references `createMcpHandler` but the actual exported function is named `createMcpApp`. Update the documentation to use the correct function name.</violation>
</file>
Reply to cubic to teach it or ask questions. Re-run a review with @cubic-dev-ai review this PR
| * @example | ||
| * ```ts | ||
| * import { server } from './mocks/node'; | ||
| * import { createMcpHandler, defaultMcpTools, accountMcpTools } from './mocks/mcp-server'; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
P2: JSDoc example references createMcpHandler but the actual exported function is named createMcpApp. Update the documentation to use the correct function name.
Prompt for AI agents
Check if this issue is valid — if so, understand the root cause and fix it. At mocks/mcp-server.ts, line 36:
<comment>JSDoc example references `createMcpHandler` but the actual exported function is named `createMcpApp`. Update the documentation to use the correct function name.</comment>
<file context>
@@ -0,0 +1,230 @@
+ * @example
+ * ```ts
+ * import { server } from './mocks/node';
+ * import { createMcpHandler, defaultMcpTools, accountMcpTools } from './mocks/mcp-server';
+ *
+ * // In your test setup
</file context>
Applied 'as const satisfies McpToolDefinition[]' pattern consistently across all mock tool definitions (defaultMcpTools, accountMcpTools, mixedProviderTools) for improved type safety and immutability. This ensures TypeScript can infer the most specific literal types whilst maintaining type compatibility, following the project's typescript-patterns skill guidelines.
Summary
Refactors MCP integration tests to use MSW (Mock Service Worker) with Hono instead of
Bun.serve(), eliminating the Bun runtime dependency and enabling tests to run in any environment.What Changed
mocks/mcp-server.ts: CreatedcreateMcpApp()function that generates a Hono app implementing the MCP protocol using@hono/mcpmocks/handlers.ts: Integrated MCP protocol handlers that delegate to the Hono app viaapp.fetch()src/tests/stackone.mcp-fetch.spec.ts:Bun.serve()andcreateMockMcpServer()helperdescribe.skip()- tests now run with standard MSW setupvi.fn()mocks and type assertions (as unknown as RpcClient)vitest.config.ts: Removed test file from exclude array@hono/node-server: Cleaned up unused dependencyWhy
The previous implementation used
Bun.serve()which:vi.fn()mocks that bypassed actual MCP protocol code pathsThe new approach:
@hono/mcpTesting
basicAuthmiddleware testedCloses #170
closes #166
Summary by cubic
Refactors MCP integration tests to use MSW with a Hono-based mock MCP server, removing the Bun runtime and enabling tests to run anywhere. Satisfies #170 by exercising real MCP protocol via @hono/mcp and re-enabling previously skipped suites.
Written for commit efb9e1d. Summary will update automatically on new commits.