mirror of
https://github.com/stablyai/orca.git
synced 2026-09-29 16:02:50 +00:00
fix(orchestration): name the pending-work exception in the nextAction rule
The kernel claimed every unverifiable row reports a `none` nextAction, but projectFleetNextAction deliberately keeps `inspect` when input or approval is pending, because that is work a command can actually move. An agent following the guide literally would have treated a waiting question as another wait-only row. The guidance test asserted the sentence verbatim, so it agreed with the wrong text instead of the behavior; it now checks the rule's two halves as fragments, and the projection suite covers both pending flags directly.
This commit is contained in:
@@ -168,9 +168,11 @@ describe('orchestration kernel', () => {
|
||||
expect(kernel).toContain(
|
||||
'`projection.attention` categories, `projection.attention.requiresAction`, and literal `projection.nextAction` argv'
|
||||
)
|
||||
expect(kernel).toContain(
|
||||
'A `none` `nextAction` has no argv to run: read `liveness.reason` and keep waiting with `check --wait`. Every `unverifiable` row reports it, `requiresAction` or not'
|
||||
)
|
||||
// Why fragments: the kernel must state both halves of projectFleetNextAction's unverifiable
|
||||
// rule — no argv to run, and the pending-input/approval exception that still returns inspect.
|
||||
expect(kernel).toContain('A `none` `nextAction` has no argv to run')
|
||||
expect(kernel).toContain('read `liveness.reason` and keep waiting with `check --wait`')
|
||||
expect(kernel).toContain('An `unverifiable` row reports it unless input or approval waits')
|
||||
expect(kernel).toContain('choose `worker-stop` or `worker-abandon`')
|
||||
})
|
||||
|
||||
|
||||
@@ -138,7 +138,7 @@ After three consecutive empty waits, stop waiting blindly and enumerate with
|
||||
Run; `--run <run_id>` overrides; the receipt's `scope` names which), acting on
|
||||
each row's `projection.attention` categories, `projection.attention.requiresAction`, and literal `projection.nextAction` argv.
|
||||
A `none` `nextAction` has no argv to run: read `liveness.reason` and keep waiting
|
||||
with `check --wait`. Every `unverifiable` row reports it, `requiresAction` or not.
|
||||
with `check --wait`. An `unverifiable` row reports it unless input or approval waits.
|
||||
Leave the wait only on positive proof the agent stopped: `exited` liveness, the
|
||||
worker's own observation of process exit, or a transcript whose final agent turn
|
||||
sent no `worker_done`. Then load `references/recovery-and-cleanup.md` and choose
|
||||
|
||||
File diff suppressed because one or more lines are too long
@@ -545,6 +545,24 @@ describe('fleet liveness and attention after a host verdict', () => {
|
||||
expect(projected.workers[0]!.nextAction.kind).toBe('inspect')
|
||||
})
|
||||
|
||||
// The exception the kernel's `none` rule names: pending work is something a command can move,
|
||||
// so these rows keep `inspect` instead of reading as another wait-only unverifiable row.
|
||||
it.each([{ pendingInput: true }, { pendingApproval: true }])(
|
||||
'keeps an unverifiable worker with %o inspectable',
|
||||
(pending) => {
|
||||
const projected = projectOrchestrationFleet({
|
||||
workers: [worker('1', pending)],
|
||||
statuses: [],
|
||||
now: 10_000
|
||||
})
|
||||
expect(projected.workers[0]!.liveness.verdict).toBe('unverifiable')
|
||||
expect(projected.workers[0]!.nextAction).toEqual({
|
||||
kind: 'inspect',
|
||||
argv: ['orchestration', 'worker-show', '--dispatch', '1']
|
||||
})
|
||||
}
|
||||
)
|
||||
|
||||
// The live worker-list row from a stopped worker: the same receipt proved the exit,
|
||||
// called it absence, and pointed back at the command that reported the settlement.
|
||||
it('never contradicts a proven exit on a stopped worker still owning its terminal', () => {
|
||||
|
||||
Reference in New Issue
Block a user