Auto-summarize your AI coding session with Anthropic's 9-section template before context compaction fires. Cross-IDE, cross-session, zero data loss.
The problem: When your session hits ~85% context, Claude Code (and every IDE that follows its spec) auto-compacts your history. The default compaction summary is lossy — verbatim user messages, load-bearing code snippets, and half-solved bugs often disappear. If you switch IDE (Claude Code → Cursor → Codex) or open a new session, there's nothing to hand off.
What this does: A PreCompact hook fires before the system compacts. It injects Anthropic's 9-section template (from Claude Code's own BASE_COMPACT_PROMPT) into the model's context, so the model writes a full structured summary first, saves it to <project>/summary/sessions/, then lets compaction proceed.
Works with Claude Code · CodeBuddy · WorkBuddy · Codex Desktop · Cursor.
⚠️ Cursor is a partial case. ItspreCompacthook is documented as observational — it fires when compaction happens but cannot inject a prompt or block the compaction. So on Cursor, this plugin can only warn you (viauser_message) that compaction is in progress; it cannot auto-write the summary. Run/session-summarizermanually at ~60-70% context. See Cursor limitations below.
| IDE | Manual /session-summarizer |
Auto-triggered summary before compaction |
|---|---|---|
| Claude Code | ✅ | ✅ (real inject) |
| CodeBuddy | ✅ | ✅ (real inject) |
| WorkBuddy | ✅ | ✅ (real inject) |
| Codex Desktop | ✅ | ✅ (real inject; needs /hooks trust on first run) |
| Cursor | ✅ |
Pick the option that matches your setup.
Inside Claude Code:
/plugin marketplace add yhwang303/session-summarizer
/plugin install session-summarizer@session-summarizer
Restart Claude Code. That's it. /session-summarizer and the PreCompact hook are both live.
If you want it in Cursor / CodeBuddy / WorkBuddy / Codex too (or in addition to Claude Code):
npx github:yhwang303/session-summarizer installOr install into specific IDEs only:
npx github:yhwang303/session-summarizer install --target claude-code,cursorThe installer:
- Drops the
/session-summarizerslash command into each IDE's commands directory - Merges a
PreCompacthook into each IDE's settings file (JSON or TOML) - Backs every file up as
<file>.bak-<timestamp>before writing - Is idempotent — re-running never duplicates entries
- Preserves your existing hooks (adds a marked entry, never touches other people's)
Verify:
npx github:yhwang303/session-summarizer statusUninstall (only removes what session-summarizer added; leaves your other hooks untouched):
npx github:yhwang303/session-summarizer uninstallFor environments where npx isn't available:
git clone https://github.com/yhwang303/session-summarizer ~/session-summarizer
cd ~/session-summarizer
node bin/cli.mjs installRequirements: Node 18+ and Python 3.8+ (Python is used by the hook script itself, not by the installer).
Two triggers, one output shape:
| Trigger | When it fires | How the summary gets written |
|---|---|---|
| Explicit | You type /session-summarizer any time |
Slash command loads the 9-section template and calls write_summary.py |
| Automatic | PreCompact event — right before the IDE auto-compacts |
Hook injects the template into additionalContext; the model writes it, calls write_summary.py, then lets the IDE compact |
Output goes to a consistent path regardless of IDE — that's the whole point:
<project>/summary/sessions/
├── index.md # append-only, human-readable
├── 2026-07-24-claude-code-1430.md
├── 2026-07-24-codebuddy-1615.md
└── 2026-07-23-cursor-2210.md
Filename format: YYYY-MM-DD-<ide>-HHMM.md — date + which IDE fired the summary + minute-precision time. Same IDE / same minute collisions get a -r2 / -r3 suffix automatically. Summaries are never overwritten — every trigger produces a fresh file, so you have a full history for the project.
Every summary follows Claude Code's official BASE_COMPACT_PROMPT:
- Primary Request and Intent — every explicit user ask, in order
- Key Technical Concepts — technologies actually discussed
- Files and Code Sections — every file touched, plus load-bearing snippets
- Errors and Fixes — every error and how it was resolved (user's own wording preserved)
- Problem Solving — completed + still-in-progress
- All User Messages — verbatim, drift anchor
- Pending Tasks — explicit unfinished asks
- Current Work — what you were doing right before compaction
- Optional Next Step — quoted from the most recent user message
Section 6 is what makes cross-session resumption safe: you can hand a new session the summary file and it can reconstruct your exact ask, not a paraphrase.
Session A (Claude Code) Session B (Cursor / Codex / anything)
───────────────────── ───────────────────────────────────
context hits 80% context "Read summary/sessions/2026-07-24-*.md
│ and continue where I left off"
▼
PreCompact hook fires │
│ ▼
9-section summary written Model picks up with §6
to summary/sessions/ (verbatim user asks) + §8
│ (what was in flight) + §9
▼ (next step)
IDE compacts normally
The output directory is fixed at summary/sessions/ regardless of which IDE triggered it. That's the design — cross-IDE handoff would be impossible with per-IDE paths.
session-summarizer <command> [options]
install Install into all IDEs (default) or --target <keys>
uninstall Remove everything session-summarizer added
status Show install state per IDE
doctor Diagnostics (Node/Python detection, layout)
Options:
--target claude-code,cursor,codebuddy,workbuddy,codex
--dry-run Print plan without touching disk
--force Overwrite existing slash-command files
--json Machine-readable output
Cursor is different from every other supported host. Read this before assuming it works the same way.
What Cursor's preCompact hook does (per official docs):
- Fires when auto-compaction happens
- Receives useful stdin fields:
context_usage_percent,is_first_compaction,messages_to_compact, etc. - Only accepts
user_messagein stdout — noadditionalContext, nodecision, noblock - Explicitly documented as: "an observational hook that cannot block or modify the compaction behavior"
What this means for session-summarizer on Cursor:
- By the time the hook fires, Cursor has already committed to compacting — details are being lost right now, not "about to be lost"
- The hook cannot ask the model to write a summary first
- The most we can do is display a
user_messagetelling you compaction is happening
What we do on Cursor:
- Install the
/session-summarizerslash command into~/.cursor/skills/session-summarizer/SKILL.mdfor manual use - Register a
preCompacthook that emits auser_messagereminding you to run/session-summarizerearlier next time (at ~60-70% context) rather than waiting for auto-compaction
Recommended workflow on Cursor:
- Run
/session-summarizerproactively during long sessions — don't wait for the auto-compact warning - Watch for the compaction warning message; when you see it, treat the current session as "already lossy" and start recovering with the summary file you wrote earlier
- For handoff to another IDE, generate the summary via
/session-summarizerbefore switching
Why we didn't build "stop-hook + SQLite polling" auto-injection:
Cursor's stop hook does support a followup_message field that could theoretically auto-inject /session-summarizer after every N turns. But this would require reading Cursor's undocumented SQLite chat storage (state.vscdb, schema is community-reversed) to estimate context usage, which is brittle across Cursor upgrades. If you want that path, open an issue — we can add it as an opt-in flag if there's demand.
Other hosts (Claude Code / CodeBuddy / WorkBuddy / Codex Desktop) don't have this limitation — their PreCompact hooks accept additionalContext and can genuinely make the model write a summary before compaction proceeds.
- Never destroys your hooks. Merge appends a marked entry (
__source: "session-summarizer"); your own hooks stay put. - Auto backup before every write:
<file>.bak-<YYYYMMDD-HHMMSS>. - Idempotent. Repeated
installshowsunchanged— no duplicate entries. - Scoped uninstall. Only removes the marked entry. Everything else you had is preserved.
- Hook never calls the LLM directly. It only injects an
additionalContextstring; the current session's model does the writing. Worst case (model ignores it): you fall back to the IDE's default compaction — nothing crashes.
Q: Where do summaries live?
<project>/summary/sessions/. Same path across every IDE — that's what makes cross-IDE handoff possible.
Q: Should I commit summary/sessions/ to git?
Your call. If not, add summary/sessions/ to .gitignore (this repo's .gitignore already excludes it).
Q: Does the hook fire when I manually run /compact?
No. Only on auto triggers. Manual compaction means you know what you're doing.
Q: Will running /session-summarizer twice on the same day overwrite the first summary?
No. Filename includes the minute (YYYY-MM-DD-<ide>-HHMM.md), so different times produce different files. Same-minute collisions get a -r2 suffix. Every summary is preserved.
Q: Does this work with Codex CLI (the terminal one, not the desktop app)?
No. Codex's Rust CLI doesn't expose user-level hooks. Codex Desktop is supported. CLI users can still run /session-summarizer manually.
Q: Is Cursor's auto-triggered path as good as the others?
No — see Cursor limitations. On Cursor the hook can only warn you, not write the summary. Manual /session-summarizer still works exactly like everywhere else. If you use Cursor heavily, get in the habit of running it proactively at ~60-70% context.
Q: Why not use Cursor's stop hook to auto-inject /session-summarizer after N turns?
It's technically possible via followup_message, but it requires reading Cursor's undocumented SQLite chat DB to estimate context usage, and the schema breaks on Cursor upgrades. Not shipped by default; open an issue if you want an opt-in flag.
Q: What if my auto-triggered summary got cut off?
The hook only injects a prompt; the model does the writing. In very tight context conditions, output may be shorter than ideal. Best practice: run /session-summarizer manually before you cross ~80% context on long design/debug sessions you plan to resume.
Q: I want to re-run install after upgrading — safe? Yes. Idempotent. Re-run to pick up any new features.
Issues and PRs welcome at github.com/yhwang303/session-summarizer.
Before opening a PR: run node bin/cli.mjs install --dry-run to sanity-check the plan output on your machine.
MIT © yhwang303