#!/usr/bin/env node
// Note: Using low-level Server API instead of McpServer because we need
// fine-grained control over request handlers via setRequestHandler()
import { Server } from '@modelcontextprotocol/sdk/server/index.js';
import { StdioServerTransport } from '@modelcontextprotocol/sdk/server/stdio.js';
import { Neo4jConnection } from './neo4j/connection.js';
import { QueryEngine } from './query/engine.js';
import { registerTools } from './tools/index.js';
class Neo4jKnowledgeGraphMCP {
private server: Server;
private neo4j?: Neo4jConnection;
private queryEngine?: QueryEngine;
constructor() {
this.server = new Server(
{
name: 'neo4j-kg-mcp',
version: '1.0.0',
},
{
capabilities: {
tools: {},
resources: {},
prompts: {},
},
}
);
}
async initialize(): Promise<void> {
try {
// Initialize Neo4j connection
const neo4jUri = process.env.NEO4J_URI || 'bolt://localhost:7687';
const neo4jUser = process.env.NEO4J_USER || 'neo4j';
const neo4jPassword = process.env.NEO4J_PASSWORD || 'password';
this.neo4j = new Neo4jConnection({
uri: neo4jUri,
user: neo4jUser,
password: neo4jPassword,
});
await this.neo4j.connect();
// Initialize query engine
this.queryEngine = new QueryEngine(this.neo4j);
// Register MCP tools
registerTools(
this.server,
this.neo4j,
this.queryEngine
);
// Set up error handling
this.server.onerror = (error) => {
console.error('[MCP Error]', error);
};
// Start server
const transport = new StdioServerTransport();
await this.server.connect(transport);
console.error('[Neo4j MCP] Server initialized and ready');
} catch (error) {
console.error('[Neo4j MCP] Initialization failed:', error);
process.exit(1);
}
}
async shutdown(): Promise<void> {
if (this.neo4j) {
await this.neo4j.close();
}
}
}
// Start the server
const mcp = new Neo4jKnowledgeGraphMCP();
mcp.initialize().catch((error) => {
console.error('[Neo4j MCP] Fatal error:', error);
process.exit(1);
});
// Graceful shutdown
process.on('SIGINT', async () => {
await mcp.shutdown();
process.exit(0);
});
process.on('SIGTERM', async () => {
await mcp.shutdown();
process.exit(0);
});