Human interaction and recovery
Questions and confirmations belong to Code Steps. The Runtime records the owning Run, cursor, and action ID and pauses that same execution until a valid answer arrives.
Ask questions
Inside an ExecutableCode:
Answers contain questionId and either { isSkipped: true } or { isSkipped: false, answer: "..." }. Option selection resolves to answer text. Code decides how to store and interpret it; a model cannot submit a human answer as part of its proposal.
Request confirmation
readableProposal should show the business result the user is approving. Revalidate the draft and its upstream basis after the wait. A confirmation is about the displayed proposal, not any newer content another operation may have written while waiting.
Cancelling the client form is different from submitting isConfirmed: false: form cancellation preserves the wait. A negative answer follows your business route.
Make a wait restartable
In-process answers resume the original function. After process exit, that Promise and its local variables no longer exist. Add ExecutableCode.recover(saved, access) to continue the saved interaction without rerunning earlier effects.
For a Stage whose State includes approved: boolean, a confirmation-only Code can use the same continuation in both paths:
A real proposal workflow must also persist the proposal identity, relevant baseline, and enough continuation information in State before waiting. Distinguish multiple possible waits using saved state and the saved action request. Never rely on a lost local variable or recreate the original external effect.
Recovery receives fresh capabilities and the saved action/answer. It is not an instruction to ask the same question again. Code without recover remains executable, but its pending wait becomes RUN_INTERRUPTED after host restart. See Operational recovery.