Every memory knows its sources. Recall a bad source, and everything learned from it goes too.
claude mcp add cheesedb -- cheesedb mcp alicego get github.com/govinargo-labs/cheesedbPreview v0.2.0. Embedded, Go standard library only, Apache-2.0.
Claude Code, Cursor and any other MCP app can store what they learn together with the sources behind it, and later remove a bad source and everything built on it. No code to write and no server to run: the app starts CheeseDB itself.
go install github.com/govinargo-labs/cheesedb/cmd/cheesedb@latest
cheesedb agent create alice
claude mcp add cheesedb -- cheesedb mcp alice
Other apps (Cursor, Claude Desktop): add {"mcpServers":{"cheesedb":{"command":"cheesedb","args":["mcp","alice"]}}} to the app’s MCP settings. Then tell the model to keep its long-term memory in CheeseDB.
add_lotRegister a new outside source: a message, a web page, a tool result.rememberStore something learned, with the ids it came from.recallRemove a source and everything built on it, and erase the text.getRead one lot or memory by id.list_memoriesList what is still alive, newest first.The agent is fixed when the server starts, so a prompt-injected model cannot reach another agent’s memory through a parameter.
The text of a recalled source and of what depended on it is removed from disk, and recalled text is never shown back to the model.
It runs on your machine over standard input and output. No network port, no account, no dependencies.
Know the limits. The model declares the sources and legs itself, so a recall is only as complete as what it wrote. A model that can also run shell commands can skip the tools and read every agent’s files. Read the MCP guide and the threat model.
An agent learned from three sources. The weather tool turns out to be wrong. Pick a source, press Recall, then flip the rule to compare.
Tap a source to select it.
The structure line (sources and legs) is never erased, so the history and the hash chain stay intact.
An agent builds memory from sources it can’t fully trust. When one turns out to be bad, everything the agent learned from it is still in memory, and the agent keeps acting on it.
A tool returned bad data, and three memories were built on it.
A web page planted false facts or instructions: memory poisoning and prompt injection.
A user asked for their data to be deleted, including what the agent concluded from it.
Erase has to remove text without losing history, so each record is split in a way that keeps the history.
cheesedb mcp. In memory, the engine keeps the family tree, leg counters and an offset table, all rebuilt from the log when an agent is opened. On disk, each agent is a folder of append-only segments. In the picture, source C has been recalled, so M2 and M3 are dead and M1 is alive.This is the same story as the demo above.
s, err := cheesedb.Open("/data/cheesedb") // a folder you choose, created 0700
tok, err := s.CreateAgent("alice") // Alice's token, shown once: keep it safe
alice, err := s.OpenAgent(tok) // the only way to reach Alice's data
defer alice.Close()
a, _ := alice.AddLot("user_message", []byte("I live in Pune"))
b, _ := alice.AddLot("web_page", []byte("profile: lives in Pune"))
c, _ := alice.AddLot("weather_tool", []byte("Pune: rain"))
m1, _ := alice.Remember([]byte("user lives in Pune"), cheesedb.Leg{a}, cheesedb.Leg{b}) // from A, or from B
m2, _ := alice.Remember([]byte("Pune is rainy"), cheesedb.Leg{c})
m3, _ := alice.Remember([]byte("carry an umbrella"), cheesedb.Leg{m1, m2}) // needs M1 and M2
removed, _ := alice.Recall(c, cheesedb.Fair, cheesedb.Untrusted) // the weather tool was wrong
// removed == [m2, m3]; m1 survives because it does not depend on C
Install the command-line tool with go install github.com/govinargo-labs/cheesedb/cmd/cheesedb@latest. It has one command per feature, including cheesedb find, which searches the raw bytes of the files to prove erased text is gone. Needs Go 1.26.5 or newer. Developed on macOS and tested on Linux in CI. Windows isn’t supported yet.
The same data on all four engines (including Neo4j, a graph database), with every write flushed to the physical disk before it is acknowledged.
| 1M memories per agent | CheeseDB | SQLite | PostgreSQL | Neo4j |
|---|---|---|---|---|
| Recall that removes 10,000 memories | 5.5 ms | 235 ms | 1.82 s | 67 ms |
| Recall that removes 20 memories | 4.8 ms | 7.1 ms | 10.5 ms | 6.8 ms |
| Read one memory by id | 1.6 µs | 7.0 µs | 44 µs | 179 µs |
| Durable write (one memory) | 4.7 ms | 5.3 ms | 6.6 ms | 6.3 ms |
| Startup, ready for the first query | 667 ms | 0.1 ms | 2.7 ms | 1.0 ms¹ |
| Disk per memory | 314 B | 249 B | 546 B | 496 B |
| RAM per memory while open | 205 B | page cache only | shared buffers only | JVM heap and page cache |
Median of 3 runs on an Apple M1 Max (macOS, internal SSD), SQLite 3.53, PostgreSQL 17 and Neo4j Community 2026.10. PostgreSQL and Neo4j ran over TCP on localhost. Writes are close because the disk flush dominates for every engine. SQLite is smaller on disk and starts far faster. ¹ A new connection to a server that is already running; booting the Neo4j server took 6.5 to 8.2 s. The Neo4j model and queries are ours, and an expert may do better. Method and caveats are in BENCHMARKS.md.
The same story three ways, with a real LLM: a plain memory list, CheeseDB with Untrusted, and CheeseDB with Erase.
Verify() returns somewhere else and compare it later.Compact(). Backups and copies keep their data.Report.DroppedBytes, so check it after opening.The full list is in the README and the threat model.
“Lot” and “recall” are food-safety words. A cheese maker records which lots of milk went into which wheels, so when one lot turns out to be contaminated, they recall exactly the cheese made from it.
CheeseDB does the same for what an agent remembers. The name also nods to the Swiss cheese model of safety: stack several layers of protection, and harm only happens when the holes in every layer line up.