Add /graph G1: parallel fan-out with worktree isolation and merge-back
With KIGI_GRAPH_CONCURRENCY > 1 (default 3, clamp [1,8]) and >=2 Ready nodes, drive_graph — the single dispatch loop shared by setup/advance/resume — runs parallel batches: each node executes as a bounded worker<->verifier subagent loop (KIGI_GRAPH_NODE_ROUNDS, default 3; general-purpose children with the full implementer toolset; worktree isolation on round 1, resume keeps context and worktree on later rounds; NODE_RESULT/NODE_VERDICT terminal contracts parsed fail-closed with fence-stripping and line anchoring). Achieved nodes merge back SEQUENTIALLY via kigi_workspace apply_worktree in Merge mode; a conflict fails the node, block_dependents fires, and surviving chains keep going. gn-final always runs serially on the full goal engine. Concurrency=1 is byte-identical to the serial G0 path; non-git projects degrade to serial. Merge primitive hardened for real use (kigi-workspace): the 3-way apply is now byte-safe (binary files no longer read as UTF-8 and silently deleted) and gains the identical-content rule (ours==theirs => already present, not a conflict) — without it, any dirty file inherited via PreserveWorkingTree false-conflicted every node merge and multi-wave graphs self-poisoned. Adversarial review pass (16 confirmed findings, all fixed): in-session resume demotes orphaned Running nodes instead of wedge-pausing forever after a mid-batch Esc; cancel re-sweeps subagents AFTER the turn abort so workers spawned in the cancel window die too; empty child ids are never adopted as resume targets (no unisolated escape to the shared tree); a successful isolated round returning no worktree fails the node (soft-fallback can no longer put N writers in one tree); main-HEAD movement during a batch aborts merges instead of reverse-applying external commits; failed nodes still charge the token budget; budget trips terminally fail the in-flight node; runaway (>600s) rounds are cancelled by spawn id and retried via resume; worker summaries are marker-sanitized before verifier embedding. Merged worktrees are removed immediately (storage discipline); failed nodes keep theirs for postmortem. Tests: 4922 kigi-shell lib tests green (58 graph-specific), including fan-out proven by a held-reply gate, real-git batch merge with cleanup assertions, budget charging across verdicts, cap trimming, resume-after- cancelled-batch, and backgrounded-round cancel semantics.
This commit is contained in:
@@ -49,6 +49,17 @@ import) or any `KIMI_*` env var.
|
||||
- `third_party/` — vendored Mermaid rendering stack (untouched policy).
|
||||
- `bin/protoc` — dotslash launcher used by proto codegen.
|
||||
|
||||
## Storage discipline
|
||||
|
||||
- Tests that touch the filesystem MUST use `tempfile::TempDir` (drop
|
||||
cleans up) — never bare `std::env::temp_dir()` + `create_dir_all`,
|
||||
which leaks directories into the OS temp root forever.
|
||||
- `target/` grows past 150GB across repeated full-workspace builds
|
||||
(incremental is already off); run `cargo clean` when it exceeds
|
||||
~50GB and at milestone boundaries.
|
||||
- Graph node worktrees are removed right after a successful merge-back;
|
||||
only FAILED nodes keep theirs for postmortem.
|
||||
|
||||
## Test seams
|
||||
|
||||
Cross-crate test hooks are behind the `test-support` cargo feature
|
||||
@@ -86,6 +97,19 @@ edges stay deterministic Rust. The harness appends a terminal
|
||||
the verifier gates completion).
|
||||
- `/goal` and `/graph` are mutually exclusive while the graph owns the
|
||||
engine; e2e suite: `acp_session_tests/graph/graph_e2e_tests.rs`.
|
||||
- Parallel fan-out (G1): with `KIGI_GRAPH_CONCURRENCY > 1` (default 3,
|
||||
clamp [1,8]) and ≥2 `Ready` nodes, `drive_graph` runs batches via
|
||||
`acp_session_impl/graph_workers.rs` — per node a bounded
|
||||
worker↔verifier subagent loop (`KIGI_GRAPH_NODE_ROUNDS`, default 3;
|
||||
`general-purpose` children; worktree isolation on round 1, resume
|
||||
keeps context+worktree on later rounds; `NODE_RESULT:` /
|
||||
`NODE_VERDICT:` terminal contracts parsed fail-closed), then
|
||||
SEQUENTIAL merge-back via `kigi_workspace::worktree::apply_worktree`
|
||||
(`ApplyMode::Merge`); a conflict fails the node and blocks its
|
||||
dependents while other chains continue. `gn-final` always runs
|
||||
serially on the full goal engine. Concurrency=1 is byte-identical to
|
||||
the serial G0 path. Ceiling: a worker round exceeding the foreground
|
||||
subagent await budget (600s) is cancelled and retried via resume.
|
||||
|
||||
## Milestones (PRD §8.3)
|
||||
|
||||
|
||||
Reference in New Issue
Block a user