# Memory MCP
<div align="center">
**Persistent Semantic Memory & Knowledge Graph for AI Assistants**
*A Model Context Protocol server providing long-term memory and knowledge graph capabilities*
[](https://opensource.org/licenses/MIT)
[](https://nodejs.org/)
[](https://www.postgresql.org/)
[](https://modelcontextprotocol.io/)
</div>
---
## π― Why This Project?
AI assistants like Claude and ChatGPT "forget" everything after a conversation ends. This project provides AI with persistent capabilities through **MCP (Model Context Protocol)**:
- **Cross-session Memory**: User preferences, conversation history, and learned facts persist across sessions
- **Semantic Retrieval**: Not just keyword matching, but understanding semantically similar content
- **Knowledge Graph**: Build relationship networks between entities for complex reasoning
```
User: "What programming languages did I say I liked before?"
AI: [calls memory_search] β Finds conversation from 3 months ago
"You mentioned liking Rust for its memory safety and Python for its simplicity."
```
---
## β¨ Core Features
### π§ Semantic Memory System
| Feature | Description |
|---------|-------------|
| **Vector Embeddings** | Aliyun DashScope `text-embedding-v3` model, 1024 dimensions |
| **HNSW Indexing** | High-performance approximate nearest neighbor search via pgvector |
| **Hybrid Search** | Weighted fusion of vector similarity (70%) + keyword matching (30%) |
| **Memory Decay** | Automatic relevance weighting based on access frequency and time |
| **LRU Cache** | Embedding cache (max 1000 entries), reduces API calls by 80%+ |
| **Version History** | Complete audit log of all changes with rollback support |
**Memory Decay Algorithm**:
```
weight = confidence Γ time_decay Γ access_bonus
= confidence Γ 0.9^(days/30) Γ (1 + min(access_countΓ0.05, 0.5))
```
### πΈοΈ Knowledge Graph Engine
| Feature | Description |
|---------|-------------|
| **Entity Management** | Create typed entity nodes with observations |
| **Relationship Tracking** | Define directed relationships (e.g., `uses`, `depends_on`) |
| **Bidirectional Relations** | Auto-create reverse relations (`A uses B` β `B is_used_by A`) |
| **Transitive Inference** | Recursive multi-hop path queries (AβBβCβD) |
| **Semantic Search** | Vector similarity search on entities |
| **Mermaid Export** | Generate visual graph diagrams |
**Supported Reverse Relation Mappings**:
```javascript
uses β is_used_by
depends_on β is_dependency_of
contains β is_contained_in
calls β is_called_by
owns β is_owned_by
creates β is_created_by
manages β is_managed_by
```
---
## ποΈ Architecture
```
ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β MCP Client (Claude Desktop / Windsurf) β
βββββββββββββββββββββββββββββ¬βββββββββββββββββββββββββββββββββββββ
β JSON-RPC 2.0 over stdio
βββββββββββββββββββββββββββββΌβββββββββββββββββββββββββββββββββββββ
β Memory MCP β
β ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β Tool Dispatcher β β
β β memory_* β memoryService graph_* β graphService β β
β ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β β
β βββββββββββββββ βββββββββββΌββββββββββ βββββββββββββββββββ β
β β Memory β β Embedding β β Graph β β
β β Service β β Service β β Service β β
β β β β βββββββββββββββ β β β β
β β β’ create β β β LRU Cache β β β β’ entities β β
β β β’ search β β β (1000 max) β β β β’ relations β β
β β β’ update β β ββββββββ¬βββββββ β β β’ transitive β β
β β β’ delete β β β β β β’ mermaid β β
β β β’ hybrid β β βΌ β β β β
β ββββββββ¬βββββββ β Aliyun DashScope β ββββββββββ¬βββββββββ β
β β β text-embedding-v3β β β
β β βββββββββββ¬ββββββββββ β β
β βββββββββββββββββββββΌββββββββββββββββββββββ β
β β β
βββββββββββββββββββββββββββββββΌβββββββββββββββββββββββββββββββββββ
β
βββββββββββββββββββββββββββββββΌββββββββββββββββββββββββββββββββββββ
β PostgreSQL 14+ with pgvector β
β ββββββββββββββ ββββββββββββββ βββββββββββββ ββββββββββββββ β
β β memories β β entities β β relations β β history β β
β β β β β β β β β β
β β β’ HNSW idx β β β’ HNSW idx β β β’ FK refs β β β’ triggers β β
β β β’ GIN tags β β β’ UNIQUE β β β’ UNIQUE β β β’ audit β β
β ββββββββββββββ ββββββββββββββ βββββββββββββ ββββββββββββββ β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
```
---
## π Quick Start
### Prerequisites
- **Node.js** >= 18.0.0
- **PostgreSQL** >= 14 with [pgvector](https://github.com/pgvector/pgvector) extension
- **Aliyun DashScope API Key** (for generating embeddings)
### Installation
```bash
# 1. Clone the repository
git clone https://github.com/YOUR_USERNAME/mcp-memory.git
cd mcp-memory
# 2. Install dependencies
npm install
# 3. Configure environment
cp .env.sample .env
# Edit .env with your database connection and API key
# 4. Initialize database
psql -c "CREATE DATABASE mcp_memory;"
psql -d mcp_memory -f migrations/init.sql
# 5. Start the server
npm start
```
### MCP Client Configuration
**Claude Desktop** (`claude_desktop_config.json`):
```json
{
"mcpServers": {
"memory": {
"command": "node",
"args": ["C:/path/to/mcp-memory/src/server.js"],
"env": {
"DATABASE_URL": "postgresql://user:pass@localhost:5432/mcp_memory",
"DASHSCOPE_API_KEY": "sk-your-api-key"
}
}
}
}
```
**Windsurf** (`mcp_config.json`):
```json
{
"mcpServers": {
"memory": {
"command": "node",
"args": ["src/server.js"],
"cwd": "C:/path/to/mcp-memory",
"env": {
"DATABASE_URL": "postgresql://user:pass@localhost:5432/mcp_memory",
"DASHSCOPE_API_KEY": "sk-your-api-key"
}
}
}
}
```
---
## π οΈ Tool Reference
### Memory Operations
#### `memory_create` - Create a Memory
```json
{
"type": "preference",
"content": { "topic": "programming", "preference": "likes Rust and Python" },
"source": "user_message",
"tags": ["programming", "preferences"],
"confidence": 0.95
}
```
| Parameter | Type | Required | Description |
|-----------|------|----------|-------------|
| `type` | string | β
| Memory type: `fact`, `preference`, `conversation`, `task`, etc. |
| `content` | object | β
| Memory content (stored as JSONB, supports any structure) |
| `source` | string | β
| Origin: `user_message`, `system_inference`, `external_api` |
| `tags` | string[] | β | Tag array for filtering |
| `confidence` | number | β
| Confidence score 0.0-1.0, affects retrieval ranking |
#### `memory_search` - Semantic Search
```json
{
"query": "what programming languages does the user like",
"type": "preference",
"tags": ["programming"],
"limit": 5
}
```
**How it works**:
1. Converts query text to 1024-dimensional vector
2. Uses HNSW index for cosine similarity calculation
3. Returns results sorted by similarity
4. Asynchronously updates access statistics (`access_count`, `last_accessed_at`)
#### `memory_update` - Update a Memory
```json
{
"id": "550e8400-e29b-41d4-a716-446655440000",
"content": { "updated": true },
"confidence": 0.8
}
```
**Note**: Automatically regenerates embedding when content changes
#### `memory_list` - List Memories
```json
{
"type": "fact",
"tags": ["important"],
"limit": 20
}
```
#### `memory_delete` - Delete a Memory
```json
{
"id": "550e8400-e29b-41d4-a716-446655440000"
}
```
**Note**: Deletion is logged to `memory_history` table
---
### Knowledge Graph Operations
#### `graph_create_entities` - Create Entities
```json
{
"entities": [
{
"name": "Memory MCP",
"entityType": "Project",
"observations": [
"Uses PostgreSQL + pgvector",
"Supports semantic search",
"MIT licensed"
]
},
{
"name": "pgvector",
"entityType": "Technology",
"observations": ["PostgreSQL vector extension", "Supports HNSW indexing"]
}
]
}
```
**Features**:
- Automatically generates embeddings for entities (batch processing)
- Same-name entities merge observations (UPSERT behavior)
#### `graph_create_relations` - Create Relations
```json
{
"relations": [
{
"from": "Memory MCP",
"to": "pgvector",
"relationType": "uses"
}
]
}
```
**Auto Bidirectional**: Creating `A uses B` automatically creates `B is_used_by A`
#### `graph_add_observations` - Add Observations
```json
{
"observations": [
{
"entityName": "Memory MCP",
"contents": ["Added hybrid search", "Supports Mermaid export"]
}
]
}
```
#### `graph_search_nodes` - Search Entities
```json
{
"query": "vector database",
"semantic": true,
"limit": 10
}
```
| Parameter | Description |
|-----------|-------------|
| `semantic: false` | Keyword matching (name, type, observations) |
| `semantic: true` | Vector similarity search |
#### `graph_open_nodes` - Open Specific Entities
```json
{
"names": ["Memory MCP", "pgvector"]
}
```
Returns entity details with all associated relations
#### `graph_read` - Read Full Graph
Returns all entities and relations. Suitable for small-scale graphs.
#### `graph_delete_*` - Delete Operations
- `graph_delete_entities`: Delete entities (cascades to relations)
- `graph_delete_relations`: Delete specific relations
- `graph_delete_observations`: Remove specific observations from entities
---
## π Database Design
### Table Schema
#### `memories` - Semantic Memory Table
| Column | Type | Description |
|--------|------|-------------|
| `id` | UUID | Primary key, auto-generated |
| `type` | TEXT | Memory type |
| `content` | JSONB | Structured content |
| `source` | TEXT | Source identifier |
| `embedding` | vector(1024) | Embedding vector |
| `tags` | TEXT[] | Tag array |
| `confidence` | FLOAT | Confidence score |
| `access_count` | INT | Access count |
| `last_accessed_at` | TIMESTAMPTZ | Last access time |
| `created_at` | TIMESTAMPTZ | Creation time |
| `updated_at` | TIMESTAMPTZ | Update time |
#### `entities` - Entity Table
| Column | Type | Description |
|--------|------|-------------|
| `id` | UUID | Primary key |
| `name` | TEXT | Entity name (unique) |
| `entity_type` | TEXT | Entity type |
| `observations` | TEXT[] | Observation array |
| `embedding` | vector(1024) | Optional, for semantic search |
#### `relations` - Relation Table
| Column | Type | Description |
|--------|------|-------------|
| `id` | UUID | Primary key |
| `from_entity` | TEXT | Source entity (FK) |
| `to_entity` | TEXT | Target entity (FK) |
| `relation_type` | TEXT | Relation type |
#### `memory_history` - History Table
| Column | Type | Description |
|--------|------|-------------|
| `memory_id` | UUID | Associated memory ID |
| `content` | JSONB | Content snapshot at change time |
| `change_type` | TEXT | `create` / `update` / `delete` |
| `previous_confidence` | FLOAT | Confidence before change |
| `new_confidence` | FLOAT | Confidence after change |
### Index Strategy
| Index | Type | Purpose |
|-------|------|---------|
| `idx_memories_embedding` | HNSW | Vector similarity search |
| `idx_memories_tags` | GIN | Tag array containment queries |
| `idx_memories_type` | B-tree | Type filtering |
| `idx_entities_embedding` | HNSW (conditional) | Entity semantic search |
| `idx_relations_from/to` | B-tree | Relation queries |
### Triggers & Functions
| Name | Type | Description |
|------|------|-------------|
| `update_memories_updated_at` | Trigger | Auto-update `updated_at` |
| `memory_history_trigger` | Trigger | Auto-log change history |
| `calculate_memory_weight()` | Function | Calculate memory decay weight |
| `update_memory_access()` | Function | Update access statistics |
| `log_memory_change()` | Function | Log change history |
---
## βοΈ Configuration
### Environment Variables
| Variable | Required | Default | Description |
|----------|----------|---------|-------------|
| `DATABASE_URL` | β
| - | PostgreSQL connection string |
| `DASHSCOPE_API_KEY` | β
| - | Aliyun DashScope API Key |
| `DASHSCOPE_API_URL` | β | `https://dashscope.aliyuncs.com/...` | Embedding API endpoint |
| `EMBEDDINGS_MODEL` | β | `text-embedding-v3` | Embedding model |
| `EMBEDDINGS_DIMENSIONS` | β | `1024` | Vector dimensions |
| `DB_MAX_POOL_SIZE` | β | `20` | Database connection pool size |
| `DB_IDLE_TIMEOUT` | β | `30000` | Idle connection timeout (ms) |
| `SEARCH_DEFAULT_LIMIT` | β | `10` | Default search result limit |
| `MCP_DEBUG_LOG_PATH` | β | `memory-debug.log` | Debug log path |
### Example `.env`
```env
# Database
DATABASE_URL=postgresql://postgres:password@localhost:5432/mcp_memory
# Aliyun DashScope
DASHSCOPE_API_KEY=sk-xxxxxxxxxxxxxxxxxxxxxxxx
# Optional
DB_MAX_POOL_SIZE=10
SEARCH_DEFAULT_LIMIT=20
```
---
## π§ Development
```bash
# Development mode (auto-reload)
npm run dev
# View debug logs
Get-Content memory-debug.log -Wait # PowerShell
tail -f memory-debug.log # Linux/Mac
# Initialize database
npm run db:init
```
### Project Structure
```
mcp-memory/
βββ src/
β βββ server.js # MCP server entry, JSON-RPC handling
β βββ config.js # Configuration loading
β βββ db/
β β βββ index.js # Database exports
β β βββ pool.js # Connection pool management
β βββ services/
β β βββ memory.js # Memory service (CRUD + search)
β β βββ graph.js # Knowledge graph service
β β βββ embedding.js # Embedding generation + LRU cache
β βββ tools/
β β βββ definitions.js # MCP tool definitions
β βββ utils/
β βββ logger.js # Logging utilities
β βββ response.js # JSON-RPC response formatting
βββ migrations/
β βββ init.sql # Database init script (idempotent)
βββ docs/
β βββ ROADMAP.md # Development roadmap
βββ .env.sample # Environment template
βββ package.json
```
---
## π Performance Optimizations
The following optimizations have been implemented (see [ROADMAP.md](docs/ROADMAP.md)):
| Optimization | Effect |
|--------------|--------|
| **Embedding Cache** | 80%+ reduction in API calls for repeated queries |
| **HNSW Indexing** | Vector search from O(n) to O(log n) |
| **Hybrid Search** | Improved recall, avoids pure semantic search misses |
| **Batch Embeddings** | Single API call when creating multiple entities |
| **Async Access Stats** | Non-blocking search responses |
---
## π License
This project is licensed under the [MIT License](LICENSE).
---
## π Acknowledgments
- [pgvector](https://github.com/pgvector/pgvector) - Vector similarity search for PostgreSQL
- [Model Context Protocol](https://modelcontextprotocol.io/) - MCP specification
- [Aliyun DashScope](https://dashscope.aliyun.com/) - Embedding API provider
---
## π€ Contributing
Issues and Pull Requests are welcome!