Wait, Input, and Resume
Suspend a flow for external input and continue the same execution
kitaru.wait(...) is the durable suspension primitive for human-in-the-loop
and external-input workflows.
When your flow reaches wait(...), what happens next depends on the environment:
- Local interactive runs (terminal with stdin/stdout): the runtime prompts for input directly in the same terminal and the flow continues in-process.
- Non-interactive runs (remote orchestrators, CI, piped output, MCP): the
execution moves to
waitingstatus and input must be supplied later via the client, CLI, or MCP.
Basic pattern
from kitaru import flow
import kitaru
@flow
def publish_flow(topic: str) -> str:
approved = kitaru.wait(
schema=bool,
name="approve_publish",
question=f"Approve publishing {topic}?",
metadata={"topic": topic},
)
if not approved:
return f"REJECTED: {topic}"
return f"PUBLISHED: {topic}"Timeout behavior
By default, kitaru.wait(...) gives the runner up to 600 seconds to receive
inline input before pausing the execution:
approved = kitaru.wait(
schema=bool,
name="approve_publish",
question="Approve publishing?",
timeout=300, # runner waits up to 300s for inline resolution
)timeout controls how long the runner keeps polling — it is not an
expiration on the wait record itself. If the timeout elapses without input, the
execution moves to waiting status and can still be resolved externally at any
time.
Resolve input externally (non-interactive runs)
When the flow is running in a non-interactive context (or after the runner has timed out and paused), resolve the pending wait from Python or the CLI.
From Python
client = kitaru.KitaruClient()
execution = client.executions.input(
exec_id,
wait="approve_publish",
value=True,
)If the execution does not continue automatically after input (e.g. the original
runner already exited), call resume(...):
execution = client.executions.resume(exec_id)To abort a wait instead of continuing:
execution = client.executions.abort_wait(exec_id, wait="approve_publish")From CLI
kitaru executions input <exec_id> --value trueThe CLI auto-detects the single pending wait. For interactive review (with JSON schema display, continue/abort choices, and multi-execution sweep):
kitaru executions input <exec_id> --interactive
kitaru executions input --interactive # sweep all waiting executionsTo abort a wait instead of continuing:
kitaru executions input <exec_id> --abortResume is only needed when the execution did not continue automatically:
kitaru executions resume <exec_id>Validation behavior
Input is validated against the wait schema:
- invalid input raises
kitaru.KitaruWaitValidationError - execution stays in
waitinguntil valid input is supplied
Example in this repository
uv sync --extra local
uv run examples/execution_management/wait_and_resume.py- Run the command above — it starts the flow and blocks.
- If you are in an interactive terminal, the runtime prompts for input directly. Type your answer and the flow continues.
- If the run is non-interactive (or you want to resolve from elsewhere), the
script prints fallback
kitaru executions input ...andkitaru executions resume ...commands you can run in a second terminal.
Automated CI coverage for the same flow lives in
tests/test_phase15_wait_example.py.
For the broader catalog, see Examples.