Skip to content

How to Manage Claude Code Sessions: Resume, Clear, Branch

CoreConceptJuly 31, 202611 min read

Close a Claude Code session mid-task and the natural fear is that you just lost an afternoon of debugging context — the files it read, the failed approaches, the decision to skip the flaky test. That fear is usually wrong. A Claude Code session is a saved conversation tied to a project directory, written to disk continuously as you work, and the CLI gives you several distinct ways back into it: some that pick up exactly where you left off, some that deliberately start clean, and some that let you fork one conversation into two so you can try a risky idea without losing the safe path.

This article is a practical reference for that lifecycle: how claude, --continue, and --resume differ, where the transcript actually lives on disk and what does and doesn't survive a resume, when /clear beats /compact beats a brand-new session, how to run more than one conversation against the same repository without them colliding, and how to structure a task that spans several days without re-explaining it each morning. We'll follow one running task through all of it — BILL-451: migrate invoice PDF generation to the new template engine in a billing-service repository — a job realistically too big for one sitting. Facts here describe Claude Code's documented CLI behavior as of July 2026; flag names and defaults can change between releases, so check claude --help or the current docs before scripting around them.

Knowledge map: what a Claude Code session is made of
Knowledge map: what a Claude Code session is made of

What a session actually is

A Claude Code session is not just a chat transcript — it's a transcript scoped to the directory you started it in. Run claude inside billing-service and every message, tool call, and tool result from that conversation gets written continuously to a session file associated with that project, independent of whether you exit cleanly, close the terminal, or the process crashes. That persistence is what makes everything else in this article possible: resuming, clearing, branching, and picking a session by name all operate on that saved state, not on something reconstructed from your shell history.

The directory scoping matters more than it looks like at first. Session lookup — by --continue, by --resume <name>, by pasting a raw session ID — is scoped to the current project directory and its git worktrees. Run claude --resume BILL-451 from billing-service and it resumes directly; run the identical command from an unrelated repository and Claude Code reports No conversation found with session ID: <id>, because it never looked in the right place. This isn't a bug to work around — it's the same boundary that keeps an unrelated project's sessions out of your picker by default.

One consequence worth internalizing early: /clear does not delete the conversation it clears. It saves the previous conversation and starts an empty one in the same running process, so "I cleared and lost everything" is almost always recoverable with /resume. What's genuinely destructive is different — closing a session that was never named, in an unclean way, on top of an auto-cleanup window (cleanupPeriodDays, 30 days by default) that eventually prunes old transcripts you never returned to.

Quick reference

  • A session is identified by an ID and, once you set one, a name — the name is what makes claude --resume BILL-451 or /resume BILL-451 resolve directly instead of opening a picker.
  • Session lookup by ID or name is scoped to the directory you run it from and that repository's other git worktrees — not global by default.
  • /clear saves the old conversation before starting a new one; the risky action is letting an unnamed session age past your retention window unresumed, not clearing it.
  • For the mechanics of what happens inside one turn of a session — the tool-call loop, permission checks, compaction — see How Claude Code Works; this article covers the lifecycle around that loop, not the loop itself.

Remember this

A session is a transcript scoped to a project directory and written continuously to disk — resuming, naming, and branching are all operations on that saved state, and directory scope is the boundary that decides whether a resume can even find it.

Starting and resuming a session

Four entry points cover almost every case. claude with no flags starts a new session in the current directory. claude --continue (short form -c) resumes the most recent session for the current directory with no picker and no session ID required — the fastest path back into whatever you were just doing. claude --resume, with no argument, opens an interactive picker listing sessions for the current repository, sorted by recent activity, with metadata like time since last activity, git branch, and file size; the same picker opens mid-session by typing /resume. claude --resume <name> skips the picker and resumes that session directly if the name matches exactly, or opens the picker pre-filtered to that search term if it doesn't.

For BILL-451, day one looks like claude -n bill-451 to start a named session (or /rename bill-451 partway through if you forgot). Day two, from the same billing-service checkout, claude --continue picks it back up without you typing the name — useful when it's the only thing you were doing there. Once you're juggling two or three tasks in the same repo, claude --resume bill-451 or the picker becomes the more reliable habit, since --continue only ever knows about "most recent," not "the one I mean."

Naming pays for itself quickly. An unnamed session gets an AI-generated title from your first prompt and a directory-plus-suffix default display name — neither is a resume handle, so claude --resume with that generated title won't match. Only a name you set with -n/--name at launch, /rename mid-session, or Ctrl+R in the picker becomes something you can resume by name later.

Three ways back into a conversation: continue, resume, or the in-session picker
Three ways back into a conversation: continue, resume, or the in-session picker

Quick reference

  • --continue/-c never asks anything — it always resumes the single most recent session for the current directory, so it's wrong the moment you have two tasks going.
  • The picker supports Ctrl+W to widen to all worktrees of the repo and Ctrl+A to widen to every project on the machine — useful when you're not sure which checkout a session lives in.
  • Sessions started with claude -p (non-interactive/scripted runs) don't appear in the picker at all, but you can still resume one by passing its session ID to --resume.
  • Passing --worktree <name> or a PR number (--worktree "#1234") starts a session in an isolated checkout rather than the current directory — covered in the concurrency section below.
Start, then resume across days
1cd billing-service2 3# Day one: name it so you can find it again4claude -n bill-4515 6# Day two, from the same directory:7claude --continue          # resumes the most recent session here8claude --resume bill-451   # resumes that specific session by name9claude --resume            # opens the picker if you're not sure which
From inside a running session
1/rename bill-451     # name (or rename) the session you're in2/resume               # open the same picker without exiting

Remember this

-c is a shortcut for "the one I was just in" with zero disambiguation; naming a session and resuming by name is the only way to reliably get back to a specific task once more than one is running in the same repo.

Where session state lives, and what a resume restores

Transcripts are stored as JSONL — one JSON object per line, per message, tool call, or metadata entry — at ~/.claude/projects/<project>/<session-id>.jsonl, where <project> is your working directory path with non-alphanumeric characters replaced by dashes. That format is internal and changes between Claude Code releases, so a script that parses these files directly can break on any update; if you need session data programmatically, use /export for a human-readable transcript, or claude -p --resume <session-id> --output-format json "your question" to get a structured answer from an existing session without touching the raw file. The storage location is configurable via CLAUDE_CONFIG_DIR, retention via the cleanupPeriodDays setting, and you can suppress transcript writes entirely with CLAUDE_CODE_SKIP_PROMPT_HISTORY or, per non-interactive run, --no-session-persistence.

A resumed session restores more than the raw text: the full conversation history including tool calls and results, the model it was using (unless that model was retired, isn't allowed by your account's availableModels, or a --model flag overrides it at launch), and the permission mode it was in — with one exception. plan and bypassPermissions modes are never restored automatically; if a session depended on bypassing permission prompts, you re-enable that explicitly at launch, because a resume silently reactivating an unattended, no-prompts mode is exactly the kind of surprise a permission system exists to prevent.

What does not come back automatically is anything tied to how the process was launched rather than to the conversation itself: --mcp-config, --settings, --plugin-dir, --fallback-model, and directories added with --add-dir all need to be passed again if the resumed work depends on them. Standard settings files (settings.json, settings.local.json) are the exception — they're re-read fresh at launch, so configuration that lives there doesn't need repeating. For BILL-451, if day one's session connected an MCP server that reads the PDF template repo, day two's claude --continue needs the same --mcp-config flag again, or that tool silently isn't there and the model has to ask you for a substitute.

Zoom: what a resumed session restores vs what you must pass again
Zoom: what a resumed session restores vs what you must pass again

Quick reference

  • Never parse ~/.claude/projects/**/*.jsonl directly in a script you plan to keep — the entry format is internal and can change between releases; use /export or claude -p --resume instead.
  • A resume on a long-idle, large session (roughly: inactive over an hour and past 100k tokens) offers a dialog to resume from a compacted summary or as-is; picking as-is reprocesses and re-caches the full history on your next message, at a token cost proportional to the conversation's size.
  • Model and permission-mode restoration have real exceptions — a retired model, an availableModels restriction, or plan/bypassPermissions mode will not silently carry over; check what actually loaded before assuming it did.
  • Launch-time flags (--mcp-config, --add-dir, --plugin-dir) are not part of the saved conversation state — they describe how the process started, so a resume needs them passed again if the task depends on them.

Remember this

A resume replays conversation, model choice, and permission mode from disk, but anything that was a launch flag rather than a message — MCP servers, added directories, bypass mode — has to be supplied again, because it was never part of the saved transcript.

/clear vs /compact vs a new session

These three look similar from the outside — all of them reduce what's in front of the model — but they trade different things away. /clear is the cheapest and safest: it doesn't touch what's already on disk, it just gives you an empty window in the same running process, and the old conversation is one /resume away if you clear the wrong thing. /compact is lossy by construction — it's a real summarization pass, not a lossless index — so a constraint mentioned once early in a long session ("don't touch the legacy PDF renderer, it's still used by the mobile app") can get compressed away if nothing reinforced it later. That's the practical argument for putting durable rules in CLAUDE.md instead of only stating them mid-conversation: CLAUDE.md reloads fresh every session, where a mid-chat instruction is exactly the kind of content a compaction pass can condense away.

A brand-new session is the right call more often than it feels like in the moment. Claude Code's own guidance after two failed correction attempts on the same issue is blunt: the context is now polluted with failed approaches, and a clean session with a better, more specific prompt that incorporates what you learned usually beats continuing to argue inside the cluttered one. For BILL-451, if the model gets stuck trying three wrong regexes to extract a PDF field and you've corrected it twice, that's the signal — not a fourth correction, but /clear and a prompt that states the extraction rule directly instead of hoping the model rediscovers it.

One more distinction worth keeping straight: automatic compaction and /compact are the same mechanism, just triggered differently — Claude Code compacts on its own as the transcript approaches a size threshold, and /compact <instructions> runs the identical summarization on demand, optionally steered (/compact focus on the API changes, drop the exploration). Neither one resets the working directory or any file already edited; only the conversation shrinks, never the code state.

Three ways to shrink or reset context, and what each keeps
ActionWhat happens to contextWhat survivesUse it when
/clearContext window emptied immediatelyOld conversation saved on disk, resumable via /resume; a name you set carries overSwitching to an unrelated task in the same directory — a new bug, not a continuation of BILL-451
/compact [instructions]History replaced with a summary, optionally focusedA condensed digest of files touched and decisions made, plus recent turns kept close to verbatimStill on the same task, but the transcript is bloated with resolved detours (dead ends, read-but-irrelevant files)
New sessionNo prior context at allNothing — a fresh transcript file from the first messageA genuinely separate task, or the previous session's history is actively steering the model wrong
/clear, /compact, and a new session shrink context in three different ways
/clear, /compact, and a new session shrink context in three different ways

Quick reference

  • Run /context any time to see what's actually consuming the window before deciding whether /clear, /compact, or a new session is the right call.
  • /compact <instructions> lets you steer what survives — /compact keep the list of modified files and the failing test command is more useful than the default summary for a task you're about to resume tomorrow.
  • CLAUDE.md rules survive compaction because they're reloaded at session start, not carried as compressible transcript — that's why durable constraints belong there, not in a chat message.
  • Esc twice, or /rewind, is a fourth, related tool: it restores conversation and/or code to an earlier checkpoint rather than summarizing forward — useful when you want to undo, not just shrink.

Remember this

/clear is reversible and cheap, /compact is a real summarization that can quietly drop a constraint nothing reinforced, and a new session beats a third correction attempt — pick based on whether you're switching tasks, trimming noise, or escaping accumulated wrong turns.

Concurrent sessions, branching, and multi-day tasks

Running more than one Claude Code conversation against the same repository is common — a second opinion on a diff, an unrelated bug fixed in parallel, or a risky rewrite you don't want to commit to yet. The mechanism you pick determines whether the two conversations collide. Resuming the exact same session from two terminals without forking is the one to avoid by default: both processes write to the same transcript, so messages from each interleave into one file, and neither Claude instance has a coherent view of what the other just did. /branch <name>, run from inside a session, avoids that by copying the conversation so far into a new session with its own ID and switching you into it — the original is untouched on disk and still in the picker. From the command line, the equivalent is claude --continue --fork-session or claude --resume <name> --fork-session. Branching is a conversation fork, not a filesystem fork: both the original and the branch still point at the same working directory, so simultaneous file edits from both can still collide.

For actual filesystem isolation, use a worktree: claude --worktree pricing-fix creates a new git worktree — a separate checkout on its own branch, sharing the same repository history — and starts a session there. Now two Claude Code processes can genuinely work in parallel without either one's edits touching the other's files, which is the right setup for BILL-451's invoice migration running alongside an unrelated hotfix. A resumed session that started inside a worktree returns to that same worktree automatically, whether you resume interactively, with -p, or through a fork; a fork that started outside a worktree starts in the directory you launched from, since there's no worktree of its own to return to.

For the multi-day shape of BILL-451 specifically: name the session on day one, resume it by name each morning rather than re-explaining the migration from scratch, and treat git commit as the durable checkpoint, not the session state — checkpoints inside Claude Code (its own automatic per-turn snapshots, or /rewind) recover conversation and file edits made through Claude's own tools, but they are not a replacement for git, and don't capture changes made through Bash commands or external processes. A session resumed after a long gap (roughly an hour of inactivity past 100k tokens) will offer to resume from a compacted summary rather than the full history — useful on day three of a five-day migration once the early exploration no longer matters, and worth declining ("resume full session as-is") on a day when you specifically need to recall an earlier decision verbatim.

Three ways to run more than one Claude Code conversation on the same repo
Three ways to run more than one Claude Code conversation on the same repo

Quick reference

  • /branch carries over "allow for this session" permission grants because it runs in the same process; --fork-session starts a separate process, so you re-approve permissions there.
  • In-flight background subagents and background Bash commands keep running through a /branch — their output appears in the branch you switched into, not the original.
  • Worktrees share the repository's .git directory and, since v2.1.211, saved permission approvals with the main checkout — so a Bash rule you approve in one worktree applies everywhere, including after that worktree is removed.
  • For coordinating several agents deliberately rather than just isolating them, see the broader anatomy in Subagents Explained; worktrees isolate files, subagents isolate context — they solve different problems and combine well.
Two isolated parallel sessions
1# Terminal A — the invoice migration, isolated2claude --worktree bill-4513 4# Terminal B — an unrelated hotfix, isolated5claude --worktree cart-hotfix
Fork one conversation to try a risky approach
1# Inside the bill-451 session:2/branch try-streaming-render3 4# Or equivalently, from the shell:5claude --resume bill-451 --fork-session

Remember this

Two terminals on the same unforked session interleave into one transcript; /branch forks the conversation but keeps one shared working directory; a worktree forks both the conversation and the filesystem — pick isolation depth by what actually needs to stay separate.

Key takeaway

None of this requires remembering exotic flags day to day — claude --continue covers most single-task mornings, --resume and named sessions cover the rest, /clear resets without deleting, and a worktree isolates real parallel work. The part worth internalizing is the boundary between what's saved automatically (the transcript, model, permission mode) and what isn't (launch flags like --mcp-config, and bypass-permissions mode), because that's where a resume quietly behaves differently from what you expect.

Practice (20 min): In a real or scratch git repository, run claude -n resume-drill and ask it to list three files in the project and summarize what each does. Exit cleanly, then run claude --continue and ask a follow-up that depends on the earlier answer ("of those three, which one would you edit first and why") — expected result: it answers using the earlier list without you repeating it, proving the transcript persisted. Now intentionally break the lookup: cd to an unrelated directory (or /tmp) and run claude --resume resume-drill — expected result is the explicit No conversation found with session ID (or name) failure, not a wrong session. Recover by cd-ing back into the original repository and resuming again; confirm it works. Pass only when you can point to where the transcript is stored on disk (~/.claude/projects/<project>/), state which one flag you'd add to restore an MCP-dependent session that a plain --continue wouldn't bring back, and reproduce the directory-scope failure on demand.

Share:

Related Articles

The Claude Code CLI has grown from claude plus a few convenience flags into a full control surface: interactive sessions

Read

Standard agent sessions require continuous human steering: after every turn, the user inspects tool outputs and types th

Read

When developers migrate from prototyping with raw LLM API calls to embedding autonomous agent workflows into production

Read

Explore this topic

Keep learning

Follow a structured path or browse all courses to go deeper.