Features

Everything Mnemo does, each one working

Every feature below has a demo built from the app's own text: the turn mnemo --demo plays, the gate's rules, the real command list and themes. Scroll the reel or jump to one.

  1. №01One turnAsk, read, edit, check, answer, remember.
  2. №02MemoryWhat it remembers, and how you control it.
  3. №03LessonsA failure leaves a pitfall with its fix.
  4. №04SkillsProcedures it writes down for itself.
  5. №05ChecksNothing is done until the checks pass.
  6. №06FleetSeveral agents, one window.
  7. №07PermissionsFour modes and rules that always hold.
  8. №08ToolsWhat the agent can reach for.
  9. №09Shared memoryClaude Code and Codex can use it too.
  10. №10CommandsEverything you can type.
  11. №11ThemesWhy it looks like a game.
  12. №12MeasuredDoes memory make a small model better?

01 one turn, start to finish

What does a turn with Mnemo look like?

  1. You askOne line, in the folder you are working in.
  2. It thinks, then reads firstMemory is searched before the model is asked anything. Then it looks at the file before it changes it.
  3. It edits, and asks firstEvery edit and command waits for you by default. The change is shown as a diff.
  4. It checks its workA change is checked before it is called done. A run that changed code and ran nothing is sent back.
  5. It answersPlain words about what changed and why.
  6. It remembersAfter the run, what it learned is written down for next time: facts, what was decided, what is still open.
▊add a retry to the fetch helper
·The user wants retries on the fetch helper. I should read it first to see how errors surface, then retry only on server errors so a 404 still fails fast.
│I'll look at the helper first.
●read src/fetch.ts 5 lines
●edit src/fetch.ts asks first
-  const res = await fetch(url);-  if (!res.ok) throw new Error(`HTTP $${res.status}`);-  return res.json();+  for (let attempt = 1; ; attempt++) {+    const res = await fetch(url);+    if (res.ok) return res.json();+    if (attempt === 3 || res.status < 500) throw …+    await new Promise((r) => setTimeout(r, 200 * 2 ** attempt));+  }
│Checking the change.
●bash git diff --check && git diff --stat
src/fetch.ts | 9 ++++++---
│Done — getJson now retries server errors up to three times: 5xx responses back off exponentially (400 ms, 800 ms); 4xx responses still fail on the first try.
◆+2 learned
languageTypeScript
http helpergetJson (src/fetch.ts) retries 5xx up to 3 times with backoff; 4xx fail fast
openno test covers the retry path yet

One turn, end to end

  1. Memory first

    Before the model sees your message, memory is searched for it and what it finds is attached: facts about the project and you, earlier sessions, pitfalls with their fixes, skills. Recalled items are candidates, never presented as fact.

  2. The model streams

    Thinking, text and tool calls stream into the transcript as they arrive. enter while it works queues your next message, alt+enter adds a newline, and esc interrupts the turn.

  3. Every tool call passes the gate

    Reads run. Edits and commands ask, unless your mode or rules say otherwise, and a deny rule always holds. The question names the command or the file it is about.

  4. Everything is logged into the session

    Each tool call and its outcome is recorded with its subject. A failure steers memory right away, once per distinct failure, so the same mistake is less likely in the same run.

  5. After the run, reflection

    A clean run reinforces the memories that fed it. Then one grounded reflection writes the session record, the facts you stated or a tool showed, the fixes that resolved failures, and a skill when one was demonstrated.

02 memory

What does Mnemo remember, and how do I control it?

Facts, conventions, pitfalls with their fixes, open threads and skills, stored on your machine and kept per project. Before every model call the relevant ones are recalled; you can read all of it with /memory, add with /remember and retire with /forget. Try it: select a node, steer it, forget it, or tell it something.

settleScattered runs settle into one structure: what the memory graph does with what each session leaves behind.

How it works

  1. It writes after every run

    When a run ends, one model call reads a grounded digest of it: your words, the answers, every tool call with its outcome, the failure-and-recovery pairs found in the tool log, and the files that changed. It returns facts, the session record (goal, outcome, what was done, decisions, open threads), fixes, and a skill when one was demonstrated. Only what you said or a tool showed is kept: a guess is not memory.

  2. It recalls before the model is asked

    At the start of each run your message is searched against memory and what it finds travels with the message, beside a standing profile of the project and of you. A small model often will not think to search, so Mnemo does not leave it to the model. The model can still look further itself with memory_search and session_search.

  3. One current value per key

    A fact is a key and a value. Saying something new about the same key supersedes the old value instead of adding a second one, so a changed rule never comes back as two live instructions. The old value keeps its place in history; nothing is erased.

  4. A graph in six areas

    Memories are nodes in areas modelled on the brain: episodic (sessions and outcomes), semantic (facts), procedural (skills), spatial (repositories, paths, services), salience (what hurt) and executive (steering decisions). A question is routed toward the likely areas but still searches all of them, and one hop along the graph's links brings related memories with it.

  5. An append-only journal on your disk

    Every change is one of eleven operations appended to a journal, and replaying the journal rebuilds the memory exactly. The journal is the only source of truth. Mnemo, its sub-agents and Claude Code's hooks can write to it at the same time without corrupting it.

  6. Earned, filtered, redacted

    A recalled memory earns a “useful” vote only when the answer reuses words that are distinctive to it, and votes gently reorder what comes back. Text that tries to instruct the agent, smuggle data out or hide characters is refused, and credential-shaped strings are redacted before anything reaches memory or a log.

languagehttp helperopen threadpackage managerpitfall → fixskillsession

fact

http helper

getJson (src/fetch.ts) retries 5xx up to 3 times with backoff; 4xx fail fast

“That was wrong” is memory_steer: what memory supplied is trusted less next time. /forget retires it.

▊write a test for the retry
◆recalled 5 before the model was asked
languageTypeScript
http helpergetJson (src/fetch.ts) retries 5xx up to 3 times with backoff; 4xx fail fast
open threadno test covers the retry path yet
pitfall → fixtests hang on the dev server port → run them with --runInBand
skillrun-checks: typecheck, then tests, before calling a change done

03 experience compounds

What happens when something fails?

Memory is steered, once per distinct failure. What hurt is marked, the memories that misled the run lose weight, and when a later step fixes the problem the fix is kept with it. Next time the same situation comes up, it is recalled as a pitfall with its fix, before the model repeats the mistake.

sieveEvery run goes through the sieves: what held up is kept, what misled is caught, and the pan is left bare.

How it works

  1. Mark that it hurt

    A pain marker is recorded first, unconditionally, in the salience area. It is linked to the session but never as a source of context, so a marker can never be blamed for the next failure.

  2. Blame what fed the run

    Every memory that supplied context to the run is checked against the failure's words; the ones it implicates lose weight. A memory that keeps misleading sinks in the ranking instead of being trusted forever.

  3. Correct, if the fix is known

    When the right value is known, the wrong fact is superseded by it, after checking that the old one still exists and is current. History keeps both.

  4. Switch to a better source

    When a source's weight falls below 0.2 and a better one exists, the link to the bad one is cut and the alternate takes its place.

  5. Reinforce what worked

    A clean run does the mirror image: every memory that fed it gains a little weight, so good context rises the more it is used.

  6. Come back as a pitfall with its fix

    Reflection pairs each failure with what resolved it. A pitfall is recalled only once it carries a fix, as a line the model can act on rather than a warning it cannot.

▊run the tests
◆recalled before the model was asked
pitfalltests hang on the dev server port → run them with --runInBand
●bash pnpm test --runInBand
✓42 passed

04 skills it writes for itself

Can Mnemo learn a procedure, not just a fact?

Yes. When it notices a procedure the project will need again, it writes a skill: a plain SKILL.md you can read and edit, in the repository's .agents/skills/ (or your own, for a personal one), and a node in memory so a later session can find it by purpose. When a skill fails, it rewrites it and keeps the old version.

riffleA tray of procedures it wrote for itself: pull one up, and the ones beside it follow.

How it works

  1. Written when a procedure is demonstrated

    create_skill saves a procedure the project or you will need again: a lowercase-with-dashes name, a description that says when to use it (that is how it is found later), and the steps, commands and pitfalls in Markdown. A project skill goes in the repository's .agents/skills/<name>/SKILL.md; a personal one in Mnemo's home.

  2. Indexed in memory

    Every skill is also a procedural node in memory, so a later session can recall that the skill exists, and why, from a question that never names it.

  3. Revised, with its history

    When a skill fails, update_skill rewrites it and says what went wrong with the old version. The previous body is kept under skill-history/.

  4. Loaded from where you already keep them

    SKILL.md files in .claude and .agents folders, walked up to the repository root, load as well. /skills lists them and /reload picks up changes without a restart.

  5. Curated so the list stays short

    mnemo memory curate sorts skills by last use: stale after 30 days, archivable after 90. With --apply a personal skill moves to skills-archive/, where nothing is lost but it is no longer loaded. A project skill belongs to the team: it is reported, never moved.

.agents/skills/run-checks/SKILL.md
---name: run-checksdescription: Use before calling a change done in this repo.---1. pnpm typecheck2. pnpm test --runInBand   (in parallel they fight over the dev server port)3. Report what failed, with the command that showed it.

v2update_skill, reason: tests hung on the dev server port. v1 is kept in skill-history/.

An example skill. Skills from .claude and .agents folders load too, and /skills lists what it can use.

05 it checks its work

How does Mnemo know a change actually works?

It runs the project's checks before it calls a change done, moves to a stronger model when they keep failing, and can race several attempts and keep the smallest one that passes.

formatNothing counts as done until the checks have run over it and everything has snapped square.

How it works

  1. Verify before done

    A run that changed code and ran nothing is sent back once, to run the project's checks: the test, typecheck, lint and build commands memory knows for this project. A change is checked before it is called done.

  2. Escalate when the checks keep failing

    With --escalate provider/id, after the checks fail twice the rest of the run moves to the stronger model, and a note in the transcript says why. The cheap model does the work it can; the expensive one only finishes what it could not.

  3. Best of n

    mnemo -p "<task>" --best-of 3 --check "npm test", or /bestof in the interface, runs attempts in separate git worktrees, runs the check in each, and applies the smallest change that passed. Every candidate's diff is kept, and if none passes nothing is applied.

  4. Headless

    mnemo -p "<task>" runs one task and prints the answer, which suits scripts and CI. It never asks, so run it in a container or a throwaway checkout.

Verify before done

A run that changed code and ran nothing is sent back once to run the project's checks.

●edit src/cart.ts
│Done, the discount now rounds down.
↺sent back: code changed and nothing was run
●bash pnpm test
✓42 passed

Escalate

--escalate provider/id finishes a run on a stronger model after two failed checks.

●bash pnpm test
✗2 failed
●bash pnpm test
✗1 failed
⇡escalated to provider/strong-model after 2 failed checks
✓all passed

Best of three

/bestof or --best-of 3 --check "pnpm test": three attempts in separate worktrees; the smallest passing change is applied.

1✗ check failed
2✗ check failed
3✓ 6 lines · applied

06 many agents, one window

Can I run several agents at once?

Yes, and they can work as a team. ctrl+n starts another agent on this project, ctrl+g opens the hub, ctrl+s splits the screen (up to four), ctrl+p switches project, and a toast tells you when one you are not watching finishes or needs you. Link two agents and they message each other on their own, within limits you can see.

hubOne hub, many agents: the one you point at comes forward, the rest keep working.

How it works

  1. Another agent, same project

    ctrl+n starts another agent on this project, with its own session. Agents on the same project share one memory, so what one learns, the others recall.

  2. The hub

    ctrl+g shows a card per agent: its status, its last prompt, and one pixel per turn, so a glance says which one is busy, idle or waiting on you.

  3. Split view

    ctrl+s puts up to four agents side by side, each with its own transcript and prompt, in columns, rows, a grid or main + side (alt+l). A sub-agent that starts while its agent is on screen takes a pane by itself.

  4. Sub-agents, and agents that talk

    An agent can start sub-agents, and they can start their own, three levels deep. Press l on two cards in the hub to link them as siblings: they see what the other is doing and message each other. A message wakes an idle agent, which reads it and can answer on its own, and the conversation marks it ✉ as another agent's words, not yours. Links are remembered, so two projects you linked are linked again when both are open.

  5. Talk to a sub-agent

    In a split, alt+, and alt+. move through every pane, sub-agents included. A focused sub-agent pane has a prompt: what you type reaches it after its current step, as your words. esc goes back to the agent.

  6. Bounded on its own

    Agents answering each other stop after 12 messages in a row since you last spoke, and turns that messages start may spend $0.50 per agent until you prompt it again. Past either, messages wait for you, and the hub card says so. A woken agent's edits and commands still ask you, as any turn does.

  7. The playground

    ctrl+y shows every agent, sub-agent and message between them, live, to watch only. c shows the selected agent's exchange with another as a thread, and enter takes you to the agent.

  8. Projects

    ctrl+p switches project. Memory is kept per project, so a command learned in one repository is not offered in another.

  9. Toasts

    When an agent you are not watching finishes or needs an answer, a toast says which one, so a long run never waits on you unnoticed.

The Mnemo hub: a card for each agent with its status, its last prompt and one pixel per turn

Every agent and what it is doing, one pixel per turn. Hover here and press g, s or t.

07 permissions

Is it safe to let it run commands?

By default it asks before every edit and command. Four modes set how much it may do on its own, and ordered allow / ask / deny rules in ~/.mnemo/permissions.json hold in all of them. The gate filters what runs; it is not a sandbox.

vaultNothing opens by accident: each kind of action has its own combination, and you set it.

How it works

  1. A deny rule outranks everything

    Rules in ~/.mnemo/permissions.json say allow, ask or deny for a tool and a pattern. A deny holds in every mode, /yolo included, with or without a terminal: “stop asking” is a statement about questions, not about permissions.

  2. Approvals generalise by subcommand, never by program

    Approving git status --short “always” covers git status*, never git*, which would also hand over git push and git clean -xdf. Arguments never generalise: a path is not a class.

  3. A compound command never inherits a grant

    ls; rm -rf / matches an approved ls* and must not use it. Anything with a shell metacharacter is its own question.

  4. Ask is the default

    There is no fallthrough that quietly allows. Plan mode refuses every change and tells the model to describe it instead. Sub-agents and programs in the Python kernel go through the same gate, and you still answer for every edit and command they make.

  5. A filter, not a sandbox

    Commands run as you and inherit your environment, provider keys included, which a prompt injection could try to read. Use /yolo and headless -p in a container or a throwaway checkout.

Asks before every edit and command.

What happens to each action in default mode
The agent wants toToolIn /default
read src/fetch.tsreadruns
edit src/fetch.tseditasks you
pnpm testbashasks you
a command your deny rules matchbashrefused

08 what it can use

What tools does the agent have?

The usual coding tools, plus memory it can search and correct, skills it can write, a Python kernel that can drive the other tools in parallel, and sub-agents it can hand work to.

relayWork is handed down a path, hop by hop: to a program, to a sub-agent, and back with an answer.

How it works

  1. A Python kernel that drives the other tools

    ipy_run runs Python in a persistent kernel whose state survives between calls. Inside it, tools.read(), tools.bash() and tools.grep() call the agent's tools, and tools.parallel([...]) sends a whole batch at once: one program instead of a dozen round trips.

  2. Sub-agents with a brief, not a transcript

    spawn_subagent hands a self-contained task to a child agent: read-only for research, or full to edit. The child gets a brief the parent wrote, the parent's model, and the same memory, so what it learns the parent can recall. Its steps stream into the parent's tool block, delegation is limited in depth, and you still approve its edits and commands. If its model call fails, the tool says why.

  3. Memory it can search and correct

    memory_search and session_search look things up; memory_remember keeps a durable fact; memory_steer says that something memory supplied was wrong, so it is trusted less next time.

  4. Skills it can write

    create_skill and update_skill, described above, plus the coding tools every turn uses: read, edit, write, bash and grep, each through the permission gate.

memory_search
session_search
memory_remember
memory_steer
create_skill
update_skill
ipy_run
spawn_subagent
list_agents
message_agent
code_search · code_symbol · code_refs · code_map
ask_user
read · edit · write · bash · grep

memory

memory_search

Search long-term memory for this project and user: conventions, past sessions, pitfalls and their fixes, lessons, skills.

09 detachable memory

Can Claude Code or Codex use the same memory?

Yes. mnemo memory setup claude-code prints the hooks and MCP entry that give Claude Code (or Codex) the same memory, and mnemo memory ingest learns from the Claude Code sessions you already have. What one agent learns, the others recall.

patchOne memory, patched into every agent you use: plug a new one in and it starts from what the others learned.

How it works

  1. One command to attach it

    mnemo memory setup claude-code prints the hooks and the MCP entry to add to Claude Code (or Codex). Nothing is changed for you: you see exactly what goes where.

  2. Hooks bring memory in, and take the session out

    At session start Claude Code gets the project and user profiles and the last session, again after /clear, resume and compaction, so memory survives a compaction. On each prompt it gets what search finds: pitfalls with their fixes, earlier sessions, skills. When it stops, the session is reflected on and learned, in the background.

  3. An MCP server for asking on purpose

    The same memory is offered as MCP tools: memory_recall, memory_search, memory_remember and session_search.

  4. Learn from sessions you already had

    mnemo memory ingest replays the Claude Code sessions already on your disk through the same loop Mnemo runs live, so a session worked by a frontier model teaches the memory a cheaper model will use. Each memory keeps where it came from.

MnemoClaude CodeCodexmemorymemsrv · local
$ mnemo memory setup claude-code
$ mnemo memory ingest

10 commands

What can I type?

Type / in Mnemo for every command: these built-ins, your skills, and whatever the agent's extensions add. Try it here.

keyboardEverything is a key or a slash away; the keys you reach for most never animate.
26
  • /memorywhat Mnemo remembers · /memory <words> searches it
  • /remembertell Mnemo something to keep: /remember we deploy with fly
  • /forgetretire a remembered fact: /forget package manager
  • /bestofrace N attempts at a task, keep the smallest that passes: /bestof 3 "npm test" <task>
  • /skillsthe skills Mnemo can load
  • /modehow much Mnemo may do without asking (default, accept-edits, plan, yolo)
  • /plantoggle plan mode (read-only)
  • /accept-editstoggle accept edits: change project files without asking, still ask before commands
  • /yolotoggle bypass: ask for nothing (deny rules in permissions.json still hold)
  • /modelchoose the model
  • /thinkingset how hard the model thinks
  • /loginadd a provider (API key or subscription)
  • /logoutremove a provider's credentials
  • /themethe look: Mnemo Night, Dracula, Nord, Gruvbox, Tokyo Night, Catppuccin, Synthwave, Amber CRT, Game Boy, Paper, Solarized
  • /resumecontinue an earlier session in this folder
  • /rewindgo back to before an earlier message: the conversation, the files, or both (esc esc)
  • /newstart a fresh session
  • /compactsummarise the conversation to free context
  • /costtokens and spend for this session
  • /statsthis session, the last 7 days, and how the tools fared
  • /reloadreload skills, prompts and extensions
  • /clearclear the screen (the session is kept)
  • /updateinstall the latest Mnemo · /update auto on|off: a daily check that only tells you
  • /mousemouse wheel scrolls the conversation (on) or your terminal selects text (off)
  • /helpcommands and keys
  • /quitleave Mnemo

11 the interface

Why does it look like a game?

Because a long session should be pleasant to watch. Mne the elephant reacts to the work, diffs and test runs are drawn as pixels, and /theme switches between eleven palettes that keep the same roles: magenta for the agent, cyan for structure, amber for anything memory did.

explodedThe interface in layers: the transcript is the application, and everything else floats over it.

files

src/fetch.ts M

memory

◆ http helper

◆ language

▊ add a retry to the fetch helper

● edit src/fetch.ts

+ for (let attempt = 1; ; attempt++) {- const res = await fetch(url);

│ Done: server errors retry up to three times.

◆ +2 learned

defaultdemo-model

12 what we measured

Does the memory make a small model better?

On a small, cheap model (DeepSeek v4.1 Flash), through the same agent loop with memory on and off: from 87% to 100% on a six-task repository and from 82% to 99% on two repositories with conflicting rules. On unrelated one-off tasks it made no difference. Small samples: read the direction, not the decimals.

Six tasks in one repo, with rules the code does not reveal (3 runs)

no memory · 87%
memory · 100%

Two repos whose rules conflict (2 runs)

no memory · 82%
memory · 99%

Terminal-Bench subset: 10 easy/medium tasks, one attempt each

no memory · 10 / 10
memory · 10 / 10

The last row is the honest one: unrelated tasks in a fresh container give memory nothing to remember (about $0.008 a task either way), and it is a subset on our own machine, not comparable to the public leaderboard. Against a simpler, global memory in the style of Hermes Agent, Mnemo matched it at one or two repos and was ahead where it keeps projects apart and picks up unfinished work. Raw results: research/, hermes-comparison.md.