PM-driven review-loop orchestrator for AI coding agents
Project description
loop-kit
PM-driven review-loop orchestrator for AI coding agents.
loop-kit runs a multi-round review loop: a Worker writes code, a Reviewer checks it, and the loop repeats until approval or max rounds. It supports OpenAI Codex and Anthropic Claude as worker/reviewer backends, with automatic dispatch and real-time streaming output.
Quick Start
# Install
pip install loop-kit
# or: uv add loop-kit
# Initialize loop directory in your project
loop init
# Write a task card (see .loop/examples/task_card.json)
# Then run the loop with auto-dispatch
loop run --task .loop/task_card.json --auto-dispatch --worker-backend codex --reviewer-backend codex
Prerequisites
- Python >= 3.11
- Git repository (the orchestrator uses git commits as the source of truth)
- At least one AI backend installed: codex or claude
CLI Reference
loop init Create .loop/ directory structure and templates
loop run Run the full PM-controlled review loop
loop status Show current loop state
loop health Show worker/reviewer heartbeat health
loop heartbeat Write role heartbeat continuously
loop archive List or restore archived bus files
loop extract-diff BASE HEAD Print git diff between two commits
loop run flags
| Flag | Default | Description |
|---|---|---|
--task PATH |
.loop/task_card.json |
Path to task card JSON |
--max-rounds N |
3 | Maximum review rounds |
--timeout N |
0 | Per-phase timeout in seconds (0=unlimited) |
--auto-dispatch |
off | Automatically invoke worker/reviewer backends |
--dispatch-backend native |
native | Subprocess transport |
--worker-backend codex|claude |
codex | Backend for worker dispatch |
--reviewer-backend codex|claude |
codex | Backend for reviewer dispatch |
--dispatch-timeout N |
600 | Per-dispatch timeout in seconds |
--dispatch-retries N |
2 | Retries on non-zero dispatch exit |
--dispatch-retry-base-sec N |
5 | Base backoff seconds between dispatch retries (max delay 60s) |
--artifact-timeout N |
90 | Post-dispatch artifact wait in seconds |
--require-heartbeat |
off | Require live heartbeat while waiting |
--heartbeat-ttl N |
30 | Heartbeat freshness threshold in seconds |
--single-round |
off | Run exactly one round and exit |
--round N |
- | Round number for single-round mode |
--resume |
off | Resume from .loop/state.json |
--allow-dirty |
off | Allow starting with dirty tracked files |
--verbose |
off | Stream full backend stdout |
--loop-dir PATH |
.loop | Loop bus directory |
File Bus Protocol
All state passes through JSON files in .loop/:
PM -> Worker: task_card.json / fix_list.json
Worker -> PM: work_report.json
PM -> Reviewer: review_request.json
Reviewer -> PM: review_report.json
Key JSON schemas
task_card.json
{
"task_id": "T-001",
"goal": "One-sentence goal",
"in_scope": ["file or module"],
"out_of_scope": [],
"acceptance_criteria": ["measurable criterion"],
"constraints": []
}
work_report.json
{
"task_id": "T-001",
"round": 1,
"head_sha": "abc123...",
"files_changed": ["src/main.py"],
"notes": "What was done",
"tests": [{"name": "test_foo", "result": "pass"}]
}
review_report.json
{
"task_id": "T-001",
"round": 1,
"decision": "approve|changes_required",
"blocking_issues": [{"severity": "high", "file": "src/main.py", "reason": "..."}],
"non_blocking_suggestions": ["..."]
}
state.json — Internal orchestrator state, the single source of truth between rounds.
Archive
All bus files are archived to .loop/archive/{task_id}/r{N}_{name}.json before being overwritten, preserving full round history.
Architecture
┌──────────┐
│ PM │ orchestrator.py
│(outer) │
└────┬─────┘
┌──────────┼──────────┐
▼ ▼ ▼
┌──────────┐ ┌──────────┐
│ Worker │ │ Reviewer │ (codex/claude subprocess)
│(codex/ │ │(codex/ │
│ claude) │ │ claude) │
└──────────┘ └──────────┘
Each round runs as a fresh subprocess (python -m loop_kit run --single-round), so code changes in the orchestrator itself take effect immediately — the orchestrator can improve itself.
Backend discovery uses shutil.which() plus known install paths. The backend registry (register_backend()) supports adding custom backends.
Prompt Templates
loop init creates templates in .loop/templates/:
- worker_prompt.txt — Worker prompt with
{task_id},{round_num},{agents_md},{role_md},{task_card_section},{prior_context_section},{work_report_path}placeholders - reviewer_prompt.txt — Reviewer prompt with
{task_id},{round_num},{role_md},{review_report_path}placeholders
The worker first reads project AGENTS.md and docs/roles/code-writer.md, and the reviewer first reads project docs/roles/reviewer.md.
If any of those files are missing, loop-kit falls back to built-in defaults in src/loop_kit/defaults/.
Project files always override built-in defaults when present.
Development
# Clone and install editable
git clone <repo-url>
cd loop-kit
uv sync
# Run tests
uv run --group dev pytest
# Run as module
uv run python -m loop_kit init
License
MIT
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file agent_task_runner-0.3.0.tar.gz.
File metadata
- Download URL: agent_task_runner-0.3.0.tar.gz
- Upload date:
- Size: 52.4 kB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via: uv/0.9.20 {"installer":{"name":"uv","version":"0.9.20","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":null,"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":null}
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
0cc5caa98e8bddb6d23915bf09672b3599ef8675152a7259c923811f4e5f122e
|
|
| MD5 |
38e4e7529c4ecd00cca714a4c1a459c6
|
|
| BLAKE2b-256 |
18b9c0e4761c2f41b13272753e34e1a49f7db4589ffd94222322825d6e22e1f6
|
File details
Details for the file agent_task_runner-0.3.0-py3-none-any.whl.
File metadata
- Download URL: agent_task_runner-0.3.0-py3-none-any.whl
- Upload date:
- Size: 33.3 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? No
- Uploaded via: uv/0.9.20 {"installer":{"name":"uv","version":"0.9.20","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":null,"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":null}
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
53dc6672de5838a3c1ae53af2fefe01b74dd457b3bbe07122ef8a294f345fd3a
|
|
| MD5 |
71b8876749c83e27ff19190288c407bb
|
|
| BLAKE2b-256 |
2343bce514a524f3eb43ecdb968cc3ec7e723b5728a68ba2d03a68583bfe089f
|