LEARN · PHASE 16 · LESSON 106

Session vs Agent Scope

You can say whether a worktree belongs to a whole session or to one agent —

Type
Learn
Prerequisites
Phase 11 (Lesson 74, Worktrees, Deep), Phase 02
Time
~30 minutes

Learning Objectives

  • Say whether a given worktree covers a session or a single agent
  • Read a subagent file and predict, from its frontmatter, whether it gets its own checkout
  • Start a session worktree and a per-agent worktree, and show the difference on disk
  • Pick the scope that stops two parallel editors from touching the same file

The Problem

You start a session with a worktree. You spawn three subagents to refactor three parts of a module that all import the same helper. You assume --worktree means "every agent gets its own checkout."

It does not. It gives the session one checkout. Ordinary subagents run in that one folder.

Two of your subagents edit the same helper file. The second one writes over the first. When the run ends there is no merge conflict waiting for you — and that is the tell that something is wrong. There was only ever one copy. The work one agent did is simply gone, and the file looks like the other agent wrote it.

Nobody lied, and no command failed. You picked the wrong scope.


The Concept

A worktree is a second working folder for the same repository, on its own branch. That much is Phase 11. The question this lesson answers is who owns it: the session, or one agent inside it.

Two scopes, and they stack.

flowchart TD
    S[Session] -->|"--worktree name"| WT[Session worktree<br/>one folder, one branch]
    WT --> A1[Subagent A]
    WT --> A2[Subagent B]
    WT --> A3[Subagent C]
    A1 -.->|"no isolation"| WT
    A2 -.->|"no isolation"| WT
    A3 -.->|"no isolation"| WT

    S2[Session] -->|"--worktree name"| WT2[Session worktree]
    WT2 --> B1["Subagent A<br/>isolation: worktree"]
    WT2 --> B2["Subagent B<br/>isolation: worktree"]
    B1 --> B1w[own temp worktree]
    B2 --> B2w[own temp worktree]
Mermaid source — renders as a diagram where mermaid.js is available

Session scope

claude --worktree <name> (or -w) creates one worktree and starts the session in it. Claude Code puts it under .claude/worktrees/<name>/ at the repository root and checks out a branch named worktree-<name>. You can also ask Claude to "work in a worktree" mid-session; it enters one with the EnterWorktree tool.

This isolates the session from other sessions. Open a second terminal, run claude --worktree bugfix, and the two sessions now have separate folders.

It does not isolate subagents from the session or from each other. Every subagent that is not configured otherwise inherits the session's working folder. That is usually what you want — an agent editing the session's files. It is a problem when you launch several at once against overlapping files.

Agent scope

A subagent can be given its own worktree by adding one line to its frontmatter:

---
name: refactorer
description: Applies mechanical refactors across many files
isolation: worktree
---

Apply the requested refactor across every affected file, then run the tests
and report the results.

Now each time that subagent runs it gets a temporary worktree of its own. Claude Code removes it automatically when the subagent finishes with no changes. If the subagent leaves changes behind, the worktree stays on disk so nothing is lost.

That is the difference in one line: session scope isolates sessions; agent scope isolates agents.

The base they branch from

Both kinds branch from your repository's default branch by default — the setting worktree.baseRef is "fresh", meaning a clean checkout of main. Set it to "head" when the agent must start from your current work, including commits you have not pushed:

{
  "worktree": {
    "baseRef": "head"
  }
}

This matters because "fresh" means every agent starts from the same clean base. If your session's work is uncommitted, an isolated subagent will not see it.

The reframe: a session worktree isolates you from other sessions; a

per-agent worktree isolates agents from each other — the same trick, aimed at

two different collisions.


Build It

You need a git repo with at least one commit. Phase 00's lab repo works.

1. Start a session worktree and find it on disk

cd ~/claude-course-lab
claude --worktree auth

Then, from another terminal or after the session ends:

git worktree list

✅ You pass when git worktree list shows a worktree under .claude/worktrees/auth on a branch named worktree-auth.

2. Confirm subagents share it

Inside that session, with no subagent configured for isolation, ask Claude to run any two subagents that touch files. While they run, watch the worktree list from a second terminal.

git worktree list

✅ You pass when no new worktree appears — both subagents are working in the one session folder.

3. Give one subagent its own scope

Create the file .claude/agents/refactorer.md with the frontmatter from above, including isolation: worktree. Run it once from the session.

✅ You pass when a second worktree appears under .claude/worktrees/ while the subagent runs, and disappears afterwards if it made no changes.

4. Make the base explicit

Add the worktree.baseRef block to .claude/settings.json and set it to "head". Run the subagent again from a session that has an uncommitted commit.

✅ You pass when the subagent's worktree contains your unpushed commit, visible with git -C <that-worktree> log --oneline -1.

5. Explain the failure from The Problem

Two subagents stampeded one helper file. Say, in one sentence, which scope was missing.

✅ You pass when your answer is "agent scope — they shared the session worktree," not "session scope — we needed a worktree."


Use It

Command / conceptWhen you reach for it
claude --worktree <name> / -wIsolating a whole session from other sessions
.claude/worktrees/<name>/Where Claude Code puts the worktrees it creates
git worktree listSeeing every checkout of the repo, and which branch each is on
isolation: worktree (subagent frontmatter)Isolating one agent from the session and from its siblings
worktree.baseRef: "fresh"Every agent starts from the default branch (the default)
worktree.baseRef: "head"Agents start from your current, possibly unpushed, work
EnterWorktreeAsking Claude to move a running session into a worktree
.gitignoreAdd .claude/worktrees/ so worktree contents don't show as untracked

Exercises

  1. Run two sessions with --worktree, edit the same file in each, and commit in each. Merge them yourself. ✅ You pass when both commits exist in the repository history and you can name the branch each came from.
  1. Take a subagent that edits several files, give it isolation: worktree, and run two copies of it at once. ✅ You pass when two separate worktrees appear in git worktree list and neither agent's edits show up in the other's folder.
  1. For each of these, write down the scope you would choose and why: (a) three research subagents that only read code; (b) three subagents that each rewrite a different package's internals; (c) one subagent fixing a typo. ✅ You pass when (a) and (c) are agent-free — they cannot collide — and (b) is per-agent isolation, with your reason matching "they edit files in parallel."

Key Terms

TermWhat people sayWhat it actually means
session worktree"isolation for my agents"One checkout for the whole session. It isolates the session from other sessions, not its subagents from each other.
agent worktree"a worktree"A checkout that belongs to one subagent, created because its frontmatter says isolation: worktree.
isolation: worktree"agent isolation"A subagent frontmatter field. One line; each run gets its own temporary checkout.
base ref"where it branches from"worktree.baseRef: "fresh" = the default branch, "head" = your current local work.
EnterWorktree"opening a worktree"Claude moving the running session into a worktree mid-session.
.worktreeinclude"copying my env file in"A list of gitignored files (.env, and so on) copied into every worktree Claude Code creates.

What this lesson skipped

The desktop app's worktree option. Select worktree when you start a desktop session and you get the same thing without the flag. Same mechanism, a different door.

Non-git version control. SVN, Perforce, and Mercurial need WorktreeCreate and WorktreeRemove hooks. Come back when you are not on git.

Sparse and partial worktrees. Useful in monorepos to check out only the part you need. Phase 17's scaling material, not this.

Every cleanup rule. Which worktrees Claude Code sweeps, locks, and keeps is a page of its own. The short version: uncommitted work and unpushed commits keep a worktree on disk, and that is exactly the safety net Lesson 110 is about.

Checked against the Claude Code worktrees documentation in October 2026: <https://code.claude.com/docs/en/worktrees>. Version-gated details drift — verify in your build.

Check yourself

4 questions. Answer before you reveal — recognising the right option is not the same as being able to produce it.

  1. You run one session with --worktree, then spawn three subagents that each rewrite a different file — but two of them import the same shared helper and both rewrite it. Nothing errors, and at the end there is no conflict to resolve. What actually happened?

    1. The session worktree isolated the subagents from each other, so their edits landed on separate branches
    2. Claude Code refused the overlapping edits but reported success anyway
    3. All three subagents shared the session's one worktree, so the second writer overwrote the first in the same file
    4. The two subagents each got a temporary worktree, which is why there was no conflict
    Show answer

    C. All three subagents shared the session's one worktree, so the second writer overwrote the first in the same file

    A session worktree gives the whole session one checkout; subagents without isolation: worktree inherit it. Two writers, one file, second wins. Option D is the tempting wrong answer because it sounds like a feature — but per-agent worktrees only appear when a subagent's frontmatter asks for them, and then a conflict would be possible rather than absent. The absence of any conflict is the clue that there was only one copy.

  2. You want three subagents to refactor three separate packages in parallel without any chance of them touching each other's files. You are not currently in a worktree session. What is the smallest change that gives you that?

    1. Add isolation: worktree to the frontmatter of the subagent they share
    2. Start the session with claude --worktree refactor
    3. Run each subagent with a different model
    4. Add .claude/worktrees/ to .gitignore
    Show answer

    A. Add isolation: worktree to the frontmatter of the subagent they share

    Per-agent isolation is the scope that stops agents colliding with each other; isolation: worktree in the subagent's frontmatter gives each run its own checkout. Option B is the tempting wrong answer because --worktree is the command you know, but it isolates the session from other sessions and leaves the three agents sharing one folder. Models and .gitignore change nothing about who edits which folder.

  3. A subagent is configured with isolation: worktree and must build on a commit you made but have not pushed. By default its worktree branches from the default branch, so it does not see your commit. What do you change?

    1. Add the commit hash to the subagent's description field
    2. Check out the branch in the main folder before running the subagent
    3. Nothing — an isolated worktree always carries your unpushed commits
    4. Set worktree.baseRef to "head" in settings
    Show answer

    D. Set worktree.baseRef to "head" in settings

    worktree.baseRef controls the base: "fresh" (the default) branches from the default branch, "head" branches from your current local HEAD, including unpushed commits. Option C is the tempting wrong answer because it reverses the default. Option B does not help — an isolated worktree is a separate checkout and does not follow the main folder's current branch.

  4. Two subagents only read code and return a written analysis; they never edit files. A colleague insists you must give them isolation: worktree or they will collide. Are they right?

    1. Yes — any two subagents that run at once need separate worktrees
    2. No — read-only agents cannot collide on files, so isolation buys nothing and costs a checkout each
    3. Yes, because the second subagent's context window overwrites the first
    4. No, because isolation: worktree is not valid on a subagent
    Show answer

    B. No — read-only agents cannot collide on files, so isolation buys nothing and costs a checkout each

    Isolation protects files from concurrent writes. Agents that do not write files have nothing to collide on, so per-agent worktrees add setup cost for no safety. Option A is the tempting wrong answer because it turns a real rule ('parallel writers need isolation') into a blanket one. Option D is simply false — isolation: worktree is valid subagent frontmatter.