Skip to content

kernel: retain failed deterministic attempt diagnostics in completion records (blocks #276) #292

Description

@miyaontherelay

The CLI-only fix for #276 is blocked because failed deterministic attempt output is discarded before the daemon journals the completion. Preserve diagnostic data in the completion record so the CLI can render the actual exit code and bounded stderr without re-executing the command or changing failure/retry behavior.

At main 3ae6c24ea5c0d98aec4eef8aef9d977fd6b376a4:

  • exec_det.rs captures exit_code, stdout_tail, and stderr_tail in AttemptResult.output.
  • machine.rs replaces that output with Value::Null on both retry and terminal failure, then writes that null into StepCompletedPayload.output.
  • Consequently journal.read cannot give the CLI the stderr. The exit code happens to survive only as free text in verification.detail for the exit-code gate, not as the structured output.exit_code.

The #276 assignment explicitly requires stopping and filing a follow-up if the required information is absent from the completion record. No CLI PR can satisfy its acceptance criteria against these records. #276 should remain open pending this prerequisite.

Evidence from the original shakedown journal (read only; the database has no WAL file). The command and captured output below are from inspection of the existing evidence, not a new shakedown execution:

python3 - <<'PY'
import sqlite3, json
p='/var/folders/_z/f_fpl8j533g_r63706k2xvp00000gn/T/flows-shakedown-runtime-data-ma7lr189/runs/01M25VBQ8W3TCRWTM15KYAM7AA.sqlite3'
db=sqlite3.connect('file:'+p+'?immutable=1',uri=True)
for seq, kind, step, raw in db.execute("SELECT seq, entry_type, step_id, payload FROM entries WHERE entry_type IN ('step.completed','run.completed')"):
    print(json.dumps({'seq':seq,'entry_type':kind,'step_id':step,'payload':json.loads(raw)},indent=2))
PY
{
  "seq": 4,
  "entry_type": "step.completed",
  "step_id": "fail-command",
  "payload": {
    "budget": {
      "dollars": "0",
      "tokens_in": 0,
      "tokens_out": 0
    },
    "completed_by": "kernel",
    "completionReason": "retries_exhausted",
    "disposition": "step_done",
    "effects": [],
    "end_pins": null,
    "next_attempt_at_ms": null,
    "output": null,
    "verification": {
      "detail": "exit code was 7",
      "gate": "exit_code",
      "verdict": "fail"
    }
  }
}
{
  "seq": 5,
  "entry_type": "run.completed",
  "step_id": null,
  "payload": {
    "budget_total": {
      "dollars": "0",
      "tokens_in": 0,
      "tokens_out": 0
    },
    "completionReason": "step_failed",
    "failed_step_id": "fail-command"
  }
}

The original CLI transcript is evidence/shakedown-0910/runtime-error.txt.

Acceptance for this prerequisite:

  • A deterministic step executing printf "shakedown intentional failure" >&2; exit 7 exposes structured exit code 7 and the captured stderr in its journaled completion through journal.read.
  • Preserve the run's step_failed outcome and existing retry, verification, and successful-output semantics. Diagnostic retention must not make failed output available as a successful step result.
  • Cover diagnostic retention on terminal failure and retries, and pin the actual journal record in tests.
  • Once the completion data is available, flows: failed deterministic runs hide the command exit code and stderr #276 can add the CLI's last-20-lines/4-KB text and JSON reporting plus journal pointer.

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