Episodic memory system for AI agents with vector search, exposed via MCP server.
Verified Performance: 65.9% R@10 on LoCoMo benchmark β’ Up to 74% on long conversations
Note: This project was developed using Kiro CLI - an AI-powered development assistant.
Agent Memory RS stores interaction episodes with vector embeddings and retrieves them using cosine similarity search. Exposed as an MCP server with learn and search tools.
- Episode Storage β Events stored with vector embeddings (BGE-Small, 384 dims)
- Vector Search β Cosine distance retrieval on episode embeddings
- BM25 Search β Keyword search with proper IDF calculation
- MCP Server β Learn and search tools via Model Context Protocol (stdio)
- Workspace Isolation β Separate SQLite databases per workspace (
~/.memory-rs/workspaces/) - Multiple Models β BGE-Small (default), Nomic (long context), MiniLM (fastest)
βββββββββββββββββββββββββββ
β MCP Client β
βββββββββββββ¬ββββββββββββββ
β stdio (JSON-RPC)
βββββββββββββΌββββββββββββββ
β MCP Server β
β βββββββββββ ββββββββββ β
β β learn β β search β β
β ββββββ¬βββββ βββββ¬βββββ β
βββββββββΌβββββββββββΌβββββββ
βββββββββΌβββββββββββΌβββββββ
β EpisodicMemoryStore β
β ββββββββββββββββββββ β
β β SQLite + vec0 β β
β β (episodes table) β β
β β (vector index) β β
β ββββββββββββββββββββ β
βββββββββββββββββββββββββββ
git clone https://github.com/yourusername/agent-memory-rs
cd agent-memory-rs
cargo build --release# Start the server
./target/release/agent-memory-mcp my-workspaceConfigure your AI assistant:
{
"mcpServers": {
"agent-memory": {
"command": "/path/to/agent-memory-mcp",
"args": ["my-workspace"],
"env": {
"MEMORY_MODEL": "bge"
}
}
}
}Configuration Options:
| Environment Variable | Values | Default | Description |
|---|---|---|---|
MEMORY_MODEL |
bge, nomic, minilm |
bge |
Embedding model to use |
Model Selection:
bge(BGE-Small) - Best quality/speed balance, 384 dims, ~33MB β Recommendednomic(Nomic Embed) - Best for long context (8K tokens), 768 dims, ~138MBminilm(MiniLM) - Fastest, 384 dims, ~23MB
Available MCP Tools:
@memory/learn- Store new memories@memory/search- Search across all memory types
Workspace Isolation: Each workspace has its own isolated database. Memories are NOT shared between workspaces.
Database Location:
~/.memory-rs/workspaces/
βββ prime-sde-workspace/
β βββ memory.db # All memories for this workspace
βββ my-project/
β βββ memory.db # Separate isolated memories
βββ default/
βββ memory.db # Default workspace
Workspace Naming:
- Specified in MCP server args:
["workspace-name"] - If no arg provided, auto-generates from current directory:
<hash>-<dirname>- Example:
/path/to/workspace/myprojectβa1b2c3d4-myproject - Hash ensures uniqueness across different paths with same directory name
- Example:
- Falls back to "default" if directory name unavailable
Data Persistence:
- β Survives Kiro restarts (stored in home directory)
- β Survives repo deletion (not stored in repo)
- β Deleting
~/.memory-rs/loses all memories - β No cross-workspace knowledge sharing (by design)
Model Cache: Models are downloaded once and cached in the standard HuggingFace cache:
~/.cache/huggingface/hub/
βββ models--BAAI--bge-small-en-v1.5/
βββ models--nomic-ai--nomic-embed-text-v1/
βββ models--sentence-transformers--all-MiniLM-L6-v2/
# Create workspace
cargo run --bin agent-memory-cli workspace create --name my-project --path /path/to/project
# List workspaces
cargo run --bin agent-memory-cli workspace list
# Store episode
cargo run --bin agent-memory-cli store --workspace 1 --type user_query --context "How do I use Rust?" --outcome "Provided tutorial" --valence 0.8
# Query memories
cargo run --bin agent-memory-cli query --workspace 1 "rust programming" --limit 10
# Check system health
cargo run --bin agent-memory-cli stats --workspace 1use agent_memory_rs::services::MemoryManager;
use agent_memory_rs::storage::Database;
// Initialize
let db = Database::new("memory.db")?;
let manager = MemoryManager::new(db.clone());
// Store episode
manager.store_episode(
1, // workspace_id
"user_query",
serde_json::json!({"query": "How do I use Rust?"}),
Some("Provided Rust tutorial"),
Some(0.8), // positive valence
)?;
// Search memories
let results = manager.retrieve("rust programming", 1, 10)?;- Getting Started Guide - Complete API reference and examples
- Design Rationale - Design decisions, formulas, algorithms, and research
The repository includes a skill for AI agents using Kiro CLI:
Location: skill/agent-memory/SKILL.md
Add to your agent configuration:
{
"resources": [
"skill:///path/to/agent-memory-rs/skill/agent-memory/SKILL.md"
]
}What the skill provides:
- When to use
@memory/learnvs@memory/search - Best practices for memory management
- Importance scoring and tagging strategies
- Workflow patterns for common scenarios
- Configuration options and troubleshooting
The skill is loaded on-demand, providing guidance only when needed without consuming context at startup.
MemoryManager (Facade)
βββ EpisodicMemoryStore - Raw interaction events
βββ HybridRetrievalEngine - BM25 + Vector search
Built with SOLID principles:
- Core traits (MemoryStore, MemoryRetriever, EmbeddingService)
- Dependency injection throughout
- Thread-safe Database pattern:
Arc<Mutex<Connection>>
# Run all tests
cargo test
# Run integration tests only
cargo test --test '*'
# Run with output
cargo test -- --nocaptureTest Coverage: 29 tests covering full lifecycle
- Episode Storage: ~5ms
- Hybrid Search: ~20ms (10k memories)
Based on modern AI agent memory research:
- Memory Management for Long-Running Agents (2025, arXiv:2509.25250v1)
- Episodic Memory for RAG (2024, arXiv:2511.07587v1)
- MIRIX Multi-Agent Memory (2024)
- Episodic Memory Properties (2025, arXiv:2502.06975v1)
- Procedural Memory Is Not All You Need (2025, arXiv:2505.03434v1)
See Design Rationale for complete references.
- Language: Rust 1.70+
- Database: SQLite with
sqlite-vecextension - Embeddings: BERT MiniLM (384 dimensions) via Candle
- Vector Search: Cosine distance with HNSW-like indexing
- Interface: MCP (Model Context Protocol)
Licensed under either of:
- Apache License, Version 2.0 (LICENSE-APACHE)
- MIT license (LICENSE-MIT)
at your option.
Contributions welcome! Please read our contributing guidelines first.
Inspired by cognitive science research on human memory systems and modern AI agent architectures.
memory-cli prune --workspace 1 --dry-run
## π§ͺ Testing
```bash
# Run all tests
cargo test
# Run integration tests only
cargo test --test '*'
# Run with output
cargo test -- --nocapture
Test Coverage: 29 tests covering full lifecycle
src/
βββ services/ # 6 core services
βββ storage/ # Database and memory store
βββ traits/ # 5 SOLID traits
βββ models/ # DTOs and types
βββ cli/ # CLI commands
βββ mcp/ # MCP server
tests/ # 16 integration test files
docs/ # 5 documentation files
# Development build
cargo build
# Release build (optimized)
cargo build --release
# Build MCP server only
cargo build --bin memory-rs-mcp --release- Episode storage: ~5ms
- Hybrid search: ~20ms (1000 memories)
- All operations: Non-blocking
- Follow SOLID principles
- Write minimal, focused code
- Add tests for new features
- Update documentation
- Run
cargo testbefore committing
MIT OR Apache-2.0
Built with:
- Rust π¦
- SQLite + sqlite-vec
- Candle (ML framework)
- MCP Protocol
Status: Production-ready β Tests: 44 passing β Documentation: Complete β }
#### Search (Query Memories)
```json
{
"jsonrpc": "2.0",
"id": 2,
"method": "tools/call",
"params": {
"name": "search",
"arguments": {
"query": "programming languages",
"workspace_id": 1,
"limit": 5
}
}
}
Response:
{
"jsonrpc": "2.0",
"id": 2,
"result": {
"results": [
{
"memory_id": 42,
"text": "Rust is a systems programming language...",
"similarity_score": 0.92,
"combined_score": 0.88,
"importance_score": 0.8,
"tags": "rust,programming",
"created_at": "2026-01-30T22:00:00Z"
}
],
"count": 1
}
}βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β CLI Tool β
ββββββββββββββββββββββββββββ¬βββββββββββββββββββββββββββββββββββ
β stdio (JSON-RPC 2.0)
ββββββββββββββββββββββββββββΌβββββββββββββββββββββββββββββββββββ
β MCP Server β
β ββββββββββββββββββ ββββββββββββββββββ β
β β Learn Tool β β Search Tool β β
β ββββββββββ¬ββββββββ ββββββββββ¬ββββββββ β
βββββββββββββΌβββββββββββββββββββΌββββββββββββββββββββββββββββββ
β β
βββββββββββββΌβββββββββββββββββββΌββββββββββββββββββββββββββββββ
β Memory System β
β ββββββββββββββββββββ ββββββββββββββββββββ β
β β FastEmbedder β β Memory Store β β
β β (MiniLM/Nomic) β β (SQLite+vec) β β
β ββββββββββββββββββββ ββββββββββββββββββββ β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β β
βββββββββββββΌβββββββββββββββββββΌββββββββββββββββββββββββββββββ
β Workspace Manager β
β ~/.memory-rs/workspaces/ β
β βββ project-a/memory.db β
β βββ project-b/memory.db β
β βββ project-c/memory.db β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
-
Storage Layer (
src/storage/)schema.rs: Database schema with sqlite-vec integrationmemory_store.rs: CRUD operations and vector search
-
Memory System (
src/memory_system.rs)- High-level API combining embedder and storage
- Atomic learn and search operations
-
MCP Server (
src/mcp/)server.rs: JSON-RPC 2.0 stdio transporttools.rs: Learn and Search tool implementations
-
Workspace Manager (
src/workspace.rs)- Multi-database support
- Workspace isolation and management
-
Embedder (
src/embedder.rs)- FastEmbedder with multiple model support
- Mock fallback for testing
Choose your embedding model based on your needs:
| Model | Dimensions | Speed | Quality |
|---|---|---|---|
| MiniLM | 384 | Fast | Good |
| BGE-small | 384 | Medium | Better |
| Nomic | 768 | Slower | Best |
Configure in code:
use memory_rs::{WorkspaceManager, ModelType};
let manager = WorkspaceManager::new(ModelType::BgeSmall)?;Workspaces are stored in ~/.memory-rs/workspaces/ by default:
use memory_rs::WorkspaceManager;
let manager = WorkspaceManager::new(ModelType::MiniLM)?;
// Create or get workspace
let system = manager.get_or_create_workspace("my-project")?;
// List all workspaces
let workspaces = manager.list_workspaces()?;
// Delete workspace
manager.delete_workspace("old-project")?;Run all tests:
cargo testRun specific test suites:
# Storage tests
cargo test --lib storage
# MCP server tests
cargo test --lib mcp
# Workspace tests
cargo test --lib workspaceworkspaces
id: Primary keyname: Workspace name (unique)path: Filesystem pathcreated_at: Timestamp
agents
id: Primary keyworkspace_id: Foreign key to workspacesname: Agent namecreated_at: Timestamp
memories
id: Primary keyworkspace_id: Foreign key to workspacesagent_id: Optional foreign key to agentstext: Memory contenttags: Comma-separated tagsimportance_score: Float 0-1access_count: Usage trackinglast_accessed: Timestampconversation_id: Optional conversation groupingparent_memory_id: Optional memory hierarchyuser_feedback: Optional feedback textcreated_at,updated_at: Timestamps
vec0 (virtual table)
memory_id: Foreign key to memoriesembedding: Float vector (384 or 768 dimensions)
idx_memories_workspace: Fast workspace filteringidx_memories_agent: Fast agent filteringidx_memories_importance: Importance-based queriesidx_memories_created: Temporal queriesidx_memories_conversation: Conversation grouping
Combines semantic similarity (70%) with importance score (30%):
use memory_rs::storage::SearchFilters;
let filters = SearchFilters {
workspace_id: Some(1),
agent_id: Some(5),
min_importance: Some(0.5),
max_importance: Some(1.0),
conversation_id: Some("conv-123".to_string()),
..Default::default()
};
let results = system.search("query text", &filters, 10)?;- workspace_id: Limit to specific workspace
- agent_id: Limit to specific agent
- min_importance / max_importance: Importance range
- created_after / created_before: Date range
- conversation_id: Conversation grouping
- tags: Tag-based filtering (future)
- initialize: Server initialization
- tools/list: List available tools
- tools/call: Execute a tool
- learn: Store a memory (via tools/call)
- search: Query memories (via tools/call)
Input Schema:
{
"type": "object",
"properties": {
"text": {"type": "string", "description": "The text to remember"},
"workspace_id": {"type": "integer", "description": "Workspace ID"},
"agent_id": {"type": "integer", "description": "Optional agent ID"},
"tags": {"type": "string", "description": "Optional comma-separated tags"},
"importance_score": {"type": "number", "description": "Importance score 0-1"},
"conversation_id": {"type": "string", "description": "Optional conversation ID"}
},
"required": ["text", "workspace_id"]
}Input Schema:
{
"type": "object",
"properties": {
"query": {"type": "string", "description": "Search query"},
"workspace_id": {"type": "integer", "description": "Optional workspace ID filter"},
"agent_id": {"type": "integer", "description": "Optional agent ID filter"},
"min_importance": {"type": "number", "description": "Minimum importance score"},
"max_importance": {"type": "number", "description": "Maximum importance score"},
"conversation_id": {"type": "string", "description": "Optional conversation ID filter"},
"limit": {"type": "integer", "description": "Maximum results (default 10, max 100)"}
},
"required": ["query"]
}See examples/ directory for complete examples:
mcp_server.rs: Full MCP server implementation- More examples coming soon!
- Storage: SQLite with sqlite-vec for efficient vector operations
- Embedding: ~300ms per embedding with real models, ~20ΞΌs with mock
- Search: Sub-second for <10K memories, optimized for 100K+ scale
- Memory: Efficient storage with optional quantization support
Contributions welcome! Please:
- Fork the repository
- Create a feature branch
- Add tests for new functionality
- Ensure all tests pass:
cargo test - Submit a pull request
MIT OR Apache-2.0
- sqlite-vec for vector search in SQLite
- Candle for ML inference
- Model Context Protocol by Anthropic
- Issues: GitHub Issues
- Discussions: GitHub Discussions
Built with β€οΈ in Rust
