--- name: parallel-worktree-path-hazard description: "\"Use when several agents edit the same repo in different git worktrees at once, or when an edit/read may have landed in the wrong checkout: which path forms bind where, how to detect with git -C status, and the repair protocol (cp + git show HEAD blob write-back) because git checkout/restore is policy-blocked in a shared workspace.\"" --- # Concurrent-worktree path hazard (shared repo, many agents) Measured 2026-10-18 on `serverAppConfigs` with two agents live at once. The failure is **silent**: the tool reports success, the diff looks right, and the change lives in a *different* worktree. ## Which path form binds where - **Parent/top-level session**: a **relative** `path` resolves against the session CWD — its own worktree — never against the worktree named in the prompt. This is how a change meant for `wt-tts-trial-docs` landed in `wt-20261017-…`. - **Subagent**: an **absolute** path to its own assigned worktree can resolve into the parent's worktree when the same *relative* path exists there (`edit` twice onto `dankclaw/.env.example`). Its `write` with the same absolute path was fine — the bug is `edit`/`read` path resolution, not `write`. Rules that hold: 1. A subagent passes paths as `..//` (relative to the parent worktree) for `read` **and** `edit`; the parent passes **absolute** paths to any worktree that is not its own CWD. 2. After every edit batch, prove the landing site, do not trust the tool's echo: `git -C status --short` must list the file. A file you edited that is missing from that list went somewhere else. 3. Keep each work item on its own branch/worktree, and keep ONE integration owner (the parent) for shared files — `scripts/deploy-remote.sh`, `scripts/deploy-plan.py`, `tests/`, `serverAppConfigs-docs/index.md`, `AGENTS.md` are the collision hot spots in this repo. Never rebase a sibling's branch. ## Repair protocol (no `git checkout`, no `git restore`) `git checkout -- ` and `git restore ` are **policy-blocked** in a shared workspace ("overwriting working-tree files … discards changes other concurrent agents rely on"). Unstaging (`git reset []`, `git restore --staged `) is allowed but does not undo content. So: ```bash F="path/with spaces if any" # 1. move the change to the worktree that should own it (both at the same base commit) cp "/$F" "/$F" # 2. undo in the wrong worktree by writing the committed blob back git -C "" show "HEAD:$F" | tee "/$F" > /dev/null # 3. prove both sides md5sum <(git -C "" show "HEAD:$F") "/$F" "/$F" git -C "" status --short # must be empty for that file git -C "" diff --stat # must show the intended delta ``` Never fix it blind: if the wrong worktree had its own uncommitted edits to that file, `cp`/blob-write-back would destroy them — check `git -C status --short` FIRST and reconcile content, don't overwrite. ## Tidy after a cancelled sibling A killed subagent can leave a worktree plus an empty branch. Removing them is safe only when verified empty: `git -C
log --oneline -3 ` (no unique commits) and `git -C status --short` (clean), then `git worktree remove ` + `git branch -D `. An orphan worktree at a stale commit is the same class of trap as a leftover bench drop-in: the next agent reads it as unfinished work. ## Report it File the misresolution to `xd://report_issue` (false positives are fine) and record the incident in the repo worklog — a repair nobody wrote down looks like a hijack later.