This cookbook demonstrates the core memory patterns using a simplified simulation. MiroFish’s actual architecture uses a factory pattern (
memory_factory.py) with abstract providers, batch buffering with retries in ZepGraphMemoryUpdater, and IPC-based agent interviews. This cookbook focuses on the Mem0 API integration points — wrap these calls in your own retry/batch logic for production use.Overview
This cookbook implements a Housing Policy Prediction Simulation following MiroFish’s five-stage workflow:- Graph Building — Ingest seed documents, extract entities and relationships
- Environment Setup — Query the knowledge graph to enrich agent profiles
- Simulation — Track agent interactions with per-agent memory isolation
- Report Generation — Semantic search + graph traversal for analysis
- Deep Interaction — Query post-simulation memory and relationships (MiroFish also supports live agent interviews via IPC — not covered here)
- Mayor Chen — Policy advocate pushing for zoning reform
- Wang (Homeowner) — Opposition leader organizing resistance
- Professor Li — Academic providing data-driven analysis
Prerequisites
| Backend | Setup | Best for |
|---|---|---|
| Neo4j Aura (free tier) | Sign up, get Bolt URI | Production, closest to Zep |
| Neo4j Docker | docker run -p 7687:7687 -e NEO4J_AUTH=neo4j/password neo4j:5 | Local development |
| Kuzu (embedded) | No setup needed — runs in-process | Quick testing, zero dependencies |
Complete Implementation
How It Works
Graph Memory: The Right Fit for MiroFish
MiroFish’s entire pipeline revolves around a knowledge graph — it extracts entities from documents, builds relationships, and queries the graph throughout simulation and reporting. Mem0’s Graph Memory provides the same capabilities:| MiroFish needs | Zep Cloud | Mem0 Graph Memory |
|---|---|---|
| Entity extraction | Built-in via Zep API | Automatic via LLM extraction |
| Relationship mining | Graph edges | (source) --[relationship]--> (destination) triples |
| Semantic + keyword search | Semantic + BM25 | Vector similarity + graph relation retrieval |
| Graph traversal | Node/edge queries | relations array in search results |
| Per-agent isolation | Single shared graph in MiroFish | Native run_id scoping |
| Self-hosting | No (cloud only) | Yes — Neo4j, Memgraph, Kuzu, Neptune |
| Node/memory limits | Capped on free tier | Unlimited (self-hosted) |
How search() Returns Both Memories and Relations
When Graph Memory is enabled, everysearch() call returns two arrays:
Per-Agent Memory Isolation
user_id scopes the simulation project. run_id tags individual agent actions at storage time (we use run_id instead of agent_id since no assistant memories are involved). Searches use user_id for project-wide retrieval:
Use
user_id for project-level data (seed documents) and run_id for agent actions — both for add() and search(). Always match the scope: if you add() with run_id, search() with run_id. Use the message list format [{"role": "user", "content": "..."}] for all add() calls — it works on both OSS and Cloud.Stage Mapping
| MiroFish Stage | What Happens | Mem0 Graph Memory Call |
|---|---|---|
| 1. Graph Building | Ingest docs, extract entities | memory.add(doc, user_id=project) — entities/relations extracted automatically |
| 2. Environment Setup | Enrich agent personas from graph | memory.search(query, user_id=project) — returns facts + relations |
| 3. Simulation | Track per-agent actions | memory.add(messages, run_id=agent) |
| 3. Simulation | Mid-round recall | memory.search(query, run_id=agent) |
| 4. Report Generation | Targeted analysis | memory.search(query, user_id=project) — memories + graph |
| 4. Report Generation | Full overview | memory.get_all(user_id=project) — all memories + all relations |
| 5. Deep Interaction | Follow-up queries | memory.search(query, user_id=project) |
Zep-to-Mem0 Migration Reference
For developers replacing MiroFish’s Zep integration. Note that Mem0 Graph Memory covers the core graph operations but some Zep features have no direct equivalent — see caveats below.| MiroFish Service | Zep Call | Mem0 Graph Memory Equivalent | Caveat |
|---|---|---|---|
| GraphBuilderService | client.graph.create() | Implicit on first memory.add() | |
| GraphBuilderService | client.graph.set_ontology() | custom_prompt in graph_store config | Freeform text, not a typed schema like Zep’s EntityModel/EdgeModel |
| GraphBuilderService | client.graph.add_batch(episodes) | memory.add() per chunk | No batch API — call per chunk |
| GraphBuilderService | client.graph.episode.get(uuid) | Not needed (add is synchronous in OSS) | |
| GraphBuilderService | client.graph.delete(id) | memory.delete_all(user_id=...) | |
| ZepEntityReader | client.graph.node.get_by_graph_id() | memory.get_all(user_id=...) → relations | |
| ZepEntityReader | client.graph.node.get(uuid) | memory.search(entity_name, user_id=...) | Semantic search, not exact ID lookup |
| ZepEntityReader | client.graph.node.get_entity_edges() | memory.search(entity_name, user_id=...) → relations | Returns all matching relations, not edges for a specific node |
| ZepGraphMemoryUpdater | client.graph.add(type="text") | memory.add(messages, run_id=...) | No batch buffering or retry — implement in your wrapper |
| ZepToolsService | search_graph(query, scope) | memory.search(query, user_id=...) → memories + relations | |
| ZepToolsService | get_entities() | memory.get_all(user_id=...) → relations | |
| ZepToolsService | Panorama (all nodes + edges) | memory.get_all(user_id=...) | No temporal fact separation (active vs historical) |
| ZepToolsService | InsightForge (multi-query decomposition) | Not available | Implement LLM-driven sub-query decomposition in your own ReportAgent |
| OasisProfileGenerator | client.graph.search() | memory.search(query, user_id=...) |
What Mem0 Graph Memory does not cover: Zep’s typed ontology schemas (
EntityModel, EdgeModel), temporal fact lifecycle (valid_at/invalid_at/expired_at), single-node-by-ID lookup, and InsightForge’s multi-query decomposition. For InsightForge-like functionality, implement sub-query logic in your own ReportAgent using memory.search() as the retrieval primitive.Custom Extraction Prompts
Guide what entities and relationships Mem0 extracts — analogous to (but less structured than) Zep’sset_ontology():
Action Types
MiroFish’s OASIS engine produces these agent action types. Format them as natural language when storing. SkipDO_NOTHING actions (no memory value). TREND and REFRESH are Reddit-only discovery actions — store if you want to track browsing behavior.
| Action Type | Platform | Example Memory Content |
|---|---|---|
CREATE_POST | Both | "Mayor Chen [CREATE_POST]: This reform will create 10,000 units" |
CREATE_COMMENT | "Wang [CREATE_COMMENT]: Replied to Prof Li: 'Your data is misleading'" | |
LIKE_POST | Both | "Mayor Chen [LIKE_POST]: Liked Prof Li's post about Shenzhen data" |
REPOST | "Prof Li [REPOST]: Reposted Mayor Chen's town hall announcement" | |
FOLLOW | Both | "Wang [FOLLOW]: Followed @MayorChen" |
QUOTE_POST | "Mayor Chen [QUOTE_POST]: 'Data confirms reform works' quoting Prof Li" | |
DISLIKE_POST | "Wang [DISLIKE_POST]: Downvoted Mayor Chen's reform post" | |
TREND | "Prof Li [TREND]: Browsed trending topics" | |
DO_NOTHING | Both | Skip — no memory value |
Running the Example
Exact output varies as Mem0 automatically extracts and deduplicates entities. The specific relations and memory counts depend on LLM extraction quality.
Best Practices
- Unique
user_idper simulation — Use timestamps or UUIDs (e.g.,mirofish_housing_1742198400) to prevent memory collisions between runs - Always set
run_idfor agent actions — Per-agent isolation prevents memory cross-contamination between agents - Use
custom_prompt— Guide entity extraction to capture domain-specific relationships (people, policies, stances) - Format actions as natural language —
"Mayor Chen [CREATE_POST]: content"extracts better entities than raw JSON - Query relations for reports — The
relationsarray in search results gives structured(source, relationship, destination)triples for building analytical reports - Cleanup old simulations — Call
delete_all(user_id=...)when a simulation run is no longer needed
Resources
- MiroFish GitHub — Source code and setup guide
- MiroFish Documentation — Full framework docs
- Mem0 Graph Memory — Graph Memory documentation
- Mem0 Documentation — Full API reference
Graph Memory
Full Graph Memory documentation with provider setup.
MiroFish GitHub
MiroFish source code and setup guide.