Backend memory store for Hermes Agent.
A semantic memory engine powered by pgvector (PostgreSQL vector database) with server-side embeddings via any OpenAI-compatible API.
Store, search, and maintain agent memories with hybrid vector + full-text retrieval, automatic decay, consolidation, and a sandbox for ephemeral context.
- Hybrid search — Reciprocal Rank Fusion over vector cosine distance and full-text search (
tsvector) - Intent routing — Automatically classifies incoming memories:
Task,Reference,Environment,Preference,Backlog,Pivot,Correction - Immortal memories — Protected from decay/pruning; set automatically for
ReferenceandEnvironmentintents - Embedding cache — In-memory
DashMapdeduplication; saves API calls on repeated content - Ephemeral sandbox —
PivotandTaskintents stage memories in aVecDequebefore committing on flush - Temporal recall — Query memories within ISO datetime windows
- Token-budget search —
recall_within_token_budgetfits results into an LLM context limit - Maintenance — Automatic decay/importance adjustment every 24 h, stale-memory listing, batch purge (immortal-protected)
- Consolidation — Merges sandbox to DB when idle
- Workspace telemetry —
notify-based file watcher drives proactive horizon sweeps - Hermes plugin — Drop-in
MemoryProviderplugin with 6 agent tools (recall,sweep,search_temporal,list_stale,purge,stats)
Hermes Agent (Python MemoryProvider plugin)
│ HTTP
▼
┌──────────────────────────────────────────┐
│ axum HTTP server (routes.rs) │
│ │
│ ┌──────────┐ ┌──────────┐ ┌────────┐ │
│ │ guard.rs │ │ embed.rs │ │ cache │ │
│ │ sanitize │→│ embedding │→│ .rs │ │
│ │ redact │ │ API call │ │ DashMap│ │
│ └──────────┘ └──────────┘ └────────┘ │
│ │ │ │
│ ▼ ▼ │
│ ┌──────────────────────────────┐ │
│ │ DoryEngine (engine.rs) │ │
│ │ process_and_route_memory │ │
│ │ hybrid_recall / temporal │ │
│ │ proactive_horizon_sweep │ │
│ └──────────┬───────────────────┘ │
│ │ │
└─────────────┼─────────────────────────────┘
│ sqlx
▼
┌──────────────────────┐
│ PostgreSQL + pgvector │
│ - dory_memories │
│ - dory_namespaces │
└──────────────────────┘
Background workers (workers.rs):
- Decay/pruning (every 24h)
- Consolidation (idle trigger)
Telemetry daemon (telemetry.rs):
- notify watcher on workspace
cp .env.example .env # edit your API key
docker compose up -d# Start PostgreSQL with pgvector
docker run -d --name dory-pg \
-e POSTGRES_USER=dory -e POSTGRES_PASSWORD=dory -e POSTGRES_DB=dory \
-p 5432:5432 pgvector/pgvector:pg16
# Build and run
cargo runAll configuration is via environment variables (no config file). Settings match the DORY_ prefix in .env.example:
| Variable | Default | Description |
|---|---|---|
DORY_DATABASE_URL |
postgres://dory:dory@localhost:5432/dory |
PostgreSQL connection string |
DORY_DATABASE_MAX_CONNECTIONS |
10 |
Connection pool size |
DORY_SERVER_HOST |
0.0.0.0 |
HTTP bind address |
DORY_SERVER_PORT |
5005 |
HTTP port |
DORY_EMBEDDING_API_URL |
https://openrouter.ai/api/v1/embeddings |
OpenAI-compatible embeddings endpoint |
DORY_EMBEDDING_API_KEY |
— | API key (required) |
DORY_EMBEDDING_MODEL |
BAAI/bge-m3 |
Embedding model name |
DORY_EMBEDDING_DIMENSIONS |
1024 |
Vector dimension count |
DORY_WORKSPACE_ROOT |
— | Workspace path for telemetry (optional) |
| Method | Path | Description |
|---|---|---|
POST |
/v1/memories |
Insert a memory |
POST |
/v1/search |
Hybrid semantic + full-text search |
POST |
/v1/search/temporal |
Recall within a time window |
POST |
/v1/search/budget |
Token-budgeted search (for prefetch) |
GET |
/v1/sweep/{namespace} |
Proactive horizon sweep (stale tasks) |
POST |
/v1/maintenance/stale |
List stale non-immortal memories |
POST |
/v1/batch/delete |
Batch delete (immortal protected) |
GET |
/v1/stats |
Database statistics |
The plugin lives in plugins/memory/dory/ and provides:
- 6 agent tools:
recall,sweep,search_temporal,list_stale,purge,stats - Auto-namespace: derived from Hermes profile name
- Background sync: async
sync_turnrecords conversation turns - CLI:
hermes dory status,hermes dory config,hermes dory stats
Install by copying plugins/memory/dory/ into your Hermes agent's plugin directory.
Set DORY_API_URL (default http://localhost:5005).
cargo check # fast validation
cargo clippy --all-targets --all-features --locked -- -D warnings
cargo test # unit + integration
cargo fmt # formattingRequires Rust ≥1.85 (edition 2024). The project pins stable in rust-toolchain.toml.
src/
├── main.rs # Entrypoint: config, pool, migrations, axum, workers
├── config.rs # Env-var config loader (DoryConfig::from_env)
├── error.rs # DoryError (thiserror) + axum IntoResponse
├── models.rs # DoryMemoryNode, DoryInsertPayload, DoryIntent, TimeWindow
├── guard.rs # Secret redaction + prompt-injection sanitization
├── embed.rs # OpenAI-compatible API client
├── cache.rs # DashMap embedding cache + VecDeque sandbox
├── engine.rs # Core engine: routing, recall, stats, maintenance
├── routes.rs # Axum HTTP handlers
├── workers.rs # Decay/pruning + consolidation
└── telemetry.rs # Workspace file watcher
This project follows Git Flow with automated releases:
- PRs to
mainordevelopmenttrigger CI (lint, build, test) - Merging to
mainbumps version + generates changelog + creates tag - Tagged releases build multi-arch binaries, publish to crates.io, and push Docker images to
ghcr.io/atareao/dory-memory
See GIT_FLOW.md for the full workflow.