There are two supported ways to drive work off the queue: the built-in
afk loop worker-driver, and an external loop you write around afk take /
afk set. Both are valid. afk run is no longer part of the public binary.
afk loop claims ready tasks and runs an agent command per task, with no
external supervisor. Each iteration:
- Claims the first ready task (taking an exclusive lease).
- Renders the configured
prompt_templateagainst the task. - Runs the configured
commandwith that prompt, extending the lease on theheartbeatinterval while it runs. - Finalizes the task
doneorfailedfrom the command exit status. - Pauses for
cooldownwhen no task is found, then repeats.
The agent command and prompt template come from ~/.config/afk/loop.yaml
(written with defaults on first run — see configuration.md). command is empty
by default, so the loop is fail-closed:
afk loop
# Error: no agent command configured (set 'command' in
# ~/.config/afk/loop.yaml or pass --command)Configure command in loop.yaml, or pass it for a single run. Use
--max-tasks N for a bounded run that exits cleanly after N tasks:
afk loop --command 'claude -p {{.Prompt}}' --max-tasks 5Loop results are emitted as JSONL on stdout; agent output goes to stderr. Any
flag overrides the matching loop.yaml value for that run
(--worker, --lease, --timeout, --cooldown, --heartbeat,
--max-failures). The loop halts after --max-failures consecutive task
failures.
Write your own loop when you want process supervision, custom retry policy, or logging the built-in driver does not provide.
Preview readiness without claiming:
afk take --dry-run --limit 5 --json --fullA minimal external loop body:
task_json=$(afk take --lease 30m --worker "$USER:$$" --summary)
test -n "$task_json" || exit 0
id=$(printf '%s\n' "$task_json" | jq -r .task.id)
body=$(printf '%s\n' "$task_json" | jq -r .task.body)
if agent-command "$body"; then
afk set "$id" done --note "agent-command completed" --worker "$USER:$$" --summary
else
afk set "$id" failed --note "agent-command failed" --worker "$USER:$$" --summary
fiThis keeps AFK focused on durable task state, readiness, claims, prompts, and visibility. The caller owns execution policy, retries, logs, and process lifetime.