Skip to content

Loop Engineering Usage

Loop engineering is for recurring, machine-checkable work. It is not the default path for ambiguous product, architecture, auth, payment, or release decisions.

Intake Test

Start a loop only when all four checks pass:

CheckRequired evidence
RepeatsThe task recurs weekly or more often, or is a known batch workflow
Automated verificationAt least one test, build, lint, schema, or security gate can fail the work
BudgetMax iterations, duration, and cost are explicit
Tool accessThe maker has enough bounded tools to act; the checker is read-only by default

If any check fails, use /quick, /verify, /team-execute, or a one-shot script instead.

Minimum Viable Loop

The first production-grade loop should have exactly these parts:

PartTSP surface
One automation/heartbeat or target adapter scheduling
One skillSKILL.md holding the project-specific loop instructions
One state file.tsp/loops/state/<loop-id>.md plus JSON runtime state
One hard gateA command exit, test report, build, lint, or scan result

Do one manual run first, then turn the instructions into a skill, then wrap it in /goal, then schedule it with /heartbeat.

Loop Spec

Use .tsp/loop.yaml for target-neutral loop configuration:

yaml
loop:
  id: ci-triage
  description: Keep CI failures triaged and fix machine-checkable failures.
  cadence: 30m
  skill: loop-ci-triage
  stateFile: .tsp/loops/state/ci-triage.md
  gates:
    - name: library-validation
      command: node scripts/validate-library.js
    - name: tests
      command: npm test
  maker:
    role: backend-engineer
    writeAccess: true
  checker:
    role: qa-engineer
    writeAccess: false
  budget:
    maxIterations: 10
    maxDuration: 2h
    maxDollars: 5

The schema is loop-spec.schema.json. Specs without gates or budgets are invalid.

State Locations

Loop runtime state resolves in this order:

  1. TSP_LOOP_STATE_DIR
  2. project-local .tsp/loops/
  3. target defaults such as ~/.claude/loops/, ~/.codex/loops/, or ~/.config/opencode/loops/

State files:

FilePurpose
goals/{goalId}.json/goal objective, budget, iterations, and oracle verdicts
triage/inbox.jsonlheartbeat and escaped goal findings that need human decision
heartbeat/last-run.jsonlast heartbeat result
state/{loopId}.mdhuman-readable done/next/blockers/stop conditions

Legacy Claude paths remain readable during migration:

  • ~/.claude/goals
  • ~/.claude/triage/inbox.jsonl
  • .claude/heartbeat.yaml

Roles

RoleResponsibility
MakerImplements one bounded iteration; may write only within the loop spec permission envelope
CheckerEvaluates gates and summarizes failures; read-only by default
Human reviewerReads diffs, checks gate quality, accepts or rejects changes

The maker never certifies completion alone. A passing gate plus checker verdict is the minimum closeout signal.

Safety Defaults

  • No auto-merge in the first loop release.
  • No permission broadening by the loop itself.
  • No auto-install of community skills inside scheduled runs.
  • All writes land on a branch or worktree.
  • Budget exhaustion creates triage instead of continuing.
  • Security findings route to a human by default.

Start with CI triage:

  • repeats frequently
  • has objective gates
  • can run with bounded permissions
  • produces reviewable branches or triage items
  • avoids product and architecture judgment

Use .tsp/loop.example.yaml as the starting template.

Released under the MIT License.