direct-http-server.jsā¢6.09 kB
#!/usr/bin/env node
// Direct HTTP MCP Server for Smithery
// No stdio bridge - direct HTTP implementation
import http from 'http';
const PORT = process.env.PORT || 3000;
// CORS headers
const corsHeaders = {
'Access-Control-Allow-Origin': '*',
'Access-Control-Allow-Methods': 'GET, POST, PUT, DELETE, OPTIONS',
'Access-Control-Allow-Headers': 'Content-Type, Authorization',
'Access-Control-Max-Age': '86400'
};
// MCP Server capabilities
const serverCapabilities = {
tools: {
search_local: {
name: "search_local",
description: "Search the local EGW writings database",
inputSchema: {
type: "object",
properties: {
query: {
type: "string",
description: "Search query"
},
limit: {
type: "number",
description: "Maximum number of results (default: 20)",
default: 20
}
},
required: ["query"]
}
},
get_local_book: {
name: "get_local_book",
description: "Get information about a specific book",
inputSchema: {
type: "object",
properties: {
bookId: {
type: "number",
description: "Book ID"
}
},
required: ["bookId"]
}
},
get_local_content: {
name: "get_local_content",
description: "Get content from a specific book",
inputSchema: {
type: "object",
properties: {
bookId: {
type: "number",
description: "Book ID"
},
limit: {
type: "number",
description: "Maximum number of paragraphs (default: 50)",
default: 50
},
offset: {
type: "number",
description: "Offset for pagination (default: 0)",
default: 0
}
},
required: ["bookId"]
}
},
list_local_books: {
name: "list_local_books",
description: "List all available books",
inputSchema: {
type: "object",
properties: {
language: {
type: "string",
description: "Language filter (default: 'en')",
default: "en"
},
limit: {
type: "number",
description: "Maximum number of books (default: 50)",
default: 50
}
}
}
},
get_database_stats: {
name: "get_database_stats",
description: "Get database statistics",
inputSchema: {
type: "object",
properties: {}
}
}
},
resources: {}
};
// Handle MCP requests
const handleMCPRequest = (request) => {
const { method, params, id } = request;
switch (method) {
case 'initialize':
return {
jsonrpc: '2.0',
id,
result: {
protocolVersion: '2025-06-18',
capabilities: serverCapabilities,
serverInfo: {
name: 'egw-research-server',
version: '1.0.0'
}
}
};
case 'tools/list':
return {
jsonrpc: '2.0',
id,
result: {
tools: Object.values(serverCapabilities.tools)
}
};
case 'tools/call':
// For now, return a demo response for any tool call
return {
jsonrpc: '2.0',
id,
result: {
content: [
{
type: 'text',
text: `Demo response for tool: ${params.name}\nParameters: ${JSON.stringify(params.arguments, null, 2)}`
}
]
}
};
default:
return {
jsonrpc: '2.0',
id,
error: {
code: -32601,
message: 'Method not found'
}
};
}
};
// Create HTTP server
const server = http.createServer((req, res) => {
// Set CORS headers for all responses
Object.entries(corsHeaders).forEach(([key, value]) => {
res.setHeader(key, value);
});
// Handle preflight OPTIONS request
if (req.method === 'OPTIONS') {
res.writeHead(200);
res.end();
return;
}
if (req.method === 'POST' && req.url === '/mcp') {
let body = '';
req.on('data', chunk => {
body += chunk.toString();
});
req.on('end', () => {
try {
const request = JSON.parse(body);
console.log('Received MCP request:', request.method);
// Process the request immediately
const response = handleMCPRequest(request);
res.writeHead(200, { 'Content-Type': 'application/json' });
res.end(JSON.stringify(response));
} catch (error) {
console.error('Error processing request:', error);
res.writeHead(400, { 'Content-Type': 'application/json' });
res.end(JSON.stringify({
jsonrpc: '2.0',
error: {
code: -32700,
message: 'Parse error'
},
id: null
}));
}
});
} else if (req.url === '/health') {
// Health check endpoint
res.writeHead(200, { 'Content-Type': 'application/json' });
res.end(JSON.stringify({
status: 'ok',
timestamp: new Date().toISOString(),
server: 'Direct HTTP MCP Server'
}));
} else {
res.writeHead(404, { 'Content-Type': 'application/json' });
res.end(JSON.stringify({ error: 'Not found' }));
}
});
// Handle server errors
server.on('error', (error) => {
console.error('HTTP Server error:', error);
});
// Start the server
server.listen(PORT, '0.0.0.0', () => {
console.log(`š Direct HTTP MCP Server running on port ${PORT}`);
console.log(`š” MCP Endpoint: http://0.0.0.0:${PORT}/mcp`);
console.log(`ā¤ļø Health Check: http://0.0.0.0:${PORT}/health`);
console.log(`ā
Server is ready and accepting requests immediately!`);
console.log(`ā° Timeout settings: MCP_SERVER_REQUEST_TIMEOUT=${process.env.MCP_SERVER_REQUEST_TIMEOUT || 'default'}`);
console.log(`ā° Timeout settings: INIT_TIMEOUT=${process.env.INIT_TIMEOUT || 'default'}`);
});