Metadata-Version: 2.4
Name: rein-agentic-kit
Version: 0.7.2
Summary: Rein — keep your Claude Code agents lean and in control. Token-lean, stack-aware agentic dev flow.
Author: Luis Farfan
License: MIT
Project-URL: Homepage, https://github.com/luisfarfan/rein-agentic-kit
Project-URL: Source, https://github.com/luisfarfan/rein-agentic-kit
Keywords: claude,claude-code,agents,tokens,cost,review,planning
Classifier: Development Status :: 4 - Beta
Classifier: Intended Audience :: Developers
Classifier: License :: OSI Approved :: MIT License
Classifier: Programming Language :: Python :: 3.9
Classifier: Programming Language :: Python :: 3.12
Classifier: Topic :: Software Development :: Quality Assurance
Requires-Python: >=3.9
Description-Content-Type: text/markdown
License-File: LICENSE
Dynamic: license-file

<div align="center">

# 🐎 Rein

**Keep your Claude Code agents lean and in control.**

A Claude Code plugin that turns agent work into a bounded, measured, independently-reviewed flow —
and tells you what it actually cost, per model.

[![License: MIT](https://img.shields.io/badge/License-MIT-blue.svg)](LICENSE)
[![CI](https://github.com/luisfarfan/rein-agentic-kit/actions/workflows/ci.yml/badge.svg)](https://github.com/luisfarfan/rein-agentic-kit/actions/workflows/ci.yml)
[![Dependencies](https://img.shields.io/badge/runtime%20deps-none-success.svg)](#)
[![Python](https://img.shields.io/badge/python-3.9%2B%20stdlib-blue.svg)](#)
[![Claude Code](https://img.shields.io/badge/Claude%20Code-plugin-8A2BE2.svg)](https://claude.com/claude-code)

</div>

---

## 💸 The problem, measured

Optimizing agent cost by "making the model write less" does nothing. Over real Claude Code
transcripts:

| Where the tokens go | Share |
|---|---:|
| 🔴 `cache_read` — context re-read **every turn** | **~90%** |
| 🟠 `cache_write` | ~10% |
| 🟢 **output** — what a compressor would attack | **~0.3%** |
| ⚪ fresh input | ~0% |

**Cost ≈ turns × context size.** One agent that ran 241 turns, re-reading ~234k of context on
every single turn, was most of a 112M-token run.

And Claude Code has **no native eviction of stale tool results** — only `/compact`, which is
lossy and breaks the prompt cache. A long agent's context only grows.

> **Measured effect of this kit: 241 turns → 26 · Opus 100% → 0% · ~7× less context per turn.**

---

## 🔁 The flow

```mermaid
flowchart TD
    A["🧭 /rein:plan<br/><i>Why · Scope · Decisions · Tasks</i>"]
    B{{"rein next<br/><i>deterministic gate</i>"}}
    C["⚙️ Implement<br/><i>bounded loop of FRESH agents</i><br/><i>context resets each step</i>"]
    D{{"Verify<br/><i>ask the plan, not the agent</i>"}}
    E["🔍 /rein:review<br/><i>whole change · 5 axes</i>"]
    F["✅ merge"]
    G["✋ escalate to you"]
    X["🛑 stop"]

    A -->|you confirm| B
    B -->|ready| C
    C --> D
    D -->|contradiction| X
    D -->|consistent| E
    E -->|"APPROVED + gate green"| F
    E -->|"needs your judgement"| G
    E -->|"CHANGES_REQUESTED · max 3"| C

    style A fill:#1e3a5f,stroke:#4a90d9,color:#fff
    style C fill:#1e4620,stroke:#4caf50,color:#fff
    style E fill:#5f1e3a,stroke:#d94a90,color:#fff
    style F fill:#2d4a1e,stroke:#8bc34a,color:#fff
    style X fill:#4a1e1e,stroke:#d94a4a,color:#fff
    style G fill:#4a3a1e,stroke:#d9a94a,color:#fff
```

Three roles, and **no agent approves its own implementation**. Every run works in its own git
worktree; unapproved work is never merged.

---

## 🚀 Quickstart

```bash
claude plugin marketplace add luisfarfan/rein-agentic-kit
```

```bash
claude plugin install rein@rein-agentic-kit --scope user
```

**Restart Claude Code**, then run inside it:

```
/rein:ping     →  is it wired here, and what did it detect?
/rein:setup    →  probe the optional tools · confirm to provision them
```

`ping` reports the detected stack, the resolved commands and where each one
came from. **If it got everything right, you configure nothing.**

> **Everything runs inside Claude Code — there is nothing to add to your `$PATH`.**
> Claude Code puts the plugin's `bin/` on the path of its own sessions, which is
> where the skills, the commands and the agents call `rein`. In a plain terminal
> `rein` will *not* be found, and that is expected: the CLI exists to be called by
> the flow, and the two commands a person runs by hand have slash commands above.
### Want `rein` in your own terminal too?

The plugin's `bin/` is only on the path of Claude Code's own sessions — a plugin
cannot add anything to your shell. For `rein dashboard`, `rein ledger` or
`rein doctor` from a terminal, install the CLI the way every tool this kit
integrates ships (serena and graphify via `uv`, codegraph and openspec via `npm`):

```bash
uv tool install rein-agentic-kit    # or: pipx install rein-agentic-kit
```

Same code, same version, zero dependencies. The two channels cannot drift: a
test fails the build if their version strings ever disagree.

> To update: `claude plugin marketplace update rein-agentic-kit` then
> `claude plugin update rein@rein-agentic-kit` — qualified with the marketplace,
> or it reports `Plugin "rein" not found`.

Then, per change:

```
/rein:plan   →   you confirm the plan   →   /rein:loop   →   read the verdict
```

You come back when it finished, not before.

---

## 🧰 What you get

### Skills — the three roles

| | |
|---|---|
| 🎭 **`/rein:role`** | Assign this session's role: planner · implementer · reviewer |
| 🧭 **`/rein:plan`** | Plan into verifiable tasks — dry-run and **explicit confirmation** before writing |
| 🔨 **`/rein:run`** | Exactly **one** task. Max 3 attempts, max 5 failed commands, no self-approval |
| 🔁 **`/rein:run-auto`** | Bounded loop of `run`, stopping on **verifiable signals** only |
| 🔍 **`/rein:review`** | The independent gate: mechanical checks first, then five-axis judgement |
| ♾️ **`/rein:loop`** | Runs all three end-to-end in an isolated worktree |

### CLI — the deterministic half

```bash
rein doctor      # 🩺 start here: stack, resolved commands, and the source of each
                 # plus a "version : <verdict> -- <reason>" line -- up-to-date / stale /
                 # unknown against the marketplace clone, with fix commands when stale
                 # --json: {"version", "pluginRoot", "project", "plan", "verifyState",
                 # "ledger", "staleness"} -- staleness is {"verdict", "reason",
                 # "installedVersion", "availableVersion"}
rein setup       # probe the optional tools · --install provisions what is missing
rein detect      # stack + commands, with the source of each
rein tasks       # the plan, parsed
rein context     # detect + plan in ONE round-trip — what the loop's first agent runs
rein verify      # actually RUN each resolved command and report the truth — an inference is not a fact
rein plan-check  # mechanical findings on a drafted plan's own text — what a regex can
                 # honestly decide; the semantic call belongs to /rein:plan's critique
rein next        # ✅ the gate: is there a task to claim, and may it be
rein close T001  # tick a checkbox deterministically — no agent hand-edits the plan
rein review      # record / check a verdict bound to a code state
rein token-report# what a run really cost, per agent and per model, plus its wall clock,
                 # agent-minutes and their ratio (1.00x = nothing overlapped)
rein event <name># record a skill invocation — an EVENT, never folded into a run total
rein ledger      # history across projects, with deltas vs a marked baseline
                 # --json: {"runs": [...], "events_by_project": {...}} -- runs are
                 # unchanged row objects; events (D3) are counted separately, never
                 # folded into a run total
rein baseline    # mark the run everything is compared against
rein dashboard   # 📊 serve it all as a local page
```

> **The rule that separates them:** if it's a *parse*, a script does it. If it's a *judgement*,
> an agent does it. Every fact an agent doesn't have to rediscover is turns you don't pay for.

---

## ⚖️ The three levers

**1️⃣ Bounded loop of fresh agents.** Each task is at most *N* short, fresh agents handing off a
**compact ledger** (`progress` / `remaining` / `filesTouched` / `verification`) — never one agent
running 200+ turns. Context **resets at every boundary**, so spend stops growing without a ceiling.

**2️⃣ Per-agent model routing.** Mechanical → Haiku · code → Sonnet · the review gate → Opus. On a
subscription this doesn't lower the bill — it frees the **scarce Opus quota**, which is the limit
you actually hit.

**3️⃣ Verifiable signals, not model judgement.** A loop that stops when the model *feels* finished
has no gate. `rein next` answers "is there work to claim" from the plan; `rein review check`
answers "does this approval still apply" from content hashes. Neither asks a model anything.

### ❌ Deliberately not included

Tried and discarded **with data**, not taste:

- **Output compressors** — they attack the 0.3%.
- **Multi-provider API swarms** — the saving doesn't apply on a subscription, and more agents means
  more contexts re-read.
- **Cross-session memory tools** — orthogonal to the actual cost driver.
- **Cache-aware proxies** — no-op on already-cached traffic.
- **Persona prompts** ("you are a hexagonal architecture expert") — the same model with the same
  weights. Constraints that can be *violated* are useful; job titles are not.

---

## ⚙️ Configure

Everything is optional. Drop a `flow.config.json` at your project root to override:

```json
{
  "commands": {
    "test": "uv run pytest -q",
    "testOne": "uv run pytest -q {target}",
    "lint": "uv run ruff check .",
    "typecheck": "uv run mypy ."
  },
  "models": { "aux": "haiku", "impl": "sonnet", "review": "opus" },
  "limits": { "maxTaskSteps": 8, "maxReviewRounds": 3 }
}
```

**Precedence:** `flow.config.json` › task runner (`justfile` / `Makefile` / `Taskfile`) ›
autodetection. A project that already declares how it is built is never second-guessed.

## 🧱 Supported stacks

| Stack | Detected by | Verification |
|---|---|---|
| 🐍 Python | `pyproject.toml`, uv / poetry | pytest · ruff · mypy |
| 🟨 Node / TS | `package.json`, pnpm / npm / yarn / bun | vitest or jest · eslint · tsc |
| 🦀 Rust | `Cargo.toml` | cargo test · clippy · check |
| 🐹 Go | `go.mod` | go test · vet |
| 🎨 **Frontend** *(Next, Vite, Astro, SvelteKit, Nuxt, Remix)* | dependencies | **rendered verification** — unit tests alone don't catch "the tests pass but the UI is broken" |
| ☁️ Serverless / infra | `serverless.yml`, `sst.config.ts`, `*.tf` | `plan` / `validate` — **never deploy** |
| 📦 Monorepo | sub-projects one or two levels down, no root manifest | reports each sub-project and its own commands — **it never picks one for you**, even when there is only one candidate |

> **A resolved command is an inference until something runs it.** `rein verify` executes each one
> and reports what happened, distinguishing *"the binary is missing"* (a **setup** problem) from
> *"the suite ran and failed"* (a **code** problem) — conflating them sends you to the wrong file.
> The loop runs it at Prepare: a broken gate found there costs nothing, the same one found at
> review costs a whole run.

Optional tools (`serena`, `codegraph`, `graphify`, `openspec`) are **probed, never
required**: if one is absent the flow degrades, it does not break. `rein setup` reports
what is missing and installs it on request — and distinguishes *installed* from *usable*,
because graphify without an index and a just-registered MCP server are both present and
inert.

> **No retrieval speedup is claimed.** With codegraph present, the loop's implementers are
> taught `codegraph query` / `callers` / `callees` / `node` / `impact` (plus `sync` to
> refresh the index after their own edits) as the one owner of "what is this / who touches
> it / what breaks if I change it"; with codegraph absent, serena's `get_symbols_overview` /
> `find_symbol` / `find_referencing_symbols` cover the same ground as a fallback. Whether
> either reduces the turns an agent spends orienting is **unmeasured**, and the one control
> available points the other way. See [docs/decisions.md](docs/decisions.md) D2.

**One owner per question.** A tool is dropped from the prompts for having no *exclusive*
question — not for being bad:

```mermaid
flowchart LR
    Q1["❓ what is this?<br/>who touches it?<br/>what breaks if I change it?"] --> CG["🔎 codegraph<br/><i>query · callers · callees</i><br/><i>node · impact</i>"]
    Q2["❓ edit this symbol<br/>type errors, no build"] --> SE["✏️ serena<br/><i>replace_symbol_body</i><br/><i>get_diagnostics_for_file</i>"]
    Q3["❓ docs · papers · images"] --> GR["📚 graphify<br/><i>/graphify skill</i><br/><i>outside the loop</i>"]

    style CG fill:#1e4620,stroke:#4caf50,color:#fff
    style SE fill:#1e3a5f,stroke:#4a90d9,color:#fff
    style GR fill:#4a3a1e,stroke:#d9a94a,color:#fff
```

Measured on this repo, same question, same index cost (~1.5s, no LLM, no API key for either):
asked *"where is it decided that a command is not invocable?"*, codegraph returns
`NOT_INVOCABLE_EXIT_CODES = (126,127)` with its file and line in **258 tokens**; the graph
tool it replaced returned **546 tokens of an unrelated example config**, because a JSON key
happened to match. Confident noise is worse for an agent than no answer — it cannot tell the
two apart, and it pays for the difference on every later turn.

## 📊 Measure

```bash
rein token-report && rein dashboard
```

Reads Claude Code's own JSONL transcripts (including `cache_read`) and breaks a run down per
agent and **per model**. Every run is summarized into `~/.claude/rein/runs.jsonl`, so history
survives transcript rotation.

**On the word "savings":** this measures *consumption*. A saving needs a baseline. Mark one with
`rein baseline mark` and every later run in that project gets a signed delta. Without one, the
honest numbers are the three that predict cost — **turns/agent**, **ctx_max/turn**,
**% of tokens on Opus**.

---

## 🙃 Honest limitations

Things a README usually hides:

- **The reviewer is calibrated hard.** Across 9 runs of this repo, 8 used all 3 rounds, and the
  LAST round produced a real BLOCKING finding in 4 of them. Review is ~52% of a run's wall
  clock and it earns it — which is why there is no `--fast` that reviews less.
- **A stalled agent burns wall-clock.** One run spent 3.4 hours almost entirely in silent API
  retries.
- **Runs are serial.** Every run measured so far reports an overlap of `1.00x` — tasks that
  declare no dependency *can* now run concurrently, but the plans written here have been
  chains, so the parallel path has yet to fire on real work.
- **`discover` was considered and rejected** — a per-run version of it was measured in the origin
  project and did not move the needle. See [docs/decisions.md](docs/decisions.md).

## 🗺️ Roadmap

| Phase | Scope | |
|---|---|---|
| 0 | Plugin plumbing · `token-report` · ledger · stack detection | ✅ [findings](docs/phase-0-findings.md) |
| 1 | Config-driven core loop · `tasks.md` adapter — **measured** | ✅ |
| 2 | Stack-aware verification policy | ✅ |
| 3 | Local dashboard · per-agent model config | ✅ |
| 4 | Compose real browser verification | ✅ |
| 5 | Docs · a second distribution channel (PyPI) · release automation | ✅ |
| 6 | A second real-world project, and the parallel path on a plan that has one | ⏳ |

## 📄 License

MIT — see [LICENSE](LICENSE).

<div align="center">
<sub>Built with Claude Code, reviewed by an agent that wrote none of it.</sub>
</div>
