Add it to Claude Code
claude mcp add mcp-honojs -- node path/to/your/server.jsMake your agent remember this setup
mcp-honojs's config, env vars, and the gotchas you hit — recalled in every future Claude Code, Cursor, and Codex session.
npx conare@latestFree · one command · indexes the sessions already on disk. Set up in the browser instead →
What it does
- Simple fluent API for tools, resources, and prompts
- Supports both SSE and HTTP (JSON-RPC 2.0) transports
- Built-in session management with automatic cleanup
- Full TypeScript support for type-safe development
- Lightweight footprint suitable for edge deployments
Try it
Original README from zahidhasanaunto/mcp-honojs
mcp-honojs
Hono.js middleware for building Model Context Protocol (MCP) servers. Create MCP-compatible APIs with a simple, fluent interface — no decorators required.
Features
- Simple fluent API —
server.tool(),server.resource(),server.prompt() - Multiple transports — SSE and HTTP (JSON-RPC 2.0)
- Session management — Built-in session handling with automatic cleanup
- Type-safe — Full TypeScript support with comprehensive types
- Zero dependencies — Only peer dependency is Hono
- Lightweight — Minimal footprint, perfect for edge deployments
Installation
npm install mcp-honojs hono
Quick Start
import { Hono } from 'hono';
import { McpServer } from 'mcp-honojs';
// Create MCP server
const mcp = new McpServer({
name: 'my-mcp-server',
version: '1.0.0',
});
// Register a tool
mcp.tool(
{
name: 'greet',
description: 'Greet someone by name',
inputSchema: {
type: 'object',
properties: {
name: { type: 'string', description: 'Name to greet' },
},
required: ['name'],
},
},
async (args) => {
return {
content: [{ type: 'text', text: `Hello, ${args.name}!` }],
};
}
);
// Create Hono app and attach MCP
const app = new Hono();
mcp.attach(app);
export default app;
Visit your endpoints:
- SSE:
GET /sse - HTTP:
POST /mcp
API Reference
McpServer
Constructor
const mcp = new McpServer(options: McpServerOptions);
Options:
interface McpServerOptions {
name: string; // Server name
version: string; // Server version
session?: {
timeout?: number; // Session timeout in ms (default: 30min)
cleanupInterval?: number; // Cleanup interval in ms (default: 5min)
maxSessions?: number; // Max concurrent sessions (default: 1000)
};
}
Methods
tool(options, handler) — Register a tool
mcp.tool(
{
name: 'add',
description: 'Add two numbers',
inputSchema: {
type: 'object',
properties: {
a: { type: 'number' },
b: { type: 'number' },
},
required: ['a', 'b'],
},
},
async (args, context) => {
return {
content: [
{ type: 'text', text: `Result: ${args.a + args.b}` }
],
};
}
);
resource(options, handler) — Register a resource
mcp.resource(
{
uri: 'example://data',
name: 'example-data',
description: 'Example data resource',
mimeType: 'application/json',
},
async (uri, context) => {
return {
contents: [
{
uri,
mimeType: 'application/json',
text: JSON.stringify({ data: 'example' }),
},
],
};
}
);
prompt(options, handler) — Register a prompt
mcp.prompt(
{
name: 'welcome',
description: 'Welcome prompt',
arguments: [
{ name: 'username', description: 'User name', required: true }
],
},
async (args, context) => {
return {
messages: [
{
role: 'user',
content: {
type: 'text',
text: `Welcome, ${args.username}!`,
},
},
],
};
}
);
attach(app, transportOptions?) — Attach transports to Hono app
mcp.attach(app, {
ssePath: '/sse', // SSE endpoint (default: /sse)
httpPath: '/mcp', // HTTP endpoint (default: /mcp)
});
sseMiddleware(path?) — Get SSE middleware
app.use(mcp.sseMiddleware('/custom-sse'));
httpMiddleware(path?) — Get HTTP middleware
app.use(mcp.httpMiddleware('/custom-mcp'));
Context
Both tool and resource handlers receive a McpContext object:
interface McpContext {
sessionId?: string; // Current session ID
honoContext?: Context; // Hono request context
metadata?: Record<string, any>; // Custom metadata
}
Access the Hono context for request details:
mcp.tool({ /* ... */ }, async (args, context) => {
const userAgent = context.honoContext?.req.header('user-agent');
// ...
});
Type Definitions
Tool Types
interface ToolResult {
content: ToolResultContent[];
isError?: boolean;
}
interface ToolResultContent {
type: 'text' | 'image' | 'resource';
text?: string;
data?: string; // Base64 for images
mimeType?: string;
uri?: string; // For resource references
}
Resource Types
interface ResourceResult {
contents: ResourceContent[];
}
interface ResourceContent {
uri: string;
mimeType?: string;
text?: string;
blob?: string; // Base64 encoded binary
}
Prompt Types
interface PromptResult {
description?: string;
messages: PromptMessage[];
}
interface PromptMessage {
role: 'user' | 'assistant';
content: PromptMess