Skip to content
Conduit

skill

cc-codex-memor

zhangshoupeng/cc_codex_memorcommunitylistedunreviewed

Set up

Skills are installed by placing their folder where your agent loads skills.

The download comes from github.com/zhangshoupeng/cc_codex_memor itself, not from our server, so what you get is exactly what its author published.

Install instructions come from the README

Skills do not use an MCP config. Follow the steps in the README below.

README

synced Oct 25, 2026

memor

Find that conversation again — across Claude Code and Codex.

node deps license

中文文档


You spent an hour with an agent working out why the token refresh kept failing. Two weeks later you hit the same bug and you know — you know — you already solved this. But was it in Claude Code or Codex? Which repo were you in? /resume only matches session titles, and yours are all called things like "fix the thing".

So you end up grepping 300 MB of JSONL by hand, or just solving it again from scratch.

memor makes that lookup take a second. It reads both agents' logs, from your terminal or from inside either agent.

What it looks like

$ memor token refresh

7 sessions matched 「token refresh」, showing top 2 by relevance

 1 │ codex · 12 days ago · 23 turns · 1.4 hours · gpt-5.5
   │ ~/work/api-gateway · feat/oauth-rotation
   │ refresh token keeps 401ing after ~1h
   │
   │ ended  Root cause: we were caching the token by user id, but the refresh
   │        endpoint rotates the *refresh* token too. Cache key now includes the
   │        rotation counter — see auth/session.go:88.
   │ match  The 401 only shows up after the first rotation, which is why it looked
   │        like a clock-skew problem at first.
   │        msg · line 214
   └ memor show 1  ·  codex resume 019fcfa7-…

 2 │ claude · 3 weeks ago · 6 turns · 22 min
   │ ~/work/api-gateway · main
   │ add token refresh to the SDK client
   │
   │ ended  Added retry-on-401 with a single refresh attempt. Left a TODO about
   │        concurrent requests all refreshing at once.
   └ memor show 2  ·  claude --resume 7e961826-…

The point isn't the list — it's that you can tell which one to open without opening any of them:

  • 23 turns · 1.4 hours — a real debugging session, not a drive-by question
  • ended … — the last thing the assistant said. Your keyword usually matches the opening question; the conclusion is at the other end of the conversation
  • memor show 1 — open it by number, no UUID juggling

Then memor show 1 prints the actual conversation, and the resume command drops you back into it with full context if you want to keep going.

Getting started

You need Node ≥ 22.5. You also need ripgrep — but if you have Claude Code installed, you already do: it ships one, and memor borrows it. No npm install, no dependencies, nothing to build.

git clone https://github.com/zhangshoupeng/cc_codex_memor.git
cd cc_codex_memor
node scripts/install-plugin.mjs

Just want to try it without installing anything? npx github:zhangshoupeng/cc_codex_memor doctor

Other install routes (npm global, release tarball, env vars, troubleshooting) are in INSTALL.md.

That one command sets up whatever you actually have:

  • Claude Code → 4 slash commands, 4 skills, and 5 MCP tools. Restart Claude Code afterwards.
  • Codex → the same skills and MCP tools. Just open a new session.
  • Neither installed? It skips them and says so. The CLI still works.

For the command line:

ln -s "$PWD/bin/memor.mjs" ~/.local/bin/memor
memor doctor

memor doctor tells you what it found — how many sessions, how big, how fast a query runs. If you've never used either agent, it'll say so and print the paths it looked in. Run --uninstall to reverse everything; your Claude Code config files get backed up to *.memor-bak before the first write.

Using it

From the terminal

memor rate limiting            # multiple words are AND
memor "connection pool"        # quote a phrase
memor show 1                   # open result #1 from your last search
memor touched src/auth/session.go   # which sessions actually edited this file
memor timeline --since 7d      # what did I work on this week
memor prompts "retry logic"    # only things *you* typed

Narrow it down with --tool cc|codex, --project, --branch, --since 7d, --limit, --scope msg,tool_in,tool_out. Full list in memor --help.

CJK works as-is — no configuration, no tokenizer setup. (Details in Design notes.)

From inside an agent

This is where it gets good. Just ask:

Didn't we already fix this token refresh thing?

The agent searches your history, reads the relevant session, and answers you — instead of handing you a list to dig through. That's the difference between the CLI and the plugin: the CLI finds sessions, the agent reads them.

If you'd rather be explicit, Claude Code has /memor:recall, /memor:touched, /memor:timeline, /memor:prompts. In Codex, type $ and pick a memor skill.

Under the hood both agents get the same five tools:

ToolAnswers
recall_search"did we discuss X before?"
recall_touched"which session actually changed this file?"
recall_sessionpulls detail out of one session, paginated
recall_timeline"what did I do last week?" — metadata only, instant
recall_prompts"how did I phrase that?" — only your own typed messages

Responses are capped (300-char excerpts, 8 sessions) so they don't eat your context window.

Design notes

There's no index, on purpose

The obvious design is a SQLite FTS5 index. I built the plan for it, then measured, and threw it out. On a real 383 MB / 474-session corpus:

memor (ripgrep)SQLite FTS5
Query15–76 ms~300 ms target
Extra disk3.3 MB of metadata400–600 MB
First run420 ms1–3 minutes
Your raw datanever copiedplaintext credentials duplicated into the index
Things that can break—incremental watermarks, WAL locks, schema-drift rebuilds

Two things made the index pointless. ripgrep is already an order of magnitude faster than the budget I'd set for the index. And CJK is stored as literal UTF-8 in the raw JSONL, not \uXXXX escapes — so ripgrep searches Chinese directly, and the trigram tokenizer the FTS design needed was solving a problem that doesn't exist.

Linear scan does grow with your history: around 2 GB you're looking at 200–400 ms, still fine. The search layer is a separate module, so a real index can slot in later without touching anything above it.

The hard part is ranking, not finding

Both agents inject AGENTS.md, CLAUDE.md, skill bodies and environment context into the transcript as if they were messages you sent. On the test corpus one such term appeared in 447 of 474 sessions, with only a handful being an actual human discussing it. Plain grep drowns.

Three layers push that down:

  1. Structural markers — <environment_context>, <user_instructions>, <skill>, # AGENTS.md instructions for, origin.kind=auto-continuation, and a dozen more. Every entry in that list came from counting real transcripts, not from guessing.
  2. Field weighting — prose 1.0 · tool calls 0.7 · compaction 0.5 · reasoning 0.5 · tool output 0.4 · injected 0.1.
  3. Boilerplate detection — text repeated across many sessions is boilerplate. The statistic is sampled across every coarse hit rather than just the shortlist, because the same AGENTS.md starts with a different project path in each repo; grouping by the head of the message splits it into fragments that never reach the threshold. Grouping by the matched excerpt fixes it.

If a term shows up in more than half your sessions, memor tells you it's low-signal instead of quietly returning noise.

Where the data comes from

rg --count-matches ──► rank via metadata cache ──► rg --json on shortlist ──► parse hit lines
   (per term, ~30ms)        (~15ms)                   (top ~24 files)         (drop false positives,
                                                                                cut excerpts, dedupe)

Parsing the hit lines doubles as the false-positive filter: if the term only lives in a base64 signature, a JSON key or a skipped record type, the decoded text won't contain it and the hit is gone.

Claude CodeCodex
Transcripts~/.claude/projects/<slug>/<uuid>.jsonl (+ subagents/)~/.codex/sessions/YYYY/MM/DD/rollout-*.jsonl
Session metadatain-line cwd/gitBranch + ai-title recordsread straight from Codex's own state_N.sqlite
What you typed~/.claude/history.jsonl~/.codex/history.jsonl

The metadata cache lives in ~/.cache/memor/, mode 0600, invalidated by (mtime, size). Writes use a PID-scoped temp file — run both agents at once and you get concurrent memor processes, and a shared temp name gets truncated mid-write by the other one (reproducible, and it cost me an afternoon).

Privacy

Transcripts contain plaintext credentials — API keys pasted into chat, config files that got cat-ed. Since MCP feeds excerpts back into a model, everything is redacted on the way out: sk-*, Bearer *, gh[pousr]_*, AKIA*, xox*-*, PEM private key headers.

Your conversation data is never copied anywhere. memor reads the files in place.

Known limits

  • ripgrep searches the raw JSON, where a newline inside a message is the two characters \n — a phrase spanning a line break won't match. Same for queries containing " or \.
  • Codex reasoning blocks are mostly encrypted_content; only the plaintext summary is searchable.
  • Sub-agent sessions can't be resumed on their own — results point at the parent.
  • ended … shows where a session finished, which can be off-topic if it drifted after your keyword.

Contributing

npm test                          # 31 unit tests: parsers, prompts, redaction, path extraction
node scripts/recall-check.mjs     # recall audit against raw `rg -l`
node scripts/recall-check.mjs your terms here    # ...on your own corpus

recall-check.mjs re-parses every file the pipeline dropped and asserts the decoded text genuinely doesn't contain the term. It proves the shortlist cap, per-file match cap, scope filters and boilerplate demotion never throw away real content — the kind of bug that's otherwise invisible.

Both agents log in slightly different, undocumented shapes that change between versions. If memor starts missing things after an update, memor doctor reports the share of lines it couldn't parse, and the parsers in src/parse/ are deliberately forgiving — unknown record types are skipped, never crashed on. PRs adding a newly-observed record type are very welcome.

While developing: the CLI symlink and the Codex plugin both point at your working tree, so edits are live. Claude Code installs a snapshot copy, so rerun node scripts/install-plugin.mjs and restart it.

Prior art

cc-search · claude-history · claude-chat-search · claude-code-chat-explorer · claude-historian-mcp

All of these are Claude-Code-only, and all use FTS5 default tokenizers, which don't segment CJK. If you only use Claude Code and only search in English, several of them are excellent — go use one. memor exists because I use both agents and search in Chinese.

License

MIT

↑↓ navigate openesc close