create-agent-rig 0.9.1 → 0.10.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (234) hide show
  1. package/CHANGELOG.md +419 -3
  2. package/README.md +267 -305
  3. package/package.json +8 -14
  4. package/packages/cli/dist/commands/create.js +56 -88
  5. package/packages/cli/dist/commands/doctor.js +213 -0
  6. package/packages/cli/dist/commands/init.js +111 -50
  7. package/packages/cli/dist/commands/integrations.js +468 -0
  8. package/packages/cli/dist/commands/setup-wizard.js +61 -0
  9. package/packages/cli/dist/commands/uninstall.js +1223 -0
  10. package/packages/cli/dist/commands/upgrade.js +472 -90
  11. package/packages/cli/dist/index.js +651 -46
  12. package/packages/cli/dist/integrations/declaration.js +158 -0
  13. package/packages/cli/dist/integrations/doctor-guards.js +126 -0
  14. package/packages/cli/dist/integrations/doctor-workflow.js +25 -0
  15. package/packages/cli/dist/integrations/mcp-json.js +107 -0
  16. package/packages/cli/dist/integrations/memory-doctor.js +124 -0
  17. package/packages/cli/dist/integrations/registry.js +22 -0
  18. package/packages/cli/dist/integrations/spawn.js +228 -0
  19. package/packages/cli/dist/integrations/spec-kit.js +280 -0
  20. package/packages/cli/dist/integrations/verify.js +193 -0
  21. package/packages/cli/dist/integrations/windows-job.js +275 -0
  22. package/packages/cli/dist/lib/elevated-paths.js +74 -0
  23. package/packages/cli/dist/lib/install-set.js +1 -44
  24. package/packages/cli/dist/lib/manifest.js +64 -5
  25. package/packages/cli/dist/lib/prompts.js +0 -23
  26. package/packages/cli/dist/lib/safe-path.js +193 -2
  27. package/packages/cli/dist/lib/safe-text.js +78 -0
  28. package/packages/cli/dist/lib/substitute.js +1 -52
  29. package/packages/cli/dist/lib/summary.js +5 -5
  30. package/packages/cli/dist/templates.js +4 -14
  31. package/scripts/prepare.mjs +28 -12
  32. package/templates/agent-os/subagent-routing.json +4 -4
  33. package/templates/agent-os/universal/.agents/skills/check-premises/SKILL.md +13 -9
  34. package/templates/agent-os/universal/.agents/skills/loop/SKILL.md +31 -6
  35. package/templates/agent-os/universal/.agents/skills/new-invariant/SKILL.md +5 -5
  36. package/templates/agent-os/universal/.agents/skills/pr-ship/SKILL.md +1 -1
  37. package/templates/agent-os/universal/.agents/skills/worktree-task/SKILL.md +3 -3
  38. package/templates/agent-os/universal/.claude/agents/code-reviewer.md +8 -6
  39. package/templates/agent-os/universal/.claude/agents/implementation-agent.md +41 -0
  40. package/templates/agent-os/universal/.claude/agents/prose-reviewer.md +8 -4
  41. package/templates/agent-os/universal/.claude/agents/security-scanner.md +4 -2
  42. package/templates/agent-os/universal/.claude/agents/test-writer.md +2 -2
  43. package/templates/agent-os/universal/.claude/hooks/inject-rules.mjs +83 -4
  44. package/templates/agent-os/universal/.claude/rules/autonomy.md +55 -27
  45. package/templates/agent-os/universal/.claude/rules/invariants.md +9 -8
  46. package/templates/agent-os/universal/.claude/rules/workflow.md +47 -22
  47. package/templates/agent-os/universal/.claude/scripts/decision-router.mjs +1 -1
  48. package/templates/agent-os/universal/.claude/scripts/detect-missed-gate.mjs +12 -9
  49. package/templates/agent-os/universal/.claude/scripts/doctor.mjs +100 -2
  50. package/templates/agent-os/universal/.claude/scripts/lib/claim-records.mjs +236 -6
  51. package/templates/agent-os/universal/.claude/scripts/queue/state.mjs +2 -2
  52. package/templates/agent-os/universal/.claude/scripts/reconcile-external-prs.mjs +4 -3
  53. package/templates/agent-os/universal/.claude/scripts/revalidate.mjs +16 -0
  54. package/templates/agent-os/universal/.claude/settings.json +0 -8
  55. package/templates/agent-os/universal/.claude/skills/check-premises/SKILL.md +13 -9
  56. package/templates/agent-os/universal/.claude/skills/loop/SKILL.md +31 -6
  57. package/templates/agent-os/universal/.claude/skills/new-invariant/SKILL.md +5 -5
  58. package/templates/agent-os/universal/.claude/skills/pr-ship/SKILL.md +1 -1
  59. package/templates/agent-os/universal/.claude/skills/worktree-task/SKILL.md +3 -3
  60. package/templates/agent-os/universal/.codex/agents/code-reviewer.toml +2 -2
  61. package/templates/agent-os/universal/.codex/agents/implementation-agent.toml +6 -0
  62. package/templates/agent-os/universal/.codex/agents/prose-reviewer.toml +2 -2
  63. package/templates/agent-os/universal/.codex/agents/security-scanner.toml +1 -1
  64. package/templates/agent-os/universal/.codex/agents/test-writer.toml +1 -1
  65. package/templates/agent-os/universal/.codex/hooks.json +0 -10
  66. package/templates/agent-os/universal/AGENTS.md +208 -107
  67. package/templates/agent-os/universal/CLAUDE.md +15 -162
  68. package/templates/agent-os/universal/PLAN.md +17 -10
  69. package/templates/agent-os/universal/docs/decisions/agents-md-canonical.md +313 -0
  70. package/templates/agent-os/universal/docs/decisions/codex-adapter.md +15 -10
  71. package/templates/agent-os/universal/docs/decisions/review-lanes.md +12 -8
  72. package/templates/agent-os/universal/docs/decisions/session-start-wire-format.md +206 -0
  73. package/templates/agent-os/universal/docs/decisions/subagent-routing.md +6 -3
  74. package/templates/agent-os/universal/docs/decisions/workflow-layer-split.md +235 -0
  75. package/templates/agent-os/universal/layers.json +25 -30
  76. package/templates/hash-history.json +8 -4
  77. package/templates/release-ledger.json +2 -1
  78. package/packages/cli/dist/lib/composition.js +0 -20
  79. package/packages/cli/dist/lib/targets.js +0 -28
  80. package/packages/cli/dist/policy/benchmark/corpus.js +0 -165
  81. package/packages/cli/dist/policy/core/adapter.js +0 -18
  82. package/packages/cli/dist/policy/core/coverage.js +0 -253
  83. package/packages/cli/dist/policy/core/decision-record.js +0 -287
  84. package/packages/cli/dist/policy/core/declaration.js +0 -127
  85. package/packages/cli/dist/policy/core/evidence-matrix.js +0 -94
  86. package/packages/cli/dist/policy/core/probe.js +0 -442
  87. package/packages/cli/dist/policy/core/registry.js +0 -115
  88. package/packages/cli/dist/policy/core/validation.js +0 -275
  89. package/packages/cli/dist/policy/core/vocabulary.js +0 -123
  90. package/packages/cli/dist/policy/harness/claude.js +0 -47
  91. package/packages/cli/dist/policy/harness/codex.js +0 -87
  92. package/packages/cli/dist/policy/harness/index.js +0 -15
  93. package/packages/cli/dist/policy/harness/shared-hooks.js +0 -28
  94. package/packages/cli/dist/policy/index.js +0 -17
  95. package/templates/agent-os/init/AGENTS.md +0 -201
  96. package/templates/agent-os/init/CLAUDE.md +0 -201
  97. package/templates/agent-os/stack/aws-cdk/.agents/skills/post-deploy-verify/SKILL.md +0 -105
  98. package/templates/agent-os/stack/aws-cdk/.agents/skills/ro-debug/SKILL.md +0 -117
  99. package/templates/agent-os/stack/aws-cdk/.claude/agents/cdk-diff-reviewer.md +0 -89
  100. package/templates/agent-os/stack/aws-cdk/.claude/rules/aws-cdk.md +0 -105
  101. package/templates/agent-os/stack/aws-cdk/.claude/skills/post-deploy-verify/SKILL.md +0 -105
  102. package/templates/agent-os/stack/aws-cdk/.claude/skills/ro-debug/SKILL.md +0 -117
  103. package/templates/agent-os/stack/aws-cdk/.codex/agents/cdk-diff-reviewer.toml +0 -6
  104. package/templates/agent-os/stack/node-ts/.claude/hooks/dod-checks.json +0 -1
  105. package/templates/agent-os/stack/node-ts/.claude/rules/node-ts.md +0 -85
  106. package/templates/agent-os/universal/.claude/hooks/guard-core-purity.mjs +0 -89
  107. package/templates/agent-os/universal/.claude/hooks/guard-web-boundary.mjs +0 -68
  108. package/templates/agent-os/universal/.claude/rules/architecture.md +0 -81
  109. package/templates/skeleton/aws-serverless/.github/workflows/ci.yml +0 -28
  110. package/templates/skeleton/aws-serverless/.github/workflows/deploy.yml +0 -90
  111. package/templates/skeleton/aws-serverless/README.md +0 -181
  112. package/templates/skeleton/aws-serverless/apps/web/next.config.mjs +0 -17
  113. package/templates/skeleton/aws-serverless/apps/web/package.json +0 -19
  114. package/templates/skeleton/aws-serverless/apps/web/src/app/layout.tsx +0 -17
  115. package/templates/skeleton/aws-serverless/apps/web/src/app/page.tsx +0 -96
  116. package/templates/skeleton/aws-serverless/apps/web/src/lib/api.ts +0 -36
  117. package/templates/skeleton/aws-serverless/apps/web/src/lib/validate.ts +0 -23
  118. package/templates/skeleton/aws-serverless/apps/web/test/shared-validation.test.ts +0 -38
  119. package/templates/skeleton/aws-serverless/apps/web/tsconfig.json +0 -14
  120. package/templates/skeleton/aws-serverless/eslint.config.mjs +0 -20
  121. package/templates/skeleton/aws-serverless/gitignore +0 -56
  122. package/templates/skeleton/aws-serverless/infra/bin/app.ts +0 -79
  123. package/templates/skeleton/aws-serverless/infra/cdk.json +0 -3
  124. package/templates/skeleton/aws-serverless/infra/lib/app-stack.ts +0 -248
  125. package/templates/skeleton/aws-serverless/infra/lib/web-stack.ts +0 -45
  126. package/templates/skeleton/aws-serverless/infra/package.json +0 -18
  127. package/templates/skeleton/aws-serverless/infra/test/allowed-origins.test.ts +0 -301
  128. package/templates/skeleton/aws-serverless/infra/test/app-composition.test.ts +0 -137
  129. package/templates/skeleton/aws-serverless/infra/test/app-stack.test.ts +0 -120
  130. package/templates/skeleton/aws-serverless/infra/test/web-stack.test.ts +0 -44
  131. package/templates/skeleton/aws-serverless/package.json +0 -30
  132. package/templates/skeleton/aws-serverless/packages/core/package.json +0 -11
  133. package/templates/skeleton/aws-serverless/packages/core/src/events.ts +0 -14
  134. package/templates/skeleton/aws-serverless/packages/core/src/index.ts +0 -15
  135. package/templates/skeleton/aws-serverless/packages/core/src/note.ts +0 -69
  136. package/templates/skeleton/aws-serverless/packages/core/test/events.test.ts +0 -23
  137. package/templates/skeleton/aws-serverless/packages/core/test/note.test.ts +0 -101
  138. package/templates/skeleton/aws-serverless/packages/db/package.json +0 -14
  139. package/templates/skeleton/aws-serverless/packages/db/src/client.ts +0 -17
  140. package/templates/skeleton/aws-serverless/packages/db/src/index.ts +0 -2
  141. package/templates/skeleton/aws-serverless/packages/db/src/note-model.ts +0 -52
  142. package/templates/skeleton/aws-serverless/packages/db/test/note-model.test.ts +0 -91
  143. package/templates/skeleton/aws-serverless/packages/shared/package.json +0 -11
  144. package/templates/skeleton/aws-serverless/packages/shared/src/env.ts +0 -17
  145. package/templates/skeleton/aws-serverless/packages/shared/src/errors.ts +0 -33
  146. package/templates/skeleton/aws-serverless/packages/shared/src/index.ts +0 -3
  147. package/templates/skeleton/aws-serverless/packages/shared/src/logger.ts +0 -20
  148. package/templates/skeleton/aws-serverless/packages/shared/test/env.test.ts +0 -26
  149. package/templates/skeleton/aws-serverless/packages/shared/test/errors.test.ts +0 -28
  150. package/templates/skeleton/aws-serverless/packages/shared/test/logger.test.ts +0 -19
  151. package/templates/skeleton/aws-serverless/pnpm-lock.yaml +0 -2855
  152. package/templates/skeleton/aws-serverless/pnpm-workspace.yaml +0 -14
  153. package/templates/skeleton/aws-serverless/services/api/package.json +0 -15
  154. package/templates/skeleton/aws-serverless/services/api/src/adapters/sqs-publisher.ts +0 -26
  155. package/templates/skeleton/aws-serverless/services/api/src/handlers/create-note.ts +0 -69
  156. package/templates/skeleton/aws-serverless/services/api/src/handlers/list-notes.ts +0 -37
  157. package/templates/skeleton/aws-serverless/services/api/src/list-main.ts +0 -12
  158. package/templates/skeleton/aws-serverless/services/api/src/main.ts +0 -21
  159. package/templates/skeleton/aws-serverless/services/api/src/usecases/create-note.ts +0 -41
  160. package/templates/skeleton/aws-serverless/services/api/src/usecases/list-notes.ts +0 -14
  161. package/templates/skeleton/aws-serverless/services/api/test/create-note.handler.test.ts +0 -211
  162. package/templates/skeleton/aws-serverless/services/api/test/create-note.usecase.test.ts +0 -45
  163. package/templates/skeleton/aws-serverless/services/api/test/list-notes.test.ts +0 -122
  164. package/templates/skeleton/aws-serverless/services/api/test/sqs-publisher.test.ts +0 -22
  165. package/templates/skeleton/aws-serverless/services/worker/package.json +0 -12
  166. package/templates/skeleton/aws-serverless/services/worker/src/handlers/note-created.ts +0 -15
  167. package/templates/skeleton/aws-serverless/services/worker/src/main.ts +0 -7
  168. package/templates/skeleton/aws-serverless/services/worker/src/usecases/process-note-created.ts +0 -37
  169. package/templates/skeleton/aws-serverless/services/worker/test/note-created.test.ts +0 -61
  170. package/templates/skeleton/aws-serverless/tsconfig.base.json +0 -15
  171. package/templates/skeleton/aws-serverless/tsconfig.json +0 -16
  172. package/templates/skeleton/aws-serverless/vitest.config.ts +0 -14
  173. package/templates/skeleton/node-service/.github/workflows/ci.yml +0 -27
  174. package/templates/skeleton/node-service/.github/workflows/deploy.yml +0 -29
  175. package/templates/skeleton/node-service/README.md +0 -104
  176. package/templates/skeleton/node-service/apps/web/next.config.mjs +0 -17
  177. package/templates/skeleton/node-service/apps/web/package.json +0 -19
  178. package/templates/skeleton/node-service/apps/web/src/app/layout.tsx +0 -17
  179. package/templates/skeleton/node-service/apps/web/src/app/page.tsx +0 -96
  180. package/templates/skeleton/node-service/apps/web/src/lib/api.ts +0 -29
  181. package/templates/skeleton/node-service/apps/web/src/lib/validate.ts +0 -23
  182. package/templates/skeleton/node-service/apps/web/test/shared-validation.test.ts +0 -38
  183. package/templates/skeleton/node-service/apps/web/tsconfig.json +0 -14
  184. package/templates/skeleton/node-service/eslint.config.mjs +0 -20
  185. package/templates/skeleton/node-service/gitignore +0 -54
  186. package/templates/skeleton/node-service/package.json +0 -30
  187. package/templates/skeleton/node-service/packages/core/package.json +0 -11
  188. package/templates/skeleton/node-service/packages/core/src/events.ts +0 -14
  189. package/templates/skeleton/node-service/packages/core/src/index.ts +0 -15
  190. package/templates/skeleton/node-service/packages/core/src/note.ts +0 -69
  191. package/templates/skeleton/node-service/packages/core/test/events.test.ts +0 -23
  192. package/templates/skeleton/node-service/packages/core/test/note.test.ts +0 -101
  193. package/templates/skeleton/node-service/packages/db/package.json +0 -12
  194. package/templates/skeleton/node-service/packages/db/src/index.ts +0 -1
  195. package/templates/skeleton/node-service/packages/db/src/note-store.ts +0 -100
  196. package/templates/skeleton/node-service/packages/db/test/note-store.test.ts +0 -100
  197. package/templates/skeleton/node-service/packages/shared/package.json +0 -11
  198. package/templates/skeleton/node-service/packages/shared/src/env.ts +0 -17
  199. package/templates/skeleton/node-service/packages/shared/src/errors.ts +0 -33
  200. package/templates/skeleton/node-service/packages/shared/src/index.ts +0 -3
  201. package/templates/skeleton/node-service/packages/shared/src/logger.ts +0 -20
  202. package/templates/skeleton/node-service/packages/shared/test/env.test.ts +0 -26
  203. package/templates/skeleton/node-service/packages/shared/test/errors.test.ts +0 -28
  204. package/templates/skeleton/node-service/packages/shared/test/logger.test.ts +0 -19
  205. package/templates/skeleton/node-service/pnpm-lock.yaml +0 -2402
  206. package/templates/skeleton/node-service/pnpm-workspace.yaml +0 -13
  207. package/templates/skeleton/node-service/scripts/build-artifact.mjs +0 -34
  208. package/templates/skeleton/node-service/services/api/package.json +0 -17
  209. package/templates/skeleton/node-service/services/api/src/adapters/spool-publisher.ts +0 -23
  210. package/templates/skeleton/node-service/services/api/src/handlers/create-note.ts +0 -40
  211. package/templates/skeleton/node-service/services/api/src/handlers/list-notes.ts +0 -23
  212. package/templates/skeleton/node-service/services/api/src/main.ts +0 -40
  213. package/templates/skeleton/node-service/services/api/src/server.ts +0 -172
  214. package/templates/skeleton/node-service/services/api/src/static-dir.ts +0 -20
  215. package/templates/skeleton/node-service/services/api/src/usecases/create-note.ts +0 -30
  216. package/templates/skeleton/node-service/services/api/src/usecases/list-notes.ts +0 -14
  217. package/templates/skeleton/node-service/services/api/test/artifact.test.ts +0 -92
  218. package/templates/skeleton/node-service/services/api/test/create-note.handler.test.ts +0 -64
  219. package/templates/skeleton/node-service/services/api/test/create-note.usecase.test.ts +0 -43
  220. package/templates/skeleton/node-service/services/api/test/list-notes.test.ts +0 -48
  221. package/templates/skeleton/node-service/services/api/test/package-manager.test.ts +0 -40
  222. package/templates/skeleton/node-service/services/api/test/package-manager.ts +0 -51
  223. package/templates/skeleton/node-service/services/api/test/server.test.ts +0 -208
  224. package/templates/skeleton/node-service/services/api/test/spool-publisher.test.ts +0 -32
  225. package/templates/skeleton/node-service/services/api/test/static-dir.test.ts +0 -29
  226. package/templates/skeleton/node-service/services/worker/package.json +0 -16
  227. package/templates/skeleton/node-service/services/worker/src/main.ts +0 -28
  228. package/templates/skeleton/node-service/services/worker/src/spool.ts +0 -60
  229. package/templates/skeleton/node-service/services/worker/src/usecases/process-note-created.ts +0 -38
  230. package/templates/skeleton/node-service/services/worker/test/process-note-created.test.ts +0 -34
  231. package/templates/skeleton/node-service/services/worker/test/spool.test.ts +0 -76
  232. package/templates/skeleton/node-service/tsconfig.base.json +0 -15
  233. package/templates/skeleton/node-service/tsconfig.json +0 -13
  234. package/templates/skeleton/node-service/vitest.config.ts +0 -12
package/README.md CHANGED
@@ -1,349 +1,311 @@
1
1
  # create-agent-rig
2
2
 
3
- Scaffold a project that ships with an **agent operating system** — rules,
4
- gates, and hooks that hold the architecture mechanically, not by prose.
5
-
6
- The same Agent OS is native to both **Claude Code and Codex**. Claude-facing
7
- files remain the authoring surface; the generator derives Codex's `AGENTS.md`,
8
- repository skills under `.agents/skills/`, custom agents under `.codex/agents/`,
9
- and `.codex/hooks.json`. `node scripts/sync-codex-adapter.mjs --check` refuses
10
- drift between the two projections.
3
+ **Rig configures a repository for reliable AI-assisted development with Claude
4
+ Code and Codex — and keeps that configuration safe to upgrade and remove.**
5
+
6
+ - **One configuration, both harnesses.** One rulebook, one set of guards and
7
+ review agents, wired natively into Claude Code _and_ Codex.
8
+ - **Upgrades that respect your changes.** Files you edited are reported, not
9
+ overwritten. Files you deleted stay deleted.
10
+ - **Guardrails that run, not just rules that are read.** Hooks refuse a
11
+ pre-commit bypass, a force-push to a shared branch or a credential written
12
+ into a file.
13
+ - **Optional integrations, done by the book.** Figma and Atlassian MCP wiring,
14
+ and GitHub Spec Kit through its own pinned CLI.
15
+ - **A clean exit.** `doctor` shows what is installed and healthy; `uninstall`
16
+ removes only what Rig can prove it wrote.
17
+
18
+ Rig configures agent harnesses. It does not generate application code, run
19
+ agents, or install plugins.
20
+
21
+ ## Quick start
11
22
 
12
23
  ```sh
13
- npx create-agent-rig my-app # choose a target interactively
14
- npx create-agent-rig my-app --target node-service # or name it up front
24
+ # a new repository
25
+ npx create-agent-rig@latest my-project
26
+ cd my-project
27
+
28
+ # …or an existing one
29
+ cd your-repo
30
+ npx create-agent-rig@latest init --dry-run # show what would be written
31
+ npx create-agent-rig@latest init
15
32
  ```
16
33
 
17
- Two coherent targets `aws-serverless` (the default) and `node-service`. On a
18
- terminal the CLI prompts; in CI it wants `--target` explicitly. `--no-git`
19
- skips the initial baseline commit; `--no-color` (and `NO_COLOR`) plainens the
20
- output.
34
+ Then open the repository in either harness nothing else to configure:
21
35
 
22
- Already have a repo? Install just the **process layer** into it — no
23
- architecture assumptions, no skeleton:
36
+ ```sh
37
+ claude # Claude Code reads CLAUDE.md and .claude/settings.json
38
+ codex # Codex reads AGENTS.md, .codex/ and .agents/skills/
39
+ ```
40
+
41
+ Check it and commit it:
24
42
 
25
43
  ```sh
26
- npx create-agent-rig init # rules, gates, stop rules into the current repo
27
- npx create-agent-rig init --dry-run # print the plan, write nothing
44
+ npx create-agent-rig@latest doctor
45
+ git add -A && git commit -m "Add agent rig"
28
46
  ```
29
47
 
30
- `init` drops in the autonomy tiers, stop rules, workflow, and the enforcement
31
- hooks **wired** for both harnesses, in `.claude/settings.json` and
32
- `.codex/hooks.json`, each naming exactly the hooks it installed — plus matching
33
- `CLAUDE.md` and `AGENTS.md` maps that describe that rig rather than the generated
34
- monorepo. It refuses to clobber either existing map; if the repo already has a
35
- Claude or Codex hook config, it keeps it and prints the entries to merge,
36
- because a hook nothing calls is not enforcement.
48
+ Commit `.claude/.rig-manifest.json` with everything else it is how later
49
+ upgrades tell your changes from Rig's.
37
50
 
38
- Two things it deliberately leaves to you, and says so in the installed
39
- maps: the Definition-of-Done gate has no `dod-checks.json` (it cannot know
40
- your commands), and the elevated-path list names only what every repo has.
51
+ Everything is written inside the repository; Rig changes no global Claude Code
52
+ or Codex configuration. The only machine-level file it can write is the
53
+ optional Memory registration described [below](#memory); Spec Kit setup also
54
+ fills uv's download cache.
41
55
 
42
- After generation or upgrade, review the checked-in `.codex/hooks.json` in Codex's
43
- `/hooks` view and explicitly trust it if Codex presents a trust prompt. The
56
+ After generation or upgrade, review the checked-in `.codex/hooks.json` in
57
+ Codex's `/hooks` view and explicitly trust it if Codex asks. The
44
58
  [official Codex hooks documentation](https://learn.chatgpt.com/docs/hooks)
45
59
  records trust against the current hook hash, so a changed hook definition may
46
- require that review again; the adapter does not silently replace user-owned hook
47
- configuration.
60
+ require that review again; Rig never silently replaces hook configuration you
61
+ own.
62
+
63
+ ## Why Rig
64
+
65
+ Agent instructions tend to rot. A `CLAUDE.md` copied between projects, a
66
+ separate set of Codex notes, hooks pasted from a blog post — each drifts on its
67
+ own, and none of it can be upgraded without overwriting what the team changed
68
+ since.
69
+
70
+ Rig treats that configuration as something with an owner and a lifecycle:
71
+
72
+ | Without Rig | With Rig |
73
+ | --------------------------------------------------- | --------------------------------------------------------- |
74
+ | Separate Claude Code and Codex setups | One rulebook, projected into each harness's native format |
75
+ | Rules that only work if the agent reads them | Hooks that refuse the dangerous action at the tool layer |
76
+ | Upgrading means re-copying and losing local changes | `upgrade` updates untouched files and reports the rest |
77
+ | A deleted rule quietly comes back | Deleted stays deleted |
78
+ | No way to tell what is installed or broken | `doctor` |
79
+ | Removal is guesswork | `uninstall` removes only files Rig can prove it wrote |
80
+
81
+ ## Claude Code and Codex
82
+
83
+ ```mermaid
84
+ flowchart TD
85
+ R["AGENTS.md — the rulebook<br/>.claude/rules, hooks, agents, skills"]
86
+ R --> C["Claude Code<br/>CLAUDE.md → @AGENTS.md<br/>.claude/settings.json<br/>.claude/agents, .claude/skills"]
87
+ R --> X["Codex<br/>AGENTS.md<br/>.codex/hooks.json, .codex/config.toml<br/>.codex/agents, .agents/skills"]
88
+ ```
89
+
90
+ `AGENTS.md` is the canonical rulebook. `CLAUDE.md` is a short shim that imports
91
+ it, so both harnesses read the same rules. The hook scripts live once in
92
+ `.claude/hooks/` and are wired by both `.claude/settings.json` and
93
+ `.codex/hooks.json`. Review agents and skills are projected into each harness's
94
+ own format.
95
+
96
+ The harnesses are not identical, and Rig does not pretend they are. Two hooks —
97
+ the subagent model guard and the routing warning — exist only for Claude Code.
98
+ MCP wiring goes into Claude Code's `.mcp.json` entry by entry, but into Codex's
99
+ `.codex/config.toml` as a whole file Rig renders.
100
+
101
+ ## What Rig installs
102
+
103
+ | Area | What you get |
104
+ | ------------------ | ------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
105
+ | Rules | `AGENTS.md`, `CLAUDE.md` and `.claude/rules/`: autonomy tiers (what an agent may do alone), stop rules, TDD workflow and a Definition of Done |
106
+ | Guards | Hooks that refuse bypassing pre-commit, force-pushing a shared branch, destructive `rm`, writing credentials, and ending a session while a configured check is red |
107
+ | Agents | `test-writer` and `implementation-agent` for the TDD steps; `code-reviewer`, `security-scanner` and `prose-reviewer` for review — each pinned to a model and effort |
108
+ | Skills | `worktree-task`, `new-invariant` and `check-premises` |
109
+ | Lifecycle metadata | `.claude/.rig-manifest.json`: which bytes Rig installed |
110
+
111
+ A guard is a check on each edit or command before it runs, not a sandbox. Each
112
+ one states what it does not catch in its own header — `guard-secret-file`, for
113
+ example, sees what an agent writes through its edit tools, not a file committed
114
+ from disk.
48
115
 
49
- ## Upgrading a rig you already have
116
+ Two things are left for you, and the installed `AGENTS.md` says so: the
117
+ commands your Definition of Done should run (`.claude/hooks/dod-checks.json`),
118
+ and the paths in your project that need a human reviewer.
50
119
 
51
- A release changes files, and `init` only ever _adds_ — so bringing an existing
52
- rig forward is its own command:
120
+ An **experimental** workflow layer adds a queue-driven autonomous loop, a
121
+ pre-merge gate skill and PR-lifecycle helpers. It is opt-in:
122
+ `init --layer workflow`.
123
+
124
+ ## How ownership works
125
+
126
+ Rig remembers exactly which bytes it installed. That lets every lifecycle
127
+ command tell Rig's files from yours:
128
+
129
+ | The file is… | `upgrade` | `uninstall` |
130
+ | --------------------------- | ---------------------------- | -------------- |
131
+ | exactly as Rig installed it | updated to the new release | removed |
132
+ | edited by you | kept, reported as a conflict | kept, reported |
133
+ | deleted by you | stays deleted | nothing to do |
134
+ | not Rig's, or there before | never claimed | never touched |
135
+
136
+ Conflicts are reported with the path to the new version, so you can compare
137
+ and merge yourself — Rig does no automatic merging of the documents your agents
138
+ obey. The details, including how line endings and hook wiring are handled, are
139
+ in [`docs/command-contract.md`](docs/command-contract.md) and
140
+ [`docs/decisions/raw-byte-ownership.md`](docs/decisions/raw-byte-ownership.md).
141
+
142
+ ## Lifecycle
143
+
144
+ **Upgrade** to the current release:
53
145
 
54
146
  ```sh
55
- npx create-agent-rig@latest upgrade --dry-run # print the plan, write nothing
56
- npx create-agent-rig@latest upgrade # print the plan, then ask before writing
57
- npx create-agent-rig@latest upgrade --yes # the answer up front (required off a terminal)
147
+ npx create-agent-rig@latest upgrade --dry-run # the plan, nothing written
148
+ npx create-agent-rig@latest upgrade # the plan, then asks before writing
149
+ npx create-agent-rig@latest upgrade --yes # no prompt (required off a terminal)
58
150
  ```
59
151
 
60
- It replaces the files the rig installed **and you have not touched**, installs
61
- what the release added, and **reports everything else** — no three-way merge, no
62
- patching. Silently merging your edits into the documents an agent loop obeys is
63
- how a rig quietly stops meaning what you think it means; a conflict report is how
64
- it does not. Each conflict names the file, why it was kept, and the path to the
65
- new version so you can diff it yourself.
66
-
67
- How it knows: `create` and `init` write `.claude/.rig-manifest.json` — the rig
68
- version plus a hash per installed file. A file `init` found already in place and
69
- left alone is recorded separately, under `kept`, with the hash of the bytes it
70
- found, and never as the rig's (`packages/cli/test/init.test.ts` › "records what
71
- it kept, with the sha256 of the bytes actually on disk — never in `files`"). An
72
- `upgrade` conflict on such a file says it was kept by init and whether it was
73
- edited since (`packages/cli/test/upgrade.test.ts` › "says "edited since"
74
- instead, once the disk sha no longer matches what init recorded"). **Commit it**; without it in the
75
- repository the command is blind on CI and on a colleague's machine. Rigs
76
- installed before 0.4.0 have no manifest, so the package also carries the hashes
77
- of every release whose published commit is on record (0.2.0 onward — 0.1.0's
78
- published bytes are not recoverable, and a rig from it reports every file as
79
- yours) and recognises a file matching one of them. The record is
80
- `templates/release-ledger.json`, written at the release _after_ the one it
81
- describes, so the newest release is never in the table a rig installed from it
82
- carries — one more reason committing the manifest is the sentence in bold above
83
- and not an aside.
84
-
85
- `.claude/settings.json` is replaced only when the manifest's recorded hash
86
- proves the rig wrote those exact bytes and you have not touched them — the case
87
- where a release adds a hook and the wiring that calls it. Anything else, and it
88
- is where your own hooks live: the new wiring is printed for you to merge, never
89
- written. Unlike every other file, a match against the released hashes is not
90
- enough for this one, and a replacement that would stop calling a hook the
91
- current wiring names — while that hook's file is still in `.claude/hooks/` — is
92
- handed over instead.
93
-
94
- ### Registering Memory on this machine
95
-
96
- Memory is a separate subsystem with its own version; the rig never imports it
97
- and never searches for it. `setup` records where it is, once per machine:
152
+ **Diagnose** the repository:
98
153
 
99
154
  ```sh
100
- npx create-agent-rig@latest setup --memory-root ~/claude-config # the checkout that holds shared-memory/memory.mjs
101
- npx create-agent-rig@latest setup --memory-root ~/claude-config --dry-run # handshake only, write nothing
155
+ npx create-agent-rig@latest doctor
156
+ npx create-agent-rig@latest doctor --json
102
157
  ```
103
158
 
104
- It derives the invocation from that one root, runs Memory's `--version --json`
105
- first, and refuses a foreign contract major with exit 4 before writing anything.
106
- What it writes is one machine-scoped manifest
107
- `~/.config/create-agent-rig/subsystems.json` (`%APPDATA%\create-agent-rig\` on
108
- Windows) — carrying the invocation, the required contract major, the pinned
109
- Memory ref (`--memory-ref`) and the version the handshake observed. `upgrade`
110
- re-runs the same derivation when the manifest exists; it never creates one. The
111
- behaviour is pinned in `packages/cli/test/setup.test.ts` and
112
- `packages/cli/test/subsystems.test.ts`; the seam itself is ADR-RP-002 R6
113
- (`docs/decisions/memory-rig-boundary.md`).
159
+ `doctor` checks the Rig manifest and the files it lists, the installed guards,
160
+ the optional workflow layer, integration wiring, Spec Kit's own offline status
161
+ and the Memory registration. It exits `1` only when a check fails. It reports
162
+ wiring, not reachability: it never contacts a provider, and never claims that
163
+ authorization, connectivity or trust were verified.
114
164
 
115
- Both bins answer the same handshake, and the rig consumes Memory only through it
116
- (RP-19):
165
+ **Uninstall**, keeping everything you wrote:
117
166
 
118
167
  ```sh
119
- npx create-agent-rig@latest --version --json # {"schemaVersion":1,"name":"create-agent-rig","version":"…","contractVersion":"1.0"}
120
- npx create-agent-rig@latest memory doctor --json # handshake first, then Memory's doctor, answer passed through unchanged
121
- npx create-agent-rig@latest memory load --json --cwd . # same, for load (`--cwd`: Memory's own contract, per its owner — RP-183); arguments pass to Memory verbatim, plus `--timeout-ms 45000` when you name none
168
+ npx create-agent-rig@latest uninstall --dry-run
169
+ npx create-agent-rig@latest uninstall
122
170
  ```
123
171
 
124
- `memory` reads the manifest above, runs Memory's `--version --json`, and only
125
- then the verb: a foreign contract major exits 4 and the verb never runs; no
126
- manifest (or an executable that has moved) is `unsupported`/`absent`, exit 0;
127
- an executable that answers but not as the manifest promised — a broken
128
- `VERSION`, a malformed handshake — is `integration-failed`, exit 1, never
129
- "absent". Pinned in `packages/cli/test/memory.test.ts` and
130
- `packages/cli/test/cli-version.test.ts`.
131
-
132
- **A file you deleted stays deleted.** The rules invite you to delete the ones
133
- whose invariant your project does not have, so an upgrade that quietly restored
134
- them would be undoing your work. With a manifest that is direct — it names the
135
- file, the disk does not have it, and the manifest is _evidence_, not a command.
136
- Without one, the shipped table answers instead: a file that was in every release
137
- it covers was there to be removed. The single case nothing can tell apart is a
138
- file a **later** release added, which your rig never had — that one is installed,
139
- and `--dry-run` lists it before anything is written.
140
-
141
- ### Conformance runner
142
-
143
- `contracts/conformance/v1/` holds the JSON schemas of the command contract's
144
- `--version --json`, `doctor --json` and `load --json` answers, and
145
- `scripts/memory-conformance.mjs` checks a Memory checkout against them:
172
+ Only files whose bytes still match what Rig installed are removed. Anything
173
+ edited is kept and listed, and the manifest stays until nothing of Rig's is
174
+ left. `--detach` removes the manifest anyway and hands the kept files over to
175
+ you. Integration wiring is removed with `setup remove`, not `uninstall`.
176
+
177
+ ## Optional integrations
178
+
179
+ `setup` adds integrations after showing the exact plan and asking for
180
+ consent. It works in a repository where Rig is installed:
146
181
 
147
182
  ```sh
148
- pnpm build
149
- node scripts/memory-conformance.mjs --from <claude-config checkout> --json [--out report.json]
183
+ npx create-agent-rig@latest setup # interactive: pick provider and harness
184
+ npx create-agent-rig@latest setup list
185
+ npx create-agent-rig@latest setup add figma-mcp --harness claude-code --harness codex
186
+ npx create-agent-rig@latest setup apply # re-apply everything declared
187
+ npx create-agent-rig@latest setup remove figma-mcp
150
188
  ```
151
189
 
152
- It is offline by construction `--from` is mandatory, nothing is fetched, no
153
- credential is read and it never imports Memory code or copies a Memory
154
- fixture into this repository (`test/template/memory-conformance.test.ts` ›
155
- "carries no fetch, clone or credential: the checkout is always the caller's"
156
- and › "the repository carries no Memory fixture"). The contract directory is
157
- this repository's own, not a rig payload: `create`, `init` and `upgrade` do
158
- not deliver it (`test/template/conformance-contract.test.ts` › "is not
159
- delivered to rigs: no template carries a conformance contract"). The report's
160
- rows, its `rigSha` / `memorySha` / `verifierDigest` fields and the `--out`
161
- file are pinned by the same test file's › "passes every row against a
162
- well-formed local fixture root and names both SHAs and the verifier digest"
163
- and › "derives verifierDigest from the runner, its validator and the contract
164
- files, in that order, and writes the same report to --out". The authoritative
165
- cross-repository run lives in the private `claude-config` repository, which
166
- checks this repository out at an explicit full SHA and runs the command above
167
- against its own tree; the CI here runs only the offline tests.
168
-
169
- ## What you get
170
-
171
- **A system of boundaries, each held by tooling.** An agent (or a human using
172
- one) cannot talk its way past them — each guard is a pre-write scan that stops
173
- the normal path cold (review and tests back it; the claim is stated exactly,
174
- never inflated). The hook implementations live once in `.claude/hooks/` and are
175
- wired by both `.claude/settings.json` and `.codex/hooks.json` — except the two
176
- marked Claude Code, which only `.claude/settings.json` wires:
177
-
178
- - **`guard-core-purity`** — refuses any edit that puts I/O, clock, randomness,
179
- environment access, or a non-allowlisted import into the pure domain core;
180
- - **`guard-web-boundary`** — refuses `db`/service imports from the frontend;
181
- the web talks to the backend over HTTP only;
182
- - **`guard-rulebook`** — in an unattended run (a flag file the `loop` skill
183
- writes at claim time), refuses an edit to the rulebook — hooks, wiring,
184
- `queue.json` and its board selector, the queue adapters, the router, the gate sweep, the rules,
185
- `CLAUDE.md` — outside the current item's allow-list; does nothing in an
186
- attended session.
187
- - **`guard-secret-file`** — refuses an edit that writes a credential: either the
188
- path names one (`jira.env`, `id_rsa`, anything under `secrets/`) or the text
189
- carries a credential VALUE. Both arms read one vocabulary,
190
- `.claude/scripts/lib/secrets.mjs`, and a refusal names the pattern and the line
191
- and **never the matched value** — printing it would leak the secret in the act
192
- of refusing it. Its blind spots are in its own header, each naming the
193
- test that pins it or saying plainly that none does — and those tests live in
194
- this generator, not in the rig;
195
- - **`block-no-verify`** — refuses bypassing pre-commit checks (and knows the
196
- difference between using the `--no-verify`/`-n` flag and merely mentioning it
197
- in a message);
198
- - **`guard-bash`** — refuses the part of the "Never" tier a text scan can decide:
199
- a force-push or `--delete` naming a shared branch, a push that names the default
200
- branch, `gh workflow run`/`gh api …/dispatches` against a production workflow,
201
- and `rm` on a catastrophic target. It **parses** the command rather than
202
- pattern-matching it, so a commit message mentioning a forbidden flag is prose,
203
- not a bypass — and the file states exactly what it does **not** inspect
204
- (`cdk deploy`, `find -delete`, a bare `git push`, and more);
205
- - **`gate-stop-dod`** — refuses to end the session while a Definition-of-Done
206
- check is red; it fails open (a missing or corrupt config never makes the
207
- session unquittable) and never blocks twice in a row;
208
- - **`inject-rules`** — re-injects the autonomy rules at session start, so they
209
- survive compaction and resumes: the whole file, minus the regions the file
210
- itself marks as reference. What is left out is a decision written in
211
- `autonomy.md` on the line above it, not one this hook infers;
212
- - **`guard-subagent-model`** (Claude Code) — refuses an `Agent` dispatch that
213
- passes a call-site `model` for a subagent whose definition pins one: the
214
- definition, not the call, decides which model a gate reads with;
215
- - **`warn-subagent-routing`** (Claude Code) — at session start, warns when
216
- `CLAUDE_CODE_SUBAGENT_MODEL_FORCE` is set (it replaces every model pin below),
217
- when `CLAUDE_CODE_EFFORT_LEVEL` is set (it replaces every effort pin), when
218
- Claude Code is older than 2.1.251 (the unnamed default then replaces the model
219
- pins), or when its version cannot be read (so the pins cannot be confirmed to
220
- hold). It warns and never blocks.
221
-
222
- **A brake that is a real file.** `touch ~/.claude/<project>-loop-STOP` and no
223
- merge lands until it is removed — enforced at the tool layer, so it holds even if
224
- nothing reads the rule. Everything short of the merge stays allowed on purpose:
225
- finish the task, push the branch, open the PR, write the journal. Stopping
226
- cleanly must not mean losing work.
227
-
228
- **Two sweeps meant to run outside any session** — nothing schedules them for you;
229
- that is deliberate, because a check a run performs on itself is one a hurried run
230
- skips. `detect-missed-gate` finds merges
231
- that crossed an elevated path with no recorded reviewer verdict;
232
- `reconcile-external-prs` accounts for work that reached the default branch outside
233
- the queue. They exist because the one failure a run cannot report is its own
234
- missed gate — the run that skipped it is exactly the run that will not mention it.
235
-
236
- **A queue behind an adapter.** The `loop` driver selects through
237
- `.claude/scripts/queue/`: a pure core (filters in order, blocker resolution, the
238
- elevated-tier ration, stop conditions) with adapters for `PLAN.md` (the default,
239
- working before a project has a remote), GitHub Issues, and Jira. Two rules are
240
- load-bearing and tested from both directions — **blockers resolve from links,
241
- never labels**, and **the agent never files its own work items**.
242
-
243
- Around all of it: **autonomy tiers** (what an agent does alone / after review /
244
- never), **stop rules** (three strikes, flaky ≠ retry, session staleness),
245
- **subagent gates** (`test-writer`, `code-reviewer`, `security-scanner`,
246
- `prose-reviewer`, and `cdk-diff-reviewer` on the AWS target), **skills** (`pr-ship` pre-merge gate;
247
- `loop` queue driver; `worktree-task` for concurrent sessions; `new-invariant`, a
248
- generator for the invariant→hook→test pattern; `post-deploy-verify` and
249
- `ro-debug` on the AWS target), and matching one-page `CLAUDE.md` / `AGENTS.md`
250
- maps a fresh session orients by.
251
-
252
- **Each gate reads with a pinned model and effort**, so a SHIP does not change
253
- meaning with whatever model the session was started on. `code-reviewer`,
254
- `security-scanner` and `cdk-diff-reviewer` pin `claude-opus-5`; `test-writer` and
255
- `prose-reviewer` pin `claude-sonnet-5`; all pin `high` effort — and their Codex
256
- profiles pin `gpt-5.6-sol` / `gpt-5.6-terra` from the same role table. A subagent
257
- with no definition defaults to `claude-sonnet-5` through
258
- `CLAUDE_CODE_SUBAGENT_MODEL` in `.claude/settings.json`; its effort cannot be
259
- pinned and follows the session. The driver session's own model and effort stay
260
- yours. To change a role in a generated project, edit `model:` / `effort:` in its
261
- `.claude/agents/<role>.md` — and the matching `.codex/agents/<role>.toml` — in a
262
- reviewed change; `upgrade` then reports the edited file as yours instead of
263
- replacing it. Why these values, and what voids them: `docs/decisions/subagent-routing.md`.
264
-
265
- **The hooks are examples, not laws.** `.claude/rules/invariants.md` states the
266
- pattern behind each one — a stated invariant, a mechanical check, a test for the
267
- check — so you can delete the ones whose invariant your project does not have and
268
- spend the slot on one it does. An inherited rule nobody chose is worse than an
269
- empty rule file: the empty one is visibly incomplete, the inherited one is
270
- invisibly wrong.
271
-
272
- The skeleton around it is real and runnable — pure core shared by server _and_
273
- browser (one schema validates on both sides of the wire), a mandatory usecase
274
- layer (`payload → handler → usecase → model`), a queue with DLQ discipline,
275
- tests at every layer.
276
-
277
- ## Targets
278
-
279
- | Target | One line |
280
- | ---------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
281
- | `aws-serverless` | DynamoDB single-table, SQS + DLQ + CloudWatch alarm, three Lambdas (POST/GET `/notes` behind an HTTP API, plus an SQS worker), static web on S3 + CloudFront, CDK with least-privilege IAM grants |
282
- | `node-service` | `node:http` server that also serves the built web bundle, atomic JSON-file store behind the same model boundary, spool-directory queue + DLQ, worker process |
283
-
284
- Coherent alternatives, not a parameterized abstraction. Flexibility is
285
- **subtraction**: the generated project is yours — delete what you don't need.
286
-
287
- ## What it deliberately does not do
288
-
289
- No authentication. No design system or UI kit. No state manager. No i18n,
290
- analytics, or error tracking. No third cloud. No component-testing apparatus.
291
-
292
- Each of these is application surface, not an architecture proof — and every
293
- addition is permanent maintenance in every target. The frontend is plain on
294
- purpose: scaffolding gets replaced without friction; a finished-looking UI
295
- gets fought. If you need one of these, add it — the project is yours.
190
+ `add`, `apply` and `remove` accept `--dry-run`. With `--json` they never
191
+ prompt, and write only with `--yes`. Intent and ownership are recorded in `.rig/integrations.json`.
296
192
 
297
- ## The 2-minute demo
193
+ | Integration | ID | What Rig does |
194
+ | --------------- | --------------- | ------------------------------------------------------------------------------------------- |
195
+ | Figma MCP | `figma-mcp` | Writes the hosted MCP entry for Claude Code and/or Codex |
196
+ | Atlassian MCP | `atlassian-mcp` | Same, for Atlassian's hosted MCP |
197
+ | Basic Memory | `basic-memory` | Preview. Wires `uvx basic-memory mcp`; never installs, reads or removes Basic Memory's data |
198
+ | GitHub Spec Kit | `spec-kit` | Runs Spec Kit's own pinned CLI (1.0.8) to set up Claude Code and Codex |
199
+
200
+ **MCP wiring is owned by Rig.** Rig writes the entries and removes only the ones
201
+ it can prove it wrote; your own MCP entries are preserved. Signing in to a
202
+ provider happens in the harness — Rig stores no credentials.
203
+
204
+ **Spec Kit is owned by Spec Kit.** Rig runs the official `specify` CLI at a
205
+ pinned version through `uvx` — so `uv`, `uvx` and `git` are required — and
206
+ Spec Kit creates, upgrades and removes its own files. Rig never copies or
207
+ deletes them. The first setup needs a clean working tree and never re-runs
208
+ `init` on an already initialized repository; an existing installation is
209
+ adopted with `setup add spec-kit --adopt`.
210
+
211
+ **Plugins are not managed.** Rig 0.10.0 has no plugin manager or marketplace.
212
+ Claude Code and Codex plugins can be used alongside Rig as usual.
213
+
214
+ ## Memory
215
+
216
+ Memory is a separate project with its own releases. Rig does not include it,
217
+ does not need it, and never searches for it. If you use Memory, register it
218
+ once per machine; Rig then passes `doctor` and `load` through to it after a
219
+ version handshake:
298
220
 
299
221
  ```sh
300
- ./demo.sh # from a clone of this repo
222
+ npx create-agent-rig@latest setup --memory-root <memory-checkout>
223
+ npx create-agent-rig@latest memory doctor --json
224
+ npx create-agent-rig@latest memory load --json --cwd .
301
225
  ```
302
226
 
303
- generates the `node-service` target the generated project's own gates pass →
304
- **an attempted core-purity violation is refused live by the hook** → the
305
- service runs, a smoke request travels every layer, the worker drains the queue,
306
- the DLQ stays empty:
227
+ The registration is written to `~/.config/create-agent-rig/subsystems.json`
228
+ (`%APPDATA%\create-agent-rig\` on Windows). A Memory with an incompatible
229
+ contract version is refused with exit code `4`. The boundary is described in
230
+ [`docs/decisions/memory-rig-boundary.md`](docs/decisions/memory-rig-boundary.md).
231
+
232
+ ## Safe by default
233
+
234
+ - **Ownership, not guesswork.** Rig changes or removes only files whose bytes
235
+ match what it installed.
236
+ - **Conflicts over overwrites.** Your edits are reported, never merged or
237
+ replaced.
238
+ - **Deleted stays deleted.** An upgrade does not restore what you removed.
239
+ - **Plan first.** `--dry-run` shows the plan for `init`, `upgrade`, `uninstall`
240
+ and `setup`; `upgrade`, `uninstall` and `setup` also ask before writing.
241
+ - **Bounded external processes.** Spec Kit runs with a fixed argument list, a
242
+ deadline, and cleanup of its whole process tree.
243
+ - **No stored credentials.** Rig does not put provider credentials in the
244
+ repository, its state files or its output.
245
+
246
+ ## Platform support
247
+
248
+ | Platform | Status for 0.10.0 |
249
+ | -------- | ---------------------------------------------------------------------- |
250
+ | Linux | Supported — the packed release is accepted on the exact release commit |
251
+ | Windows | Supported — same acceptance; one Spec Kit limitation below |
252
+ | macOS | Supported on Apple silicon — same acceptance |
253
+
254
+ On Windows, Spec Kit 1.0.8 rewrites `.claude/settings.json` and
255
+ `.codex/config.toml` with CRLF line endings. `doctor` then reports Rig's files
256
+ with a warning, and where a Codex MCP integration is also wired, a later change
257
+ to it asks you to merge the Codex config by hand instead of overwriting it.
258
+
259
+ ## Limitations and non-goals
260
+
261
+ - No application scaffolding, no project templates to choose from.
262
+ - Not an agent runtime, scheduler or workflow engine; it configures the
263
+ harnesses you already run.
264
+ - No plugin manager, and no bundled memory engine.
265
+ - Provider accounts, authorization and connectivity are between you, the
266
+ provider and the harness.
267
+ - The workflow layer is experimental.
307
268
 
269
+ ## The 2-minute demo
270
+
271
+ From a clone of this repository:
272
+
273
+ ```sh
274
+ ./demo.sh
308
275
  ```
309
- == 3/4 an agent tries to put I/O and clock access into the pure core… ==
310
- BLOCKED packages/core is a pure module and this change breaks its purity:
311
- - imports "node:fs/promises" — the core may import only its own modules and: zod
312
- - reads the clock — take a timestamp as an argument
313
- Move the impure part behind the usecase layer or into an adapter.
314
- …and the guard-core-purity hook REFUSED the edit at the tool layer (exit 2). ✔
315
- ```
276
+
277
+ It installs the rig into a scratch directory and shows a hook refusing an
278
+ attempted pre-commit bypass.
316
279
 
317
280
  ## Requirements
318
281
 
319
- - Node ≥ 20 (pnpm recommended for the generated workspace). The CLI itself
320
- carries zero runtime dependencies — the `npx github:…`, tarball, and
321
- published-package paths all work.
322
-
323
- ## How it stays honest
324
-
325
- Every template is a real project, installed with a frozen lockfile and run in
326
- place on every push. Every e2e run generates a project cold and runs the
327
- generated project's own checks (install lint typecheck test, plus
328
- `cdk synth` on the AWS target); the pack-path and git-path installs are both
329
- under test, because that is exactly where scaffolders break. A grep-test keeps
330
- the universal rules free of any provider mention; the hook-blocking behavior
331
- itself is under test; and a weekly lockfile-free run resolves each template's
332
- dependencies fresh to catch upstream breakage early. This repo dogfoods its own
333
- rulebook — the Claude and Codex projections are composed from the templates,
334
- and drift fails the suite.
335
-
336
- **And the enforcement layer is adversarially reviewed, not just tested.** The
337
- Bash guard went through four review rounds with ten reviewers, who executed it
338
- rather than read it. They found a PR body that could forge its own reviewer
339
- verdict, a queue write that deleted the wrong line, and three ways to make the
340
- guard crash into permitting everything. Each round's findings — including the
341
- ones introduced by the previous round's _fix_ — are in the git history and in
342
- `CHANGELOG.md`. The rule that came out of it is now part of what ships: a guard
343
- that fails open must do provably bounded work, because fail-open turns every line
344
- of its own work into a potential bypass.
345
-
346
- Development (from a clone — `PLAN.md` and `demo.sh` live in the repository, not
347
- in the published tarball): `pnpm test` (full), `pnpm test:unit` (fast loop), `pnpm test:smoke` (the unit project only — the Windows pull-request lane),
348
- `pnpm template:check` (templates in place). The plan of record is `PLAN.md`;
349
- release notes and the release checklist ship in `CHANGELOG.md`.
282
+ - Node ≥ 20. The CLI has no runtime dependencies.
283
+ - Git.
284
+ - For Spec Kit only: `uv` and `uvx`.
285
+
286
+ ## Documentation
287
+
288
+ | Document | Covers |
289
+ | ------------------------------------------------------ | --------------------------------------------------------------------- |
290
+ | [`docs/command-contract.md`](docs/command-contract.md) | Every command's options, output, exit codes and ownership rules |
291
+ | [`CHANGELOG.md`](CHANGELOG.md) | What changed in each release, and the release checklist |
292
+ | [`docs/decisions/`](docs/decisions/) | Design decisions: ownership, `AGENTS.md`, Codex adapter, integrations |
293
+ | [`docs/compatibility.md`](docs/compatibility.md) | What each capability does per harness and platform |
294
+ | [`docs/releasing.md`](docs/releasing.md) | How a release is prepared and accepted |
295
+
296
+ ## Development
297
+
298
+ ```sh
299
+ pnpm install
300
+ pnpm test # build and the full suite
301
+ pnpm test:unit # the fast suite
302
+ pnpm lint
303
+ pnpm typecheck
304
+ ```
305
+
306
+ This repository uses its own rig: changes go through a branch, tests first, and
307
+ review before merge. [`AGENTS.md`](AGENTS.md) is the working agreement.
308
+
309
+ ## License
310
+
311
+ [MIT](LICENSE)