diff --git a/app/remote-server/package.json b/app/remote-server/package.json index 207dedb..34dfe5f 100644 --- a/app/remote-server/package.json +++ b/app/remote-server/package.json @@ -29,6 +29,7 @@ "@modelcontextprotocol/sdk": "^1.12.1", "chalk": "^5.4.1", "chrome-mcp-shared": "workspace:*", + "dotenv": "^16.5.0", "eventsource": "^4.0.0", "fastify": "^5.3.2", "node-fetch": "^3.3.2", diff --git a/app/remote-server/src/index.ts b/app/remote-server/src/index.ts index c202446..c840892 100644 --- a/app/remote-server/src/index.ts +++ b/app/remote-server/src/index.ts @@ -4,11 +4,15 @@ import websocket from '@fastify/websocket'; import { pino } from 'pino'; import chalk from 'chalk'; import { randomUUID } from 'node:crypto'; +import { config } from 'dotenv'; import { isInitializeRequest } from '@modelcontextprotocol/sdk/types.js'; import { SSEServerTransport } from '@modelcontextprotocol/sdk/server/sse.js'; import { StreamableHTTPServerTransport } from '@modelcontextprotocol/sdk/server/streamableHttp.js'; import { MCPRemoteServer } from './server/mcp-remote-server.js'; +// Load environment variables from .env file +config(); + const logger = pino({ level: 'info', }); @@ -351,8 +355,8 @@ async function startServer() { const connectionWrapper = { socket: connection, send: (data: string) => connection.send(data), - on: (event: string, handler: Function) => connection.on(event, handler), - off: (event: string, handler: Function) => connection.off(event, handler), + on: (event: string, handler: (...args: any[]) => void) => connection.on(event, handler), + off: (event: string, handler: (...args: any[]) => void) => connection.off(event, handler), get readyState() { // WebSocket states: 0=CONNECTING, 1=OPEN, 2=CLOSING, 3=CLOSED return connection.readyState || 1; // Default to OPEN if not available @@ -364,7 +368,7 @@ async function startServer() { const ipAddress = req.headers['x-forwarded-for'] || req.socket?.remoteAddress || 'Unknown'; // Initialize with temporary user ID (will be updated when Chrome extension sends connection_info) - let currentUserId = `temp_user_${Date.now()}_${Math.random().toString(36).substring(2, 8)}`; + const currentUserId = `temp_user_${Date.now()}_${Math.random().toString(36).substring(2, 8)}`; // Register this connection with the Chrome tools with session management const sessionInfo = mcpServer.registerChromeExtension(connectionWrapper, currentUserId, { @@ -452,15 +456,26 @@ async function startServer() { // Start the server const port = process.env.PORT ? parseInt(process.env.PORT) : 3001; const host = process.env.HOST || '0.0.0.0'; + const domain = process.env.DOMAIN || `http://${host}:${port}`; + + // Determine the base URL for logging + const baseUrl = domain.includes('://') ? domain : `http://${host}:${port}`; + const wsProtocol = baseUrl.startsWith('https://') ? 'wss://' : 'ws://'; + const wsBaseUrl = baseUrl.replace(/^https?:\/\//, ''); try { await fastify.listen({ port, host }); console.log(chalk.green(`🚀 MCP Remote Server started successfully!`)); - console.log(chalk.blue(`📡 Server running at: http://${host}:${port}`)); - console.log(chalk.blue(`🌊 Streaming HTTP endpoint: http://${host}:${port}/mcp`)); - console.log(chalk.blue(`📡 SSE endpoint: http://${host}:${port}/sse`)); - console.log(chalk.blue(`🔌 WebSocket endpoint: ws://${host}:${port}/ws/mcp`)); - console.log(chalk.blue(`🔌 Chrome extension endpoint: ws://${host}:${port}/chrome`)); + console.log(chalk.gray(`🔧 Server Configuration:`)); + console.log(chalk.gray(` - Binding Host: ${host}`)); + console.log(chalk.gray(` - Port: ${port}`)); + console.log(chalk.gray(` - Domain: ${process.env.DOMAIN || 'Not set'}`)); + console.log(chalk.blue(`📡 Server running at: ${baseUrl}`)); + console.log(chalk.blue(`🌊 Streaming HTTP endpoint: ${baseUrl}/mcp`)); + console.log(chalk.blue(`📡 SSE endpoint: ${baseUrl}/sse`)); + console.log(chalk.blue(`🔌 WebSocket endpoint: ${wsProtocol}${wsBaseUrl}/ws/mcp`)); + console.log(chalk.blue(`🔌 Chrome extension endpoint: ${wsProtocol}${wsBaseUrl}/chrome`)); + console.log(chalk.blue(`🏥 Health check endpoint: ${baseUrl}/health`)); console.log(chalk.yellow(`💡 Use 'npm run start:server' to start the server`)); } catch (err) { console.error('Error starting server:', err); diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 6256b1d..4e26c77 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -193,6 +193,9 @@ importers: chrome-mcp-shared: specifier: workspace:* version: link:../../packages/shared + dotenv: + specifier: ^16.5.0 + version: 16.5.0 eventsource: specifier: ^4.0.0 version: 4.0.0 @@ -5086,7 +5089,7 @@ snapshots: '@eslint/config-array@0.20.0': dependencies: '@eslint/object-schema': 2.1.6 - debug: 4.4.1 + debug: 4.4.1(supports-color@5.5.0) minimatch: 3.1.2 transitivePeerDependencies: - supports-color @@ -5100,7 +5103,7 @@ snapshots: '@eslint/eslintrc@3.3.1': dependencies: ajv: 6.12.6 - debug: 4.4.1 + debug: 4.4.1(supports-color@5.5.0) espree: 10.4.0 globals: 14.0.0 ignore: 5.3.2 @@ -5660,7 +5663,7 @@ snapshots: '@typescript-eslint/types': 8.33.1 '@typescript-eslint/typescript-estree': 8.33.1(typescript@5.8.3) '@typescript-eslint/visitor-keys': 8.33.1 - debug: 4.4.1 + debug: 4.4.1(supports-color@5.5.0) eslint: 9.28.0(jiti@2.4.2) typescript: 5.8.3 transitivePeerDependencies: @@ -5670,7 +5673,7 @@ snapshots: dependencies: '@typescript-eslint/tsconfig-utils': 8.33.1(typescript@5.8.3) '@typescript-eslint/types': 8.33.1 - debug: 4.4.1 + debug: 4.4.1(supports-color@5.5.0) typescript: 5.8.3 transitivePeerDependencies: - supports-color @@ -5688,7 +5691,7 @@ snapshots: dependencies: '@typescript-eslint/typescript-estree': 8.33.1(typescript@5.8.3) '@typescript-eslint/utils': 8.33.1(eslint@9.28.0(jiti@2.4.2))(typescript@5.8.3) - debug: 4.4.1 + debug: 4.4.1(supports-color@5.5.0) eslint: 9.28.0(jiti@2.4.2) ts-api-utils: 2.1.0(typescript@5.8.3) typescript: 5.8.3 @@ -5703,7 +5706,7 @@ snapshots: '@typescript-eslint/tsconfig-utils': 8.33.1(typescript@5.8.3) '@typescript-eslint/types': 8.33.1 '@typescript-eslint/visitor-keys': 8.33.1 - debug: 4.4.1 + debug: 4.4.1(supports-color@5.5.0) fast-glob: 3.3.3 is-glob: 4.0.3 minimatch: 9.0.5 @@ -6471,10 +6474,6 @@ snapshots: dependencies: ms: 2.1.3 - debug@4.4.1: - dependencies: - ms: 2.1.3 - debug@4.4.1(supports-color@5.5.0): dependencies: ms: 2.1.3 @@ -6725,7 +6724,7 @@ snapshots: ajv: 6.12.6 chalk: 4.1.2 cross-spawn: 7.0.6 - debug: 4.4.1 + debug: 4.4.1(supports-color@5.5.0) escape-string-regexp: 4.0.0 eslint-scope: 8.4.0 eslint-visitor-keys: 4.2.1 @@ -7876,7 +7875,7 @@ snapshots: dependencies: chalk: 5.4.1 commander: 13.1.0 - debug: 4.4.1 + debug: 4.4.1(supports-color@5.5.0) execa: 8.0.1 lilconfig: 3.1.3 listr2: 8.3.3 @@ -9363,7 +9362,7 @@ snapshots: vue-eslint-parser@10.1.3(eslint@9.28.0(jiti@2.4.2)): dependencies: - debug: 4.4.1 + debug: 4.4.1(supports-color@5.5.0) eslint: 9.28.0(jiti@2.4.2) eslint-scope: 8.4.0 eslint-visitor-keys: 4.2.1 diff --git a/pnpm-workspace.yaml b/pnpm-workspace.yaml index c6998f4..f4dd015 100644 --- a/pnpm-workspace.yaml +++ b/pnpm-workspace.yaml @@ -1,3 +1,9 @@ packages: - - 'app/*' - - 'packages/*' \ No newline at end of file + - app/* + - packages/* + +ignoredBuiltDependencies: + - esbuild + - protobufjs + - sharp + - spawn-sync