Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

14 changes: 10 additions & 4 deletions src/redis/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -14,12 +14,18 @@ A Model Context Protocol server that provides access to Redis databases. This se
### Connection Errors

**ECONNREFUSED**
- **Cause**: Redis server is not running or unreachable
- **Cause**: Redis/Memurai server is not running or unreachable
- **Solution**:
- Verify Redis is running: `redis-cli ping` should return "PONG"
- Check Redis service status: `systemctl status redis` (Linux) or `brew services list` (macOS)
- Verify server is running:
- Redis: `redis-cli ping` should return "PONG"
- Memurai (Windows): `memurai-cli ping` should return "PONG"
- Check service status:
- Linux: `systemctl status redis`
- macOS: `brew services list`
- Windows: Check Memurai in Services (services.msc)
- Ensure correct port (default 6379) is not blocked by firewall
- Verify Redis URL format: `redis://hostname:port`
- If `redis://localhost:6379` fails with ECONNREFUSED, try using the explicit IP: `redis://127.0.0.1:6379`

### Server Behavior

Expand Down Expand Up @@ -57,7 +63,7 @@ To use this server with the Claude Desktop app, add the following configuration
### Docker

* when running docker on macos, use host.docker.internal if the server is running on the host network (eg localhost)
* Redis URL can be specified as an argument, defaults to "redis://localhost:6379"
* Redis URL can be specified as an argument, defaults to "redis://localhost:6379" (use "redis://127.0.0.1:6379" if localhost fails)

```json
{
Expand Down
8 changes: 4 additions & 4 deletions src/redis/package.json
Original file line number Diff line number Diff line change
@@ -1,20 +1,20 @@
{
"name": "@modelcontextprotocol/server-redis",
"version": "0.1.0",
"version": "0.1.1",
"description": "MCP server for using Redis",
"license": "MIT",
"author": "Anthropic, PBC (https://anthropic.com)",
"homepage": "https://modelcontextprotocol.io",
"bugs": "https://github.com/modelcontextprotocol/servers/issues",
"type": "module",
"bin": {
"redis": "./build/index.js"
"mcp-server-redis": "dist/index.js"
},
"files": [
"build"
"dist"
],
"scripts": {
"build": "tsc && shx chmod +x build/*.js",
"build": "tsc && shx chmod +x dist/*.js",
"prepare": "npm run build",
"watch": "tsc --watch"
},
Expand Down
75 changes: 40 additions & 35 deletions src/redis/src/index.ts
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
#!/usr/bin/env node

import { Server } from "@modelcontextprotocol/sdk/server/index.js";
import { StdioServerTransport } from "@modelcontextprotocol/sdk/server/stdio.js";
import {
Expand All @@ -19,11 +21,14 @@ const redisClient = createClient({
socket: {
reconnectStrategy: (retries) => {
if (retries >= MAX_RETRIES) {
console.error(`Maximum retries (${MAX_RETRIES}) reached. Giving up.`);
console.error(`[Redis Error] Maximum retries (${MAX_RETRIES}) reached. Giving up.`);
console.error(`[Redis Error] Connection: ${REDIS_URL}`);
return new Error('Max retries reached');
}
const delay = Math.min(Math.pow(2, retries) * MIN_RETRY_DELAY, MAX_RETRY_DELAY);
console.error(`Reconnection attempt ${retries + 1}/${MAX_RETRIES} in ${delay}ms`);
console.error(`[Redis Retry] Attempt ${retries + 1}/${MAX_RETRIES} failed`);
console.error(`[Redis Retry] Next attempt in ${delay}ms`);
console.error(`[Redis Retry] Connection: ${REDIS_URL}`);
return delay;
}
}
Expand Down Expand Up @@ -233,26 +238,27 @@ server.setRequestHandler(CallToolRequestSchema, async (request) => {
}
});

// Start the server
async function main() {
try {
// Set up Redis event handlers
redisClient.on('error', (err: Error) => {
console.error('Redis Client Error:', err);
});
// Set up Redis event handlers
redisClient.on('error', (err: Error) => {
console.error(`[Redis Error] ${err.name}: ${err.message}`);
console.error(`[Redis Error] Connection: ${REDIS_URL}`);
console.error(`[Redis Error] Stack: ${err.stack}`);
});

redisClient.on('connect', () => {
console.error(`Connected to Redis at ${REDIS_URL}`);
});
redisClient.on('connect', () => {
console.error(`[Redis Connected] Successfully connected to ${REDIS_URL}`);
});

redisClient.on('reconnecting', () => {
console.error('Attempting to reconnect to Redis...');
});
redisClient.on('reconnecting', () => {
console.error('[Redis Reconnecting] Connection lost, attempting to reconnect...');
});

redisClient.on('end', () => {
console.error('Redis connection closed');
});
redisClient.on('end', () => {
console.error('[Redis Disconnected] Connection closed');
});

async function runServer() {
try {
// Connect to Redis
await redisClient.connect();

Expand All @@ -261,26 +267,25 @@ async function main() {
await server.connect(transport);
console.error("Redis MCP Server running on stdio");
} catch (error) {
console.error("Error during startup:", error);
await cleanup();
const err = error as Error;
console.error("[Redis Fatal] Server initialization failed");
console.error(`[Redis Fatal] Error: ${err.name}: ${err.message}`);
console.error(`[Redis Fatal] Connection: ${REDIS_URL}`);
console.error(`[Redis Fatal] Stack: ${err.stack}`);
await redisClient.quit().catch(() => {});
process.exit(1);
}
}

// Cleanup function
async function cleanup() {
try {
await redisClient.quit();
} catch (error) {
console.error("Error during cleanup:", error);
}
process.exit(1);
}

// Handle process termination
process.on('SIGINT', cleanup);
process.on('SIGTERM', cleanup);
process.on('SIGINT', async () => {
await redisClient.quit().catch(() => {});
process.exit(0);
});

main().catch((error) => {
console.error("Fatal error in main():", error);
cleanup();
process.on('SIGTERM', async () => {
await redisClient.quit().catch(() => {});
process.exit(0);
});

runServer();
3 changes: 1 addition & 2 deletions src/redis/tsconfig.json
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
"target": "ES2022",
"module": "Node16",
"moduleResolution": "Node16",
"outDir": "./build",
"outDir": "./dist",
"rootDir": "./src",
"strict": true,
"esModuleInterop": true,
Expand All @@ -13,4 +13,3 @@
"include": ["src/**/*"],
"exclude": ["node_modules"]
}