live: heartbeat sync 2026-10-18T16:47:59-07:00 (Refs #11)
This commit is contained in:
1 parent
a550db6027
commit
979e9ef711
173 files changed
+3844
-57
No files matched your search
@@ -0,0 +1,68 @@
|
||||
---
|
||||
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 `../<its-worktree>/<rel>` (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 <intended-worktree> 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 -- <path>` and `git restore <path>` are **policy-blocked** in a
|
||||
shared workspace ("overwriting working-tree files … discards changes other
|
||||
concurrent agents rely on"). Unstaging (`git reset [<path>]`,
|
||||
`git restore --staged <path>`) 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 "<wrong-wt>/$F" "<right-wt>/$F"
|
||||
# 2. undo in the wrong worktree by writing the committed blob back
|
||||
git -C "<wrong-wt>" show "HEAD:$F" | tee "<wrong-wt>/$F" > /dev/null
|
||||
# 3. prove both sides
|
||||
md5sum <(git -C "<wrong-wt>" show "HEAD:$F") "<wrong-wt>/$F" "<right-wt>/$F"
|
||||
git -C "<wrong-wt>" status --short # must be empty for that file
|
||||
git -C "<right-wt>" 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 <wrong-wt> 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 <main> log --oneline -3 <branch>` (no
|
||||
unique commits) and `git -C <wt> status --short` (clean), then
|
||||
`git worktree remove <wt>` + `git branch -D <branch>`. 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.
|
||||
Reference in new issue
Block a user