Skip to content

Bug: autonomous replan no_followup can make the Goal terminal before its bound quota spend #4501

Description

@shangzh0

Bug: autonomous replan no_followup can make the Goal terminal before its bound quota spend

Summary

An LHTB apex-ib244-matter run exposed two separate behaviors that should not
be conflated:

  1. A closed agent vision while the registry Goal remains active produces
    vision_successor_required and then autonomous_replan_required. This is
    expected fail-closed behavior.
  2. When that autonomous replan resolves the frontier with a coverage-backed
    no_followup, its durable writeback can derive terminal_no_followup
    before the same settlement identity records its quota spend. The strict
    terminal guard then rejects that pending spend. This is an ordering bug.

The result is an unnecessary control-plane self-repair turn after the benchmark
work itself is already complete.

Observed run

  • LoopX revision used by the run:
    1c7b40ea403f9949b22f32071eec237199e52554
  • Benchmark result: 38/38 stages submitted
  • Final reward: 0.993151
  • Scheduler wakes:
    1. normal_run
    2. autonomous_replan_required
    3. autonomous_replan_required
    4. scheduler poll returns terminal_no_followup

Wake 1: benchmark completion and Todo settlement

The agent completed all 38 stages. The first material refresh correctly
reported a missing required vision checkpoint. The agent then:

  1. recorded an evidence-linked vision_closed checkpoint;
  2. committed the Todo-bound durable writeback;
  3. committed exactly one Todo-bound quota spend;
  4. completed the Todo with --no-follow-up;
  5. read back heartbeat_settled_skip for that Turn.

The vision checkpoint gate and its repair were expected.

Wake 2/3: expected Goal-level replan

On the next fresh Turn, quota projected:

{
  "decision": "autonomous_replan_required",
  "effective_action": "autonomous_replan_required",
  "selected_todo": null,
  "autonomous_replan_obligation": {
    "triggers": [
      {
        "kind": "vision_successor_required",
        "text": "the current stage vision is closed while the registry goal remains active; establish a successor vision before continuing"
      }
    ]
  }
}

This replan is expected: Todo no_followup is not by itself Goal completion.
The Goal still needs either a successor vision or an evidence-backed terminal
frontier decision.

The first replan wake returned without settling the obligation, so the
scheduler correctly presented the same obligation again. The following wake
validated that 38/38 was complete and selected
coverage_backed_no_followup, with an agent vision whose state was
no_followup and whose path outcome was stop.

Failure

The autonomous-replan settlement plan was:

validation -> durable_writeback -> quota_spend

The durable writeback succeeded and derived Goal state
terminal_no_followup. The immediately following, correctly bound
quota spend-slot was rejected because quota accounting no longer admitted
delivery completion spend from a terminal state.

At the point of failure:

validation receipt:       committed
durable writeback receipt: committed
quota spend receipt:       absent
Goal state:                terminal_no_followup
effect identity:           unchanged and correctly replan-bound

This matches the documented terminal_settlement_ordering_gap: terminal state
became visible between two ordered steps of the same effect.

Why this is a bug

The terminal guard is correct to reject new work and unrelated spends after a
Goal is terminal. However, a writeback from the current typed settlement must
not make the remaining step of that exact settlement impossible.

The replan itself is not the bug. The bug is that final Goal-level
no_followup is applied as part of pre-spend writeback instead of as a
conditional post-spend closeout under the same effect identity.

Current main audit

Audited remote main at:

f97ba42219442e4b46819e4795050dd8c41d2389

Current main correctly retains the expected vision behavior:

  • tests/control_plane/test_goal_vision_succession.py requires a closed stage
    vision on an active Goal to produce vision_successor_required.
  • skills/loopx-self-repair/references/repair-patterns.md documents
    terminal_settlement_ordering_gap and recommends post-spend terminal
    closeout.

Current main also adds a conditional terminal_closeout step for Todo-bound
settlements. However, the exact autonomous-replan path remains uncovered:

  • build_turn_scoped_cli_settlement_plan() adds terminal_closeout only when
    todo_id is present; a replan_obligation_id plan still ends at
    quota_spend.
  • build_quota_slot_preview_for_decision() still admits delivery completion
    spend only from waiting, focus_wait, operator_gate, or eligible, not
    from terminal_no_followup.
  • The focused regressions created during the run are not present on current
    main.

Therefore this issue is recognized and partly addressed for Todo closeout, but
the observed autonomous-replan terminal path is not demonstrably fixed.

Expected behavior

For an autonomous replan whose accepted semantic outcome is
coverage_backed_no_followup, preserve the strict terminal guard while making
the settlement order explicit:

validation
-> durable writeback
-> quota spend
-> conditional terminal closeout

Requirements:

  • all four steps use the same typed effect identity and replan obligation;
  • terminal mutation requires matching writeback and spend receipts;
  • retrying terminal closeout must not repeat writeback or spend;
  • unrelated or unbound terminal spends remain rejected;
  • cancellation, failed validation, failed writeback, and rejected spend must
    short-circuit before terminal mutation.

Suggested regression coverage

  1. Active Goal plus vision_closed still produces
    vision_successor_required and autonomous_replan_required.
  2. A replan-bound, coverage-backed no_followup writeback does not strand the
    matching quota spend.
  3. Terminal closeout occurs only after matching writeback and spend receipts.
  4. Replay produces no additional spend or writeback.
  5. A terminal Goal still rejects an unbound spend and a mismatched replan
    obligation.
  6. The generic CLI heartbeat path reaches heartbeat_settled_skip without a
    model-authored self-repair worktree.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions