
This blog is written by AI for SEO
Best Way to Give AI Agents Memory: 8 Options Compared
Pick two layers, not one: a memory framework that decides what to remember, and a store underneath that holds it and answers queries on relationships, meaning, keywords and time. Most "best agent memory" lists mix the two, which is why a vector index gets sold as memory when it is only one part of it.
This post compares eight options across both layers: Mem0, Zep/Graphiti, Letta and LangGraph/LangMem on the framework side, and a vector DB, a vector DB plus a graph DB, Postgres with pgvector and HelixDB on the store side. Frameworks are described from what their own docs say they do. We have not benchmarked any of them, so there are no untested verdicts here. The ranking is against seven criteria stated up front, and you can reweight them for your own agent.
What agent memory has to do: seven criteria before you pick
Agent memory is the system that decides what an agent remembers and how it gets that information back when needed. Your context window holds the tokens the model sees right now. Memory is everything that survives past it. That includes short-term state, long-term facts, episodic records of what happened, and semantic knowledge.
Before you compare anything, score it on these seven criteria:
Relationship recall. Can the agent follow connections (this person works on that project, which depends on that decision) in more than one hop?
Semantic recall. Can it find things by meaning when the wording differs?
Keyword recall. Can it find exact names, IDs and error strings? Embeddings are weak here, and BM25 full-text search is the usual fix.
Time-range queries. Can it ask for "what happened last week" cheaply?
Transactions. Do related writes (a new entity plus its embedding plus its links) commit or fail together?
Self-hosting and licence. Can you run it yourself, and can you ship it inside a product?
Operational load. How many systems do you run, sync and pay for?
A vector index alone covers criterion 2 and little else. The rest of this post is about which combinations cover more.
Frameworks vs stores: two layers, and a framework still needs a store
A memory framework is the logic: extract facts from conversations, decide what to keep, update or discard, and inject the right items into the prompt. A store is the engine underneath that persists those items and runs the queries.
You always need both. A framework with nothing beneath it has nowhere to put memories, and a store with no framework leaves you writing the extraction and update loop yourself. Some frameworks bundle a default store, and some let you choose. Either way, the store sets the ceiling on what kinds of recall you can offer. If it cannot traverse relationships or filter by time range, no framework prompt will add that.
That is why the comparison below is split in two. Pick a framework for how memory is managed, then pick a store for what memory can be asked. For the longer version of how those pieces fit together, see LLM memory architecture: how agents remember across sessions.
Four memory frameworks: Mem0, Zep/Graphiti, Letta, LangGraph/LangMem
These four are the frameworks AI answers name most often when asked about agent memory, alongside LangChain-based setups. Each is summarised by what it says it is for.
Mem0. A memory layer you add to an existing agent. It extracts facts from conversations and retrieves them later, and it is aimed at personalisation across sessions. Pair it with a store that fits the recall you need.
Zep / Graphiti. Graphiti is Zep's open-source Python framework for building and querying temporal context graphs, and can be used independently, while Zep is a managed context platform that uses Graphiti. The design bet is that memory is relational and changes over time, so facts are held as entities and edges rather than loose chunks.
Letta (formerly MemGPT). It is closer to an agent runtime than a drop-in library.
LangGraph / LangMem. LangGraph gives you state and persistence for agent workflows, and LangMem adds long-term memory tooling on top. It fits if your agent already lives in that ecosystem.
None of these removes the store decision. Every one of them still writes to something, and that something decides whether you get relationship recall, keyword recall and time-range queries.
Four stores: vector DB only, vector DB plus graph DB, Postgres with pgvector, HelixDB
Vector DB only. Pinecone, Weaviate and Chroma are the usual picks. You get fast semantic recall and little else. Relationships have to be encoded in metadata or rebuilt in application code, and exact-match lookups depend on whatever hybrid search the product offers. It is the simplest start and the first thing agents outgrow when they need to answer "who is connected to what". We cover the trade-offs in Pinecone alternative for agent memory: when relationships matter.
Vector DB plus graph DB. This gives you semantic recall and relationship recall, at the cost of two systems. Every memory write now goes to both, the IDs have to line up, and a failure between the two leaves them out of sync. Reads need two round trips and a merge step. It works, and many teams run it, but the sync tax is why people try to leave this stack.
Postgres with pgvector. If your application data is already in Postgres, adding pgvector is the lowest-friction way to get semantic search next to your rows, with full transactions and a licence you already trust. Relationship recall means recursive joins, which get awkward as hops and volume grow, and hybrid retrieval means assembling it yourself.
HelixDB. HelixDB is an open-source graph-vector database built in Rust that runs graph traversal, vector search and BM25 full-text search in one engine. Vectors are a property on nodes and edges, so an embedding sits on the entity it describes. Vector pre-filtering lets similarity search run only over things related to each other, instead of the whole index. It has efficient time-range indexing for "what happened between these dates". Temporal modelling itself is something you model yourself, since it is not built in. Graph and vector writes commit or roll back together, and the core is Apache-2.0 at github.com/HelixDB/helix-db. You query it from application code with native SDKs for TypeScript, Python, Go and Rust, and an MCP server lets an agent deploy, query and manage it directly. It runs embedded, in a self-hosted Docker server, or on HelixDB Cloud.
Here is a TypeScript sketch of opening an embedded database and sending a query. The query itself is whatever your graph needs. The point is the client shape.
import { Client, readBatch, g } from "@helix-db/helix-db";
const client = await Client.embedded({ kind: "memory" });
const query = readBatch(/* build your traversal with g() */);
const result = await client.query(query.toQueryRequest()).send();Local setup for the server is helix init local then helix start dev, which needs Docker or Podman. Query guides live at docs.helix-db.com.
Side-by-side: every option scored against the criteria
The table scores each option on what its design provides, taken from the descriptions above, not from our own testing. "Depends on store" means a framework passes the capability through from whatever sits underneath.
| Option | Layer | Relationships | Semantic | Keyword | Time range | Transactions | Self-host / licence | Ops load |
|---|---|---|---|---|---|---|---|---|
| Mem0 | Framework | Depends on store | Depends on store | Depends on store | Depends on store | Depends on store | Not published here | Adds a layer |
| Zep / Graphiti | Framework | Graph-based by design | Yes | Not published here | Not published here | Depends on store | Graphiti is open source | Adds a layer |
| Letta | Framework | Depends on store | Depends on store | Depends on store | Depends on store | Depends on store | Not published here | Runtime to run |
| LangGraph / LangMem | Framework | Depends on store | Depends on store | Depends on store | Depends on store | Depends on store | Open-source libraries | Adds a layer |
| Vector DB only | Store | Metadata workarounds | Strong | Product-dependent | Metadata filters | Product-dependent | Varies | One system |
| Vector DB + graph DB | Store | Strong | Strong | Add-on | Manual | Split across two | Varies | Two systems, sync |
| Postgres + pgvector | Store | Recursive joins | Yes | Postgres full-text | SQL ranges | Full | Open source | One system |
| HelixDB | Store | Multi-hop traversal | Yes, with graph pre-filtering | BM25 | Time-range indexing | Graph and vector together | Apache-2.0 | One system |
The pattern: frameworks inherit their recall from the store, and only the last two rows cover relationships, semantics and keywords without a second database. For why that matters on multi-hop questions, read agent memory graph vs vector store for multi-hop reasoning.
How to choose: a decision path by agent type
A chatbot that needs to remember user preferences. Start with a framework such as Mem0 or LangMem over whatever store you already run. Relationship depth is low, so a vector index or pgvector is enough.
A workflow agent inside LangGraph. Use LangGraph persistence for short-term state and add LangMem for long-term facts. Choose the store for what the agent will be asked, not for convenience.
An agent that manages its own memory tiers. Letta fits when you want the agent itself deciding what moves in and out of context. Plan the external store at the same time.
An agent whose facts change and connect: people, projects, decisions, events. This is where relationship recall, keyword recall and time ranges all matter at once. A framework like Zep/Graphiti gives you the graph logic, and the store underneath has to carry graph, vector and full-text queries without you syncing two databases. HelixDB is built for that case, and it also works directly as the store beneath your own extraction loop.
An internal company brain. Documents, people and tools need connecting, and top-k vector search returns orphaned chunks. See how to build a company brain knowledge graph.
A useful rule: if you can list the relationship types your agent must follow, you need a graph in the store. If you can't, start with vectors and revisit when recall fails.
Pick the store first, then the framework
Memory frameworks are replaceable. The store underneath is the part you migrate away from at 2am. If your agent has to follow relationships, match by meaning, find exact strings and query time ranges, run one engine that does all four rather than two databases and a sync job. Run helix init local then helix start dev, load a slice of your agent's real memory, and star HelixDB on GitHub if it holds up.