@aperant/framework 0.7.0 → 0.7.3

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 (151) hide show
  1. package/CHANGELOG.md +180 -0
  2. package/agents/apt-planner.md +12 -0
  3. package/agents/apt-pr-review-fixer.md +13 -9
  4. package/bin/apt-tools.mjs +7 -0
  5. package/dist/cli/ci-watch/stop-matrix.d.mts.map +1 -1
  6. package/dist/cli/ci-watch/stop-matrix.mjs +16 -0
  7. package/dist/cli/ci-watch/stop-matrix.mjs.map +1 -1
  8. package/dist/cli/commands/ci-watch.d.mts +11 -0
  9. package/dist/cli/commands/ci-watch.d.mts.map +1 -1
  10. package/dist/cli/commands/ci-watch.mjs +108 -2
  11. package/dist/cli/commands/ci-watch.mjs.map +1 -1
  12. package/dist/cli/commands/features-audit.d.mts +24 -0
  13. package/dist/cli/commands/features-audit.d.mts.map +1 -1
  14. package/dist/cli/commands/features-audit.mjs +159 -5
  15. package/dist/cli/commands/features-audit.mjs.map +1 -1
  16. package/dist/cli/commands/health-check.d.mts +16 -0
  17. package/dist/cli/commands/health-check.d.mts.map +1 -1
  18. package/dist/cli/commands/health-check.mjs +118 -2
  19. package/dist/cli/commands/health-check.mjs.map +1 -1
  20. package/dist/cli/commands/init.d.mts +9 -0
  21. package/dist/cli/commands/init.d.mts.map +1 -1
  22. package/dist/cli/commands/init.mjs +49 -4
  23. package/dist/cli/commands/init.mjs.map +1 -1
  24. package/dist/cli/commands/modes.d.mts.map +1 -1
  25. package/dist/cli/commands/modes.mjs +11 -0
  26. package/dist/cli/commands/modes.mjs.map +1 -1
  27. package/dist/cli/commands/pr-review-audit-fixer.d.mts +13 -0
  28. package/dist/cli/commands/pr-review-audit-fixer.d.mts.map +1 -1
  29. package/dist/cli/commands/pr-review-audit-fixer.mjs +18 -5
  30. package/dist/cli/commands/pr-review-audit-fixer.mjs.map +1 -1
  31. package/dist/cli/commands/task.d.mts.map +1 -1
  32. package/dist/cli/commands/task.mjs +84 -5
  33. package/dist/cli/commands/task.mjs.map +1 -1
  34. package/dist/cli/commands/validate-evidence.d.mts +24 -2
  35. package/dist/cli/commands/validate-evidence.d.mts.map +1 -1
  36. package/dist/cli/commands/validate-evidence.mjs +154 -17
  37. package/dist/cli/commands/validate-evidence.mjs.map +1 -1
  38. package/dist/cli/commands/vitest-doctor.d.mts +2 -0
  39. package/dist/cli/commands/vitest-doctor.d.mts.map +1 -0
  40. package/dist/cli/commands/vitest-doctor.mjs +168 -0
  41. package/dist/cli/commands/vitest-doctor.mjs.map +1 -0
  42. package/dist/cli/config/gitignore-drift.d.mts +23 -1
  43. package/dist/cli/config/gitignore-drift.d.mts.map +1 -1
  44. package/dist/cli/config/gitignore-drift.mjs +81 -3
  45. package/dist/cli/config/gitignore-drift.mjs.map +1 -1
  46. package/dist/cli/config/load.d.mts +56 -2
  47. package/dist/cli/config/load.d.mts.map +1 -1
  48. package/dist/cli/config/load.mjs +192 -2
  49. package/dist/cli/config/load.mjs.map +1 -1
  50. package/dist/cli/consistency/parse-review.mjs +7 -0
  51. package/dist/cli/consistency/parse-review.mjs.map +1 -1
  52. package/dist/cli/dispatch.d.mts.map +1 -1
  53. package/dist/cli/dispatch.mjs +24 -2
  54. package/dist/cli/dispatch.mjs.map +1 -1
  55. package/dist/cli/gate/gates/gitignore-in-sync.d.mts +1 -1
  56. package/dist/cli/gate/gates/gitignore-in-sync.d.mts.map +1 -1
  57. package/dist/cli/gate/gates/gitignore-in-sync.mjs +5 -2
  58. package/dist/cli/gate/gates/gitignore-in-sync.mjs.map +1 -1
  59. package/dist/cli/gate/gates/review-clean.d.mts +5 -1
  60. package/dist/cli/gate/gates/review-clean.d.mts.map +1 -1
  61. package/dist/cli/gate/gates/review-clean.mjs +23 -18
  62. package/dist/cli/gate/gates/review-clean.mjs.map +1 -1
  63. package/dist/cli/gate/gates/verify-approved.d.mts +49 -1
  64. package/dist/cli/gate/gates/verify-approved.d.mts.map +1 -1
  65. package/dist/cli/gate/gates/verify-approved.mjs +93 -14
  66. package/dist/cli/gate/gates/verify-approved.mjs.map +1 -1
  67. package/dist/cli/help.d.mts.map +1 -1
  68. package/dist/cli/help.mjs +7 -2
  69. package/dist/cli/help.mjs.map +1 -1
  70. package/dist/cli/install/runtime-detect.d.mts +13 -0
  71. package/dist/cli/install/runtime-detect.d.mts.map +1 -1
  72. package/dist/cli/install/runtime-detect.mjs +9 -0
  73. package/dist/cli/install/runtime-detect.mjs.map +1 -1
  74. package/dist/cli/task/index-md.d.mts.map +1 -1
  75. package/dist/cli/task/index-md.mjs +14 -2
  76. package/dist/cli/task/index-md.mjs.map +1 -1
  77. package/dist/plugin/.claude-plugin/plugin.json +11 -2
  78. package/dist/plugin/agents/apt-improver.md +99 -0
  79. package/dist/plugin/agents/apt-planner.md +127 -10
  80. package/dist/plugin/agents/apt-pr-review-fixer.md +13 -9
  81. package/dist/plugin/skills/apt/SKILL.md +1 -0
  82. package/dist/plugin/skills/apt-close-task/SKILL.md +63 -1
  83. package/dist/plugin/skills/apt-debug/SKILL.md +39 -6
  84. package/dist/plugin/skills/apt-debug/appendices/diagnose-discipline.md +119 -0
  85. package/dist/plugin/skills/apt-diagram/SKILL.md +378 -0
  86. package/dist/plugin/skills/apt-diagram/appendices/design-discipline.md +97 -0
  87. package/dist/plugin/skills/apt-discuss/SKILL.md +72 -5
  88. package/dist/plugin/skills/apt-discuss/appendices/grill-discipline.md +104 -0
  89. package/dist/plugin/skills/apt-discuss/appendices/zoom-out-helper.md +79 -0
  90. package/dist/plugin/skills/apt-execute/SKILL.md +57 -5
  91. package/dist/plugin/skills/apt-execute/appendices/tdd-mode.md +107 -0
  92. package/dist/plugin/skills/apt-improve/DEEPENING.md +84 -0
  93. package/dist/plugin/skills/apt-improve/INTERFACE-DESIGN.md +97 -0
  94. package/dist/plugin/skills/apt-improve/LANGUAGE.md +104 -0
  95. package/dist/plugin/skills/apt-improve/SKILL.md +141 -0
  96. package/dist/plugin/skills/apt-plan/SKILL.md +171 -4
  97. package/dist/plugin/skills/apt-plan/adapters/conductor.md +98 -0
  98. package/dist/plugin/skills/apt-pr-review/SKILL.md +57 -18
  99. package/dist/plugin/skills/apt-prototype/LOGIC.md +109 -0
  100. package/dist/plugin/skills/apt-prototype/SKILL.md +143 -0
  101. package/dist/plugin/skills/apt-prototype/UI.md +90 -0
  102. package/dist/plugin/skills/apt-quick/SKILL.md +49 -8
  103. package/dist/plugin/skills/apt-release-notes/SKILL.md +193 -0
  104. package/dist/plugin/skills/apt-release-notes/appendices/persona-voice.md +59 -0
  105. package/dist/plugin/skills/apt-review/SKILL.md +2 -0
  106. package/dist/plugin/skills/apt-run/SKILL.md +32 -4
  107. package/dist/plugin/skills/apt-setup/SKILL.md +308 -6
  108. package/dist/plugin/skills/apt-ship/SKILL.md +122 -1
  109. package/dist/plugin/skills/apt-spar/SKILL.md +315 -0
  110. package/dist/plugin/skills/apt-triage/AGENT-BRIEF.md +84 -0
  111. package/dist/plugin/skills/apt-triage/OUT-OF-SCOPE.md +75 -0
  112. package/dist/plugin/skills/apt-triage/SKILL.md +169 -0
  113. package/dist/plugin/skills/apt-update/SKILL.md +77 -10
  114. package/dist/plugin/skills/apt-verify/SKILL.md +3 -0
  115. package/dist/plugin/skills/apt-verify-proof/SKILL.md +10 -5
  116. package/dist/plugin/skills/apt-watch-ci/SKILL.md +166 -0
  117. package/dist/plugin/skills/apt-zoom-out/SKILL.md +130 -0
  118. package/package.json +133 -133
  119. package/prompts/conductor-framework-context.md +63 -0
  120. package/prompts/conductor-system.md +11 -0
  121. package/skills/apt-close-task/SKILL.md +1 -0
  122. package/skills/apt-discuss/SKILL.md +47 -5
  123. package/skills/apt-execute/SKILL.md +9 -0
  124. package/skills/apt-plan/SKILL.md +12 -0
  125. package/skills/apt-pr-review/SKILL.md +11 -2
  126. package/skills/apt-quick/SKILL.md +19 -8
  127. package/skills/apt-researcher.md +1 -0
  128. package/skills/apt-setup/SKILL.md +33 -2
  129. package/skills/apt-verify-proof/SKILL.md +7 -5
  130. package/src/cli/ci-watch/stop-matrix.mjs +17 -0
  131. package/src/cli/commands/ci-watch.mjs +113 -2
  132. package/src/cli/commands/features-audit.mjs +164 -5
  133. package/src/cli/commands/health-check.mjs +115 -2
  134. package/src/cli/commands/init.mjs +52 -4
  135. package/src/cli/commands/modes.mjs +11 -0
  136. package/src/cli/commands/pr-review-audit-fixer.mjs +18 -5
  137. package/src/cli/commands/task.mjs +83 -5
  138. package/src/cli/commands/validate-evidence.mjs +158 -17
  139. package/src/cli/commands/vitest-doctor.mjs +173 -0
  140. package/src/cli/config/gitignore-drift.mjs +74 -3
  141. package/src/cli/config/load.mjs +188 -2
  142. package/src/cli/consistency/parse-review.mjs +6 -0
  143. package/src/cli/dispatch.mjs +23 -2
  144. package/src/cli/gate/gates/gitignore-in-sync.mjs +5 -2
  145. package/src/cli/gate/gates/review-clean.mjs +24 -19
  146. package/src/cli/gate/gates/verify-approved.mjs +97 -14
  147. package/src/cli/help.mjs +7 -2
  148. package/src/cli/install/runtime-detect.mjs +9 -0
  149. package/src/cli/task/index-md.mjs +15 -2
  150. package/templates/config.json +2 -7
  151. package/workflows/verify-proof.md +8 -3
package/package.json CHANGED
@@ -1,134 +1,134 @@
1
1
  {
2
- "name": "@aperant/framework",
3
- "version": "0.7.0",
4
- "description": "AI coding framework — composable skills for planning, executing, verifying, and reviewing code with any LLM provider. Works as Claude Code commands, Codex tasks, or programmatically.",
5
- "author": "Mikalsen AI <hello@mikalsen.ai>",
6
- "type": "module",
7
- "main": "./dist/index.js",
8
- "types": "./dist/index.d.ts",
9
- "bin": {
10
- "framework": "./bin/apt-tools.mjs",
11
- "apt-tools": "./bin/apt-tools.mjs",
12
- "apt-proof-video": "./bin/apt-proof-video.mjs"
13
- },
14
- "exports": {
15
- ".": {
16
- "types": "./dist/index.d.ts",
17
- "import": "./dist/index.js"
18
- },
19
- "./types": {
20
- "types": "./dist/types/index.d.ts",
21
- "import": "./dist/types/index.js"
22
- },
23
- "./cost": {
24
- "types": "./dist/cost/index.d.ts",
25
- "import": "./dist/cost/index.js"
26
- },
27
- "./mappers": {
28
- "types": "./dist/mappers/index.d.ts",
29
- "import": "./dist/mappers/index.js"
30
- },
31
- "./schemas": {
32
- "types": "./dist/schemas/index.d.ts",
33
- "import": "./dist/schemas/index.js"
34
- },
35
- "./standalone": {
36
- "types": "./dist/standalone/index.d.ts",
37
- "import": "./dist/standalone/index.js"
38
- },
39
- "./coordination/event-schema": {
40
- "types": "./src/cli/coordination/event-schema.d.ts",
41
- "import": "./src/cli/coordination/event-schema.mjs"
42
- },
43
- "./roadmap/conductor-view": {
44
- "types": "./src/cli/roadmap/conductor-view.d.ts",
45
- "import": "./src/cli/roadmap/conductor-view.mjs"
46
- },
47
- "./design/scan": {
48
- "import": "./src/cli/design/scan.mjs"
49
- },
50
- "./design/extract-repo": {
51
- "import": "./src/cli/design/extract-repo.mjs"
52
- },
53
- "./design/synthesize": {
54
- "import": "./src/cli/design/synthesize.mjs"
55
- }
56
- },
57
- "files": [
58
- "dist/",
59
- "bin/",
60
- "src/cli/",
61
- "src/cost/",
62
- "commands/",
63
- "skills/",
64
- "agents/",
65
- "prompts/",
66
- "templates/",
67
- "context/",
68
- "workflows/",
69
- "examples/",
70
- "LICENSE",
71
- "README.md",
72
- "CHANGELOG.md",
73
- "!**/__tests__/**",
74
- "!**/*.test.*",
75
- "!**/*.spec.*",
76
- "!**/*.test.d.ts.map",
77
- "!**/*.test.js.map"
78
- ],
79
- "keywords": [
80
- "ai",
81
- "framework",
82
- "coding-assistant",
83
- "claude-code",
84
- "codex",
85
- "aperant"
86
- ],
87
- "license": "AGPL-3.0-only",
88
- "homepage": "https://github.com/Mikalsen-AI/aperant-cloud-desktop/tree/main/packages/framework#readme",
89
- "bugs": {
90
- "url": "https://github.com/Mikalsen-AI/aperant-cloud-desktop/issues"
91
- },
92
- "repository": {
93
- "type": "git",
94
- "url": "https://github.com/Mikalsen-AI/aperant-cloud-desktop.git",
95
- "directory": "packages/framework"
96
- },
97
- "engines": {
98
- "node": ">=18.0.0"
99
- },
100
- "publishConfig": {
101
- "access": "public"
102
- },
103
- "dependencies": {
104
- "@clack/prompts": "^1.2.0",
105
- "proper-lockfile": "^4.1.2",
106
- "yaml": "^2.8.3",
107
- "zod": "^4.3.6"
108
- },
109
- "optionalDependencies": {
110
- "@babel/parser": "^7.29.2",
111
- "@babel/traverse": "^7.29.0",
112
- "@google/genai": "^1.50.1",
113
- "css-tree": "^3.2.1",
114
- "playwright": "^1.59.1"
115
- },
116
- "devDependencies": {
117
- "@vitest/coverage-v8": "^4.1.5"
118
- },
119
- "scripts": {
120
- "build": "tsc && node scripts/extract-personas-schema.mjs",
121
- "dev": "tsc --watch --preserveWatchOutput",
122
- "typecheck": "tsc --noEmit",
123
- "lint": "biome check . --diagnostic-level=error",
124
- "lint:fix": "biome check --write . --diagnostic-level=error",
125
- "clean": "rm -rf dist",
126
- "test": "vitest run",
127
- "c28:cutover": "node scripts/c28-cutover.mjs",
128
- "build-plugin": "node scripts/build-plugin.mjs",
129
- "publish-plugin": "node scripts/publish-plugin.mjs",
130
- "publish:verdaccio": "node scripts/publish-verdaccio.mjs",
131
- "release:verdaccio": "pnpm build && pnpm publish:verdaccio",
132
- "ship:verdaccio": "npm version patch --no-git-tag-version && pnpm build && pnpm publish:verdaccio"
133
- }
134
- }
2
+ "name": "@aperant/framework",
3
+ "version": "0.7.3",
4
+ "description": "AI coding framework — composable skills for planning, executing, verifying, and reviewing code with any LLM provider. Works as Claude Code commands, Codex tasks, or programmatically.",
5
+ "author": "Mikalsen AI <hello@mikalsen.ai>",
6
+ "type": "module",
7
+ "main": "./dist/index.js",
8
+ "types": "./dist/index.d.ts",
9
+ "bin": {
10
+ "framework": "./bin/apt-tools.mjs",
11
+ "apt-tools": "./bin/apt-tools.mjs",
12
+ "apt-proof-video": "./bin/apt-proof-video.mjs"
13
+ },
14
+ "exports": {
15
+ ".": {
16
+ "types": "./dist/index.d.ts",
17
+ "import": "./dist/index.js"
18
+ },
19
+ "./types": {
20
+ "types": "./dist/types/index.d.ts",
21
+ "import": "./dist/types/index.js"
22
+ },
23
+ "./cost": {
24
+ "types": "./dist/cost/index.d.ts",
25
+ "import": "./dist/cost/index.js"
26
+ },
27
+ "./mappers": {
28
+ "types": "./dist/mappers/index.d.ts",
29
+ "import": "./dist/mappers/index.js"
30
+ },
31
+ "./schemas": {
32
+ "types": "./dist/schemas/index.d.ts",
33
+ "import": "./dist/schemas/index.js"
34
+ },
35
+ "./standalone": {
36
+ "types": "./dist/standalone/index.d.ts",
37
+ "import": "./dist/standalone/index.js"
38
+ },
39
+ "./coordination/event-schema": {
40
+ "types": "./src/cli/coordination/event-schema.d.ts",
41
+ "import": "./src/cli/coordination/event-schema.mjs"
42
+ },
43
+ "./roadmap/conductor-view": {
44
+ "types": "./src/cli/roadmap/conductor-view.d.ts",
45
+ "import": "./src/cli/roadmap/conductor-view.mjs"
46
+ },
47
+ "./design/scan": {
48
+ "import": "./src/cli/design/scan.mjs"
49
+ },
50
+ "./design/extract-repo": {
51
+ "import": "./src/cli/design/extract-repo.mjs"
52
+ },
53
+ "./design/synthesize": {
54
+ "import": "./src/cli/design/synthesize.mjs"
55
+ }
56
+ },
57
+ "scripts": {
58
+ "build": "tsc && node scripts/extract-personas-schema.mjs",
59
+ "dev": "tsc --watch --preserveWatchOutput",
60
+ "typecheck": "tsc --noEmit",
61
+ "lint": "biome check . --diagnostic-level=error",
62
+ "lint:fix": "biome check --write . --diagnostic-level=error",
63
+ "clean": "rm -rf dist",
64
+ "test": "vitest run",
65
+ "c28:cutover": "node scripts/c28-cutover.mjs",
66
+ "build-plugin": "node scripts/build-plugin.mjs",
67
+ "publish-plugin": "node scripts/publish-plugin.mjs",
68
+ "publish:verdaccio": "node scripts/publish-verdaccio.mjs",
69
+ "release:verdaccio": "pnpm build && pnpm publish:verdaccio",
70
+ "ship:verdaccio": "npm version patch --no-git-tag-version && pnpm build && pnpm publish:verdaccio"
71
+ },
72
+ "files": [
73
+ "dist/",
74
+ "bin/",
75
+ "src/cli/",
76
+ "src/cost/",
77
+ "commands/",
78
+ "skills/",
79
+ "agents/",
80
+ "prompts/",
81
+ "templates/",
82
+ "context/",
83
+ "workflows/",
84
+ "examples/",
85
+ "LICENSE",
86
+ "README.md",
87
+ "CHANGELOG.md",
88
+ "!**/__tests__/**",
89
+ "!**/*.test.*",
90
+ "!**/*.spec.*",
91
+ "!**/*.test.d.ts.map",
92
+ "!**/*.test.js.map"
93
+ ],
94
+ "keywords": [
95
+ "ai",
96
+ "framework",
97
+ "coding-assistant",
98
+ "claude-code",
99
+ "codex",
100
+ "aperant"
101
+ ],
102
+ "license": "AGPL-3.0-only",
103
+ "homepage": "https://github.com/Mikalsen-AI/aperant-cloud-desktop/tree/main/packages/framework#readme",
104
+ "bugs": {
105
+ "url": "https://github.com/Mikalsen-AI/aperant-cloud-desktop/issues"
106
+ },
107
+ "repository": {
108
+ "type": "git",
109
+ "url": "https://github.com/Mikalsen-AI/aperant-cloud-desktop.git",
110
+ "directory": "packages/framework"
111
+ },
112
+ "engines": {
113
+ "node": ">=18.0.0"
114
+ },
115
+ "publishConfig": {
116
+ "access": "public"
117
+ },
118
+ "dependencies": {
119
+ "@clack/prompts": "^1.2.0",
120
+ "proper-lockfile": "^4.1.2",
121
+ "yaml": "^2.8.3",
122
+ "zod": "^4.3.6"
123
+ },
124
+ "optionalDependencies": {
125
+ "@babel/parser": "^7.29.2",
126
+ "@babel/traverse": "^7.29.0",
127
+ "@google/genai": "^1.50.1",
128
+ "css-tree": "^3.2.1",
129
+ "playwright": "^1.59.1"
130
+ },
131
+ "devDependencies": {
132
+ "@vitest/coverage-v8": "^4.1.5"
133
+ }
134
+ }
@@ -0,0 +1,63 @@
1
+ <!-- Conductor Framework Context (auto-injected) -->
2
+ # Aperant framework — slash-skills dispatchable in sub-terminals
3
+
4
+ Dispatch via `sendToTerminal(terminalId, '/<skill> <args>\\r', ...)`.
5
+
6
+ ## Skills
7
+
8
+ | Skill | When to dispatch |
9
+ |-------|------------------|
10
+ | `/apt:author-skill` | Author a new Aperant skill (test-first stub). |
11
+ | `/apt:bootstrap` | Generate / refresh PROJECT.md. |
12
+ | `/apt:close-task` | Post-merge: confirm PR merged, flip phase, GC state. |
13
+ | `/apt:create-docs` | Persona-first product docs from PROJECT.md + features. |
14
+ | `/apt:debug` | Systematic debugging with persistent state. |
15
+ | `/apt:design` | DESIGN.md + wireframe + critique. Hands off to apt:plan. |
16
+ | `/apt:diagram` | .excalidraw / MCP-canvas diagrams. |
17
+ | `/apt:discuss` | Brainstorm vision or lock ambiguous decisions. |
18
+ | `/apt:docs` | Generate / update documentation verified against code. |
19
+ | `/apt:execute` | Execute an implementation plan — build code from subtasks. |
20
+ | `/apt:improve` | Proactive refactor via DEEPENING / INTERFACE / LANGUAGE lenses. |
21
+ | `/apt:mockup` | HTML+Tailwind mockup loop with parallel variants. |
22
+ | `/apt:pause` | Human-initiated session handoff. |
23
+ | `/apt:personas` | Discover 3-5 personas grounded in code + PROJECT.md. |
24
+ | `/apt:plan` | Create an implementation plan from a task description. |
25
+ | `/apt:pr-review` | Multi-agent PR review (6 specialists, validator, fixer). |
26
+ | `/apt:prototype` | Question-driven throwaway prototyping. |
27
+ | `/apt:quick` | Fast task execution — skip planning. |
28
+ | `/apt:release-notes` | Persona-aware user-facing release notes. |
29
+ | `/apt:resume` | Restore context from paused session / crash. |
30
+ | `/apt:review` | Task-level code review (6-pass fix-all pipeline). |
31
+ | `/apt:roadmap` | Manage per-scope roadmaps (milestones, phases). |
32
+ | `/apt:roundtable` | 10-agent structured debate w/ supermajority vote. |
33
+ | `/apt:run` | Full pipeline — plan/execute/verify/review. |
34
+ | `/apt:scan` | Build/refresh the .aperant/features/ registry. |
35
+ | `/apt:setup` | Configure Aperant preferences. |
36
+ | `/apt:ship` | Open PR with QA scores + decision traceability. |
37
+ | `/apt:spar` | Adversarial sparring loop between two CLIs (max 3 rounds). |
38
+ | `/apt:stress-test` | Scenario simulation to catch plan gaps. |
39
+ | `/apt:terminal` | Spawn a sibling Aperant terminal w/ its own worktree. |
40
+ | `/apt:triage` | Move a task through the 5-state triage machine. |
41
+ | `/apt:update` | Refresh installed skills/agents/hooks across runtimes. |
42
+ | `/apt:verify` | Validate implementation against spec (QA review loop). |
43
+ | `/apt:verify-proof` | Visual proof-of-work verification (screenshots, BETA). |
44
+ | `/apt:watch-ci` | Post-ship CI watcher (poll, auto-fix red, push). |
45
+ | `/apt:zoom-out` | Orient yourself in an unfamiliar area — one-page summary. |
46
+
47
+ ## Dispatch recipe
48
+
49
+ Spawn a Claude Code CLI in a fresh terminal, then send the slash:
50
+
51
+ ```
52
+ spawnTerminal({ projectPath, cwd, cliCommand: 'claude --dangerously-skip-permissions', ... })
53
+ sendToTerminal(terminalId, '/apt:plan <terse task description>\r', ...)
54
+ ```
55
+
56
+ Codex / Gemini / OpenCode ports exist — swap `cliCommand` accordingly.
57
+ Skill semantics are identical across CLIs.
58
+
59
+ ## Observe-then-act
60
+
61
+ Read what a sub-terminal produced via `readFromTerminal(terminalId,
62
+ {tailBytes?})`. Use AFTER a write to confirm the skill took. NEVER assume
63
+ the write landed — observe.
@@ -97,10 +97,21 @@ Write (use when needed, no human approval gating):
97
97
  - `listTerminals()` — fleet snapshot (cwd, busyState, isCLIMode).
98
98
  - `sendToTerminal(terminalId, input, requestId, reasoning)` — tap-on-
99
99
  shoulder. Always one line. Append `\r` to submit. NEVER multi-line essay.
100
+ - `readFromTerminal(terminalId, {tailBytes?})` — snapshot recent PTY
101
+ output (~100 KB cap). Use AFTER `sendToTerminal` to confirm the write
102
+ took. NEVER assume — observe. On self-hosted web / cloud the host may
103
+ return `{output: null, error: 'host not action-capable in this mode'}`;
104
+ fall back to `readEventLog` polling there.
100
105
  - `destroyTerminal(terminalId, requestId, reasoning)` — irreversible.
101
106
  Prefer graceful `sendToTerminal('exit\r')`.
102
107
  - `emitIntent({...})` — audit envelope for non-tool decisions.
103
108
 
109
+ ## Framework knowledge
110
+
111
+ The auto-injected `conductor-framework-context` block at the very top of
112
+ this system prompt lists every `/apt:*` skill you can dispatch into a
113
+ sub-terminal. Consult it BEFORE deciding which skill to send.
114
+
104
115
  Tool surface depends on host. If `spawnTerminal` is not in your tools,
105
116
  you are in observe-only mode — do not promise spawns; describe what you
106
117
  WOULD do.
@@ -40,6 +40,7 @@ Confirm a shipped PR has merged on GitHub, then run the closer side of the task
40
40
  - `.aperant/events/{today}.jsonl` — emits `task.closed.merged`.
41
41
  - `.aperant/config.json` — strips `authorship_overrides['pr-{N}']` entries for merged PRs.
42
42
  - `.aperant/roadmap/{scope}/**` — linked-phase flip (when `task_isolation.auto_close_phase: true`).
43
+ - `.aperant/ci-watches/{pr}.json` — removed for each merged PR (BUG-027 (b) side-effect: prevents watcher state files leaking past PR-terminal-state). Idempotent — already-removed state is a no-op. For retroactive cleanup of orphan state files left behind by pre-fix runs, use `apt-tools ci-watch sweep . --orphaned`.
43
44
  </state_files>
44
45
 
45
46
  <process>
@@ -17,7 +17,7 @@ execution_modes:
17
17
  - step
18
18
  - research
19
19
  allowed-tools: "Bash, Read, Grep, Glob, Write"
20
- argument-hint: "apt:discuss [--brainstorm] [topic]"
20
+ argument-hint: "apt:discuss [--brainstorm] [--grill] [topic]"
21
21
  gates: []
22
22
  ---
23
23
  <objective>
@@ -183,10 +183,11 @@ If any file is missing, proceed with what's available. The framework works with
183
183
  Extract the task description from `$ARGUMENTS`:
184
184
 
185
185
  1. Strip mode flags (`--assumptions`, `--power`, `--auto`, `--review-auto`, `--continue`) from arguments
186
- 2. The remaining text is the task description
187
- 3. If task description is empty but `state.json` has an `active_task`, use that task's description
188
- 4. If still empty, ask: "What are you working on?"
189
- 5. Generate a `task-id` slug from the description: lowercase, hyphens, max 40 characters
186
+ 2. Strip the **`--grill`** overlay flag from arguments (orthogonal to the mode flags — see Section 6.5). `--grill` may combine with any mode; standalone `--grill` defaults to Interactive.
187
+ 3. The remaining text is the task description
188
+ 4. If task description is empty but `state.json` has an `active_task`, use that task's description
189
+ 5. If still empty, ask: "What are you working on?"
190
+ 6. Generate a `task-id` slug from the description: lowercase, hyphens, max 40 characters
190
191
  - Example: "Add OAuth login with Google" -> `add-oauth-login-with-google`
191
192
 
192
193
  ## 3.5. Brainstorm (skip if you picked decision-lock in Section 1)
@@ -564,6 +565,47 @@ Review-Auto is Auto Mode **plus one human checkpoint at the batch end**. It does
564
565
 
565
566
  Do NOT introduce per-decision staging ("show me D-01, wait, show me D-02, wait...") — that collapses review-auto into spaced interactive mode and defeats the point of joint reasoning up front. Do NOT skip the pause ("autonomy is high, let's just write it") — that collapses review-auto into auto. The one pause at the end is the whole identity of this mode.
566
567
 
568
+ ## 6.5. Grill Mode (`--grill` flag — Pocock `grill-with-docs` overlay)
569
+
570
+ **Activate when:** the user invoked the skill with `--grill`. This is an **overlay**, not a mode — it stacks on top of whichever Section 6 mode is active (Interactive by default; combine with `--auto` etc. as desired). The overlay does two things: (1) it applies Pocock's 4 grill moves during decision resolution; (2) it fires inline writes to CONTEXT.md and ADRs as terms resolve and decisions pass the Nygard 3-gate.
571
+
572
+ The discipline this overlay loads is already in [`appendices/grill-discipline.md`](./appendices/grill-discipline.md) — re-read the reframe sentence and the autonomy degradation table before each grill turn. **Do NOT duplicate that content here.** What follows is only the moves + writer-call instructions specific to the overlay.
573
+
574
+ ### The 4 grill moves (apply during gray-area resolution)
575
+
576
+ 1. **Challenge against the glossary.** When the user uses a term that conflicts with an existing CONTEXT.md term-block, call it out immediately: *"Your glossary defines 'cancellation' as X, but you seem to mean Y — which is it?"* Read `CONTEXT.md` (or per-context CONTEXT files via `CONTEXT-MAP.md`) when the overlay activates; skip silently if absent.
577
+ 2. **Sharpen fuzzy language.** When the user uses vague or overloaded terms, propose a precise canonical term: *"You're saying 'account' — do you mean Customer or User? Those are different things."*
578
+ 3. **Stress-test with concrete scenarios.** When domain relationships are being discussed, invent specific scenarios that probe edge cases and force precision about the boundaries between concepts.
579
+ 4. **Cross-reference with code.** When the user states how something works, check whether the code agrees. If you find a contradiction, surface it: *"Your code cancels entire Orders, but you just said partial cancellation is possible — which is right?"*
580
+
581
+ ### Inline writer calls (NOT batched)
582
+
583
+ When a term resolves with confidence during the grill, invoke `apt-tools context write` to upsert the term-block into CONTEXT.md **right there** — do NOT batch:
584
+
585
+ ```bash
586
+ node .aperant/deps/node_modules/@aperant/framework/bin/apt-tools.mjs context write . \
587
+ --term "Plan thread" \
588
+ --definition "<one-line definition>" \
589
+ --aliases-to-avoid "Plan session,plan chat" \
590
+ --cardinality "one-to-many"
591
+ ```
592
+
593
+ **Lazy creation:** if no `CONTEXT.md` exists at the project root (or in the relevant per-context directory when `CONTEXT-MAP.md` is present), the first resolved term creates the file. Do NOT create CONTEXT.md upfront with placeholder content.
594
+
595
+ **Glossary-only rule:** CONTEXT.md is a glossary of domain terms — NO implementation details, NO spec content, NO scratch-pad notes. Implementation lives in `spec.md` / `implementation_plan.json`; scratch lives in `.aperant/context/notes/{task-id}.md`. Term-blocks are user-facing concepts (e.g. "Plan thread", "Sparring round"), not code identifiers (e.g. "ChatSession", "useTaskStore").
596
+
597
+ When a decision passes the **Nygard 3-gate**, offer to write an ADR via `apt-tools adr write .`. The 3-gate (ALL three must hold — miss one and skip the ADR):
598
+
599
+ 1. **Hard to reverse** — the cost of changing your mind later is meaningful.
600
+ 2. **Surprising without context** — a future reader will wonder *"why did they do it this way?"*.
601
+ 3. **Result of a real trade-off** — there were genuine alternatives and you picked one for specific reasons.
602
+
603
+ If only one or two hold, the decision belongs in `.aperant/context/notes/{task-id}.md` (locked-decisions list), not in an ADR.
604
+
605
+ ### Autonomy interaction
606
+
607
+ `--grill` does not change the autonomy degradation already specified in [`appendices/grill-discipline.md`](./appendices/grill-discipline.md). Autonomy 1 grills every term/decision interactively; Autonomy 2 batches recommendations; Autonomy 3 auto-locks with the three escalation triggers (conflict-with-locked, critical-path file, no-defensible-default). The overlay simply ensures that whichever autonomy path runs, the writer CLIs fire as side-effects of the resolution work.
608
+
567
609
  ## 7. Advanced Elicitation (DEEP Tasks Only)
568
610
 
569
611
  After all decisions are locked, check the task track. If the track is DEEP (from state.json or router context), behavior depends on the resolved mode from Section 6's precedence chain (D-07):
@@ -383,11 +383,20 @@ executor commits introduce a new feature surface without registering it.
383
383
 
384
384
  ```bash
385
385
  node packages/framework/bin/apt-tools.mjs features-audit . \
386
+ --task-id "$TASK_ID" \
386
387
  --diff-files "$(git diff --name-only HEAD^ HEAD | tr '\n' ',')" \
387
388
  --apply-stubs
388
389
  ```
389
390
 
390
391
  Notes:
392
+ - `--task-id $TASK_ID` (BUG-025b) is mandatory when the executor runs
393
+ from the main-repo cwd instead of inside the worktree (the
394
+ orchestrator's common path). features-audit resolves the worktree's
395
+ `.aperant/features/` from the active task record and writes there,
396
+ preventing generated `*.json` from leaking into main. When invoked
397
+ from the worktree cwd directly, `--task-id` is a no-op (layer 1
398
+ detection short-circuits). Pass `--no-worktree-redirect` only when
399
+ you intentionally want to write to the invoking cwd.
391
400
  - `--apply-stubs` only runs when the matched surface's policy is
392
401
  `auto-update` (the default for `.aperant/features/*.json`). Users who
393
402
  opted out via `/apt:setup` Batch 7 get a no-op — the command still
@@ -99,6 +99,18 @@ For STANDARD and COMPLEX tasks:
99
99
  - Test files that will need updates
100
100
  - Configuration that may need changes
101
101
 
102
+ ### 4.4. React state guidance — sync-store vs render-committed ref (BUG-025-planner)
103
+
104
+ When a planned event handler fires a flush/persist immediately after mutating a Zustand/Jotai/refs-stored store, the spec MUST recommend reading from `store.getState()` (or the equivalent direct-read primitive) on the synchronous path, NOT from a `useRef`-populated-by-`useEffect`.
105
+
106
+ Why: refs populated via `useEffect` lag the store by exactly one render cycle. A handler that mutates the store and immediately reads the ref sees the pre-mutation value, silently corrupting persists and order-of-operations contracts. Reference pattern: `apps/desktop/src/renderer/src/App.tsx::runUpsertForIds` (post-fix commit `4c263856`).
107
+
108
+ Investigation checklist when the task touches a Zustand/Jotai store or any handler that does flush-after-mutate:
109
+
110
+ - Grep for `useRef(` references that cache store state (e.g. `const fooRef = useRef(foo)` populated by `useEffect(() => { fooRef.current = foo }, [foo])`).
111
+ - If the spec or planned subtasks read from such a ref on a synchronous path that ALSO mutates the store, recommend `store.getState()` (or `useFooStore.getState()`) as the read primitive.
112
+ - Note the caveat explicitly in the spec's Implementation Decisions section so the executor doesn't silently revert it.
113
+
102
114
  ### 4.5. Consume design.md (C24)
103
115
 
104
116
  If `{task_dir}/design.md` exists (emitted by a prior `/apt:design` run), load it before decomposing subtasks:
@@ -257,7 +257,7 @@ When the result is `unknown`, treat it as `external` for safety and prompt the u
257
257
  Authorship could not be auto-detected for PR #${PR_NUMBER}. Treat as [owned / external]? (default: external)
258
258
  ```
259
259
 
260
- If `autonomy_level >= 3` (yolo), skip the prompt and lock in `external`. Persist the user's answer to BOTH `pr-state.json:authorship` AND `config.json:pr_review.authorship_overrides['pr-${PR_NUMBER}']` so subsequent rounds don't re-ask.
260
+ If `autonomy_level >= 3` (yolo), skip the prompt and lock in `external`. Persist the user's answer to `pr-state.json:authorship` so subsequent rounds don't re-ask. (Per C56 A3 — authorship overrides moved from `config.json:pr_review.authorship_overrides` to per-PR `pr-state.json` so they GC with the pr-review round. Legacy `config.json` entries are still read with a deprecation warning + auto-promoted to pr-state on next `init-pr`; do NOT write to `config.json` from new code.)
261
261
 
262
262
  Store the result as `AUTHORSHIP_MODE` and use it as a gate at every later phase:
263
263
 
@@ -1195,6 +1195,12 @@ Take all confirmed, fixable findings and group them into up to 3 independent gro
1195
1195
 
1196
1196
  #### Step 3: Spawn Fix Agents
1197
1197
 
1198
+ **Capture the iteration-start SHA BEFORE spawning fixers** (used by both the Step 4b audit gate AND the per-fixer Pre-Return Self-Audit added in BUG-016 — fixers now commit atomically per finding, and the audit window is scoped by this SHA):
1199
+
1200
+ ```bash
1201
+ ITERATION_START_SHA=$(cd "${WORKTREE_PATH}" && git rev-parse HEAD)
1202
+ ```
1203
+
1198
1204
  For each fix group, spawn a fix agent. Read the agent definition from `.claude/agents/apt-pr-review-fixer.md` and fill in:
1199
1205
 
1200
1206
  | Placeholder | Value |
@@ -1207,6 +1213,7 @@ For each fix group, spawn a fix agent. Read the agent definition from `.claude/a
1207
1213
  | `[CRITICAL_APPROVAL]` | `true` or `false` for each critical finding in this group |
1208
1214
  | `[PARALLEL_FIXERS]` | `true` if more than 1 fixer is spawned this iteration |
1209
1215
  | `[WORKTREE_PATH]` | The worktree path — fix agents edit files HERE, not in the user's working directory |
1216
+ | `[ITERATION_START_SHA]` | The SHA captured BEFORE spawning fixers (see Step 4b's `ITERATION_START_SHA=$(...)` capture). Required for BUG-016 commit-discipline Pre-Return Self-Audit. |
1210
1217
 
1211
1218
  ```
1212
1219
  Agent(
@@ -1260,7 +1267,9 @@ If `--since-sha` is **omitted**, the CLI falls back to `git merge-base HEAD orig
1260
1267
 
1261
1268
  Rule of thumb: pass `--since-sha "${ITERATION_START_SHA}"` on every audit invocation. The merge-base fallback exists only so a missing flag doesn't flip every standard-branch-workflow repo into a false-positive hallucination — it is NOT a replacement for the explicit flag.
1262
1269
 
1263
- The CLI returns a JSON envelope with `verdict` ∈ `verified | hallucinated | skipped`, writes `iterations/${ITERATION}/audit.json` (append-only), and bumps `metadata.json.fixer_hallucinations_total` on every `hallucinated` outcome. The envelope's `observed.since_sha` + `observed.since_sha_source` fields record which SHA was used and where it came from (`flag` | `merge-base` | `null`). The same envelope is used for the fixer and the self-reviewer (Phase 7) — `--fixer self-reviewer` reads from `self-review.md` instead of `fixes-applied-group{N}.md`.
1270
+ The CLI returns a JSON envelope with `verdict` ∈ `verified | hallucinated | skipped`, writes `iterations/${ITERATION}/audit.json` (append-only), and bumps `metadata.json.fixer_hallucinations_total` on every `hallucinated` outcome. The envelope's `observed.since_sha` + `observed.since_sha_source` fields record which SHA was used and where it came from (`flag` | `merge-base` | `null`). The same envelope is used for the fixer and the self-reviewer (Phase 7) — `--fixer self-reviewer` reads from `self-review.md`.
1271
+
1272
+ **Canonical fix-report filename per fixer (BUG-030):** each fixer agent writes to `fixes-applied-${FIXER_NAME}.md` (e.g. `fixes-applied-fixer-1.md`). The audit CLI resolves candidates in strict order: `fixes-applied-group{N}.md` (legacy group-named, pre-BUG-030 reviews) → `fixes-applied-fixer-{N}.md` (NEW fixer-named) → `fixes-applied-${FIXER_NAME}.md` (exact match, preferred for non-numeric fixer names) → `fixes-applied.md` (legacy unscoped, single-fixer reviews only). Writing the canonical name eliminates the cross-fixer false-positive `hallucinated` verdict that fired when two parallel fixers shared `fixes-applied.md`.
1264
1273
 
1265
1274
  | Verdict | Orchestrator Action |
1266
1275
  |---------|---------------------|
@@ -279,18 +279,29 @@ skill MUST exit silently regardless of the config value, so spawned subagents
279
279
  never block on a prompt that no human will answer.
280
280
 
281
281
  ```bash
282
- # Pseudocode the model executes inline:
282
+ # Pseudocode the model executes inline.
283
+ # AUDIT-001: `preferences.quick_task_post_verify` is per-device — read from
284
+ # the MERGED config (shared `.aperant/config.json` + local
285
+ # `.aperant/config.local.json`). Local wins on collision. Reading raw
286
+ # `config.json` only would miss per-device overrides.
283
287
  node -e '
284
288
  const fs = require("fs");
285
289
  const path = require("path");
286
- const cfgPath = path.join(process.cwd(), ".aperant/config.json");
290
+ const readJsonOrEmpty = (p) => { try { return JSON.parse(fs.readFileSync(p, "utf-8")) ?? {} } catch { return {} } };
291
+ const shared = readJsonOrEmpty(path.join(process.cwd(), ".aperant/config.json"));
292
+ const local = readJsonOrEmpty(path.join(process.cwd(), ".aperant/config.local.json"));
293
+ function merge(a, b) {
294
+ if (a === null || typeof a !== "object" || Array.isArray(a)) return b;
295
+ if (b === null || typeof b !== "object" || Array.isArray(b)) return b;
296
+ const out = { ...a };
297
+ for (const k of Object.keys(b)) out[k] = (k in a) ? merge(a[k], b[k]) : b[k];
298
+ return out;
299
+ }
300
+ const cfg = merge(shared, local);
287
301
  let mode = "ask";
288
- try {
289
- const cfg = JSON.parse(fs.readFileSync(cfgPath, "utf-8"));
290
- if (cfg && cfg.preferences && cfg.preferences.quick_task_post_verify) {
291
- mode = cfg.preferences.quick_task_post_verify;
292
- }
293
- } catch {}
302
+ if (cfg.preferences && cfg.preferences.quick_task_post_verify) {
303
+ mode = cfg.preferences.quick_task_post_verify;
304
+ }
294
305
  if (mode === "never" || !process.stdin.isTTY) process.exit(0);
295
306
  if (mode === "always") { /* invoke apt:verify {task-id} */ process.exit(0); }
296
307
  // mode === "ask": readline prompt with 30s timeout, default = skip.
@@ -41,6 +41,7 @@ Parse the investigation query. Identify:
41
41
  3. Read key files to understand the full picture
42
42
  4. Follow import chains to map dependencies
43
43
  5. Check tests for behavioral documentation
44
+ 6. **Report which refs cache store state on a render-cycle delay** (BUG-025-planner): when investigating React state or any Zustand/Jotai store touched by handlers, grep for `useRef(` patterns populated via `useEffect`. Flag them explicitly — they lag the store by one render and any sync-mutate-then-read code path against them silently corrupts. Reference pattern: `apps/desktop/src/renderer/src/App.tsx::runUpsertForIds` (post-fix commit `4c263856`).
44
45
 
45
46
  ## 3. Report Findings
46
47
  Produce a clear, structured answer:
@@ -1111,6 +1111,34 @@ The selective-edit pass through Batch 9 MUST respect the §1b dispatch — it do
1111
1111
 
1112
1112
  ## 4. Map Answers to Config
1113
1113
 
1114
+ **AUDIT-001 — file-routing contract for per-device fields (UPDATED 0.7.2):** the
1115
+ following five fields are PER-DEVICE and MUST land in `.aperant/config.local.json`
1116
+ (gitignored), NOT the shared `.aperant/config.json`:
1117
+ - `verification.open_report` — covered in the "Auto-Open" mapping below.
1118
+ - `multi_model.cross_verification.tools` — covered in the "Cross-Verification" mapping below.
1119
+ - `preferences.date_format` — covered in the "Date Format" mapping below.
1120
+ - `preferences.time_format` — covered in the "Time Format" mapping below.
1121
+ - `preferences.quick_task_post_verify` — covered in apt-quick SKILL config block.
1122
+
1123
+ All other fields (including `verification.evidence_capture`,
1124
+ `multi_model.cross_verification.enabled`, `multi_model.video_review.*`,
1125
+ `preferences.task_index`, every `orchestration.*` value) stay in shared
1126
+ `.aperant/config.json`.
1127
+
1128
+ Implementation: use the framework's `writeLocalConfigField(targetDir, dotPath, value)`
1129
+ helper from `packages/framework/src/cli/config/load.mjs` (or its shell-out
1130
+ equivalent via `apt-tools config write . --local --key <dotpath> --value <json>`)
1131
+ for the five fields above. NEVER hand-roll `JSON.parse(readFileSync('.aperant/config.json'))`
1132
+ followed by `writeFileSync('.aperant/config.json', ...)` for these fields — it
1133
+ will land per-device data in the shared file and re-introduce the
1134
+ shared-config trap AUDIT-001 was designed to close.
1135
+
1136
+ Reads of these fields anywhere in the framework MUST go through
1137
+ `loadMergedProjectConfig(targetDir)` or `readLocalOrSharedField(targetDir, dotPath)`
1138
+ so per-device overrides are honored.
1139
+
1140
+ ---
1141
+
1114
1142
  Map the user's selections to config values:
1115
1143
 
1116
1144
  **Verify Mode:**
@@ -1180,13 +1208,16 @@ Note: task ids are slug-first since v0.6.6 — the date-format setting controls
1180
1208
 
1181
1209
  ## 5. Write Config
1182
1210
 
1183
- Write merged config to `.aperant/config.json`:
1211
+ Write merged config to two files per AUDIT-001 routing (see Step 4 block):
1212
+
1213
+ - Shared `.aperant/config.json` — all project policy values (the bulk of the answers).
1214
+ - Per-device `.aperant/config.local.json` — the five AUDIT-001 fields enumerated in Step 4.
1184
1215
 
1185
1216
  ```bash
1186
1217
  mkdir -p .aperant
1187
1218
  ```
1188
1219
 
1189
- Write the JSON file with 2-space indentation. Bump `version` to 4 if upgrading from an older config (versions 2/3 load forward-compatibly — the new `tdd` block is optional).
1220
+ Write each JSON file with 2-space indentation. Bump shared `config.json`'s `version` to 4 if upgrading from an older config (versions 2/3 load forward-compatibly — the new `tdd` block is optional). `config.local.json` is gitignored by `.aperant/.gitignore` — do not check it in.
1190
1221
 
1191
1222
  ## 6. Save as Global Defaults (Optional)
1192
1223