Skip to content

agent: nudge a turn that only announces its next step - #311

Merged
thedancingdeveloper merged 3 commits into
mainfrom
wi-1301-trailoff-guard
Oct 13, 2026
Merged

thedancingdeveloper merged 3 commits into
mainfrom
wi-1301-trailoff-guard

Conversation

@thedancingdeveloper

Copy link
Copy Markdown
Contributor

Summary

  • A headless, goal-loop, or stream-json run that ends on a reply which only announces the next step ("I'll read X next.") now gets a nudge back into the same turn instead of ending, capped at two nudges per run. The count is reported on Result.TrailOffNudges.
  • A reply that asks a question, or that carries AUTOPILOT: DONE or <goal-complete/>, still ends the turn. Interactive TUI turns are unaffected — ending there is how the user gets to answer.

Closes the failure mode behind WI-1301: an unattended run that trails off otherwise costs a whole re-prompt to recover.

Test plan

  • go test ./internal/agent/ ./internal/cli/ — detector cases, the nudge-then-continue path, the cap, the off-by-default path, and the completion-marker / question exemptions
  • A live -p run whose model announces a next step continues instead of exiting

thedancingdeveloper and others added 3 commits October 13, 2026 07:07
A headless or goal-loop run that ends on "I'll read X next" has done
nothing, and recovering it costs a whole re-prompt. When
ContinueOnTrailOff is set, a tool-less reply that matches an
announcement pattern gets one user-message nudge back into the same
loop, capped at two, and the count lands on Result.TrailOffNudges.

A question and a reply carrying AUTOPILOT: DONE or <goal-complete/>
still end the turn. The flag is on for -p, the goal loop, and the
stream-json peer, and off for an interactive TUI turn where ending is
how the user gets to answer.

Co-Authored-By: Klaudia <noreply@greenthread.ai>
… only the last sentence

Fixes the three blockers from the WI-1301 review of PR #311.

Reporting: Result.TrailOffNudges was set but never surfaced. It now
appears as trail_off_nudges on the -p JSON result and the stream-json
result line (omitted when zero), and sumResults adds it across a
background-drain follow-up. docs/embedding.md lists the field.

Limits: the nudge's continue skipped the max_turns and budget checks at
the bottom of the loop, so MaxTurns=1 with three announcements ran three
turns. The nudge now fires only while withinLimits(opts, res) holds;
past the cap the announcement stands as the answer.

False positives: the patterns matched "I'll <verb>" anywhere in the last
~200 characters. The detector now looks at the last sentence only, and
exempts conditional offers ("If you approve, I'll push") and deferrals
("in a follow-up PR", "later"). The review's three examples are negative
test cases now.

Measured: go build, go vet ./..., go test ./internal/..., scripts/hermetic.sh
and go test ./e2e/... pass. A live -p run on grok-4.7, told to answer
"I'll read notes.txt next." with no tool call, returned trail_off_nudges:1,
num_turns:4, and went on to read the file. Not measured: how often the
conditional/deferral exemptions skip a real trail-off in practice.

Co-Authored-By: Klaudia <noreply@greenthread.ai>
The WI-1301 re-review found closing lines nudged as announcements:
"Let me know what you think.", "Summary above. Let me know.",
"Done. I'll leave the rest to you.", "I'm going to stop here." and
"I will now stop." A last sentence with "let me know" or a stop or
hand-back verb (stop, pause, end, wrap up, leave, hand back/over) now
counts as an ending. The five are must-not-nudge tests.

Measured: go build, go vet ./..., go test ./internal/..., scripts/hermetic.sh
and go test ./e2e/... pass. Assumed: an announcement whose last sentence
uses one of these verbs for something else ("I'll read the end of the
log") is rare enough to give up.

Co-Authored-By: Klaudia <noreply@greenthread.ai>
@thedancingdeveloper
thedancingdeveloper merged commit 7c45a7f into main Oct 13, 2026
3 checks passed
@thedancingdeveloper
thedancingdeveloper deleted the wi-1301-trailoff-guard branch October 13, 2026 09:48
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant