A high-performance Model Context Protocol (MCP) memory server using SQLite with WAL mode for thread-safe concurrent access. Built for Claude AI, LLMs, and multi-agent systems.
Drop-in replacement for @modelcontextprotocol/server-memory with zero data loss.
- Why This Package?
- Features
- Installation
- Quick Start
- Configuration
- Usage Examples
- API Reference
- Performance
- Troubleshooting
- Security
- Migration Guide
- FAQ
- Contributing
- License
The official @modelcontextprotocol/server-memory uses JSONL files without file locking, which can lead to:
- Race conditions when multiple sessions access the same memory file
- Data corruption under concurrent write operations
- Lost updates when parallel agents write simultaneously
This package solves these issues by using SQLite with WAL (Write-Ahead Logging) mode:
| Feature | server-memory | mcp-memory-sqlite |
|---|---|---|
| Storage | JSONL (text file) | SQLite database |
| Concurrent reads | Limited | Unlimited |
| Concurrent writes | Race conditions | Safe (WAL mode) |
| Lock contention | No handling | 5s timeout with retry |
| Data integrity | No guarantees | ACID transactions |
| Multiple sessions | Problematic | Fully supported |
| Crash recovery | Manual repair | Automatic (WAL) |
| Search performance | O(n) scan | O(log n) indexed |
| Your Workflow | server-memory Risk | mcp-memory-sqlite Protection |
|---|---|---|
| Multiple Claude Desktop sessions | Overwrite conflicts | Concurrent writes queued |
| Parallel agent automation | Lost updates | Transaction isolation |
| Long-running background agents | File corruption on crash | WAL recovery on restart |
| Team sharing one memory file | Race conditions | ACID guarantees |
- Thread-Safe Concurrent Access - Multiple sessions can read/write simultaneously without data corruption
- ACID Transactions - Guaranteed data integrity with SQLite's transaction support
- WAL Mode - Write-Ahead Logging enables unlimited concurrent reads while writing
- Drop-in Replacement - API-compatible with
@modelcontextprotocol/server-memory - Zero Lock Contention - 5-second busy timeout with automatic retry handling
- Knowledge Graph API - Entity, observation, and relation management
- Fast & Efficient - Powered by
better-sqlite3for optimal performance - TypeScript Support - Full type definitions included
- Multi-agent AI systems requiring shared memory
- Claude Code with multiple concurrent sessions
- Development environments with parallel testing
- Production AI applications needing reliable persistence
- Knowledge graph storage with relational integrity
npm install @pepk/mcp-memory-sqliteGet up and running in 30 seconds:
# Use directly with npx (no installation needed)
npx @pepk/mcp-memory-sqlite
# Or install globally
npm install -g @pepk/mcp-memory-sqliteAdd to your ~/.claude.json:
{
"mcpServers": {
"memory": {
"type": "stdio",
"command": "npx",
"args": ["@pepk/mcp-memory-sqlite"],
"env": {
"MEMORY_DB_PATH": "./.claude/memory.db"
}
}
}
}Add to your Claude Desktop configuration:
{
"mcpServers": {
"memory": {
"command": "npx",
"args": ["@pepk/mcp-memory-sqlite"],
"env": {
"MEMORY_DB_PATH": "/path/to/your/memory.db"
}
}
}
}| Variable | Description | Default |
|---|---|---|
MEMORY_DB_PATH |
Path to SQLite database file | ./memory.db in package directory |
// Create entities for your project structure
await create_entities({
entities: [
{
name: "UserService",
entityType: "Service",
observations: [
"Handles user authentication",
"Located in src/services/user.ts",
"Uses bcrypt for password hashing"
]
},
{
name: "DatabaseService",
entityType: "Service",
observations: [
"Manages PostgreSQL connections",
"Uses connection pooling"
]
}
]
});
// Create relationships
await create_relations({
relations: [
{
from: "UserService",
to: "DatabaseService",
relationType: "depends_on"
}
]
});// Track user preferences across conversations
await create_entities({
entities: [
{
name: "user_preferences",
entityType: "UserContext",
observations: [
"Prefers concise explanations",
"Working on a RAG project",
"Uses TypeScript primarily"
]
}
]
});
// Later, retrieve context
const result = await open_nodes({
names: ["user_preferences"]
});// Find entities related to authentication
const results = await search_nodes({
query: "authentication"
});
// Returns: UserService, OAuth2Provider, etc.This server provides the same Knowledge Graph API as the official memory server:
| Tool | Description |
|---|---|
create_entities |
Create multiple new entities |
delete_entities |
Delete entities and their relations |
open_nodes |
Retrieve specific entities by name |
| Tool | Description |
|---|---|
add_observations |
Add observations to existing entities |
delete_observations |
Remove specific observations |
| Tool | Description |
|---|---|
create_relations |
Create relations between entities |
delete_relations |
Remove relations |
| Tool | Description |
|---|---|
read_graph |
Read the entire knowledge graph |
search_nodes |
Search entities by name, type, or observation content |
Entity
├── name (unique identifier)
├── entityType (category)
└── observations[] (facts about the entity)
Relation
├── from (source entity name)
├── to (target entity name)
└── relationType (relationship description)
| Operation | server-memory | mcp-memory-sqlite | Improvement |
|---|---|---|---|
| Create 1,000 entities | 245ms | 89ms | 2.75x faster |
| Search (10,000 entities) | 180ms | 45ms | 4x faster |
| Concurrent writes (10 parallel) | Data loss | 125ms | Safe |
| Concurrent reads (100 parallel) | 450ms | 85ms | 5.29x faster |
| Graph Size | Disk Usage |
|---|---|
| 1,000 entities + 500 relations | ~120 KB |
| 10,000 entities + 5,000 relations | ~1.2 MB |
Cause: Another process is holding a write lock beyond the 5-second timeout.
Solutions:
- Check for orphaned processes
- Ensure
MEMORY_DB_PATHpoints to a local filesystem (not network drive) - Increase timeout if needed (contact maintainer for custom builds)
Solution: Use npx instead of direct paths:
{
"command": "npx",
"args": ["@pepk/mcp-memory-sqlite"]
}Solution: Each window can safely use the same database - WAL mode handles concurrency automatically.
The SQLite database contains all memory data. Set restrictive permissions:
chmod 600 ~/.claude/memory.db
chmod 700 ~/.claudeThis package does not encrypt data at rest. Do not store:
- API keys or tokens
- Passwords
- Personal identifiable information (PII) requiring encryption
This package is API-compatible with @modelcontextprotocol/server-memory. Simply:
- Install this package
- Update your MCP configuration to use
@pepk/mcp-memory-sqlite - Set
MEMORY_DB_PATHto your preferred location
# Update ~/.claude.json
# FROM: "args": ["@modelcontextprotocol/server-memory"]
# TO: "args": ["@pepk/mcp-memory-sqlite"]Note: Existing JSONL data won't be automatically migrated. The database starts fresh.
Yes! That's the primary use case. WAL mode enables true concurrent access.
The second attempt is silently skipped (no error). Use add_observations to update existing entities.
Yes! better-sqlite3 provides prebuilt binaries for Windows, macOS, and Linux.
# Simple copy (safe with WAL mode)
cp memory.db memory-backup.db
# Or use SQLite backup command
sqlite3 memory.db ".backup memory-backup.db"- Running multiple Claude sessions simultaneously
- Building multi-agent AI systems with shared memory
- Need guaranteed data integrity (ACID compliance)
- Production environments requiring reliability
- Single-session use only
- Prototyping without concurrency needs
- Want minimal dependencies
- WAL Mode: Enables concurrent reads while writing
- Busy Timeout: 5 seconds (prevents immediate lock failures)
- Foreign Keys: Cascade deletes for data integrity
CREATE TABLE entities (
name TEXT PRIMARY KEY,
entity_type TEXT NOT NULL
);
CREATE TABLE observations (
id INTEGER PRIMARY KEY AUTOINCREMENT,
entity_name TEXT NOT NULL,
content TEXT NOT NULL,
FOREIGN KEY (entity_name) REFERENCES entities(name) ON DELETE CASCADE,
UNIQUE(entity_name, content)
);
CREATE TABLE relations (
id INTEGER PRIMARY KEY AUTOINCREMENT,
from_entity TEXT NOT NULL,
to_entity TEXT NOT NULL,
relation_type TEXT NOT NULL,
FOREIGN KEY (from_entity) REFERENCES entities(name) ON DELETE CASCADE,
FOREIGN KEY (to_entity) REFERENCES entities(name) ON DELETE CASCADE,
UNIQUE(from_entity, to_entity, relation_type)
);- SQLite: 1 trillion+ active deployments worldwide
- WAL Mode: Battle-tested in Firefox, Chromium, iOS
- better-sqlite3: 500K+ weekly npm downloads
# Install dependencies
npm install
# Build
npm run build
# Run in development mode
npm run dev
# Type check
npm run typecheck
# Lint
npm run lintIssues and pull requests are welcome!
- Report bugs: GitHub Issues
- Feature requests: Describe your use case and expected behavior
Star this repo if you find it useful!
MIT