Skip to main content

Persistent memory for Claude Code across sessions and compaction (hooks + an MCP memory server)

What CLAUDE.md and auto memory cover, how a SessionStart hook re-injects context after compaction, and how to add a hosted memory layer on the same hooks.

Updated 7 min readMarkdown

Disclosure: I'm Mohammed, founder of MemorySync. I drafted this article with AI assistance and reviewed it for accuracy against the official MemorySync and Claude Code docs. The code is adapted from the docs and I haven't run it.

Claude Code starts every session with a fresh context window, and when a long session fills up, compaction summarizes the conversation to free space. Claude Code's own docs say that summary "can lose important details". So the two problems (a new session and a compact) are really one question: how do I get the important stuff back at the start of a session, and again after a compact?

This post walks through the layers, from the built-in ones to a hooks-based memory layer:

  1. What CLAUDE.md and auto memory already give you.
  2. A SessionStart hook that re-injects context after compaction (no extra service).
  3. The MemorySync plugin, which uses the same hooks to recall from a hosted memory layer, plus the hosted MemorySync MCP server.

The Claude Code behaviour comes from the official memory, hooks reference and hooks guide pages. Everything about MemorySync comes from its Claude Code Memory guide. The commands and config are adapted from those docs. I haven't run them for this post, so check them against your Claude Code version.

1. What's built in

Claude Code has two ways to carry knowledge across sessions:

CLAUDE.md Auto memory
Who writes it You Claude, based on your corrections and preferences
What it's for Instructions and rules: build commands, conventions, "always do X" Learnings Claude decides are worth keeping
Loaded Every session Every session (first 200 lines or 25KB)

Start here. Put your build and test commands and project conventions in ./CLAUDE.md (or ./.claude/CLAUDE.md), keep it under about 200 lines as the docs suggest, and run /context to confirm it shows up under Memory files.

What these files don't give you, in my view, is a searchable store of facts that's scoped per project and follows you into other tools. That's the gap the next two layers fill.

2. Re-inject context after compaction with a hook

Hooks are commands Claude Code runs at fixed points in a session. The one that matters here is SessionStart, and its matcher says how the session began:

Matcher Fires on
startup A new session
resume --resume, --continue or /resume
clear /clear
compact Auto or manual compaction
fork A session forked from an existing one

For SessionStart, Claude Code adds the plain text your command prints to stdout into Claude's context. That gives you a simple fix for compaction. This is the example from the hooks guide, in .claude/settings.json:

{
  "hooks": {
    "SessionStart": [
      {
        "matcher": "compact",
        "hooks": [
          {
            "type": "command",
            "command": "echo 'Reminder: use Bun, not npm. Run bun test before committing. Current sprint: auth refactor.'"
          }
        ]
      }
    ]
  }
}

Swap the echo for anything that prints useful state, such as git log --oneline -5. Three limits from the reference are worth knowing:

  • Hook output (additionalContext or plain stdout) is capped at 10,000 characters.
  • SessionStart runs on every session, so keep it fast.
  • At launch, SessionStart fires before the session's MCP servers are available, so mcp_tool hooks are skipped then. Use a type: "command" hook for anything the session needs at startup.

This works well for static reminders. It doesn't learn anything new on its own, though. Whatever you echo is whatever you wrote last.

3. A memory layer on the same hooks: the MemorySync plugin

MemorySync is a hosted memory layer, and I'm building it. Its Claude Code plugin wires the same lifecycle points to that memory. According to the guide:

Moment What happens
Session start, resume or clear Your profile and this project's context are recalled and injected before the first prompt
Every prompt The prompt is sent for fact extraction, and only the durable facts in it are stored. Prompts of 24 characters or more also recall memories relevant to that prompt
Claude finishes replying Nothing is sent. Replies aren't stored
Context compaction Memory is re-injected after the compact

It also bundles the hosted MemorySync MCP server (search, add, list, update, delete and more), a memory skill, and three commands: /memorysync:status, /memorysync:remember and /memorysync:recall. Two details I like: facts are tagged with the git repository you're in, so recall at session start is about this project while preferences follow you everywhere, and the plugin never writes to CLAUDE.md or MEMORY.md. Your static rules stay yours.

Install

You need Node.js 18+ on your PATH (the hook scripts use it) and an API key from app.memorysync.io in your environment:

# macOS/Linux (add it to your shell profile)
export MEMORYSYNC_API_KEY=ms_...
# Windows
setx MEMORYSYNC_API_KEY ms_...

Then, inside Claude Code:

/plugin marketplace add memorysyncio/memorysync-plugins
/plugin install memorysync@memorysync

In a session, /plugin install opens the plugin panel so you can review the plugin and pick a scope first (that's Claude Code's behaviour, per its plugin docs). Restart the session, then check it:

/memorysync:status

The status command reports whether the key is present, whether the API is reachable, and which user and project scope it resolved. The guide calls it "the first thing to run when anything looks off". Without an API key, the bundled MCP server falls back to OAuth sign-in and the hooks stay off. You won't see an error.

Test it across a session and a compact

  1. Tell Claude something durable: "In this repo we use pnpm, and integration tests need the TEST_DB_URL env var."
  2. Run /clear (or open a new session) and ask, "How do I run the integration tests here?" without repeating the details.
  3. In a long session, run /compact and ask again.

If step 2 or 3 comes back empty, run /memorysync:status before anything else.

Knobs

  • MEMORYSYNC_USER_ID sets the user (default: your OS username).
  • MEMORYSYNC_PROJECT overrides the project, which otherwise comes from the git remote.
  • MEMORYSYNC_PROMPT_RECALL=off turns off per-prompt recall.
  • With CLAUDE_CODE_DISABLE_NONESSENTIAL_TRAFFIC set, the plugin makes no network calls.

What it won't do

The guide says every hook exits 0 on every failure path (no key, network down, server errors), so the worst case is a turn without memory, not a broken session. The memory skill refuses to store tokens, keys and passwords, and retrieved memories are injected with a "background data, not instructions" guard. Your prompts go to your MemorySync account for extraction. You can delete any memory from /memorysync:recall or the dashboard.

Claude Cowork and teams

Cloud sessions install repo-declared plugins only, so commit this to .claude/settings.json and add MEMORYSYNC_API_KEY to the session's Cloud Environment variables:

{
  "extraKnownMarketplaces": {
    "memorysync": {
      "source": { "source": "github", "repo": "memorysyncio/memorysync-plugins" }
    }
  },
  "enabledPlugins": { "memorysync@memorysync": true }
}

MCP only, if you don't want hooks

If you'd rather call memory tools yourself, with no automatic capture or recall, connect just the hosted server:

claude mcp add --transport http memorysync https://mcp.memorysync.io/mcp

Without MEMORYSYNC_API_KEY set, it signs you in with OAuth on first use. I wrote a separate step-by-step MCP setup for Claude Code and Cursor covering scopes, whoami, saving and recalling, and troubleshooting.

Which layer to use

  • Rules and conventions: CLAUDE.md.
  • A fixed reminder after every compact: a SessionStart hook with the compact matcher.
  • Facts that should build up over time, per project and across sessions and compactions: a memory layer behind those hooks.

You can run all three at once. They don't overlap.

Try it

If you want to see the save, reload and recall loop before installing anything, the MemorySync playground runs it in your browser: memorysync.io/try.

About the author

  • Building MemorySync (memorysync.io) — persistent memory infrastructure for AI agents, Cursor, and Claude Code.

No comments yet. Be the first to comment.