agents/openai.yaml
interface:
display_name: "AI Coding Agents — Sessions"
short_description: "Design coding-agent session lifecycle"
default_prompt: "Use $ai-coding-agents-sessions to design resume flows, transcript restoration, cross-worktree recovery, or session-state persistence for a coding-agent runtime."
data/sources.json
{
"metadata": {
"skill": "ai-coding-agents-sessions",
"title": "AI Coding Agents Sessions - Sources",
"description": "Official documentation and implementation references for coding-agent session lifecycle, resume, checkpointing, and transcript restoration",
"last_updated": "2026-07-11",
"updated": "2026-07-11",
"total_sources": 12,
"version": "1.1"
},
"categories": {
"official_documentation": [
{
"name": "Claude Code Documentation",
"url": "https://code.claude.com/docs/en",
"type": "documentation",
"relevance": "Primary runtime documentation for Claude Code session behavior",
"update_frequency": "monthly",
"access": "free",
"add_as_web_search": true
},
{
"name": "Claude Code Manage Sessions",
"url": "https://code.claude.com/docs/en/sessions",
"type": "documentation",
"relevance": "Authoritative source for --continue/--resume/--from-pr, the /resume picker, session naming and default names, session-picker scoping and widen keys (Ctrl+W/Ctrl+A/Ctrl+B), /branch and --fork-session semantics, transcript storage path and cleanupPeriodDays retention",
"update_frequency": "monthly",
"access": "free",
"add_as_web_search": true
},
{
"name": "Claude Code Checkpointing",
"url": "https://code.claude.com/docs/en/checkpointing",
"type": "documentation",
"relevance": "Authoritative source for /rewind, Esc-Esc entry, per-prompt checkpoint creation, restore modes (code/conversation/both), Summarize from here / Summarize up to here, the bash-command tracking limitation, and rewind-past-/clear- behavior (v2.1.191+)",
"update_frequency": "monthly",
"access": "free",
"add_as_web_search": true
},
{
"name": "Claude Code Create Custom Subagents",
"url": "https://code.claude.com/docs/en/sub-agents",
"type": "documentation",
"relevance": "Authoritative source for fork-vs-named-subagent startup modes, CLAUDE_CODE_FORK_SUBAGENT env var, /fork slash command, version gates (v2.1.117 minimum, v2.1.161 default-on), coordinator-mode incompatibility, no-nested-forks rule, isolation: worktree option, and prompt-cache economics",
"update_frequency": "monthly",
"access": "free",
"add_as_web_search": true
},
{
"name": "Claude Code Agent View Documentation",
"url": "https://code.claude.com/docs/en/agent-view",
"type": "guide",
"relevance": "Agent-view panel for monitoring and resuming background agents; claude agents / claude attach / claude stop / claude respawn / claude rm; disableAgentView setting; daemon roster.json, jobs/<id>/state.json, and worktree.bgIsolation; CI use via claude agents --json",
"update_frequency": "monthly",
"access": "free",
"add_as_web_search": true
},
{
"name": "Claude Code Agent View Blog Post",
"url": "https://claude.com/blog/agent-view-in-claude-code",
"type": "engineering_post",
"relevance": "Announcement and deep dive on agent-view: background session state paths, daemon architecture, awaySummary behavior, and CI integration via claude agents --json",
"update_frequency": "static",
"access": "free",
"add_as_web_search": true
},
{
"name": "Claude Code Settings Reference",
"url": "https://code.claude.com/docs/en/settings",
"type": "documentation",
"relevance": "Confirms exact settings.json keys and defaults relevant to session lifecycle: disableAgentView, cleanupPeriodDays (default 30 days, minimum 1), awaySummaryEnabled (default true)",
"update_frequency": "monthly",
"access": "free",
"add_as_web_search": true
}
],
"implementation_references": [
{
"name": "Claude Code GitHub Repository",
"url": "https://github.com/anthropics/claude-code",
"type": "repository",
"relevance": "Closed-source product page and issue tracker for Claude Code; not the implementation source — use code.claude.com/docs/en for authoritative behavior docs",
"update_frequency": "weekly",
"access": "free",
"add_as_web_search": false
},
{
"name": "Anthropic: Claude Code Best Practices",
"url": "https://www.anthropic.com/engineering/claude-code-best-practices",
"type": "guide",
"relevance": "Broader operational patterns for stable Claude Code usage and recovery",
"update_frequency": "quarterly",
"access": "free",
"add_as_web_search": true
}
],
"cross_runtime_references": [
{
"name": "Codex CLI Developer Commands Reference",
"url": "https://learn.chatgpt.com/docs/developer-commands?surface=cli",
"type": "documentation",
"relevance": "Current official reference (redirect target of developers.openai.com/codex/cli/reference) for codex resume/--last/--all, codex fork, and codex cloud/cloud-tasks (list/exec/apply) command syntax; re-verified 2026-07-11. Does not publicly document SQLite storage internals — those remain sourced from the pinned commit below",
"update_frequency": "monthly",
"access": "free",
"add_as_web_search": true
},
{
"name": "Codex CLI Documentation (GitHub)",
"url": "https://github.com/openai/codex",
"type": "documentation",
"relevance": "Cross-runtime comparison point for session behavior in coding-agent CLIs",
"update_frequency": "monthly",
"access": "free",
"add_as_web_search": false
},
{
"name": "OpenAI Codex Session/Task/Turn Protocol Source",
"url": "https://github.com/openai/codex/blob/7d47056ea42636271ac020b86347fbbef49490aa/codex-rs/docs/protocol_v1.md",
"type": "repository_source",
"relevance": "Pinned first-party source for Codex Session, Task, Turn, SQ/EQ protocol, response bookmarks, interruption, and one-active-task semantics. Storage/protocol internals not restated in public docs as of 2026-07-11 — treat as commit-pinned engineering detail, re-check against current source before relying on exact file/module names",
"update_frequency": "pinned",
"access": "free",
"add_as_web_search": false
},
{
"name": "Anthropic: Building Effective Agents",
"url": "https://www.anthropic.com/engineering/building-effective-agents",
"type": "guide",
"relevance": "General guidance on durable agent workflows and operational state",
"update_frequency": "quarterly",
"access": "free",
"add_as_web_search": true
}
]
}
}
learnings.consolidated.md
# ai-coding-agents-sessions — Consolidated Learnings
Curated, dated, committed memory for this skill. Pruned from raw `learnings.md` via `agents-skills-feedback-loop/scripts/consolidate.py`. Human-approved.
Cap: 60 entries. When exceeded, promote durable rules to `references/`.
## Filter Override
<!-- Add 2-4 bullets that sharpen what counts as a learning for this skill. Leave empty to use the default filter from agents-skills-feedback-loop/references/learnings-format.md. -->
## Patterns That Work
## Mistakes to Avoid
## Domain Knowledge
## Open Questions
## Consolidated Principles
learnings.md
# ai-coding-agents-sessions — Learnings
## Patterns That Work
## Mistakes to Avoid
- [2026-07-11] cleanupPeriodDays defaults to 30 days, not 7; background-agent worktrees live at project-relative .claude/worktrees/, not ~/.claude/worktrees/<id>/.
- [2026-07-11] Don't conflate /fork (subagent-level context inheritance, CLAUDE_CODE_FORK_SUBAGENT) with /branch or --fork-session (mints a whole new independent session) — both officially documented but easily confused.
## Domain Knowledge
- [2026-07-11] Claude Code checkpoint/rewind tracks only file-editing-tool changes, never bash-modified files (rm/mv/cp) — verified 2026-07-11 against code.claude.com/docs/en/checkpointing.
## Open Questions
## Consolidated Principles
references/context-forking.md
# Context Forking In Subagent Sessions
Subagents in coding-agent runtimes have two distinct context-startup modes. Each implies different session-lifecycle, cost, and isolation behavior. This file owns the **session-layer** view; the **subagent-design** view lives in `agents-subagents` §"Forking Parent Context Into Subagents".
Source: officially documented at [`code.claude.com/docs/en/sub-agents`](https://code.claude.com/docs/en/sub-agents) §"Fork the current conversation" (re-verified 2026-07-11). This was community-reported before it shipped in official docs; it is no longer an unverified surface, but it is still a fast-moving one — the docs themselves flag Claude-initiated forking as an experimental, staged rollout that may change.
## Two startup modes
| Mode | Startup context | Cache behavior | Tool-call visibility |
|---|---|---|---|
| Blank (named subagent) | Fresh, isolated context; own system prompt, own tool access, no parent history, skills, or already-read files | No shared prefix with parent; every spawn pays full input-token cost on its first request | Tool calls stay in subagent; only final summary returns to parent |
| Fork | Inherits the entire parent conversation so far — same system prompt, tools, model, and message history | First request reuses the parent's prompt-cache prefix, making it cheaper than a fresh spawn needing the same context; effective price on cache-hit tokens is roughly cache-read rate (~10% of normal input price on Sonnet tiers) | Tool calls stay isolated; only the fork's final result returns to the main conversation |
Both modes return only the final result to the parent/main session — that part is identical. The difference is what the subagent starts with, and a fork drops the input-isolation property subagents otherwise provide.
## Version gate and activation surfaces
- **Minimum version:** forked subagents require Claude Code **v2.1.117 or later** — the fork path existed in source before that but was compiled out of public releases.
- **`/fork <directive>`** — starts a fork directly, named from the first words of the directive. As of **v2.1.161, `/fork` is enabled by default**; on earlier versions it requires the env var below set to `1`.
- **`CLAUDE_CODE_FORK_SUBAGENT`** — set to `1` to force-enable fork mode (including letting Claude itself decide to spawn a fork instead of a fresh subagent when no `subagent_type` is specified), or `0` to force-disable it everywhere, including any server-side default rollout. Honored in interactive mode, the SDK, and `claude -p`.
- Once fork mode is enabled, **every** subagent spawn — fork or named — runs in the background by default (a panel below the prompt shows running forks/subagents; `Enter` opens a transcript, `x` dismisses or stops one). Set `CLAUDE_CODE_DISABLE_BACKGROUND_TASKS=1` to force spawns back to synchronous.
- A fork can optionally be given `isolation: "worktree"` so its file edits land in a separate git worktree instead of the main checkout.
## Session-lifecycle implications
- **Resume after fork** — a forked subagent's transcript is logically a sidechain of the parent. Resume should treat the parent transcript as primary; the fork's transcript is a sidechain artifact, not a separate session, unless the runtime explicitly promotes it.
- **Cache invalidation** — the fork shares prompt-cache prefix with the parent. If the parent's earlier turns are evicted from cache, the fork loses its discount and pays full input-token cost. Plan budget assuming eviction is possible during long sessions.
- **Isolation guarantee** — forked tool calls do not pollute the parent transcript. The parent sees only the summary returned at fork completion. Persist enough sidechain telemetry that a fork failure can be debugged without rerunning.
- **Cross-worktree** — if the parent moves worktrees mid-fork, the fork keeps operating against the snapshot it received (or its own `isolation: "worktree"` copy). Treat moved-worktree resume as a special case for forks, separate from same-repo worktree adoption.
- **No nested forks** — a fork cannot spawn another fork, though it can spawn other (non-fork) subagent types, which count toward any depth limit. Design resume/audit tooling assuming fork depth is always exactly one level from a real (non-fork) session.
- **Not the same as session branching.** `/fork` inherits context into a *subagent* that reports back into the same session; `/branch` (or `--fork-session`) mints a whole new *independent session* the user switches into. Do not conflate the two in documentation or UI — see the parent SKILL.md §"Rewind vs Git vs Session Branching".
## When to fork vs stay blank
Fork only when you can answer **both** questions:
1. What understanding has the parent built that the subagent needs?
2. Why is recomputing it more expensive than inheriting parent context (with its cache penalty risk and noise)?
If you can name a specific build-up the subagent would otherwise re-derive (read the same 30 files, rerun the same grep sweep, re-establish the same architectural mental model), forking earns its keep. If not, stay blank — fresh context still wins for reviewers, verifiers, and bounded scoped research, where parent transcripts contain noise the worker should not see.
Per `agents-subagents` §"Current Runtime Model", **fresh context per worker is the default**. Forking is the documented exception.
## Anti-patterns
- **Forking by default for every subagent.** Inherits parent's noise (failed tool calls, dead-end exploration) and re-introduces context rot the subagent boundary was meant to prevent.
- **Forking review and verification roles.** A reviewer who inherits the implementer's reasoning is no longer an independent check; the value of review collapses.
- **Forking a coordinator-role subagent.** A forked coordinator inherits the parent's "delegate work" system prompt and starts orchestrating instead of executing — the two modes cannot share a session's role definition cleanly.
- **Treating fork as free.** The cache-discount only applies once the parent prefix is cache-warm; the first fork of a session still pays full cost, and any cache eviction wipes the discount for later forks too.
- **Forking when the parent has touched secrets.** The fork inherits the parent transcript, including any accidentally surfaced secrets, tokens, or PII. Audit before enabling for sensitive sessions.
- **Assuming `/fork` and `/branch` are interchangeable.** They solve different problems (in-session delegation vs. new independent session) and confusing them in a runbook or UI copy causes users to lose track of which session is "real."
## Cross-references
- `agents-subagents` §"Forking Parent Context Into Subagents" — design-side rules and decision matrix.
- [`../../ai-coding-agents-command-runtime/references/command-dispatch-forking-and-remote-safety.md`](../../ai-coding-agents-command-runtime/references/command-dispatch-forking-and-remote-safety.md) — fork model for prompt commands.
- [`context-lifecycle-and-branching.md`](context-lifecycle-and-branching.md) — per-turn branching (continue / rewind / clear / compact / subagent) at the parent thread level.
- [`session-lifecycle-and-resume.md`](session-lifecycle-and-resume.md) — session identity and resume semantics that govern parent-and-fork session pairs.
- Parent SKILL.md §"Rewind vs Git vs Session Branching" — how `/fork` (subagent-level) differs from `/branch`/`--fork-session` (session-level).
references/context-lifecycle-and-branching.md
# Context Lifecycle and Per-Turn Branching
## Table of Contents
- [What Is in the Context Window](#what-is-in-the-context-window)
- [Context Rot](#context-rot)
- [The Five Options at Every Turn](#the-five-options-at-every-turn)
- [Rewind > Correction](#rewind--correction)
- [Compact vs Clear](#compact-vs-clear)
- [Subagents as Context Management](#subagents-as-context-management)
- [When to Start a New Session](#when-to-start-a-new-session)
- [Decision Flow Between Turns](#decision-flow-between-turns)
- [Design Implications for Coding-Agent Runtimes](#design-implications-for-coding-agent-runtimes)
- [See Also](#see-also)
When a session has a large context window (Claude Code's is 1M tokens), session management shifts from "avoid running out" to **deciding what belongs in the window at every turn**. This reference covers the decision points between turns and the behaviour of the four context-management tools: continue, rewind, clear, and compact — plus subagents as a fifth escape.
For the runtime storage layer (session identity, resume, transcript persistence), see [`session-lifecycle-and-resume.md`](session-lifecycle-and-resume.md) and the Checkpointing and Rewind section in the parent SKILL.
## What Is in the Context Window
Every turn, the model sees all of:
- System prompt (loaded memory, repo instructions)
- Full conversation so far (user + assistant messages)
- Every tool call request and its full output
- Every file that has been read
This is why tool-heavy turns and file-read turns balloon context much faster than pure-chat turns. A single `grep` across a large repo can cost more than 20 back-and-forth messages.
## Context Rot
Model performance degrades as the window grows — attention thins across more tokens and older irrelevant content starts distracting from the current task. On Claude Code's 1M model, rot becomes **noticeable around ~300–400k tokens**, but it is highly task-dependent and not a fast rule. Complex reasoning degrades first, instruction following next.
Consequence: the model is at its **least intelligent point exactly when the context is largest** — which is exactly when compaction has to run. This is why bad compacts happen (see below).
## The Five Options at Every Turn
When Claude finishes a turn, five actions are available. "Continue" is the natural choice, but the other four exist specifically to manage context.
| Option | Shortcut | What happens | When it's right |
|---|---|---|---|
| **Continue** | just reply | Keep everything, add next turn | Current context is still relevant and below rot zone |
| **Rewind** | `Esc Esc` or `/rewind` | Drop messages after a chosen point; re-prompt from there | Claude tried an approach and it didn't work — you know why it failed |
| **Clear** | `/clear` | New session, zero carryover | New task, or context is no longer useful and you can summarise what matters yourself |
| **Compact** | `/compact` | Model summarises history, replaces it with the summary | Current work must continue but context has grown too large |
| **Subagent** | `Agent` tool / explicit request | Delegate to a fresh-context agent; only the result returns | Next chunk of work will produce noise you don't need later |
## Rewind > Correction
The single habit that signals good context management: **rewind instead of correcting**.
Anti-pattern:
```
Claude reads 5 files, tries approach A, fails.
User: "That didn't work, try B instead."
```
All 5 file reads + the failed approach A are still in context. Every subsequent turn pays for them.
Better:
```
Esc Esc → jump back to just after the file reads
User: "Don't use approach A — the foo module doesn't expose that. Go straight to B."
```
Failed attempt is gone. File reads are preserved (they were useful). Claude re-enters the fork with what you learned.
**Summarise from here** is the extended form: before rewinding, ask Claude to write a handoff message summarising what it tried and what it learned. Then rewind and paste that as the next prompt — a note from the previous iteration of Claude to its future self.
## Compact vs Clear
Both shed weight; they behave very differently.
| | Compact (`/compact`) | Clear (`/clear`) |
|---|---|---|
| Who decides what matters | The model | You |
| Effort | Low | Higher — you write the handoff |
| Lossiness | Lossy; Claude might drop something load-bearing | Deterministic; only what you typed survives |
| Thoroughness | Can include files/decisions you would have forgotten | Only as thorough as your handoff brief |
| Best for | Related continuation inside the same task | New task, or when you know exactly what's relevant |
**Steering compaction:** pass instructions to `/compact` so the summary focuses on the right axis:
```
/compact focus on the auth refactor, drop the test debugging
```
### What Causes a Bad Compact
Bad compacts happen when **the model can't predict the direction of your next work**. Example:
```
Long debugging session on foo.ts → auto-compact fires → summary
focuses on the foo.ts investigation.
User: "Now fix that other warning we saw in bar.ts."
```
The bar.ts warning was a throwaway observation during debugging. The summariser dropped it because the session was clearly about foo.ts. Claude now has no memory of the warning.
Amplifier: context rot means the model is at peak token load, which is the point of lowest intelligence, when it has to summarise. The lossier the call, the more this matters.
**Mitigation — proactive compact with steering.** Because the 1M window gives you more time before auto-compact fires, compact **deliberately at a known transition point**, with explicit instructions about what comes next:
```
/compact I'm about to switch from the foo.ts fix to the bar.ts warning.
Keep both contexts — don't drop the warning observation from earlier.
```
Never let auto-compact run during a task pivot.
## Subagents as Context Management
Subagents are not only a parallelism tool — they are **the right primitive when the next chunk of work will produce intermediate output you won't need again**.
The mental test:
> Will I need this **tool output** again, or only the **conclusion**?
If only the conclusion, spawn a subagent. It runs in a fresh context, produces its summary, and the parent window only absorbs the final report — not the 30 file reads or 20 tool calls that produced it.
Claude Code auto-dispatches subagents in some cases, but explicit requests produce more predictable behaviour:
```
Spin up a subagent to verify the result of this work against {spec file}.
Spin up a subagent to read {other repo} and summarise how it implements
the auth flow; I'll implement it here in the same style afterwards.
Spin up a subagent to write docs for this feature based on my git changes.
```
**Rule of thumb for coding-agent runtimes:** any sub-task whose output is a *report* (verification result, summary, review) belongs in a subagent. Any sub-task whose output is *integrated code changes* belongs in the parent.
## When to Start a New Session
Rule: **new task = new session.** Carrying context from a DB refactor into a frontend redesign produces confused, conflicting code.
Grey zone: related tasks where *some* prior context helps but not all. Example: writing documentation for a feature you just implemented.
- New session = Claude re-reads the files you just touched (slower, more expensive, but clean).
- Same session = extra context lingers but doc generation is not highly intelligence-sensitive, so the efficiency gain usually wins.
Decision: if the next task is **intelligence-sensitive** (architecture, tricky debugging, security-sensitive code), prefer a fresh session. If it's **formatting, docs, repetitive translation**, keeping context is fine.
## Decision Flow Between Turns
```
After Claude finishes a turn:
├─ Is the next work the same task?
│ ├─ No → /clear (write a handoff first if the task was long)
│ └─ Yes ↓
│
├─ Did the last attempt fail in an instructive way?
│ └─ Yes → Esc Esc (rewind to before the failed approach,
│ re-prompt with what you learned)
│
├─ Is the next chunk going to produce noise you don't need later?
│ └─ Yes → explicit subagent
│
├─ Is the context approaching rot zone (300–400k) or clearly bloated?
│ ├─ Yes and I can write a handoff → /clear with handoff
│ └─ Yes and I can't → /compact with steering instructions
│
└─ Otherwise → continue
```
## Design Implications for Coding-Agent Runtimes
- **Expose all five options visibly.** Users default to "continue" unless the alternatives are one keystroke away.
- **Surface token counts at every turn.** Users can't decide between compact and continue without knowing context weight relative to the rot zone.
- **Make rewind atomic.** Rewinding to a specific message must cleanly drop everything after it — partial drops produce worse context than not rewinding.
- **Steerable auto-compact.** When auto-compact must fire, prompt the user for an optional steering instruction ("what are you about to work on next?") — this alone prevents the most common bad-compact cause.
- **Distinguish rewind from clear in UI.** Both drop context but rewind preserves session identity and transcripts; clear starts a new session.
- **Surface subagent results distinctly** from parent tool calls so users can audit which chunk of context came back as a summary vs. verbatim.
## See Also
- Parent SKILL.md §Checkpointing and Rewind — the concrete key bindings and restore modes
- [`session-lifecycle-and-resume.md`](session-lifecycle-and-resume.md) — storage and identity for the sessions this file's decisions operate on
- [`../../ai-context-layer/references/context-hygiene.md`](../../ai-context-layer/references/context-hygiene.md) — the four context failure modes (poisoning, distraction, clash, confusion) and context rot as a system-design concern
- [`../../agents-swarm-orchestration/SKILL.md`](../../agents-swarm-orchestration/SKILL.md) — when subagent dispatch becomes multi-agent orchestration
references/openai-codex-session-persistence.md
---
source_snapshot: openai/codex main branch (verified 2026-05-25)
anchors:
- codex-rs/cli/src/main.rs — Resume, Fork, Cloud subcommand variants
- codex-rs/external-agent-sessions/ — SQLite-backed session index (ledger.rs, records.rs, detect.rs)
- codex-rs/config/src/config_toml.rs — config.toml path, sqlite_home, CODEX_HOME
---
# OpenAI Codex Session Persistence
## Table of Contents
- [When To Use](#when-to-use)
- [What It Covers](#what-it-covers)
- [Storage Architecture](#storage-architecture)
- [Session Resume](#session-resume)
- [Session Forking](#session-forking)
- [Cloud Task Resume](#cloud-task-resume)
- [Contrast With JSONL / Transcript Model](#contrast-with-jsonl--transcript-model)
- [Design Rules](#design-rules)
- [Anti-Patterns](#anti-patterns)
## When To Use
Use this reference when designing session resume, fork, or cloud-task-apply flows in a Codex-class coding-agent runtime, or when reviewing how Codex persists and queries session state.
## What It Covers
- SQLite-backed session index: crate structure, storage paths
- `codex resume` — UUID lookup and picker flow
- `codex fork` — branch semantics
- `codex cloud` — cloud task resume surface
- Contrast with JSONL/rollout transcript model (covered in `openai-codex-rollout-doctor-telemetry.md`)
## Storage Architecture
Codex uses two parallel persistence layers for sessions. Understanding the boundary prevents architectural confusion:
| Layer | Format | Purpose | Canonical? |
|-------|--------|---------|------------|
| Rollout JSONL | Append-only JSONL files | Durable transcript — prompts, tool calls, compaction markers, token counts | Yes — source of truth |
| SQLite index | `codex-rs/external-agent-sessions` | Fast lookup by session ID, title, recency; rebuildable from JSONL | No — rebuildable cache |
The SQLite index is managed by the `codex-rs/external-agent-sessions` crate:
- `ledger.rs` — session ledger: insert, update, query session records
- `records.rs` — record shapes: session metadata, thread IDs, timestamps
- `detect.rs` — detection helpers: find existing sessions by path or identity
- `export.rs` — export session metadata for external consumers
### Storage Path
Config file: `~/.codex/config.toml` (constant `CONFIG_TOML_FILE = "config.toml"`)
Storage paths default to `$CODEX_HOME` (e.g. `~/.codex/`):
- SQLite DB: `$CODEX_HOME` (or `$CODEX_SQLITE_HOME` if set)
- Logs: `$CODEX_HOME/log/`
## Session Resume
CLI subcommand: `codex resume`
> "Resume a previous interactive session (picker by default; use --last)"
Behavior:
- Default: opens an interactive picker over the SQLite session index, ordered by recency
- `--last`: bypasses the picker and resumes the most recent session directly
- With UUID: performs a direct lookup in the SQLite index; falls back to scanning JSONL if the index misses
Design implications:
- The SQLite index is the fast path; it must be kept consistent with rollout JSONL
- A session that exists in JSONL but not in the index should still be resumable via fallback scan — do not gate recoverability on index freshness
- Resume must clear stale derived caches (tool registry, config cache) before rebuilding live state from persisted transcript
## Session Forking
CLI subcommand: `codex fork`
> "Fork a previous interactive session (picker by default; use --last)"
Fork semantics:
- Creates a new session that starts with the transcript and context of the source session
- The source session remains unchanged; the fork is an independent branch
- Useful for exploring an alternative approach without losing the original thread
Contrast with resume: `resume` continues the same session in-place; `fork` branches off a copy. They share the same picker UI (session ID, recency ordering) but diverge after selection.
Design implication for storage: forked sessions need an ancestry reference (`forked_from: Option<SessionId>`) so developers can trace decision trees. This is different from how Claude Code tracks subagent context inheritance.
## Cloud Task Resume
CLI subcommand: `codex cloud` (alias: `cloud-tasks`)
> "[EXPERIMENTAL] Browse tasks from Codex Cloud and apply changes locally"
This surface connects local Codex invocations to Codex Cloud task history. The flow:
1. Fetch task metadata from Codex Cloud
2. Present task list (analogous to the local session picker)
3. User selects a cloud task
4. Codex downloads the task artifact and applies the diff locally
This is a different resume surface from `codex resume`:
| Surface | Source | What resumes |
|---------|--------|-------------|
| `codex resume` | Local SQLite + JSONL | Full interactive session with transcript |
| `codex cloud` | Codex Cloud API | Task artifacts (diffs, results); interactive session re-seed is separate |
## Contrast With JSONL / Transcript Model
The transcript model (documented in `openai-codex-rollout-doctor-telemetry.md`) is the canonical session record. This file covers the *index* and *lookup* layer on top of it.
Rule: treat SQLite as a rebuildable cache over the JSONL canonical record. If they diverge, JSONL wins.
The `external-agent-sessions` crate's `detect.rs` implements logic for detecting whether an existing session matches by path or identity — this is the entry point for both `resume` and `fork` picker flows.
## Design Rules
- Persist the SQLite index as a fast lookup cache; design the resume path to fall back to JSONL scan when the index is stale or missing.
- `fork` requires an `forked_from` ancestry field so session branching is traceable — do not treat it as just another new session.
- Cloud task resume and local session resume are different flows with different artifacts; do not conflate them in the UI.
- Storage paths should respect `$CODEX_HOME` and `$CODEX_SQLITE_HOME` so enterprise deployments can relocate them without patching config.
- Clear stale discovery caches (tool registry, config, MCP) before rebuilding live state after any resume.
## Anti-Patterns
- Treating SQLite as the source of truth and making sessions unrecoverable when the index is corrupt or missing.
- Implementing `fork` as a shallow copy that shares mutable state with the source session.
- Gating `codex cloud` task apply on the same code path as `codex resume` — they have different authentication, transport, and artifact shapes.
- Using human-readable session titles as the primary identity key for either resume or fork lookup.
references/openai-codex-session-task-turn-protocol.md
# OpenAI Codex Session Task Turn Protocol
Source snapshot: OpenAI Codex commit `7d47056ea42636271ac020b86347fbbef49490aa` (2026-05-22), especially `codex-rs/docs/protocol_v1.md` and `codex-rs/protocol/src/protocol.rs`.
## Table Of Contents
- [Design Goal](#design-goal)
- [Vocabulary To Reuse](#vocabulary-to-reuse)
- [Queue Contract](#queue-contract)
- [Resume And Fork Bookmarks](#resume-and-fork-bookmarks)
- [Interruption Rules](#interruption-rules)
## Design Goal
Use Codex's protocol vocabulary when designing a coding-agent runtime that must be driven by more than one UI. The important idea is the boundary: UI clients submit operations, the core owns session and task state, and events stream back over a stable protocol.
## Vocabulary To Reuse
Codex separates:
- **Session**: current configuration plus persistent runtime state.
- **Task**: the agent doing work in response to user input.
- **Turn**: one model request plus any tool execution and follow-up output.
Copy this split when writing runtime docs. It avoids overloaded terms like "conversation" for both the saved thread and the currently running work.
## Queue Contract
Codex models the core protocol as submission and event queues:
- UI -> core: `Submission` with a UI-provided correlation ID and an `Op`.
- core -> UI: `Event` with matching correlation information and an `EventMsg`.
- Transport can be channels, IPC, stdio, TCP, HTTP/2, or gRPC.
- Non-framed transports should use newline-delimited JSON.
For new runtimes, this gives a clean test seam: record submitted ops, assert emitted events, and keep UI rendering out of core behavior tests.
## Resume And Fork Bookmarks
Each completed turn can return a model `response_id`. The UI can store that bookmark and pass it into later input to continue or fork from a previous point.
Design implication:
- transcript replay and provider-native response continuation are different restore paths
- store both the human-readable rollout and the provider bookmark when available
- make fork explicit so users can tell whether they continued the current task or branched from a prior turn
## Interruption Rules
Codex's protocol makes interruption host-owned:
- a session has at most one active task
- a new user turn or explicit interrupt aborts the current task
- reconfiguration aborts running execution
- a task can also pause on approval or fatal provider/runtime errors
Copy this as an invariant. Parallel work should be separate sessions or separate agent instances, not hidden concurrent tasks inside one session.
## Traps
- Treating `Session` as the same thing as a task queue.
- Letting a UI mutate core state without an operation/event audit trail.
- Resuming only from transcript text when a provider-native response bookmark exists.
- Allowing multiple active tasks in one session without explicit cancellation semantics.
references/resume-path-decision-tree.md
# Resume Path Decision Tree
Use this reference when deciding which session-resume mechanism to use. Apply at design time (choosing an architecture) and at runtime (code that dispatches to the right resume path).
## Table of Contents
- [Decision Tree](#decision-tree)
- [Path Comparison](#path-comparison)
- [Invariants](#invariants)
- [Prompt-cache economics in subagent spawning](#prompt-cache-economics-in-subagent-spawning)
- [Anti-patterns](#anti-patterns)
- [Related](#related)
## Decision Tree
```
Start: Why does the session need to resume?
│
├── User explicitly named a session ID (flag, env var, deep link)
│ └── → Session-ID direct resume
│ - Validate ID format before lookup
│ - Clear stale discovery caches
│ - Fail hard with a clean error if not found (no silent fallback to picker)
│
├── User ran `--continue` or `/continue` without naming a session
│ └── → Most-recent-session shortcut
│ - Resolve from session index, sorted by last-active timestamp
│ - If only one session exists: resume directly
│ - If multiple sessions exist: show picker (see picker path below)
│
├── User is looking for a session by keyword, title, or description
│ └── → Interactive picker / fuzzy search
│ - Exclude: current session, sidechain-only artifacts, corrupted entries
│ - Rank by: last-active, then title match score
│ - If exactly one match: offer direct resume with confirm
│ - If zero matches: fall through to direct-log fallback
│
├── Session is in a different git worktree on the same repo
│ └── → Same-repo worktree adoption
│ - Check: does the session's stored worktree path still resolve?
│ ├── YES → resume with worktree relocation note in the REPL
│ └── NO → offer to re-attach to current worktree (user confirms)
│ - Never silently adopt a session from a different project
│
├── Session was started by an editor (Zed, JetBrains, etc.) via ACP stdio
│ └── → ACP session re-attach
│ - Client sends `session/resume` with `session_id` on new stdin pipe
│ - Agent looks up session from daemon-side store (not from transcript file)
│ - If found: replay catch-up messages (seq > last_seq), re-attach sender
│ - If not found: return `session_not_found`; editor starts new session
│ - Process restart does NOT lose session state if daemon-owned store is used
│
├── User wants to try an alternative approach without losing the current thread (not a recovery case — a branch case)
│ └── → Session branch, not resume
│ - In-session: `/branch [name]` — copies the conversation so far into a new session and switches into it
│ - From the shell: `claude --continue --fork-session` or `claude --resume <id> --fork-session`
│ - The source session is untouched and stays in the picker; the new branch is grouped under it
│ - Permissions granted with "allow for this session" do NOT carry over to the branch — re-grant explicitly
│ - Do not route this through the resume paths below; it creates a new session ID rather than recovering an existing one
│
├── Session was spawned from a Goose-style recipe
│ └── → Recipe re-seed
│ - Two resume modes (show both in UI):
│ 1. "Replay transcript" — high fidelity, large artifact
│ 2. "Re-run from recipe + last checkpoint" — deterministic, small
│ - Prefer recipe re-seed when transcript references tools no longer in scope
│ - Fall back to transcript replay if no `seed_ref` is stored in session metadata
│
└── No session found through any of the above paths
└── → Direct-log / transcript fallback
- Scan session storage directory for transcript files matching the session ID
- Do not use enriched index as the only lookup; it may be stale
- If transcript found: rebuild session metadata from raw log, then resume
- If nothing found: declare session unrecoverable, offer to start fresh
```
## Path Comparison
| Path | Trigger | Requires | Fails when |
|------|---------|----------|-----------|
| Session-ID direct | Explicit flag or deep link | Valid ID in session store | ID not found (no fallback) |
| Most-recent shortcut | `--continue` with no ID | Session index with timestamps | Index corrupted or empty |
| Interactive picker | `--continue` + multiple candidates, or `/resume` | Active terminal; session index | Headless mode; all sessions excluded by filter |
| Worktree adoption | Same repo, different worktree | Repo-root match; user confirmation | Different project root |
| Session branch | `/branch` or `--fork-session` | An existing session to copy from | N/A — always succeeds by creating a new session; not a recovery path |
| ACP re-attach | Editor reconnects over stdio | Daemon-owned session store | Process restarted without persistent store |
| Recipe re-seed | Session has `seed_ref` in metadata | Recipe version still resolvable | Recipe version gone; extension set changed |
| Direct-log fallback | All above failed | Transcript files on disk | Storage wiped; encrypted storage without key |
## Invariants
- Session identity must use a stable UUID, not the human-readable title.
- Picker flows must exclude the current active session and sidechain-only artifacts.
- Same-repo worktree and cross-project sessions must follow different code paths. Never conflate them.
- Stale discovery caches (file index, skill index, config) must be cleared before any resume path rebuilds live state.
- ACP re-attach must be daemon-side (process-outliving) state; binding session lifetime to a file descriptor is the canonical anti-pattern.
- Recipe re-seed must offer transcript replay as an alternative; never silently re-run the recipe without showing the user which mode was chosen.
- Branching is not resume: it always succeeds (it copies rather than recovers) and always produces a new session ID. Keep it out of the failure-driven decision tree above except as the explicit "don't route here" leaf — conflating the two makes users lose track of which session is authoritative.
## Prompt-cache economics in subagent spawning
Session resume decisions interact with prompt-cache prefix sharing. When a subagent is spawned from a lead session:
- A **blank subagent** starts fresh — no cache overlap with the lead. Use when the subagent task is entirely independent and tool sets differ significantly.
- A **forked subagent** (`CLAUDE_CODE_FORK_SUBAGENT=1` or `/fork`) copies the lead's context prefix and maximizes prompt-cache hits. Use when the subagent needs most of the same system prompt, tool list, and project instructions. See [`../ai-coding-agents-sessions/references/context-forking.md`](context-forking.md) for economics.
Resume path interacts with fork: resuming a forked subagent from transcript is safe; resuming via recipe re-seed requires re-pinning the extension list to the parent's envelope, not the recipe's original envelope.
For full prompt-cache economics in subagent spawning, see [`../../ai-coding-agents-sessions/SKILL.md`](../SKILL.md) and [`context-forking.md`](context-forking.md).
## Anti-patterns
- Using title as primary session identity and silently resolving to a wrong session when titles collide.
- Declaring a session unrecoverable without checking direct-log fallback.
- Treating enriched session indexes as the only source of truth (they lag behind, can be corrupted, and may not exist in fresh environments).
- Adopting a cross-project session silently — always require explicit user confirmation.
- Binding ACP session lifetime to the editor process PID; the editor may restart without the agent restarting.
## Related
- [`session-lifecycle-and-resume.md`](session-lifecycle-and-resume.md) — Session identity, picker flows, cache clearing, and resume entrypoints
- [`context-forking.md`](context-forking.md) — Blank vs. forked subagent startup and cache-prefix economics
- [`../../ai-coding-agents-remote-runtime/references/recipe-reconnect-with-sequence.md`](../../ai-coding-agents-remote-runtime/references/recipe-reconnect-with-sequence.md) — ACP reconnect with sequence numbers
references/session-lifecycle-and-resume.md
# Session Lifecycle And Resume
## Table Of Contents
- [Design Goal](#design-goal)
- [Session Identity](#session-identity)
- [Resume Entry Modes](#resume-entry-modes)
- [Cache Handling](#cache-handling)
- [Picker And Search Behavior](#picker-and-search-behavior)
- [Confirmed Storage And Scoping (Claude Code)](#confirmed-storage-and-scoping-claude-code)
## Design Goal
Coding-agent CLIs should treat resume as a controlled state transition, not a best-effort convenience command. Claude Code's public docs (re-verified 2026-07-11 against `code.claude.com/docs/en/sessions`) confirm that session identity, picker flows, stale-cache clearing, and search aliases are all part of the runtime contract.
## Session Identity
The resume flow uses a stable session ID as the primary identity, then layers convenience lookup on top:
- UUID session ID
- custom title search
- interactive session picker
That is the right order:
- stable ID for correctness
- titles and search for human usability
- picker fallback when the input is ambiguous
## Resume Entry Modes
The source supports several resume entry shapes:
- explicit session ID
- interactive picker when no argument is provided
- exact custom-title match
- search-term fallback when the title is ambiguous
- filtered entrypoints such as PR-related resume paths
Use the same idea in new runtimes: one resume command can support multiple operator entry modes without changing the underlying restore contract.
## Cache Handling
`main.tsx` clears stale session caches before resuming so file and skill discovery are fresh.
That is a critical rule:
- transcript and session identity may be trusted from storage
- discovery caches should not be trusted across resume
Resume should restore persisted state, then rebuild the environment-dependent parts.
## Picker And Search Behavior
`resume.tsx` also shows two useful UI rules:
- exclude the current session and sidechain-only logs from the picker
- same-repo worktrees can resume directly, while other-project sessions should produce an explicit resume command instead of silently teleporting the user
That boundary is worth copying because it keeps resume predictable and reviewable.
## Confirmed Storage And Scoping (Claude Code)
The following details were re-verified against public docs on 2026-07-11 and sharpen the abstract rules above into concrete behavior worth copying:
- **Storage path:** transcripts default to `~/.claude/projects/<project>/<session-id>.jsonl`, where `<project>` is the working-directory path with non-alphanumeric characters replaced by `-`. Anthropic documents this entry format as internal and version-fragile — build against `/export` or the scripting interfaces (`claude -p --output-format json`, hook `transcript_path`, Agent SDK), not by parsing the JSONL directly.
- **Scoping is strict, not best-effort:** session-ID lookup for `claude --resume <id>` is scoped to the current project directory and its git worktrees. A session created elsewhere returns a clean "No conversation found" error rather than a silent cross-project resume — copy this fail-closed default.
- **Picker default scope and widen keys:** the picker defaults to the current worktree plus any directory added via `/add-dir`. `Ctrl+W` widens to all worktrees of the current repo; `Ctrl+A` widens to every project on the machine; `Ctrl+B` filters to the current git branch. Exposing scope as an explicit, reversible widen action (rather than showing everything by default) is the reusable pattern.
- **Name resolution is exact-or-explicit:** `claude --resume <name>` and `/resume <name>` only match names the user set (`/rename`, `-n` at startup, or accepting a plan). An ambiguous name either opens the picker pre-filled with the name as a search term (CLI form) or reports an error and asks the user to run the bare picker command (in-session form) — never silently guesses.
- **Cross-project selection in the picker copies a command, it does not jump:** selecting a session from an unrelated project in the widened picker copies a `cd`-and-resume command to the clipboard instead of switching the working directory underneath the user. This is the concrete implementation of "cross-project resume must be explicit."
- **PR-linked resume exists as a first-class entrypoint:** `claude --from-pr <number>` resumes the session tied to a given pull request, and pasting a PR/MR URL into picker search finds the session that created it. Worth modeling as a named resume path alongside ID and title lookup, not bolted on as a search hack.
references/transcript-restoration-and-cross-worktree-recovery.md
# Transcript Restoration And Cross-Worktree Recovery
## Table Of Contents
- [Design Goal](#design-goal)
- [Transcript vs Summary State](#transcript-vs-summary-state)
- [Cross-Worktree Recovery](#cross-worktree-recovery)
- [Failure Handling](#failure-handling)
## Design Goal
Long-lived coding-agent sessions need more than raw message replay. They need a recovery model for:
- visible REPL history
- transcript side data
- summary or collapse stores
- worktree-aware session selection
The `claude_code` comments around `query.ts`, `resume.tsx`, and `main.tsx` show this separation clearly.
## Transcript vs Summary State
The source indicates that not all conversation state lives in the visible REPL array:
- some summary or collapse information persists outside the immediate message list
- some session fields are persisted specifically because resume needs to read them back
That yields a strong rule:
- keep the user-visible transcript separate from compressed or support-state stores
- resume should restore both where needed, but not confuse them as one data structure
## Cross-Worktree Recovery
The picker flow distinguishes:
- same-directory sessions
- same-repo worktree sessions
- different-project sessions
Same-repo worktrees can often be resumed directly. Different-project sessions should usually return an explicit command so the user changes context intentionally.
This avoids unsafe implicit cwd switches and makes recovery auditable.
Useful restore sequence from the source behavior:
1. resolve the target session by stable ID when possible
2. if enriched picker data misses the session, try direct log lookup
3. load the full conversation payload
4. restore transcript and session metadata
5. restore agent mode, worktree state, and cost state
6. rebuild environment-dependent caches and agent definitions
7. only then hand control back to the live REPL
## Failure Handling
Model these failure paths explicitly:
- session not found
- multiple matches for a title
- stale or missing worktree path
- failed full-log load for lite logs
- resume partially starts but cannot finish
The runtime should return a clear error or fallback picker state instead of silently dropping into a mismatched session.
## Edge Cases And Workarounds
Additional cases worth documenting for a real clone:
- picker data is partial
- support progressive loading rather than blocking on global history hydration
- current session appears in results
- exclude it so resume does not loop back into the active session
- sidechain-only or support-only logs appear
- keep them out of normal operator-facing resume flows
- same-repo worktree resume
- allow direct recovery when the workspace relationship is still valid
- cross-project resume
- show an explicit next command rather than silently teleporting cwd
- transcript collapse or summary state exists outside the visible message list
- restore it explicitly; do not assume replaying messages is enough
Practical tip:
- separate "can identify the session" from "can safely restore the runtime context"
- many resume bugs come from treating those as the same operation
SKILL.md
---
name: ai-coding-agents-sessions
description: "Designs session lifecycle for coding-agent runtimes. Use when implementing resume, transcript restoration, checkpoint rewind, cross-worktree recovery, or session-state persistence."
compatibility: Portable core. Works on Claude Code and Codex.
version: "1.1"
last_validated: 2026-07-11
---
# AI Coding Agents Sessions
Use this skill to design or review the session lifecycle for a coding-agent runtime: session IDs, transcript persistence, resume pickers, stale-cache clearing, cross-worktree recovery, and what state must be restored versus recomputed.
This skill owns runtime session lifecycle. For persistent repo instructions and always-loaded memory, use [`../agents-memory/SKILL.md`](../agents-memory/SKILL.md).
## ASCII Flow
```text
new or resumed invocation
|
v
session identity
project + worktree + session_id + title + runtime mode
|
v
state restoration
transcript + summaries + tool state + task state + provider cache metadata
|
v
branch decision
continue | rewind | compact | clear | fork subagent | exact resume | claude agents (background resume)
|
v
active turn
append events, persist checkpoints, keep recovery path auditable
```
## Quick Reference
| Question | Read | Outcome |
|----------|------|---------|
| What belongs in a coding-agent session model? | [`references/session-lifecycle-and-resume.md`](references/session-lifecycle-and-resume.md) | Session IDs, picker flows, stale-cache reset, and resume semantics |
| How should transcripts recover across worktrees and summaries? | [`references/transcript-restoration-and-cross-worktree-recovery.md`](references/transcript-restoration-and-cross-worktree-recovery.md) | Restoration boundaries, search, cross-project safeguards, and replay rules |
| How do users decide between continue / rewind / clear / compact / subagent at each turn? | [`references/context-lifecycle-and-branching.md`](references/context-lifecycle-and-branching.md) | 1M-context branching model, context rot zone, rewind > correction, compact-vs-clear, bad-compact causes, subagent mental test |
| How do forked subagents change session lifecycle (cache, isolation, resume, cost)? | [`references/context-forking.md`](references/context-forking.md) | Blank-vs-forked startup, `CLAUDE_CODE_FORK_SUBAGENT=1` and `/fork` surfaces, cache-prefix economics, fork-as-exception rule |
| Which resume path should I use (session ID / picker / ACP re-attach / recipe re-seed)? | [`references/resume-path-decision-tree.md`](references/resume-path-decision-tree.md) | Decision tree, path comparison table, prompt-cache economics in subagent spawning |
| How does OpenAI Codex split Session / Task / Turn protocol state? | [`references/openai-codex-session-task-turn-protocol.md`](references/openai-codex-session-task-turn-protocol.md) | SQ/EQ protocol, response bookmarks, one-active-task invariant, and interruption rules |
| How does Codex persist, resume, fork, and cloud-resume sessions? | [`references/openai-codex-session-persistence.md`](references/openai-codex-session-persistence.md) | SQLite-backed session index, `codex resume` UUID lookup, `codex fork` branch semantics, `codex cloud` task-apply |
## When To Use
- Design resume and continue flows for a coding-agent CLI
- Decide how session IDs, titles, or logs map to recovery behavior
- Restore transcripts, summaries, or worktree-bound state safely
- Build interactive resume pickers or exact-match resume commands
- Separate project memory from session memory and transcript state
## Use Other Skills
| Need | Use Instead |
|------|-------------|
| Persistent repo instructions and shared memory files | [`../agents-memory/SKILL.md`](../agents-memory/SKILL.md) |
| Remote execution or bridge sessions | [`../ai-coding-agents-remote-runtime/SKILL.md`](../ai-coding-agents-remote-runtime/SKILL.md) |
| Background task lifecycle | [`../ai-coding-agents-tasks/SKILL.md`](../ai-coding-agents-tasks/SKILL.md) |
## Default Workflow
1. **Define session identity first.** Use a stable session ID and keep title or search aliases as secondary lookup keys.
2. **Split restoreable from recomputable state.** Persist transcripts, summaries, and user-visible session identity; recompute caches and discovery indexes after resume.
3. **Clear stale discovery caches before restore.** Resume should not inherit old file, skill, or config caches.
4. **Support both exact and interactive recovery.** Resume should work by UUID, exact title match, and picker/search fallback.
5. **Treat worktree and project boundaries explicitly.** Same-repo worktrees can often resume directly or adopt the worktree; different projects should route through an explicit user command.
6. **Use fallback lookup order deliberately.** Enriched session indexes may fail; direct log or transcript lookup should exist as a second path before the runtime declares a session missing.
7. **Restore summary state, not just raw logs.** Transcript collapse, synthesized summaries, and lightweight cost or usage state should survive resume even if the visible REPL list is truncated.
8. **Test failure paths.** Verify missing sessions, multiple title matches, stale worktree paths, interrupted resume, index miss with direct-log fallback, and cross-project recovery.
## Host Rules
- Session lifecycle is runtime state, not project memory.
- Resume should restore only state that is safe to trust from storage.
- Search aliases and custom titles are convenience layers on top of session IDs.
- Cross-project resume must be explicit and reviewable.
- Same-repo worktree adoption and cross-project resume should follow different code paths.
- Resume should clear stale discovery caches before rebuilding live runtime state.
- If enriched indexes miss a session, the runtime should have a direct-log or transcript fallback before failing hard.
- Picker flows should exclude the current session and sidechain-only artifacts.
## Build Order
1. Define stable session identity and storage keys.
2. Separate durable session state from recomputable caches.
3. Implement exact-ID resume before title or picker-based recovery.
4. Add cache clearing and live-state rebuild on resume.
5. Add worktree-aware recovery rules.
6. Add transcript compaction, summary restore, and fallback lookup paths.
## Core Invariants
- Session identity must not depend on mutable titles.
- Resume must only trust persisted state that is safe to restore.
- Discovery caches are disposable and should be rebuilt.
- Same-repo worktree recovery and cross-project recovery are different problems.
- Missing enriched indexes must not be the only reason a session becomes unrecoverable.
## Failure Modes
- Resuming the wrong session because title lookup overrode session identity.
- Restoring stale discovery or config caches into a new runtime.
- Treating a moved worktree as a missing session instead of a relocation case.
- Losing summaries or collapsed transcript state even though raw logs exist.
- Declaring a session missing without checking direct log or transcript fallbacks.
## Minimal Viable Version
- Stable session IDs and exact resume by ID.
- Persisted transcripts and lightweight session metadata.
- Cache clear on resume.
- One picker or search fallback for humans.
- Direct-log or transcript fallback when secondary indexes fail.
## What Strong Implementations Add
- Worktree adoption and same-repo relocation handling.
- Progressive transcript loading for large sessions.
- Summary and usage-state restore alongside raw logs.
- Picker exclusions for current session and sidechain artifacts.
- Clear auditability around why a resume succeeded, failed, or switched paths.
## Background Agent Sessions
Claude Code supports background agents: daemon-supervised processes that run independently of the active terminal, persisting between invocations and resumable through the agent-view UI.
### How Background Sessions Work
| Aspect | Detail |
|--------|--------|
| Launch | `claude --bg "<task>"` from the shell, or `/bg <task>` / `/background <task>` from within a session (carries over in-flight shell commands, subagents, and workflows) |
| Isolation | Each background session moves into its own git worktree under project-relative `.claude/worktrees/` before editing, unless it's already in a worktree, isn't a git repo, or `worktree.bgIsolation` is set to `"none"` |
| Session state | Written to `~/.claude/jobs/<id>/state.json`; each job also gets a scratch dir at `~/.claude/jobs/<id>/tmp/` and a `CLAUDE_JOB_DIR` env var pointing at it |
| Roster | All active background sessions tracked in `~/.claude/daemon/roster.json`, used to reconnect after a supervisor restart |
| Daemon | A persistent on-demand supervisor process runs background sessions and restarts stopped ones (idle timeout ~1 hour) with conversation state intact |
| Resume/manage | `claude agents` opens the agent-view roster (no `/agents` slash command exists); `claude attach <id>`, `claude stop <id>`, `claude respawn <id>`, `claude rm <id>` operate on a specific job from the shell |
| CI usage | `claude agents --json` (add `--all` for completed sessions, `--cwd <path>` to scope) returns the roster as JSON with `id`, `state`, `status`, `waitingFor` fields; CI can poll this before collecting output |
### Storage Paths
```text
~/.claude/jobs/<id>/state.json — per-job session state (transcript, tool state, task state)
~/.claude/jobs/<id>/tmp/ — per-job scratch directory (no permission prompts)
~/.claude/daemon/roster.json — daemon-maintained roster of all known background jobs
~/.claude/daemon.log — supervisor process log
<project>/.claude/worktrees/ — isolated worktrees for background sessions (project-relative, not under the user's home config dir)
```
### Resume Path Decision
When a user returns to a background agent after leaving the terminal:
1. Run `claude agents` to open the roster (or `claude agents --cwd <path>` to scope to a directory) → select the row → attach with `Enter`/`→`, or peek with `Space` without attaching.
2. Direct attach without the roster UI: `claude attach <id>` (or `claude attach <name>` if the session was renamed).
3. If agent view is disabled (`disableAgentView: true` in settings, or `CLAUDE_CODE_DISABLE_AGENT_VIEW=1`): fall back to `claude --resume <id>` using the job ID from `roster.json`.
4. From CI: `claude agents --json | jq '.[] | select(.id == "<id>") | .status'` to poll job completion before collecting output.
5. If a session shows as failed after a machine shutdown, `claude attach <id>` restarts it in place; if the transcript was misread as empty on restart, Claude Code renames it with an `.orphaned-` suffix rather than discarding it (v2.1.196+).
### Lifecycle Settings
| Setting | Effect |
|---------|--------|
| `disableAgentView: true` (or `CLAUDE_CODE_DISABLE_AGENT_VIEW=1`) | Turns off `claude agents`, `--bg`, `/background`, and the on-demand supervisor entirely — not just the panel |
| `cleanupPeriodDays: <n>` | Governs local session/transcript retention generally (default 30 days, minimum 1); also bounds how long completed background jobs and their worktrees stick around |
| `awaySummaryEnabled: true` (default) | Shows a one-line recap of what happened while you were away (5+ minutes) when you return to a session; set to `false` (or `CLAUDE_CODE_ENABLE_AWAY_SUMMARY=0`) to suppress it |
### Design Implications
- Background session state must be written durably enough to survive supervisor restart (`state.json` is flushed on every checkpoint, and in-flight shell commands/subagents/scheduled tasks are handed off across a stop-restart cycle as of v2.1.196 — `CLAUDE_CODE_DISABLE_BG_EXIT_HANDOFF=1` opts out).
- Worktree isolation means background agents cannot accidentally dirty the main working tree; merging results back is an explicit user action — though as of v2.1.198, sessions that create a worktree may auto-commit, push, and open a draft PR without asking, which implementations should treat as a policy decision, not a hidden default to copy blindly.
- `roster.json` is the authoritative list of background sessions; session pickers should read from it when building the resume list, but it is a rebuildable cache over supervisor-managed process state, not the sole source of truth for a crashed daemon.
- `disableAgentView` is a managed enterprise setting exposed both as a `settings.json` key and an env var — enterprise deployments may hide the whole feature, not just the UI; implementations must not assume it is always present.
- `awaySummaryEnabled` is independent of agent-view visibility; a summary can be generated even for a foreground session resumed after being away.
### Integration With the Resume Decision Tree
The `references/resume-path-decision-tree.md` decision tree should route to `claude agents` as a named path when:
- The session was started with `--bg` or `/bg`
- The session ID is present in roster.json
- The terminal was closed and agent-view is the preferred UX
This path sits between "exact session ID resume" (lower UX friction) and "picker search" (broader coverage) in the tree.
## Checkpointing and Rewind
Claude Code creates a new checkpoint on every user prompt, capturing the code state before that prompt's edits begin. Checkpoints track **only file changes made through Claude's own file-editing tools** — they do not capture files touched by bash commands (`rm`, `mv`, `cp`, etc.) or by any process outside the current session. That is a load-bearing limitation, not an edge case: any runtime cloning this pattern must decide explicitly whether to widen tracked-change scope beyond editor-tool calls, and must not imply broader coverage than it has.
### Entry Points
| Method | Behavior |
|--------|----------|
| `Esc Esc` (double-tap, empty prompt) | Open the rewind menu. If the prompt has text, double-Esc clears the input instead (recoverable via `Up`) |
| `/rewind` | Open the rewind menu via slash command |
| Select a checkpoint | Restore conversation, code, both — or summarize around that point |
### Restore Modes
- **Restore code and conversation**: full rollback to the selected point
- **Restore conversation**: rewind chat history, keep current code
- **Restore code**: revert file changes, keep the conversation
- **Summarize from here**: keeps messages before the selected point intact; the selected message and everything after collapses into a summary — use to discard a side discussion while keeping earlier context in full detail
- **Summarize up to here**: keeps messages after the selected point intact; everything before collapses into a summary and you remain at the end of the conversation — use to compress early setup while keeping recent work in full detail
Both summarize modes preserve the original messages in the session transcript (Claude can still reference them if needed) and accept optional steering instructions, the same way `/compact` does — but scoped to one side of a chosen point instead of the whole conversation.
### Rewind Past a Cleared Conversation
If `/clear` ran earlier in the same process, the rewind menu shows an extra top entry, `/resume <session-id> (previous session)`, to jump back to the pre-clear conversation (requires a recent-enough Claude Code version; on older versions use `/resume` and pick it from the picker instead). Design implication: `/clear` does not destroy the prior session's checkpoints — it starts a new one and the old session remains independently resumable/rewindable.
### Design Implications for Session Storage
- Checkpoints are runtime state, not project memory — they live in the session layer alongside transcripts
- Checkpoints persist across session resume, so a user can close the terminal and still rewind later
- Checkpoint storage should be cheap per operation (copy-on-write or incremental diff) to avoid blocking the agent loop
- The rewind menu should clearly distinguish restore modes (conversation vs code vs both) from the two non-destructive summarize modes, since only the restore modes actually discard state
- Document the bash-command blind spot explicitly in any user-facing rewind UI — silently implying full coverage is the most common trust-breaking bug in this feature class
### Rewind vs Git vs Session Branching
Checkpointing is not a replacement for git, and it is not the same primitive as branching a session. Three distinct mechanisms solve three distinct problems — conflating them is a common design mistake:
| Mechanism | Scope | What survives | Use when |
|---|---|---|---|
| Rewind / checkpoint (`/rewind`, `Esc Esc`) | Same session, same conversation | Files reverted via copy-on-write/diff; conversation truncated or summarized in place | Undo the agent's own recent edits or steer the current thread without starting over |
| Session branch (`/branch`, or `claude --continue`/`--resume <id> --fork-session`) | New, independent session — a full copy of the conversation so far | Original session is untouched and stays resumable; the new session diverges from that point forward | Try a different top-level approach while preserving the path you were on; A/B test prompting or implementation strategy from the same loaded context |
| Git commit | Durable, cross-session, cross-tool | Whatever you committed, forever | Permanent history and collaboration |
Rewind and `/branch`/`--fork-session` are easy to confuse because both "go back to an earlier point," but rewind mutates the current session in place while branching spins up a second, independent session ID that shows up grouped under the root session in the picker. Permissions approved with "allow for this session" do **not** carry over to a branched session. Users should still commit to git regularly — rewind and branching are for fast in-session experimentation, not long-term version control.
### Integration With Compaction
Checkpoints interact with compaction: "Summarize from here" and "Summarize up to here" let the user choose a point to compact around, keeping the side that matters intact while compressing the rest. This is a more targeted alternative to auto-compaction at the context limit, which always summarizes the entire history.
## Known Traps
- Using human-readable titles or recent-path heuristics as the real session identity and colliding restores across worktrees or projects.
- Persisting caches and derived state that should be recomputed, then replaying stale tool registries, settings, or summaries after resume.
- Treating transcript restoration as enough while background tasks, checkpoints, and remote-control state are still missing.
- Assuming one resume path works across local, remote, and cross-worktree recovery without explicit environment validation.
- Letting compaction destroy decision boundaries that later rewind or debugging workflows still depend on.
- Conflating in-place rewind/summarize with session branching. Rewind mutates the current session; `/branch` or `--fork-session` mints a second, independent session ID. Documenting them as one feature causes users to lose the original thread when they only meant to peek at an alternative.
- Assuming checkpoint/rewind covers every file mutation. It only tracks changes made through the agent's own file-editing tools — bash-driven renames, deletes, and copies are invisible to it and cannot be undone through rewind.
## Common Anti-Patterns
- Using titles as primary session identity.
- Persisting caches that should be recomputed.
- Treating repo memory and runtime session state as the same layer.
- Assuming one resume code path works equally well across worktrees and projects.
- Requiring enriched indexes to exist before any session can be restored.
## Cross-Platform Patterns (Goose)
Goose adds two session patterns not covered by the Claude Code-derived core: **cross-process session re-attach over ACP**, and **recipe-as-session-seed** for deterministic resume.
### Cross-process session re-attach (ACP)
Goose runs as an ACP stdio server. When an editor (Zed, JetBrains, etc.) disconnects and reconnects, the session ID is passed back on the new stdin pipe and the agent re-attaches in-place. This is different from in-process resume (already covered by rewind/checkpoint) and different from same-machine file-watch continuation — the process may have restarted, but the session object persists.
- **Pattern:** session identity must survive the parent process it was spawned by. Persist session state server-side; require the re-attaching client to prove it holds the session ID.
- **Anti-pattern:** binding session lifetime to the stdin FD or parent PID. That collapses editor restarts, agent upgrades, and sleep/resume into session loss.
- **Recipe:** on ACP connect, the agent looks up the session ID in its session store; if found and auth proof matches, resume from persisted transcript + checkpoint. If not, create new. Log whether a resume hit or missed so operators can distinguish session loss from client-side amnesia.
### Recipe-as-session-seed
A resumed session is usually rehydrated from the transcript. Goose's recipe model offers an alternative: a session can be re-seeded from the *recipe* that spawned it plus its parameters — a typed, versioned, much smaller artifact than a raw transcript. This is stronger than transcript replay because inputs are structured and the recipe version pins extension set and instructions.
- **Pattern:** for recipe-spawned sessions, persist `(recipe ref, recipe version, parameter values, output checkpoints)` alongside the transcript. Resume can choose: replay transcript (high fidelity, large) or re-spawn from recipe + parameters + last checkpoint (deterministic, small).
- **Anti-pattern:** storing only the transcript for recipe-spawned sessions. On cross-version resume, the transcript may reference tools or extensions no longer in the envelope.
- **Recipe:** add a `seed_ref: Option<RecipeSeed>` field to session metadata. When present, resume UI should offer "replay transcript" and "re-run recipe from last checkpoint" as named modes.
## Navigation
### References
- [`references/session-lifecycle-and-resume.md`](references/session-lifecycle-and-resume.md) — Session identity, picker flows, cache clearing, and resume entrypoints
- [`references/transcript-restoration-and-cross-worktree-recovery.md`](references/transcript-restoration-and-cross-worktree-recovery.md) — Transcript recovery, summary persistence, and cross-worktree safeguards
- [`references/context-lifecycle-and-branching.md`](references/context-lifecycle-and-branching.md) — Per-turn branching (continue/rewind/clear/compact/subagent), 1M-context rot zone, steered compaction, and subagents as context-management primitive
- [`references/context-forking.md`](references/context-forking.md) — Blank-vs-forked subagent startup, `CLAUDE_CODE_FORK_SUBAGENT=1` and `/fork` surfaces, cache-prefix economics, isolation guarantees, and fork-as-exception rule
- [`references/resume-path-decision-tree.md`](references/resume-path-decision-tree.md) — When to use session ID vs picker vs ACP re-attach vs recipe re-seed
- [`references/openai-codex-session-task-turn-protocol.md`](references/openai-codex-session-task-turn-protocol.md) — OpenAI Codex Session / Task / Turn protocol, queue contract, response bookmarks, and interruption rules
- [`references/openai-codex-session-persistence.md`](references/openai-codex-session-persistence.md) — SQLite session index, `codex resume` / `fork` / `cloud` subcommand semantics, storage path layering
### Data
- [`data/sources.json`](data/sources.json) — Primary documentation and source references for session lifecycle guidance
### Related Skills
- [`../agents-memory/SKILL.md`](../agents-memory/SKILL.md)
- [`../ai-coding-agents-remote-runtime/SKILL.md`](../ai-coding-agents-remote-runtime/SKILL.md)
- [`../ai-coding-agents-tasks/SKILL.md`](../ai-coding-agents-tasks/SKILL.md)
## Fact-Checking
- Known bugs, regressions, framework/compiler/runtime footguns, and version-specific crash or workaround guidance must be verified against current primary web sources before being treated as current fact.
- Session/resume/checkpoint mechanics were re-verified against `code.claude.com/docs/en/{sessions,checkpointing,sub-agents,agent-view}` and `learn.chatgpt.com/docs/developer-commands` on 2026-07-11. Several details in this file are gated behind a specific Claude Code version (noted inline, e.g. "v2.1.117+", "v2.1.196+"); re-check the changelog before asserting exact behavior on an unknown build.
- Resume, checkpoint, and log storage formats drift release to release — Anthropic's own docs state the transcript JSONL entry format is internal and can change between versions. Preserve the architecture and behavioral contracts described here; re-verify exact file formats and flag names before shipping code that parses them directly.
- The Codex references in this skill mix two source types: CLI-surface behavior (re-verified against `learn.chatgpt.com/docs/developer-commands`, 2026-07-11) and internal storage architecture (SQLite index, crate/file names) pinned to a specific `openai/codex` source commit from 2026-05-25 that is not restated in public docs — treat the storage-layer claims as commit-pinned engineering detail, not a documented public contract, and re-check against current source before relying on exact file/module names.
## Learnings Loop
Before applying this skill on a non-trivial task, read `learnings.consolidated.md` in this directory (and `learnings.md` if present).
After applying it, if you encountered a pattern worth remembering, a mistake worth preventing, or a domain fact that surprised you, append one dated bullet to `learnings.md` via `agents-skills-feedback-loop/scripts/append_learning.py`. Do not modify `SKILL.md` itself.