Skip to main content

memory3l-mcp

Auditable memory over MCP: an append-only fact ledger plus verifiable invariants, served read-only from SQLite.

The mcp-name: string above and server.json's name must stay identical: the MCP Registry verifies PyPI package ownership by matching them. Changing one without the other fails verification.

What this is for

A memory system claims it never loses a fact. Almost none can prove it, because nothing keeps an independent record to compare against.

memory3l keeps one: an append-only ledger of every (slot, value) ever extracted, written when each summary is created — including the summaries later overridden or merged away, which is exactly where facts disappear. This server exposes the cross-check as tools, so an agent can ask whether a value is still reachable, why a fact left the working set, or whether a deletion actually completed, and get an answer derived from persisted state rather than from the summary's own paraphrase.

The checks are the product. The storage is ordinary SQLite.

Install

uvx memory3l-mcp                  # no install step, runs from PyPI

The audit core (memory3l) is installed as an ordinary dependency. MEMORY3L_ROOT is only needed when developing against a source checkout:

MEMORY3L_ROOT=/path/to/Memory uvx memory3l-mcp

The ledger defaults to ~/.memory3l/memory3l.db and is created on demand, so a fresh install starts and answers episodes: [] instead of failing. Point it somewhere else with MEMORY3L_DB, or --db PATH.

Try it without your own pipeline

python3 scripts/seed_demo.py --db /tmp/demo.db   # generates a real ledger offline
MEMORY3L_DB=/tmp/demo.db uvx memory3l-mcp

No network, no API key, no Redis.

Tools

Read-only by default. Without --allow-write (or MEMORY3L_ALLOW_WRITE=1) the server is an audit surface: it can inspect memory but not create it.

Tool Answers
memory_context the memory block to put in your prompt — call before answering
remember record a completed turn — call after answering
store_info which database is served, whether it is readable, and whether memory is on
list_episodes which episode ids exist — call this first
audit the invariant report for one episode
audit_summary the same, aggregated over every episode
current the newest value of every slot, as the model should be told it
history every value a slot ever held, with supersession
fact why one fact left the working set (live / archived / missing)
evidence the original dialogue a fact was extracted from
tombstones what was erased, what is provably gone, what prose remains
temporal the versioned projection, its anomalies, and its DDL
append_facts intake for your own extractor; it cannot make a fact visible

Giving an agent memory

The memory half is two calls per turn, and the order matters:

memory_context(episode_id)                       # before you answer
remember(episode_id, user_message, agent_message) # after you answer

memory_context returns memory in a fixed order (recent dialogue, current values, index titles, summary chain) with no persona attached, so it drops into any prompt. An empty block is the correct answer for a new conversation.

MCP has no hook, so nothing is automatic: if you skip memory_context the agent answers without memory even though remember recorded the turns. The memory3l skill is what teaches an agent to make both calls.

Two operational notes:

  • remember is where the model call goes. It summarises, so each turn costs a summariser call. Point --summarizer at a small model.
  • The conversation survives a restart. One episode_id is one conversation; the chain and the turn counter are read back from SQLite, so a restarted server continues rather than starting over.

Without a model (--summarizer none) memory still works — turns are stored verbatim — but nothing is extracted, so the current-value registry stays empty and the audit tools have nothing to check. store_info reports which mode you are in rather than letting the difference be discovered later.

The invariants

  • I1 conservation — a ledger fact resolves to no summary, active or archived: it was extracted and now nothing can reach it. Real silent loss.
  • I2 top-level reachability — a slot's newest value lives only inside an index member, so the model is never told it: stored, and practically invisible.
  • I3 provenance — a fact's evidence no longer resolves to stored dialogue.
  • I4 extraction completeness — the extractor itself missed facts present in the raw turns. The blind spot the other invariants cannot see: they all pass when nothing was extracted at all.
  • I5 deletion — an erasure is verified rather than assumed: the value is gone and its evidence destroyed, with residual prose mentions counted.

An episode with no facts satisfies every invariant trivially, so an unknown episode is an explicit error rather than an empty pass. A tool that answers "no violations" about an episode that does not exist is worse than one that fails.

Configure your client

Any MCP client that can launch a stdio server. For DSH, add one row to $DSH_HOME/profiles/<name>/cordis.patch.yml:

- insert:
    - id: mcp-memory
      name: '@deepseek-ai/dsh-mcp-client'
      config:
        serverName: memory
        transport: stdio
        command: uvx
        args: ['memory3l-mcp']
        env:
          MEMORY3L_DB: /path/to/your/memory3l.db

Tools then appear as mcp__memory__audit, mcp__memory__current, and so on — the same mcp__<server>__<tool> shape Claude Code and Codex use. DSH passes the env entries through to the server (credential-shaped variables are scrubbed from the ambient environment, which is why the ledger path is set explicitly here).

The skill

skills/memory3l/SKILL.md is an Agent Skills bundle that teaches an agent when to reach for these tools and how to report the answer without overstating it — chiefly that "no violations" is not a guarantee that nothing was lost.

Install it into the cross-client directory so every compliant agent sees it:

memory3l-mcp-install-skill           # → ~/.agents/skills/memory3l

Skills installed there are visible to any client that scans .agents/skills/, and vice versa. No per-client adaptation. The command refuses to overwrite an existing skill whose content differs — pass --force if you mean it, or --target DIR to install somewhere else.

Development

MEMORY3L_ROOT=$PWD PYTHONPATH=$PWD/src python -m unittest discover -s tests
python scripts/seed_demo.py --db /tmp/demo.db

Requires mcp>=2. Note that mcp 2.0 renamed FastMCP to MCPServer and made mcp.server.fastmcp raise on import; this package targets 2.x.

License

MIT

Release files for memory3l-mcp 0.2.0

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for memory3l-mcp 0.2.0
File Size Uploaded
memory3l_mcp-0.2.0.tar.gz 21.3 kB Details

Built distribution (wheel)

Table of built distributions (wheels) for memory3l-mcp 0.2.0
File Interpreter ABI Platform
memory3l_mcp-0.2.0-py3-none-any.whl Python 3 none any Details

Total release size: 44.8 kB

Release files / memory3l_mcp-0.2.0.tar.gz

Download URL memory3l_mcp-0.2.0.tar.gz
Size 21.3 kB
Tags Source
SHA-256 checksum
How to use checksums
bba70384366dad960812c5ce6d0f0d158442c41171c9769b7f6d372451d50971
BLAKE2b-256 checksum
How to use checksums
39a0752a728d439e950e3b0208d8f97b90aef2d81aad35a02d235d4724f838f7
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.14

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Sep 20, 2026.

Transparency log

Release files / memory3l_mcp-0.2.0-py3-none-any.whl

Download URL memory3l_mcp-0.2.0-py3-none-any.whl
Size 23.5 kB
Tags Python 3
SHA-256 checksum
How to use checksums
9d62bddf2ac9a89ca864a74a627eed5a0ca31b059f79927fdd5fa630ba8f69d1
BLAKE2b-256 checksum
How to use checksums
c0c6ae01dd27e7fa2b04681512ff7082351ab3a1c0f763812a6790a89c420975
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.14

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Sep 20, 2026.

Transparency log

Release history Release notifications | RSS feed

This release

0.2.0 This release

2 release files

0.1.1

2 release files

0.1.0

2 release files

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page