{
  "id": "ralph-loop-guarded",
  "type": "loadout",
  "title": "Guarded Ralph loop",
  "summary": "Run an agent in a Ralph-style loop with guard rails: a fresh process per pass, state in files, iteration and no-progress limits, and a check it cannot fake.",
  "description": "The Ralph loop (one prompt, re-run in a fresh agent process until the work is done) went mainstream this autumn: Claude Code and Codex both shipped /goal, and practitioners noticed that plugin versions often keep one long context instead of clearing it. This loadout keeps the original idea and adds the limits people learnt the hard way: a branch-only runner, a check command run outside the agent every pass, a false DONE removed, an edited prompt ending the loop, iteration, timeout and no-progress caps, and a STOP file. A self-test drives the runner with fake agents through every exit path.\n",
  "highlights": [
    "Fresh agent process per pass; plan, progress and prompt live in .ralph/",
    "DONE only counts when the check passes outside the agent",
    "Iteration, per-pass timeout and no-progress limits, plus a STOP file",
    "Refuses to run on main or master; never pushes or merges",
    "Works with claude -p, codex exec and agy -p; /goal compared honestly"
  ],
  "version": "1.0.0",
  "license": "MIT",
  "author": {
    "name": "Agent Loadout",
    "url": "https://loadout.jnw-it.com"
  },
  "credits": [
    {
      "title": "Geoffrey Huntley: Ralph Wiggum as a software engineer",
      "url": "https://ghuntley.com/ralph/"
    },
    {
      "title": "@DRMacIver: the Claude Ralph plugin didn't clear context between iterations",
      "url": "https://x.com/DRMacIver/status/2102456718915469473"
    },
    {
      "title": "Claude Code docs: keep Claude working toward a goal (/goal)",
      "url": "https://code.claude.com/docs/en/goal"
    },
    {
      "title": "OpenAI cookbook: using Goals in Codex",
      "url": "https://developers.openai.com/cookbook/examples/codex/using_goals_in_codex"
    }
  ],
  "categories": [
    "workflow",
    "ai-agents"
  ],
  "stacks": [
    "any",
    "bash",
    "git"
  ],
  "files": [
    {
      "path": "AGENTS.md",
      "role": "instructions",
      "description": "Per-pass rules for an agent running in a loop.",
      "skill": null,
      "agent": null,
      "install_to": {
        "claude-code": "AGENTS.md",
        "codex": "AGENTS.md",
        "cursor": "AGENTS.md",
        "gemini-cli": "AGENTS.md",
        "antigravity-cli": "AGENTS.md",
        "copilot": "AGENTS.md"
      },
      "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/AGENTS.md",
      "raw_latest_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/latest/AGENTS.md",
      "bytes": 1468,
      "lang": "markdown",
      "content": "# AGENTS.md: guarded agent loop (Ralph style)\n\nThis repository may be worked on by an agent running in a loop: the same prompt, a fresh context each pass,\nprogress kept in files. These rules apply on every pass.\n\n## Each pass\n- Read `.ralph/prompt.md`, then `.ralph/plan.md` and the last 20 lines of `.ralph/progress.md`. Nothing else carries over.\n- Pick ONE unchecked item from the plan. Do only that item.\n- Run the check command from the prompt before you finish. Do not tick an item while checks fail.\n- Tick the item in `.ralph/plan.md` and append one line to `.ralph/progress.md`: date, item, result, next step.\n- Commit with a message naming the item. One item, one commit.\n- When every item is ticked and checks pass, create `.ralph/DONE` containing one line of evidence (the check output summary).\n\n## Never\n- Never edit `.ralph/prompt.md`, the check command, CI config or tests you were not asked to change, to make a pass look green.\n- Never delete or skip a failing test. Fix it, or write the blocker into `.ralph/progress.md` and stop.\n- Never push, deploy, merge or touch the default branch. The loop runs on its own branch; a human lands it.\n- Never install new dependencies unless the plan item says so.\n- If the same item fails twice in a row, write `BLOCKED: <reason>` in `.ralph/progress.md` and stop without creating `.ralph/DONE`.\n\n## Starting a loop\nUse the `ralph-loop` skill. It sets up `.ralph/`, a branch and the guarded runner with limits.\n"
    },
    {
      "path": "CLAUDE.md",
      "role": "adapter",
      "description": "Imports AGENTS.md for Claude Code.",
      "skill": null,
      "agent": "claude-code",
      "install_to": {
        "claude-code": "CLAUDE.md",
        "codex": null,
        "cursor": null,
        "gemini-cli": null,
        "antigravity-cli": null,
        "copilot": null
      },
      "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/CLAUDE.md",
      "raw_latest_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/latest/CLAUDE.md",
      "bytes": 367,
      "lang": "markdown",
      "content": "# CLAUDE.md\n\n@AGENTS.md\n\n## Claude Code notes\n- Skills from this loadout live in `.claude/skills/`: `ralph-loop`. Use them when their description matches the task.\n- Follow AGENTS.md above; where this file and AGENTS.md disagree, AGENTS.md wins.\n\n<!-- From the Agent Loadout \"Guarded Ralph loop\" v1.0.0 — https://loadout.jnw-it.com/loadouts/ralph-loop-guarded/ -->\n"
    },
    {
      "path": "GEMINI.md",
      "role": "adapter",
      "description": "Imports AGENTS.md for Gemini CLI.",
      "skill": null,
      "agent": "gemini-cli",
      "install_to": {
        "claude-code": null,
        "codex": null,
        "cursor": null,
        "gemini-cli": "GEMINI.md",
        "antigravity-cli": null,
        "copilot": null
      },
      "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/GEMINI.md",
      "raw_latest_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/latest/GEMINI.md",
      "bytes": 368,
      "lang": "markdown",
      "content": "# GEMINI.md\n\n@./AGENTS.md\n\n## Gemini CLI notes\n- Skills from this loadout live in `.agents/skills/`: `ralph-loop`. Use them when their description matches the task.\n- Follow AGENTS.md above; where this file and AGENTS.md disagree, AGENTS.md wins.\n\n<!-- From the Agent Loadout \"Guarded Ralph loop\" v1.0.0 — https://loadout.jnw-it.com/loadouts/ralph-loop-guarded/ -->\n"
    },
    {
      "path": "skills/ralph-loop/SKILL.md",
      "role": "skill",
      "description": "Set up, run and review a guarded loop.",
      "skill": "ralph-loop",
      "agent": null,
      "install_to": {
        "claude-code": ".claude/skills/ralph-loop/SKILL.md",
        "codex": ".agents/skills/ralph-loop/SKILL.md",
        "cursor": ".agents/skills/ralph-loop/SKILL.md",
        "gemini-cli": ".agents/skills/ralph-loop/SKILL.md",
        "antigravity-cli": ".agents/skills/ralph-loop/SKILL.md",
        "copilot": ".agents/skills/ralph-loop/SKILL.md"
      },
      "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/skills/ralph-loop/SKILL.md",
      "raw_latest_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/latest/skills/ralph-loop/SKILL.md",
      "bytes": 3145,
      "lang": "markdown",
      "content": "---\nname: ralph-loop\ndescription: Set up and run a guarded Ralph-style loop (fresh agent process per pass, state in files, iteration and no-progress limits, independent check). Use when a task is a long list of similar, checkable steps.\n---\n\n# Guarded Ralph loop\n\nA Ralph loop re-runs one prompt in a fresh agent process until the work is done. Fresh context each pass is the point:\nstate lives in files, not in the conversation. The guard rails stop the classic failures: endless loops, a pass that\n\"fixes\" the tests, and quiet drift.\n\n## When to use it\n- Good fit: migrations, porting, test backfill, lint clean-up, one checklist item per pass, each provable by a command.\n- Bad fit: design work, anything without a check command, anything touching production.\n\n## Set up\n1. Create a branch: `git switch -c ralph/<task>`. The runner refuses to start on main, master or a detached HEAD.\n2. `mkdir -p .ralph` and copy `references/PROMPT.md` to `.ralph/prompt.md`. Fill in the goal, constraints and check command.\n3. Write `.ralph/plan.md` as a checklist, one small item per line (`- [ ] ...`). Ask the human to approve it.\n4. Copy `scripts/ralph.sh` into the repository (for example `scripts/ralph.sh`) and make it executable.\n5. Add `.ralph/log/` to `.gitignore`. Keep `prompt.md`, `plan.md` and `progress.md` committed.\n\n## Run\nSet the agent command and the check, then start. The prompt file path is in `$RALPH_PROMPT`.\n\n    AGENT_CMD='claude -p --permission-mode acceptEdits --max-budget-usd 3 < \"$RALPH_PROMPT\"' \\\n    CHECK_CMD='npm test' MAX_ITER=15 scripts/ralph.sh\n\nOther agents (one process per pass in each case):\n- Codex: `AGENT_CMD='codex exec --sandbox workspace-write - < \"$RALPH_PROMPT\"'`\n- Antigravity CLI: `AGENT_CMD='agy -p \"$(cat \"$RALPH_PROMPT\")\" --cwd .'`\n\nLimits (environment variables): `MAX_ITER` (default 10), `MAX_NO_PROGRESS` passes without a new commit or diff\n(default 2), `PASS_TIMEOUT` seconds per pass (default 1800). Create `.ralph/STOP` to stop after the current pass.\n\nExit codes: 0 done and checks green, 2 iteration limit, 3 no progress, 4 stopped by `.ralph/STOP`, 5 refused to start.\n\n## Guard rails the runner enforces\n- `.ralph/DONE` only counts if `CHECK_CMD` passes after the pass. A false DONE is removed and logged.\n- The check runs outside the agent, every pass. The agent cannot mark its own homework.\n- `.ralph/prompt.md` is hashed at start; a pass that edits it ends the loop (exit 5).\n- Each pass's output goes to `.ralph/log/pass-N.txt` for review.\n\n## In-session alternatives\nClaude Code `/goal` and Codex `/goal` keep one session working towards a condition, judged by a separate evaluator\n(Claude) or the goal tracker (Codex). They are convenient, but the context is not cleared between turns. Use this runner\nwhen you want a clean context per pass and limits enforced outside the agent; use `/goal` for shorter jobs.\n\n## After the loop\nReview `git log --oneline` and `.ralph/progress.md`, run the full test suite yourself, and open a pull request. Never let\nthe loop merge its own work.\n\nSelf-test: `bash scripts/selftest.sh` runs the runner against fake agents and checks every exit path.\n"
    },
    {
      "path": "skills/ralph-loop/references/PROMPT.md",
      "role": "reference",
      "description": "Loop prompt template for .ralph/prompt.md.",
      "skill": "ralph-loop",
      "agent": null,
      "install_to": {
        "claude-code": ".claude/skills/ralph-loop/references/PROMPT.md",
        "codex": ".agents/skills/ralph-loop/references/PROMPT.md",
        "cursor": ".agents/skills/ralph-loop/references/PROMPT.md",
        "gemini-cli": ".agents/skills/ralph-loop/references/PROMPT.md",
        "antigravity-cli": ".agents/skills/ralph-loop/references/PROMPT.md",
        "copilot": ".agents/skills/ralph-loop/references/PROMPT.md"
      },
      "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/skills/ralph-loop/references/PROMPT.md",
      "raw_latest_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/latest/skills/ralph-loop/references/PROMPT.md",
      "bytes": 790,
      "lang": "markdown",
      "content": "# Loop prompt (copy to .ralph/prompt.md)\n\nGoal: <one sentence: the end state>\n\nRead first: AGENTS.md, .ralph/plan.md, the last 20 lines of .ralph/progress.md.\n\nEach pass:\n1. Pick the first unchecked item in .ralph/plan.md. Do only that item.\n2. Run the check: <command, for example npm test>. It must pass before you tick the item.\n3. Tick the item, append one line to .ralph/progress.md (date, item, result, next step) and commit.\n4. If every item is ticked and the check passes, write the check summary to .ralph/DONE.\n\nConstraints:\n- Do not edit .ralph/prompt.md, tests you were not asked to change, CI config or lockfiles.\n- No new dependencies unless the item says so. No pushes, deploys or merges.\n- If the item fails twice, append \"BLOCKED: <reason>\" to .ralph/progress.md and stop.\n"
    },
    {
      "path": "skills/ralph-loop/scripts/ralph.sh",
      "role": "reference",
      "description": "The guarded runner with limits and exit codes.",
      "skill": "ralph-loop",
      "agent": null,
      "install_to": {
        "claude-code": ".claude/skills/ralph-loop/scripts/ralph.sh",
        "codex": ".agents/skills/ralph-loop/scripts/ralph.sh",
        "cursor": ".agents/skills/ralph-loop/scripts/ralph.sh",
        "gemini-cli": ".agents/skills/ralph-loop/scripts/ralph.sh",
        "antigravity-cli": ".agents/skills/ralph-loop/scripts/ralph.sh",
        "copilot": ".agents/skills/ralph-loop/scripts/ralph.sh"
      },
      "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/skills/ralph-loop/scripts/ralph.sh",
      "raw_latest_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/latest/skills/ralph-loop/scripts/ralph.sh",
      "bytes": 2576,
      "lang": "markdown",
      "content": "#!/usr/bin/env bash\n# Guarded Ralph loop: one fresh agent process per pass, state in .ralph/, hard limits, check run outside the agent.\n# Exit codes: 0 done, 2 iteration limit, 3 no progress, 4 stopped by .ralph/STOP, 5 refused to start or prompt edited.\nset -uo pipefail\n\n: \"${AGENT_CMD:?set AGENT_CMD, for example: claude -p --permission-mode acceptEdits < \\\"\\$RALPH_PROMPT\\\"}\"\n: \"${CHECK_CMD:?set CHECK_CMD, for example: npm test}\"\nMAX_ITER=\"${MAX_ITER:-10}\"\nMAX_NO_PROGRESS=\"${MAX_NO_PROGRESS:-2}\"\nPASS_TIMEOUT=\"${PASS_TIMEOUT:-1800}\"\nDIR=\".ralph\"\nexport RALPH_PROMPT=\"$DIR/prompt.md\"\n\nsay() { printf 'ralph: %s\\n' \"$*\"; }\nlog() { printf '%s %s\\n' \"$(date -u +%Y-%m-%dT%H:%M:%SZ)\" \"$*\" >> \"$DIR/progress.md\"; }\nstate() { printf '%s %s' \"$(git rev-parse HEAD 2>/dev/null)\" \"$(git status --porcelain=v1 -- . \":(exclude)$DIR/log\" | sha256sum | cut -c1-16)\"; }\n\ngit rev-parse --is-inside-work-tree >/dev/null 2>&1 || { say \"not a git repository\"; exit 5; }\nbranch=\"$(git symbolic-ref --quiet --short HEAD || true)\"\ncase \"$branch\" in\n  \"\"|main|master) say \"refusing to run on '${branch:-detached HEAD}'; create a ralph/<task> branch first\"; exit 5 ;;\nesac\n[ -f \"$RALPH_PROMPT\" ] || { say \"missing $RALPH_PROMPT\"; exit 5; }\nmkdir -p \"$DIR/log\"\nprompt_hash=\"$(sha256sum \"$RALPH_PROMPT\" | cut -c1-64)\"\nno_progress=0\n\nfor ((i = 1; i <= MAX_ITER; i++)); do\n  if [ -f \"$DIR/STOP\" ]; then say \"stop file found before pass $i\"; log \"stopped by .ralph/STOP\"; exit 4; fi\n  before=\"$(state)\"\n  say \"pass $i/$MAX_ITER\"\n  timeout \"$PASS_TIMEOUT\" bash -c \"$AGENT_CMD\" > \"$DIR/log/pass-$i.txt\" 2>&1\n  rc=$?\n  [ \"$rc\" -eq 124 ] && log \"pass $i timed out after ${PASS_TIMEOUT}s\"\n\n  if [ \"$(sha256sum \"$RALPH_PROMPT\" | cut -c1-64)\" != \"$prompt_hash\" ]; then\n    say \"pass $i edited $RALPH_PROMPT; stopping\"; log \"pass $i edited the prompt; loop stopped\"; exit 5\n  fi\n\n  if [ -f \"$DIR/DONE\" ]; then\n    if bash -c \"$CHECK_CMD\" > \"$DIR/log/check-$i.txt\" 2>&1; then\n      say \"done after $i pass(es); check passed\"; log \"done after $i passes; check passed\"; exit 0\n    fi\n    say \"pass $i wrote DONE but the check fails; removing DONE\"; rm -f \"$DIR/DONE\"; log \"pass $i: false DONE removed (check failed)\"\n  fi\n\n  if [ \"$(state)\" = \"$before\" ]; then\n    no_progress=$((no_progress + 1))\n    say \"no change in pass $i ($no_progress/$MAX_NO_PROGRESS)\"\n    if [ \"$no_progress\" -ge \"$MAX_NO_PROGRESS\" ]; then log \"no progress for $no_progress passes; loop stopped\"; exit 3; fi\n  else\n    no_progress=0\n  fi\ndone\nsay \"iteration limit ($MAX_ITER) reached\"; log \"iteration limit $MAX_ITER reached\"; exit 2\n"
    },
    {
      "path": "skills/ralph-loop/scripts/selftest.sh",
      "role": "reference",
      "description": "Drives the runner with fake agents through every exit path.",
      "skill": "ralph-loop",
      "agent": null,
      "install_to": {
        "claude-code": ".claude/skills/ralph-loop/scripts/selftest.sh",
        "codex": ".agents/skills/ralph-loop/scripts/selftest.sh",
        "cursor": ".agents/skills/ralph-loop/scripts/selftest.sh",
        "gemini-cli": ".agents/skills/ralph-loop/scripts/selftest.sh",
        "antigravity-cli": ".agents/skills/ralph-loop/scripts/selftest.sh",
        "copilot": ".agents/skills/ralph-loop/scripts/selftest.sh"
      },
      "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/skills/ralph-loop/scripts/selftest.sh",
      "raw_latest_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/latest/skills/ralph-loop/scripts/selftest.sh",
      "bytes": 2190,
      "lang": "markdown",
      "content": "#!/usr/bin/env bash\n# Runs ralph.sh against fake agents in throwaway repositories and checks every exit path.\nset -u\nhere=\"$(cd \"$(dirname \"$0\")\" && pwd)\"\nrunner=\"$here/ralph.sh\"\npass=0; failed=0\n\nrepo() {\n  local d; d=\"$(mktemp -d)\"\n  ( cd \"$d\" && git init -q -b main && git config user.email t@example.com && git config user.name t \\\n    && mkdir .ralph && echo \"goal\" > .ralph/prompt.md && echo \"- [ ] a\" > .ralph/plan.md && : > .ralph/progress.md \\\n    && git add -A && git commit -qm init && git switch -qc ralph/test )\n  echo \"$d\"\n}\nexpect() { # name, want-exit, dir, env...\n  local name=\"$1\" want=\"$2\" d=\"$3\"; shift 3\n  ( cd \"$d\" && env MAX_ITER=4 PASS_TIMEOUT=20 \"$@\" bash \"$runner\" > out.txt 2>&1 ); local got=$?\n  if [ \"$got\" -eq \"$want\" ]; then pass=$((pass + 1)); else failed=$((failed + 1)); echo \"FAIL: $name (exit $got, wanted $want)\"; cat \"$d/out.txt\"; fi\n}\n\nd=\"$(repo)\"; ( cd \"$d\" && git switch -q main )\nexpect \"refuses main\" 5 \"$d\" AGENT_CMD=true CHECK_CMD=true\n\nd=\"$(repo)\"\nexpect \"idle agent stops on no progress\" 3 \"$d\" AGENT_CMD=true CHECK_CMD=true\n\nd=\"$(repo)\"\nexpect \"busy agent hits the iteration limit\" 2 \"$d\" 'AGENT_CMD=date +%s%N >> work.txt && git add work.txt && git commit -qm pass' CHECK_CMD=true\n\nd=\"$(repo)\"\nexpect \"DONE with a green check exits 0\" 0 \"$d\" 'AGENT_CMD=echo ok > .ralph/DONE' CHECK_CMD=true\n\nd=\"$(repo)\"\nexpect \"false DONE is removed and the loop goes on\" 3 \"$d\" 'AGENT_CMD=echo ok > .ralph/DONE' CHECK_CMD=false\ngrep -q \"false DONE removed\" \"$d/.ralph/progress.md\" && pass=$((pass + 1)) || { failed=$((failed + 1)); echo \"FAIL: false DONE not logged\"; }\n\nd=\"$(repo)\"\nexpect \"editing the prompt stops the loop\" 5 \"$d\" 'AGENT_CMD=echo cheat >> .ralph/prompt.md' CHECK_CMD=true\n\nd=\"$(repo)\"; touch \"$d/.ralph/STOP\"\nexpect \"STOP file stops the loop\" 4 \"$d\" AGENT_CMD=true CHECK_CMD=true\n\nd=\"$(repo)\"\nexpect \"a pass that hangs is timed out\" 3 \"$d\" 'AGENT_CMD=sleep 30' CHECK_CMD=true PASS_TIMEOUT=1\ngrep -q \"timed out\" \"$d/.ralph/progress.md\" && pass=$((pass + 1)) || { failed=$((failed + 1)); echo \"FAIL: timeout not logged\"; }\n\nif [ \"$failed\" -eq 0 ]; then echo \"ok: $pass cases\"; else echo \"failed: $failed of $((pass + failed))\"; exit 1; fi\n"
    }
  ],
  "requires": {
    "tools": [
      "bash",
      "git"
    ],
    "env": [],
    "mcp": []
  },
  "tested": {
    "status": "untested",
    "last_run": null,
    "fixture": null,
    "per_agent": {
      "claude-code": "untested",
      "codex": "untested",
      "cursor": "untested",
      "gemini-cli": "untested",
      "antigravity-cli": "untested",
      "copilot": "untested"
    }
  },
  "security": {
    "scanned": true,
    "scanner": "intake-precheck/1",
    "verdict": "clean",
    "network": true,
    "scripts": [
      "ralph.sh",
      "selftest.sh"
    ],
    "notes": "ralph.sh runs the agent command you give it, unattended, so that agent calls its model provider's API. The runner itself makes no network calls, refuses to run on main or master and never pushes."
  },
  "featured": false,
  "deprecated": false,
  "last_checked": "2026-10-17",
  "published": "2026-10-17",
  "updated": "2026-10-17",
  "compatibility": {
    "claude-code": "native",
    "codex": "native",
    "cursor": "native",
    "gemini-cli": "native",
    "antigravity-cli": "native",
    "copilot": "native"
  },
  "counts": {
    "rules": 1,
    "skills": 1,
    "mcp": 0
  },
  "url": "https://loadout.jnw-it.com/loadouts/ralph-loop-guarded/",
  "api_url": "https://loadout.jnw-it.com/api/loadouts/ralph-loop-guarded.json",
  "verification": {
    "level": "verified-install",
    "status": "verified",
    "label": "Verified install",
    "verified": true,
    "checked_at": "2026-10-17T08:09:30Z",
    "commit": "03c1b9839c40eb1e44c0a2877baaa3978a96895c",
    "content_current": true,
    "agent_tests": "not-run",
    "counts": {
      "pass": 9,
      "fail": 0,
      "skip": 0,
      "not_applicable": 1
    },
    "meaning": "Level 1: automated checks on the files (parse, install paths, MCP config, safety scan, references, size, licence, starter build). No AI agent was run.",
    "checks": [
      {
        "id": "listing",
        "name": "Listing",
        "status": "pass",
        "summary": "Schema valid; 7 files declared, none missing or extra",
        "details": [
          "tested.status: untested (agent tests are separate from Level 1)"
        ]
      },
      {
        "id": "parse",
        "name": "Files parse",
        "status": "pass",
        "summary": "All 7 files parse; front matter valid",
        "details": []
      },
      {
        "id": "adapters",
        "name": "Adapters",
        "status": "pass",
        "summary": "CLAUDE.md and GEMINI.md import AGENTS.md and are up to date",
        "details": [
          "CLAUDE.md: matches the generator",
          "GEMINI.md: matches the generator"
        ]
      },
      {
        "id": "install-paths",
        "name": "Install paths",
        "status": "pass",
        "summary": "Correct paths for all 6 agents; layouts re-discovered",
        "details": [
          "Claude Code: 6 files, 1 skill in .claude/skills/",
          "Codex CLI: 5 files, 1 skill in .agents/skills/",
          "Cursor: 5 files, 1 skill in .agents/skills/",
          "Gemini CLI: 6 files, 1 skill in .agents/skills/",
          "Antigravity CLI: 5 files, 1 skill in .agents/skills/",
          "GitHub Copilot: 5 files, 1 skill in .agents/skills/"
        ]
      },
      {
        "id": "mcp",
        "name": "MCP config",
        "status": "n/a",
        "summary": "No MCP servers in this loadout",
        "details": []
      },
      {
        "id": "safety",
        "name": "Safety scan",
        "status": "pass",
        "summary": "Clean: no credentials, risky shell or hidden text",
        "details": [
          "Scanner intake-precheck/1: verdict clean; network no (listing says yes)"
        ]
      },
      {
        "id": "references",
        "name": "References",
        "status": "pass",
        "summary": "2 references between files resolve for every agent",
        "details": []
      },
      {
        "id": "size",
        "name": "Size limits",
        "status": "pass",
        "summary": "7 files, 10.6 KB total; largest skills/ralph-loop/SKILL.md 3.1 KB",
        "details": [
          "Limits: 30 files, 32 KB per file, 128 KB total, 500 lines per skill or rule"
        ]
      },
      {
        "id": "licence",
        "name": "Licence",
        "status": "pass",
        "summary": "MIT, by Agent Loadout; text in the repository LICENSE",
        "details": []
      },
      {
        "id": "starter-build",
        "name": "Starter build",
        "status": "pass",
        "summary": "The installed runner passes its self-test against fake agents in both skill layouts: every exit path, the false-DONE check, prompt tampering, the STOP file and the per-pass timeout",
        "details": [
          "Applied 11 loadout files at every agent's paths",
          "✓ bash -n on the scripts: bash -c for f in .claude/skills/ralph-loop/scripts/*.sh; do bash -n \"$f\" || exit 1; done; echo syntax ok",
          "✓ self-test (Claude Code layout): bash .claude/skills/ralph-loop/scripts/selftest.sh",
          "✓ self-test (.agents layout): bash .agents/skills/ralph-loop/scripts/selftest.sh",
          "Covers: Refuses to start on main (exit 5)",
          "Covers: An idle agent stops on no progress (exit 3); a busy one stops at the iteration limit (exit 2)",
          "Covers: DONE with a green check exits 0; a false DONE is removed and logged",
          "Covers: A pass that edits the prompt ends the loop; the STOP file ends it; a hung pass is timed out and logged"
        ]
      }
    ]
  },
  "install": {
    "claude-code": {
      "files": [
        {
          "path": "AGENTS.md",
          "target": "AGENTS.md",
          "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/AGENTS.md",
          "role": "instructions"
        },
        {
          "path": "CLAUDE.md",
          "target": "CLAUDE.md",
          "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/CLAUDE.md",
          "role": "adapter"
        },
        {
          "path": "skills/ralph-loop/SKILL.md",
          "target": ".claude/skills/ralph-loop/SKILL.md",
          "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/skills/ralph-loop/SKILL.md",
          "role": "skill"
        },
        {
          "path": "skills/ralph-loop/references/PROMPT.md",
          "target": ".claude/skills/ralph-loop/references/PROMPT.md",
          "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/skills/ralph-loop/references/PROMPT.md",
          "role": "reference"
        },
        {
          "path": "skills/ralph-loop/scripts/ralph.sh",
          "target": ".claude/skills/ralph-loop/scripts/ralph.sh",
          "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/skills/ralph-loop/scripts/ralph.sh",
          "role": "reference"
        },
        {
          "path": "skills/ralph-loop/scripts/selftest.sh",
          "target": ".claude/skills/ralph-loop/scripts/selftest.sh",
          "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/skills/ralph-loop/scripts/selftest.sh",
          "role": "reference"
        }
      ],
      "manual_steps": [],
      "zip_url": "https://loadout.jnw-it.com/download/ralph-loop-guarded/claude-code.zip"
    },
    "codex": {
      "files": [
        {
          "path": "AGENTS.md",
          "target": "AGENTS.md",
          "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/AGENTS.md",
          "role": "instructions"
        },
        {
          "path": "skills/ralph-loop/SKILL.md",
          "target": ".agents/skills/ralph-loop/SKILL.md",
          "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/skills/ralph-loop/SKILL.md",
          "role": "skill"
        },
        {
          "path": "skills/ralph-loop/references/PROMPT.md",
          "target": ".agents/skills/ralph-loop/references/PROMPT.md",
          "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/skills/ralph-loop/references/PROMPT.md",
          "role": "reference"
        },
        {
          "path": "skills/ralph-loop/scripts/ralph.sh",
          "target": ".agents/skills/ralph-loop/scripts/ralph.sh",
          "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/skills/ralph-loop/scripts/ralph.sh",
          "role": "reference"
        },
        {
          "path": "skills/ralph-loop/scripts/selftest.sh",
          "target": ".agents/skills/ralph-loop/scripts/selftest.sh",
          "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/skills/ralph-loop/scripts/selftest.sh",
          "role": "reference"
        }
      ],
      "manual_steps": [],
      "zip_url": "https://loadout.jnw-it.com/download/ralph-loop-guarded/codex.zip"
    },
    "cursor": {
      "files": [
        {
          "path": "AGENTS.md",
          "target": "AGENTS.md",
          "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/AGENTS.md",
          "role": "instructions"
        },
        {
          "path": "skills/ralph-loop/SKILL.md",
          "target": ".agents/skills/ralph-loop/SKILL.md",
          "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/skills/ralph-loop/SKILL.md",
          "role": "skill"
        },
        {
          "path": "skills/ralph-loop/references/PROMPT.md",
          "target": ".agents/skills/ralph-loop/references/PROMPT.md",
          "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/skills/ralph-loop/references/PROMPT.md",
          "role": "reference"
        },
        {
          "path": "skills/ralph-loop/scripts/ralph.sh",
          "target": ".agents/skills/ralph-loop/scripts/ralph.sh",
          "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/skills/ralph-loop/scripts/ralph.sh",
          "role": "reference"
        },
        {
          "path": "skills/ralph-loop/scripts/selftest.sh",
          "target": ".agents/skills/ralph-loop/scripts/selftest.sh",
          "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/skills/ralph-loop/scripts/selftest.sh",
          "role": "reference"
        }
      ],
      "manual_steps": [],
      "zip_url": "https://loadout.jnw-it.com/download/ralph-loop-guarded/cursor.zip"
    },
    "gemini-cli": {
      "files": [
        {
          "path": "AGENTS.md",
          "target": "AGENTS.md",
          "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/AGENTS.md",
          "role": "instructions"
        },
        {
          "path": "GEMINI.md",
          "target": "GEMINI.md",
          "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/GEMINI.md",
          "role": "adapter"
        },
        {
          "path": "skills/ralph-loop/SKILL.md",
          "target": ".agents/skills/ralph-loop/SKILL.md",
          "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/skills/ralph-loop/SKILL.md",
          "role": "skill"
        },
        {
          "path": "skills/ralph-loop/references/PROMPT.md",
          "target": ".agents/skills/ralph-loop/references/PROMPT.md",
          "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/skills/ralph-loop/references/PROMPT.md",
          "role": "reference"
        },
        {
          "path": "skills/ralph-loop/scripts/ralph.sh",
          "target": ".agents/skills/ralph-loop/scripts/ralph.sh",
          "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/skills/ralph-loop/scripts/ralph.sh",
          "role": "reference"
        },
        {
          "path": "skills/ralph-loop/scripts/selftest.sh",
          "target": ".agents/skills/ralph-loop/scripts/selftest.sh",
          "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/skills/ralph-loop/scripts/selftest.sh",
          "role": "reference"
        }
      ],
      "manual_steps": [],
      "zip_url": "https://loadout.jnw-it.com/download/ralph-loop-guarded/gemini-cli.zip"
    },
    "antigravity-cli": {
      "files": [
        {
          "path": "AGENTS.md",
          "target": "AGENTS.md",
          "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/AGENTS.md",
          "role": "instructions"
        },
        {
          "path": "skills/ralph-loop/SKILL.md",
          "target": ".agents/skills/ralph-loop/SKILL.md",
          "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/skills/ralph-loop/SKILL.md",
          "role": "skill"
        },
        {
          "path": "skills/ralph-loop/references/PROMPT.md",
          "target": ".agents/skills/ralph-loop/references/PROMPT.md",
          "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/skills/ralph-loop/references/PROMPT.md",
          "role": "reference"
        },
        {
          "path": "skills/ralph-loop/scripts/ralph.sh",
          "target": ".agents/skills/ralph-loop/scripts/ralph.sh",
          "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/skills/ralph-loop/scripts/ralph.sh",
          "role": "reference"
        },
        {
          "path": "skills/ralph-loop/scripts/selftest.sh",
          "target": ".agents/skills/ralph-loop/scripts/selftest.sh",
          "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/skills/ralph-loop/scripts/selftest.sh",
          "role": "reference"
        }
      ],
      "manual_steps": [],
      "zip_url": "https://loadout.jnw-it.com/download/ralph-loop-guarded/antigravity-cli.zip"
    },
    "copilot": {
      "files": [
        {
          "path": "AGENTS.md",
          "target": "AGENTS.md",
          "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/AGENTS.md",
          "role": "instructions"
        },
        {
          "path": "skills/ralph-loop/SKILL.md",
          "target": ".agents/skills/ralph-loop/SKILL.md",
          "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/skills/ralph-loop/SKILL.md",
          "role": "skill"
        },
        {
          "path": "skills/ralph-loop/references/PROMPT.md",
          "target": ".agents/skills/ralph-loop/references/PROMPT.md",
          "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/skills/ralph-loop/references/PROMPT.md",
          "role": "reference"
        },
        {
          "path": "skills/ralph-loop/scripts/ralph.sh",
          "target": ".agents/skills/ralph-loop/scripts/ralph.sh",
          "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/skills/ralph-loop/scripts/ralph.sh",
          "role": "reference"
        },
        {
          "path": "skills/ralph-loop/scripts/selftest.sh",
          "target": ".agents/skills/ralph-loop/scripts/selftest.sh",
          "raw_url": "https://loadout.jnw-it.com/raw/ralph-loop-guarded/1.0.0/skills/ralph-loop/scripts/selftest.sh",
          "role": "reference"
        }
      ],
      "manual_steps": [],
      "zip_url": "https://loadout.jnw-it.com/download/ralph-loop-guarded/copilot.zip"
    }
  },
  "source_zip_url": "https://loadout.jnw-it.com/download/ralph-loop-guarded/source.zip"
}