fix(goal): quiet waits and unify fleet NG ownership (#56, #57, #58)

This commit is contained in:
Dewey
2026-09-06 04:07:09 -05:00
parent 7345f330fc
commit 9a5fbdbda7
14 changed files with 892 additions and 26 deletions
+25 -9
View File
@@ -14,7 +14,7 @@ Requirements record: `docs/PRD.md` in mosaic-brain (issue #52). Design locked wi
/goal <text> set (or replace, with a notify) the active goal
/goal --max N <text> set with a non-default run limit (default 25)
/goal stop pause the loop, goal retained
/goal resume continue a paused goal (kicks a check turn)
/goal resume reconcile a paused or waiting goal (kicks one check turn)
/goal clear remove the goal entirely
```
@@ -24,7 +24,7 @@ Requirements record: `docs/PRD.md` in mosaic-brain (issue #52). Design locked wi
1. `before_agent_start` appends the active goal and reporting instructions to the system
prompt every turn, so the goal survives context growth and compaction.
2. When the agent settles without the goal being satisfied, the extension injects a check
2. When the agent settles with ready work and no unresolved wait, the extension injects a check
prompt (`sendUserMessage`), forcing the next turn: the check<->proceed loop. Before reporting,
follow the continuation loop in `skills-local/ms-proactive-agent/SKILL.md`.
3. The agent reports via `goal_report`, the loop's only exit:
@@ -87,15 +87,26 @@ The suite includes pure state, persistence, incarnation fencing, exact report-on
duplicate evidence, legitimate wait, headless extension-runtime, and enforcement-neutralization
red controls.
## Bounded waits (operator opt-in)
## Quiet waits and optional deadlines
Use `/goal --wait-timeout 60 <goal text>` to suspend automatic checks during a
reported wait. The flag accepts 1086400 seconds and combines with `--max N`.
Omitting it preserves the previous wait-loop behavior. Existing running sessions
must `/reload` to load this patch; do not reload unrelated seats for a trial.
Every accepted wait suspends automatic checks, including untimed waits. No
cooldown or model polling is used. A next-check condition describes the dependency;
it is not executed as code, and the extension does not register a watch for it.
Existing external message/watch delivery or explicit `/goal resume` can start
reconciliation. Incoming messages alone do not clear the wait. The model must
verify the dependency and report substantive progress or completion. Unrelated
input preserves the wait. Explicit resume clears the old wait; another unresolved
wait report suspends checks again. Paused and blocked goals still require explicit
operator resume, not merely an incoming message.
Use `/goal --wait-timeout 60 <goal text>` to add one deadline wake to a wait.
The flag accepts 1086400 seconds and combines with `--max N`. Without it,
no deadline timer is armed. Existing running sessions require a controlled reload
after an approved deployment; do not reload unrelated seats for a trial.
A valid `goal_report` with `status: "in_progress"`, `progress.kind: "wait"`, an
owner, and a watch id or concrete `nextCheck` persists the deadline and yields.
owner, and a watch id or concrete `nextCheck` persists the wait and yields.
A deadline is persisted only when the operator configured one.
There are no model heartbeats during that wait. Repeated wait reports preserve
its original deadline. A substantive progress report clears the wait. The
extension neither evaluates arbitrary shell conditions nor sends messages to
@@ -124,6 +135,11 @@ Late reports cannot settle a paused goal. Reports also refuse if the goal change
while an asynchronous policy check is running. State snapshots use atomic file
replacement; failed saves stop continuation instead of claiming a saved result.
The tests exercise unchanged waits, deadline dispatch and observation, unresolved
An in-memory pending-check guard prevents duplicate settle/startup events from
queuing the same check before its matching start is observed. It does not cancel
messages already queued by Pi, span independent extension instances, or supply a
process supervisor. Wait state itself persists across same-incarnation reloads.
The tests exercise timed and untimed waits, deadline dispatch and observation, unresolved
pause, compaction, reload, cancellation, print mode, malformed persisted waits,
and actual filesystem write failure. This is separate from live seat acceptance.