mirror-mind 0.0.1 → 0.33.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 (474) hide show
  1. package/.claude/hooks/log-assistant-reply.sh +85 -0
  2. package/.claude/hooks/log-session-end.sh +85 -0
  3. package/.claude/hooks/log-user-prompt.sh +85 -0
  4. package/.claude/hooks/mirror-inject.sh +85 -0
  5. package/.claude/hooks/session-start.sh +85 -0
  6. package/.gemini/hooks/log-assistant.sh +85 -0
  7. package/.gemini/hooks/log-user.sh +85 -0
  8. package/.gemini/hooks/session-end.sh +85 -0
  9. package/.gemini/hooks/session-start.sh +85 -0
  10. package/.pi/extensions/mirror-logger.ts +646 -0
  11. package/.pi/skills/mm-backup/SKILL.md +21 -0
  12. package/.pi/skills/mm-build/SKILL.md +1206 -0
  13. package/.pi/skills/mm-consolidate/SKILL.md +112 -0
  14. package/.pi/skills/mm-consult/SKILL.md +70 -0
  15. package/.pi/skills/mm-conversations/SKILL.md +16 -0
  16. package/.pi/skills/mm-discard/SKILL.md +39 -0
  17. package/.pi/skills/mm-explore/SKILL.md +255 -0
  18. package/.pi/skills/mm-help/SKILL.md +74 -0
  19. package/.pi/skills/mm-identity/SKILL.md +96 -0
  20. package/.pi/skills/mm-journal/SKILL.md +16 -0
  21. package/.pi/skills/mm-journey/SKILL.md +23 -0
  22. package/.pi/skills/mm-journeys/SKILL.md +15 -0
  23. package/.pi/skills/mm-memories/SKILL.md +17 -0
  24. package/.pi/skills/mm-mirror/SKILL.md +98 -0
  25. package/.pi/skills/mm-mute/SKILL.md +18 -0
  26. package/.pi/skills/mm-new/SKILL.md +18 -0
  27. package/.pi/skills/mm-recall/SKILL.md +17 -0
  28. package/.pi/skills/mm-release-notes/SKILL.md +52 -0
  29. package/.pi/skills/mm-seed/SKILL.md +19 -0
  30. package/.pi/skills/mm-shadow/SKILL.md +117 -0
  31. package/.pi/skills/mm-soul/SKILL.md +502 -0
  32. package/.pi/skills/mm-tasks/SKILL.md +24 -0
  33. package/.pi/skills/mm-update/SKILL.md +32 -0
  34. package/.pi/skills/mm-week/SKILL.md +28 -0
  35. package/.pi/skills/mm-welcome/SKILL.md +24 -0
  36. package/AGENTS.md +188 -0
  37. package/README.md +126 -9
  38. package/bin/loader.js +67 -0
  39. package/bin/mirror-hook.js +7 -0
  40. package/bin/mirror.js +7 -0
  41. package/docs/releases/index.md +100 -0
  42. package/docs/releases/pending-cutoffs.md +510 -0
  43. package/docs/releases/v0.10.0.md +123 -0
  44. package/docs/releases/v0.10.1.md +66 -0
  45. package/docs/releases/v0.10.10.md +51 -0
  46. package/docs/releases/v0.10.11.md +39 -0
  47. package/docs/releases/v0.10.12.md +57 -0
  48. package/docs/releases/v0.10.13.md +35 -0
  49. package/docs/releases/v0.10.14.md +42 -0
  50. package/docs/releases/v0.10.15.md +53 -0
  51. package/docs/releases/v0.10.16.md +35 -0
  52. package/docs/releases/v0.10.17.md +43 -0
  53. package/docs/releases/v0.10.2.md +64 -0
  54. package/docs/releases/v0.10.3.md +78 -0
  55. package/docs/releases/v0.10.4.md +42 -0
  56. package/docs/releases/v0.10.5.md +57 -0
  57. package/docs/releases/v0.10.6.md +47 -0
  58. package/docs/releases/v0.10.7.md +53 -0
  59. package/docs/releases/v0.10.8.md +49 -0
  60. package/docs/releases/v0.10.9.md +37 -0
  61. package/docs/releases/v0.11.0.md +86 -0
  62. package/docs/releases/v0.12.0.md +67 -0
  63. package/docs/releases/v0.13.0.md +64 -0
  64. package/docs/releases/v0.14.0.md +68 -0
  65. package/docs/releases/v0.15.0.md +48 -0
  66. package/docs/releases/v0.16.0.md +50 -0
  67. package/docs/releases/v0.16.1.md +55 -0
  68. package/docs/releases/v0.16.2.md +36 -0
  69. package/docs/releases/v0.17.0.md +50 -0
  70. package/docs/releases/v0.17.1.md +58 -0
  71. package/docs/releases/v0.17.2.md +42 -0
  72. package/docs/releases/v0.17.3.md +58 -0
  73. package/docs/releases/v0.18.0.md +84 -0
  74. package/docs/releases/v0.18.1.md +51 -0
  75. package/docs/releases/v0.18.2.md +69 -0
  76. package/docs/releases/v0.19.0.md +85 -0
  77. package/docs/releases/v0.19.1.md +46 -0
  78. package/docs/releases/v0.20.0.md +85 -0
  79. package/docs/releases/v0.21.0.md +61 -0
  80. package/docs/releases/v0.21.1.md +47 -0
  81. package/docs/releases/v0.22.0.md +77 -0
  82. package/docs/releases/v0.22.1.md +42 -0
  83. package/docs/releases/v0.23.0.md +105 -0
  84. package/docs/releases/v0.24.0.md +125 -0
  85. package/docs/releases/v0.25.0.md +107 -0
  86. package/docs/releases/v0.26.0.md +139 -0
  87. package/docs/releases/v0.26.1.md +65 -0
  88. package/docs/releases/v0.26.2.md +43 -0
  89. package/docs/releases/v0.27.0.md +63 -0
  90. package/docs/releases/v0.28.0.md +59 -0
  91. package/docs/releases/v0.29.0.md +61 -0
  92. package/docs/releases/v0.29.1.md +59 -0
  93. package/docs/releases/v0.29.2.md +59 -0
  94. package/docs/releases/v0.29.3.md +93 -0
  95. package/docs/releases/v0.30.0.md +75 -0
  96. package/docs/releases/v0.30.1.md +93 -0
  97. package/docs/releases/v0.30.2.md +66 -0
  98. package/docs/releases/v0.31.0.md +122 -0
  99. package/docs/releases/v0.31.1.md +142 -0
  100. package/docs/releases/v0.31.10.md +118 -0
  101. package/docs/releases/v0.31.11.md +88 -0
  102. package/docs/releases/v0.31.12.md +105 -0
  103. package/docs/releases/v0.31.13.md +99 -0
  104. package/docs/releases/v0.31.14.md +97 -0
  105. package/docs/releases/v0.31.2.md +115 -0
  106. package/docs/releases/v0.31.3.md +142 -0
  107. package/docs/releases/v0.31.4.md +117 -0
  108. package/docs/releases/v0.31.5.md +155 -0
  109. package/docs/releases/v0.31.6.md +132 -0
  110. package/docs/releases/v0.31.7.md +132 -0
  111. package/docs/releases/v0.31.8.md +120 -0
  112. package/docs/releases/v0.31.9.md +120 -0
  113. package/docs/releases/v0.32.0.md +261 -0
  114. package/docs/releases/v0.32.1.md +59 -0
  115. package/docs/releases/v0.33.0.md +164 -0
  116. package/docs/releases/v0.8.0.md +118 -0
  117. package/docs/releases/v0.9.0.md +98 -0
  118. package/docs/releases/v0.9.1.md +83 -0
  119. package/package.json +102 -6
  120. package/plugins/mirror-mind/.claude-plugin/plugin.json +17 -0
  121. package/plugins/mirror-mind/hooks/hooks.json +62 -0
  122. package/plugins/mirror-mind/hooks/log-assistant-reply.sh +98 -0
  123. package/plugins/mirror-mind/hooks/log-session-end.sh +98 -0
  124. package/plugins/mirror-mind/hooks/log-user-prompt.sh +98 -0
  125. package/plugins/mirror-mind/hooks/mirror-inject.sh +98 -0
  126. package/plugins/mirror-mind/hooks/session-start.sh +98 -0
  127. package/plugins/mirror-mind/skills/mm-backup/SKILL.md +27 -0
  128. package/plugins/mirror-mind/skills/mm-build/SKILL.md +1206 -0
  129. package/plugins/mirror-mind/skills/mm-consolidate/SKILL.md +112 -0
  130. package/plugins/mirror-mind/skills/mm-consult/SKILL.md +83 -0
  131. package/plugins/mirror-mind/skills/mm-conversations/SKILL.md +17 -0
  132. package/plugins/mirror-mind/skills/mm-discard/SKILL.md +40 -0
  133. package/plugins/mirror-mind/skills/mm-explore/SKILL.md +241 -0
  134. package/plugins/mirror-mind/skills/mm-help/SKILL.md +104 -0
  135. package/plugins/mirror-mind/skills/mm-identity/SKILL.md +96 -0
  136. package/plugins/mirror-mind/skills/mm-journal/SKILL.md +21 -0
  137. package/plugins/mirror-mind/skills/mm-journey/SKILL.md +37 -0
  138. package/plugins/mirror-mind/skills/mm-journeys/SKILL.md +15 -0
  139. package/plugins/mirror-mind/skills/mm-memories/SKILL.md +20 -0
  140. package/plugins/mirror-mind/skills/mm-mirror/SKILL.md +67 -0
  141. package/plugins/mirror-mind/skills/mm-mute/SKILL.md +18 -0
  142. package/plugins/mirror-mind/skills/mm-new/SKILL.md +18 -0
  143. package/plugins/mirror-mind/skills/mm-recall/SKILL.md +17 -0
  144. package/plugins/mirror-mind/skills/mm-release-notes/SKILL.md +31 -0
  145. package/plugins/mirror-mind/skills/mm-seed/SKILL.md +15 -0
  146. package/plugins/mirror-mind/skills/mm-shadow/SKILL.md +117 -0
  147. package/plugins/mirror-mind/skills/mm-soul/SKILL.md +488 -0
  148. package/plugins/mirror-mind/skills/mm-tasks/SKILL.md +36 -0
  149. package/plugins/mirror-mind/skills/mm-update/SKILL.md +30 -0
  150. package/plugins/mirror-mind/skills/mm-week/SKILL.md +46 -0
  151. package/plugins/mirror-mind/skills/mm-welcome/SKILL.md +22 -0
  152. package/scripts/codex-hooks/session-end.sh +85 -0
  153. package/scripts/codex-hooks/session-start.sh +85 -0
  154. package/scripts/codex-mirror.sh +48 -0
  155. package/templates/identity/README.md +119 -0
  156. package/templates/identity/ego/behavior.yaml +52 -0
  157. package/templates/identity/ego/constraints.yaml +15 -0
  158. package/templates/identity/ego/identity.yaml +43 -0
  159. package/templates/identity/journeys/personal-growth.yaml +39 -0
  160. package/templates/identity/organization/identity.yaml +24 -0
  161. package/templates/identity/organization/principles.yaml +17 -0
  162. package/templates/identity/personas/coach.yaml +94 -0
  163. package/templates/identity/personas/designer.yaml +93 -0
  164. package/templates/identity/personas/doctor.yaml +96 -0
  165. package/templates/identity/personas/engineer.yaml +77 -0
  166. package/templates/identity/personas/financial.yaml +97 -0
  167. package/templates/identity/personas/prompt-engineer.yaml +122 -0
  168. package/templates/identity/personas/researcher.yaml +88 -0
  169. package/templates/identity/personas/strategist.yaml +91 -0
  170. package/templates/identity/personas/teacher.yaml +95 -0
  171. package/templates/identity/personas/therapist.yaml +91 -0
  172. package/templates/identity/personas/thinker.yaml +74 -0
  173. package/templates/identity/personas/writer.yaml +76 -0
  174. package/templates/identity/self/config.yaml +16 -0
  175. package/templates/identity/self/soul.yaml +105 -0
  176. package/templates/identity/user/identity.yaml +30 -0
  177. package/ts/src/backup/staging.ts +62 -0
  178. package/ts/src/backup/zipBackup.ts +267 -0
  179. package/ts/src/backup/zipReader.ts +109 -0
  180. package/ts/src/backup/zipWriter.ts +148 -0
  181. package/ts/src/builder/activeCheckpoint.ts +134 -0
  182. package/ts/src/builder/aggregateStatus.ts +34 -0
  183. package/ts/src/builder/approve.ts +149 -0
  184. package/ts/src/builder/argv.ts +292 -0
  185. package/ts/src/builder/ariadMethod.ts +536 -0
  186. package/ts/src/builder/artifacts/artifactSurfaces.ts +106 -0
  187. package/ts/src/builder/artifacts/artifactWriter.ts +113 -0
  188. package/ts/src/builder/artifacts/closureArtifacts.ts +199 -0
  189. package/ts/src/builder/artifacts/deliveryStoryArtifacts.ts +316 -0
  190. package/ts/src/builder/artifacts/planArtifacts.ts +242 -0
  191. package/ts/src/builder/artifacts/scaffoldSections.ts +273 -0
  192. package/ts/src/builder/artifacts/scaffoldState.ts +227 -0
  193. package/ts/src/builder/artifacts/storyFiles.ts +61 -0
  194. package/ts/src/builder/artifacts/storyIndex.ts +166 -0
  195. package/ts/src/builder/cadence.ts +59 -0
  196. package/ts/src/builder/card.ts +192 -0
  197. package/ts/src/builder/checkpointRefused.ts +66 -0
  198. package/ts/src/builder/closure.ts +964 -0
  199. package/ts/src/builder/commands.ts +2053 -0
  200. package/ts/src/builder/cursorPosition.ts +176 -0
  201. package/ts/src/builder/cursorTransitions.ts +77 -0
  202. package/ts/src/builder/deliveryCursor.ts +577 -0
  203. package/ts/src/builder/deliveryStoryClosure.ts +521 -0
  204. package/ts/src/builder/deliveryStoryPlan.ts +536 -0
  205. package/ts/src/builder/deliveryStoryReady.ts +160 -0
  206. package/ts/src/builder/deliveryStoryRoadmapClosure.ts +151 -0
  207. package/ts/src/builder/expand.ts +336 -0
  208. package/ts/src/builder/flowUnit.ts +339 -0
  209. package/ts/src/builder/homeSurface.ts +122 -0
  210. package/ts/src/builder/implementationGuard.ts +125 -0
  211. package/ts/src/builder/index.ts +11 -0
  212. package/ts/src/builder/lifecycleRefusal.ts +92 -0
  213. package/ts/src/builder/lifecycleRibbon.ts +159 -0
  214. package/ts/src/builder/load.ts +313 -0
  215. package/ts/src/builder/methodAdoption.ts +113 -0
  216. package/ts/src/builder/methodDefinition.ts +429 -0
  217. package/ts/src/builder/methodInspection.ts +371 -0
  218. package/ts/src/builder/plan.ts +408 -0
  219. package/ts/src/builder/planPreauthorization.ts +265 -0
  220. package/ts/src/builder/prepare.ts +225 -0
  221. package/ts/src/builder/projectPaths.ts +64 -0
  222. package/ts/src/builder/pull.ts +356 -0
  223. package/ts/src/builder/pullCandidates.ts +463 -0
  224. package/ts/src/builder/pullCandidatesRender.ts +238 -0
  225. package/ts/src/builder/refinementField.ts +93 -0
  226. package/ts/src/builder/releaseIntent.ts +173 -0
  227. package/ts/src/builder/resumeState.ts +84 -0
  228. package/ts/src/builder/resumeSurface.ts +149 -0
  229. package/ts/src/builder/roadmapGrammar.ts +300 -0
  230. package/ts/src/builder/roadmapScan.ts +97 -0
  231. package/ts/src/builder/roadmapScope.ts +210 -0
  232. package/ts/src/builder/scopePhrases.ts +146 -0
  233. package/ts/src/builder/storyPaths.ts +196 -0
  234. package/ts/src/builder/storyPlanPreauthorization.ts +287 -0
  235. package/ts/src/builder/surfaceProtocol.ts +42 -0
  236. package/ts/src/builder/templateGeneration.ts +148 -0
  237. package/ts/src/builder/transition.ts +178 -0
  238. package/ts/src/consult/args.ts +99 -0
  239. package/ts/src/consult/core.ts +122 -0
  240. package/ts/src/consult/modelCatalog.ts +55 -0
  241. package/ts/src/consult/render.ts +47 -0
  242. package/ts/src/conversation/append.ts +414 -0
  243. package/ts/src/conversation/backfill.ts +387 -0
  244. package/ts/src/conversation/closeTail.ts +467 -0
  245. package/ts/src/conversation/extraction.ts +333 -0
  246. package/ts/src/conversation/extractionDriver.ts +130 -0
  247. package/ts/src/conversation/extractionRun.ts +70 -0
  248. package/ts/src/conversation/hookPayload.ts +51 -0
  249. package/ts/src/conversation/journeyInference.ts +165 -0
  250. package/ts/src/conversation/journeyRepair.ts +114 -0
  251. package/ts/src/conversation/lifecycleFaces.ts +197 -0
  252. package/ts/src/conversation/lifecycleWrites.ts +313 -0
  253. package/ts/src/conversation/listing.ts +77 -0
  254. package/ts/src/conversation/logger.ts +851 -0
  255. package/ts/src/conversation/loggerCli.ts +321 -0
  256. package/ts/src/conversation/loggerRuntime.ts +259 -0
  257. package/ts/src/conversation/metadataLifecycle.ts +443 -0
  258. package/ts/src/conversation/recall.ts +66 -0
  259. package/ts/src/conversation/sessionComposites.ts +258 -0
  260. package/ts/src/conversation/sessionImport.ts +90 -0
  261. package/ts/src/conversation/transcriptBackfill.ts +141 -0
  262. package/ts/src/cultivation/applyActions.ts +241 -0
  263. package/ts/src/cultivation/cluster.ts +86 -0
  264. package/ts/src/cultivation/consolidationStore.ts +281 -0
  265. package/ts/src/cultivation/promptContext.ts +62 -0
  266. package/ts/src/cultivation/propose.ts +305 -0
  267. package/ts/src/cultivation/scan.ts +155 -0
  268. package/ts/src/db/backupGate.ts +47 -0
  269. package/ts/src/db/bootstrap.ts +108 -0
  270. package/ts/src/db/bootstrapLock.ts +223 -0
  271. package/ts/src/db/copyGuard.ts +60 -0
  272. package/ts/src/db/database.ts +397 -0
  273. package/ts/src/db/decode.ts +66 -0
  274. package/ts/src/db/ftsIntegrity.ts +41 -0
  275. package/ts/src/db/migrateOnOpen.ts +214 -0
  276. package/ts/src/db/migrations.ts +576 -0
  277. package/ts/src/db/readyOnOpen.ts +35 -0
  278. package/ts/src/db/rowDecode.ts +42 -0
  279. package/ts/src/db/schema.ts +432 -0
  280. package/ts/src/db/schemaInventory.ts +225 -0
  281. package/ts/src/db/schemaInventorySnapshot.ts +2107 -0
  282. package/ts/src/db/schemaState.ts +91 -0
  283. package/ts/src/db/schemaTsDivergence.ts +114 -0
  284. package/ts/src/descriptor/descriptorRead.ts +49 -0
  285. package/ts/src/docs/docsLint.ts +265 -0
  286. package/ts/src/explorer/handoff.ts +522 -0
  287. package/ts/src/explorer/render.ts +335 -0
  288. package/ts/src/explorer/story.ts +769 -0
  289. package/ts/src/explorer/transition.ts +72 -0
  290. package/ts/src/extensions/bindings.ts +170 -0
  291. package/ts/src/extensions/catalog.ts +249 -0
  292. package/ts/src/extensions/catalogCommands.ts +513 -0
  293. package/ts/src/extensions/catalogWrites.ts +652 -0
  294. package/ts/src/extensions/contextRuntime.ts +325 -0
  295. package/ts/src/extensions/dispatch.ts +374 -0
  296. package/ts/src/extensions/errors.ts +24 -0
  297. package/ts/src/extensions/manifest.ts +356 -0
  298. package/ts/src/extensions/migrations.ts +350 -0
  299. package/ts/src/extraction/conversation.ts +304 -0
  300. package/ts/src/extraction/conversationMetadata.ts +206 -0
  301. package/ts/src/extraction/fencing.ts +106 -0
  302. package/ts/src/extraction/json.ts +17 -0
  303. package/ts/src/extraction/prompts.ts +470 -0
  304. package/ts/src/frontDoor/args.ts +30 -0
  305. package/ts/src/frontDoor/argvShape.ts +106 -0
  306. package/ts/src/frontDoor/buildLoadRuntime.ts +139 -0
  307. package/ts/src/frontDoor/buildRoute.ts +398 -0
  308. package/ts/src/frontDoor/cli.ts +1872 -0
  309. package/ts/src/frontDoor/cloneRoleGuard.ts +98 -0
  310. package/ts/src/frontDoor/consultRoute.ts +50 -0
  311. package/ts/src/frontDoor/contentTailRoute.ts +239 -0
  312. package/ts/src/frontDoor/conversationLoggerRoute.ts +83 -0
  313. package/ts/src/frontDoor/cultivationRoute.ts +210 -0
  314. package/ts/src/frontDoor/dbPath.ts +131 -0
  315. package/ts/src/frontDoor/dbSafetyToolsRoute.ts +240 -0
  316. package/ts/src/frontDoor/exploreRoute.ts +572 -0
  317. package/ts/src/frontDoor/extensionCatalogRoute.ts +252 -0
  318. package/ts/src/frontDoor/frontDoorLog.ts +57 -0
  319. package/ts/src/frontDoor/identityWrite.ts +36 -0
  320. package/ts/src/frontDoor/journeyWriteRoute.ts +26 -0
  321. package/ts/src/frontDoor/lifecycleWriteRoute.ts +110 -0
  322. package/ts/src/frontDoor/liveBackup.ts +100 -0
  323. package/ts/src/frontDoor/mirrorModeRoute.ts +163 -0
  324. package/ts/src/frontDoor/namedRefusal.ts +35 -0
  325. package/ts/src/frontDoor/nodeSupport.ts +24 -0
  326. package/ts/src/frontDoor/render/consolidate.ts +199 -0
  327. package/ts/src/frontDoor/render/conversations.ts +33 -0
  328. package/ts/src/frontDoor/render/cultivationShared.ts +21 -0
  329. package/ts/src/frontDoor/render/descriptor.ts +20 -0
  330. package/ts/src/frontDoor/render/detectPersona.ts +50 -0
  331. package/ts/src/frontDoor/render/icons.ts +13 -0
  332. package/ts/src/frontDoor/render/identity.ts +59 -0
  333. package/ts/src/frontDoor/render/identityRows.ts +17 -0
  334. package/ts/src/frontDoor/render/inspectPersona.ts +53 -0
  335. package/ts/src/frontDoor/render/journeyStatus.ts +78 -0
  336. package/ts/src/frontDoor/render/journeys.ts +79 -0
  337. package/ts/src/frontDoor/render/list.ts +41 -0
  338. package/ts/src/frontDoor/render/memories.ts +67 -0
  339. package/ts/src/frontDoor/render/recall.ts +49 -0
  340. package/ts/src/frontDoor/render/shadow.ts +155 -0
  341. package/ts/src/frontDoor/render/tasks.ts +99 -0
  342. package/ts/src/frontDoor/render/tasksImportSync.ts +63 -0
  343. package/ts/src/frontDoor/render/week.ts +113 -0
  344. package/ts/src/frontDoor/routing.ts +1001 -0
  345. package/ts/src/frontDoor/runtimeRoute.ts +623 -0
  346. package/ts/src/frontDoor/searchRoute.ts +166 -0
  347. package/ts/src/frontDoor/seedPaths.ts +98 -0
  348. package/ts/src/frontDoor/sessionStartWelcomeRoute.ts +166 -0
  349. package/ts/src/frontDoor/soulRoute.ts +433 -0
  350. package/ts/src/frontDoor/stdinSource.ts +37 -0
  351. package/ts/src/frontDoor/tasksImportSyncRoute.ts +110 -0
  352. package/ts/src/frontDoor/tasksWriteRoute.ts +101 -0
  353. package/ts/src/frontDoor/usage.ts +176 -0
  354. package/ts/src/guards/claudePlugin.ts +298 -0
  355. package/ts/src/guards/packContents.ts +306 -0
  356. package/ts/src/guards/piSourcedSkills.ts +70 -0
  357. package/ts/src/guards/retiredRouteShadows.ts +57 -0
  358. package/ts/src/guards/retiredSurfaces.ts +564 -0
  359. package/ts/src/hooks/claude.ts +214 -0
  360. package/ts/src/hooks/codex.ts +45 -0
  361. package/ts/src/hooks/gemini.ts +126 -0
  362. package/ts/src/hooks/main.ts +109 -0
  363. package/ts/src/hooks/mirrorState.ts +71 -0
  364. package/ts/src/hooks/payload.ts +73 -0
  365. package/ts/src/hooks/runtime.ts +179 -0
  366. package/ts/src/hooks/runtimeDetection.ts +34 -0
  367. package/ts/src/identity/applyConsolidationIdentityUpdate.ts +67 -0
  368. package/ts/src/identity/descriptorGenerate.ts +162 -0
  369. package/ts/src/identity/identityEdit.ts +143 -0
  370. package/ts/src/identity/identityKey.ts +77 -0
  371. package/ts/src/identity/identityRead.ts +69 -0
  372. package/ts/src/identity/identityStore.ts +80 -0
  373. package/ts/src/identity/journeyListing.ts +53 -0
  374. package/ts/src/identity/personaInspect.ts +44 -0
  375. package/ts/src/identity/personaListing.ts +37 -0
  376. package/ts/src/identity/setIdentity.ts +64 -0
  377. package/ts/src/index.ts +231 -0
  378. package/ts/src/init/init.ts +111 -0
  379. package/ts/src/journey/journeyOptions.ts +131 -0
  380. package/ts/src/journey/journeyRemoval.ts +158 -0
  381. package/ts/src/journey/journeyStatus.ts +149 -0
  382. package/ts/src/journey/journeySyncFile.ts +87 -0
  383. package/ts/src/journey/journeyWrite.ts +203 -0
  384. package/ts/src/journey/parentJourney.ts +41 -0
  385. package/ts/src/journey/validateParentJourney.ts +55 -0
  386. package/ts/src/mcp/boundary.ts +151 -0
  387. package/ts/src/mcp/guards.ts +244 -0
  388. package/ts/src/mcp/main.ts +121 -0
  389. package/ts/src/mcp/payload.ts +141 -0
  390. package/ts/src/mcp/protocol.ts +141 -0
  391. package/ts/src/mcp/readModels.ts +241 -0
  392. package/ts/src/mcp/registry.ts +201 -0
  393. package/ts/src/mcp/serve.ts +120 -0
  394. package/ts/src/mcp/tools/deterministic.ts +137 -0
  395. package/ts/src/mcp/tools/providerCrossing.ts +187 -0
  396. package/ts/src/mcp/wire.ts +8 -0
  397. package/ts/src/memory/journal.ts +180 -0
  398. package/ts/src/memory/listing.ts +107 -0
  399. package/ts/src/memory/memoryWrite.ts +88 -0
  400. package/ts/src/memory/reinforcement.ts +35 -0
  401. package/ts/src/mirror/context.ts +161 -0
  402. package/ts/src/mirror/defaultResolution.ts +199 -0
  403. package/ts/src/mirror/mirrorForm.ts +43 -0
  404. package/ts/src/mirror/orchestration.ts +364 -0
  405. package/ts/src/mirror/reception.ts +194 -0
  406. package/ts/src/mirror/render.ts +75 -0
  407. package/ts/src/mirror/runtimeSession.ts +205 -0
  408. package/ts/src/mode/operatingMode.ts +148 -0
  409. package/ts/src/observability/callOutcome.ts +115 -0
  410. package/ts/src/observability/inspectLedger.ts +329 -0
  411. package/ts/src/observability/ledgerHooks.ts +126 -0
  412. package/ts/src/observability/llmCalls.ts +154 -0
  413. package/ts/src/persona/detectPersona.ts +81 -0
  414. package/ts/src/planning/promptAssembly.ts +111 -0
  415. package/ts/src/planning/weekPending.ts +81 -0
  416. package/ts/src/planning/weekPlan.ts +183 -0
  417. package/ts/src/planning/weekSave.ts +117 -0
  418. package/ts/src/providers/config.ts +189 -0
  419. package/ts/src/providers/cost.ts +64 -0
  420. package/ts/src/providers/credits.ts +204 -0
  421. package/ts/src/providers/embedding.ts +321 -0
  422. package/ts/src/providers/familyProviders.ts +147 -0
  423. package/ts/src/providers/llm.ts +334 -0
  424. package/ts/src/providers/openrouter.ts +244 -0
  425. package/ts/src/providers/redaction.ts +110 -0
  426. package/ts/src/providers/replay.ts +15 -0
  427. package/ts/src/providers/transport.ts +410 -0
  428. package/ts/src/repair/encodingRepair.ts +253 -0
  429. package/ts/src/runtime/backup.ts +151 -0
  430. package/ts/src/runtime/channel.ts +146 -0
  431. package/ts/src/runtime/config.ts +168 -0
  432. package/ts/src/runtime/diagnose.ts +686 -0
  433. package/ts/src/runtime/git.ts +510 -0
  434. package/ts/src/runtime/installKind.ts +220 -0
  435. package/ts/src/runtime/migrate.ts +154 -0
  436. package/ts/src/runtime/packageIdentity.ts +102 -0
  437. package/ts/src/runtime/releaseNotes.ts +244 -0
  438. package/ts/src/runtime/status.ts +557 -0
  439. package/ts/src/runtime/strategies/clone.ts +200 -0
  440. package/ts/src/runtime/strategies/package.ts +328 -0
  441. package/ts/src/runtime/treeRoot.ts +30 -0
  442. package/ts/src/runtime/update.ts +445 -0
  443. package/ts/src/runtime/updateGate.ts +40 -0
  444. package/ts/src/runtime/updatePipeline.ts +159 -0
  445. package/ts/src/runtime/version.ts +36 -0
  446. package/ts/src/runtime/wiring.ts +130 -0
  447. package/ts/src/search/memorySearch.ts +338 -0
  448. package/ts/src/search/ranker.ts +154 -0
  449. package/ts/src/seed/seed.ts +256 -0
  450. package/ts/src/seed/seedYaml.ts +133 -0
  451. package/ts/src/soul/apply.ts +218 -0
  452. package/ts/src/soul/harvest.ts +267 -0
  453. package/ts/src/soul/prompts/soul_beauty_voice.md +103 -0
  454. package/ts/src/soul/prompts/soul_self_voice.md +219 -0
  455. package/ts/src/soul/prompts/soul_wisdom_voice.md +121 -0
  456. package/ts/src/soul/prompts.ts +85 -0
  457. package/ts/src/soul/render.ts +358 -0
  458. package/ts/src/soul/state.ts +212 -0
  459. package/ts/src/soul/transition.ts +37 -0
  460. package/ts/src/tasks/journeyPathParse.ts +113 -0
  461. package/ts/src/tasks/taskImportSync.ts +142 -0
  462. package/ts/src/tasks/taskStore.ts +312 -0
  463. package/ts/src/tasks/weekView.ts +120 -0
  464. package/ts/src/util/clipCodePoints.ts +26 -0
  465. package/ts/src/util/paths.ts +63 -0
  466. package/ts/src/util/program.ts +9 -0
  467. package/ts/src/util/pyGenerators.ts +144 -0
  468. package/ts/src/util/pythonText.ts +317 -0
  469. package/ts/src/util/semver.ts +45 -0
  470. package/ts/src/util/shellWord.ts +25 -0
  471. package/ts/src/util/slug.ts +64 -0
  472. package/ts/src/welcome/card.ts +339 -0
  473. package/ts/src/welcome/statusLine.ts +101 -0
  474. package/ts/src/welcome/updateCache.ts +129 -0
@@ -0,0 +1,242 @@
1
+ // CV22.DS7.US8 plateau 3 — the three files Plan materializes.
2
+ //
3
+ // Port of `_write_story_package` and its renderers from
4
+ // `src/memory/builder/lifecycle.py`.
5
+ //
6
+ // `writeStoryPackage` is the preservation rule in code: `if not path.exists()`, per
7
+ // FILE, so a package where a Driver authored `plan.md` but not `test-guide.md` gets
8
+ // the guide created and the plan left alone. A port that writes unconditionally
9
+ // destroys authored work silently, in someone else's git history — the worst defect
10
+ // available in this story, and the subject of CR004/CR015/CR079.
11
+ //
12
+ // The generated `plan.md` is also read back by `planSectionsToAuthor`
13
+ // (`scaffoldState.ts`), the rule both approval routes apply, so its `## ` headings
14
+ // are a contract with the approval rule, not decoration: rename one and a freshly
15
+ // scaffolded Plan reads as incomplete forever.
16
+
17
+ import { mkdirSync } from "node:fs";
18
+ import { dirname, join } from "node:path";
19
+ import type { ContractDefinition } from "../methodDefinition.ts";
20
+ import {
21
+ existingArtifact,
22
+ type MaterializedArtifact,
23
+ materializedArtifact,
24
+ } from "./artifactSurfaces.ts";
25
+ import { requireProjectRoot, writeBuilderArtifact } from "./artifactWriter.ts";
26
+ import { type ArtifactName, artifactState, describeArtifactState } from "./scaffoldState.ts";
27
+
28
+ /** Python `_markdown_list`: an empty list renders the literal fallback line. */
29
+ export function markdownList(items: readonly string[]): string {
30
+ return items.length > 0 ? items.map((item) => `- ${item}`).join("\n") : "- None declared.";
31
+ }
32
+
33
+ import { NAVIGATOR_VALIDATION_GUIDANCE, VALIDATION_EVIDENCE_PENDING } from "./scaffoldSections.ts";
34
+ /** Python `_user_story_statement` / `_technical_story_statement`, shared with Expand. */
35
+ import { technicalStoryStatement, userStoryStatement } from "./storyIndex.ts";
36
+
37
+ /** The subset of the Plan report these renderers read. */
38
+ export interface PlanArtifactInput {
39
+ readonly activeItem: string;
40
+ readonly activeItemTitle: string | null;
41
+ readonly activeItemLevel: string | null;
42
+ readonly objective: string;
43
+ readonly scope: readonly string[];
44
+ readonly nonGoals: readonly string[];
45
+ readonly acceptanceBehavior: readonly string[];
46
+ readonly validationRoute: readonly string[];
47
+ readonly e2eDecision: string;
48
+ readonly localRules: readonly string[];
49
+ readonly implementContract: ContractDefinition;
50
+ readonly activeCheckpoint: string | null;
51
+ readonly pendingConfirmation: string | null;
52
+ }
53
+
54
+ /** Python `_render_story_index_artifact`. */
55
+ export function renderStoryIndexArtifact(report: PlanArtifactInput): string {
56
+ // `"technical_story".replace("_", " ").title()` -> `Technical Story`; a null level
57
+ // becomes the literal `Story`.
58
+ const storyType = (report.activeItemLevel ?? "story")
59
+ .replaceAll("_", " ")
60
+ .replace(/\p{L}+/gu, (word) => word.charAt(0).toUpperCase() + word.slice(1).toLowerCase());
61
+ const title = report.activeItemTitle ?? report.activeItem;
62
+ const statement =
63
+ report.activeItemLevel === "technical_story"
64
+ ? technicalStoryStatement(title)
65
+ : userStoryStatement(title);
66
+ return `[< Parent](../index.md)
67
+
68
+ # ${report.activeItem} — ${title}
69
+
70
+ **Status:** 🟡 Planned
71
+ **Type:** ${storyType}
72
+
73
+ ---
74
+
75
+ ## Outcome
76
+
77
+ ${report.objective}
78
+
79
+ ## Story Statement
80
+
81
+ ${statement}
82
+
83
+ ## Acceptance Behavior
84
+
85
+ \`\`\`text
86
+ ${report.acceptanceBehavior.join("\n")}
87
+ \`\`\`
88
+
89
+ ## Scope
90
+
91
+ ${markdownList(report.scope)}
92
+
93
+ ## Out Of Scope
94
+
95
+ ${markdownList(report.nonGoals)}
96
+
97
+ ## Validation
98
+
99
+ ${markdownList(report.validationRoute)}
100
+
101
+ ---
102
+
103
+ ## Artifacts
104
+
105
+ - [Plan](plan.md)
106
+ - [Test Guide](test-guide.md)
107
+ `;
108
+ }
109
+
110
+ /**
111
+ * Ariad's own rule for staging, a method line in every Plan: the card and the
112
+ * scaffold both print it from here (CR019).
113
+ */
114
+ export const STORY_SCOPED_COMMIT_RULE = "Do not use git add .; commit only story-scoped files.";
115
+
116
+ /** Python `_render_plan_artifact`. */
117
+ export function renderPlanArtifact(report: PlanArtifactInput): string {
118
+ // The project's own rules follow the method lines; none is an honest empty (CR019).
119
+ const contract = [
120
+ "- Use TDD or characterization tests for behavior changes when testable.",
121
+ `- Keep changes scoped to \`${report.activeItem}\`.`,
122
+ `- ${STORY_SCOPED_COMMIT_RULE}`,
123
+ ...report.localRules.map((rule) => `- ${rule}`),
124
+ ].join("\n");
125
+ const stopConditions = report.implementContract.stopConditions
126
+ .map((condition) => `- ${condition}`)
127
+ .join("\n");
128
+ return `# Plan — ${report.activeItem}
129
+
130
+ ## Objective
131
+
132
+ ${report.objective}
133
+
134
+ ## Scope
135
+
136
+ ${markdownList(report.scope)}
137
+
138
+ ## Non-Goals
139
+
140
+ ${markdownList(report.nonGoals)}
141
+
142
+ ## Acceptance Behavior
143
+
144
+ \`\`\`text
145
+ ${report.acceptanceBehavior.join("\n")}
146
+ \`\`\`
147
+
148
+ ## Validation Route
149
+
150
+ ${markdownList(report.validationRoute)}
151
+
152
+ E2E decision: ${report.e2eDecision}
153
+
154
+ ## Implementation Contract
155
+
156
+ ${contract}
157
+
158
+ ## Stop Conditions
159
+
160
+ ${stopConditions}
161
+
162
+ ## Approval Gate
163
+
164
+ - active checkpoint: \`${report.activeCheckpoint}\`
165
+ - pending confirmation: \`${report.pendingConfirmation}\`
166
+ - implementation remains blocked until Navigator approval.
167
+ `;
168
+ }
169
+
170
+ /** Python `_render_test_guide_artifact`. */
171
+ export function renderTestGuideArtifact(report: PlanArtifactInput): string {
172
+ return `[< Story](index.md)
173
+
174
+ # Test Guide — ${report.activeItem}
175
+
176
+ ## Automated Validation
177
+
178
+ ${markdownList(report.validationRoute)}
179
+
180
+ ## E2E Decision
181
+
182
+ ${report.e2eDecision}
183
+
184
+ ## Navigator Validation
185
+
186
+ ${NAVIGATOR_VALIDATION_GUIDANCE}
187
+
188
+ ## Validation Evidence
189
+
190
+ ${VALIDATION_EVIDENCE_PENDING}
191
+ `;
192
+ }
193
+
194
+ /**
195
+ * Python `_plan_package_artifacts`: what Plan did to each file of the package.
196
+ *
197
+ * A file that existed before Plan is left alone (CR079) and named with what it is
198
+ * (CR112): a scaffold nobody authored, an incomplete file, or an authored one, so the
199
+ * reader of the artifacts card can tell which. The command and the recorded corpus
200
+ * both call this, so the card they print cannot differ.
201
+ */
202
+ export function planPackageArtifacts(
203
+ planPath: string | null,
204
+ existedBefore: ReadonlyMap<string, boolean>,
205
+ ): MaterializedArtifact[] {
206
+ if (planPath === null) return [];
207
+ const directory = dirname(planPath);
208
+ const triple: [string, string, ArtifactName][] = [
209
+ ["story index", join(directory, "index.md"), "index.md"],
210
+ ["plan", planPath, "plan.md"],
211
+ ["test guide", join(directory, "test-guide.md"), "test-guide.md"],
212
+ ];
213
+ return triple.map(([kind, path, name]) =>
214
+ existedBefore.get(path) === true
215
+ ? existingArtifact(kind, path, describeArtifactState(artifactState(name, path).state))
216
+ : materializedArtifact(kind, path, { existedBefore: false }),
217
+ );
218
+ }
219
+
220
+ /**
221
+ * Python `_write_story_package`.
222
+ *
223
+ * The directory is created unconditionally, the FILES conditionally. Both halves
224
+ * matter: a missing directory would make the whole package fail, while an existing
225
+ * file must survive untouched.
226
+ */
227
+ export function writeStoryPackage(
228
+ directory: string,
229
+ projectRoot: string | null | undefined,
230
+ report: PlanArtifactInput,
231
+ ): void {
232
+ const root = requireProjectRoot(projectRoot, directory);
233
+ mkdirSync(directory, { recursive: true });
234
+ const artifacts: [string, string][] = [
235
+ [join(directory, "index.md"), renderStoryIndexArtifact(report)],
236
+ [join(directory, "plan.md"), renderPlanArtifact(report)],
237
+ [join(directory, "test-guide.md"), renderTestGuideArtifact(report)],
238
+ ];
239
+ for (const [path, content] of artifacts) {
240
+ writeBuilderArtifact({ path, content, policy: "create-only", projectRoot: root });
241
+ }
242
+ }
@@ -0,0 +1,273 @@
1
+ // CR112 — the one home of every sentence a story scaffold carries.
2
+ //
3
+ // Expand writes a child story's `index.md`; Plan writes `index.md`, `plan.md`, and
4
+ // `test-guide.md`. Until CR112 the sentences those files carry lived where each
5
+ // writer happened to compose them: the statement and outcome in `storyIndex.ts`,
6
+ // the Plan context in `commands.ts`, and a second set of Plan defaults in `plan.ts`,
7
+ // reached only when a caller passed no sections. Nothing could read a file back and
8
+ // say whether it was still the scaffold, because nothing held the scaffold's lines in
9
+ // a form a reader could compare against.
10
+ //
11
+ // This module holds them as TEMPLATES: fixed text with a `{title}` slot.
12
+ // The writers fill them (`fill`) and produce the same bytes they always did; the
13
+ // reader (`scaffoldState.ts`) matches a file's lines against them with the slots
14
+ // wildcarded (`matchesTemplate`), so the check reads nothing but the file and this
15
+ // module -- not the cursor's title, which a re-pull can change, and not the roadmap.
16
+ //
17
+ // Every section also carries a KIND. A `placeholder` section is where the scaffold
18
+ // stands in for content the Driver must write. A `default` section is a rule or a
19
+ // default that may legitimately stand as written: keeping "Do not use git add ."
20
+ // verbatim leaves no placeholder behind; keeping "Deliver X as an observable slice"
21
+ // does.
22
+ //
23
+ // One Plan vocabulary, `PRODUCT_PLAN`, which `planLifecycleItem` fills for every
24
+ // caller. CR112 recorded a second one, the defaults Python's `plan_lifecycle_item`
25
+ // wrote when a caller passed no sections; no product path wrote it, only the recorded
26
+ // corpus and the tests, so the corpus graded a scaffold no user received. CR111 (D3)
27
+ // retired it.
28
+
29
+ export type SectionKind = "placeholder" | "default";
30
+
31
+ /** A `## ` section of a scaffold: its heading, its kind, and the template lines it may hold. */
32
+ export interface SectionSpec {
33
+ readonly header: string;
34
+ readonly kind: SectionKind;
35
+ /** Template lines a scaffold writes under this heading; empty for a `default` section. */
36
+ readonly lines: readonly string[];
37
+ }
38
+
39
+ /** The slot a template may carry: the item's title, the one thing a scaffold varies by. */
40
+ export interface SlotValues {
41
+ readonly title?: string;
42
+ }
43
+
44
+ const SLOT_RE = /\{(title)\}/g;
45
+
46
+ /** Fill a template's slots. A slot with no value is left as written. */
47
+ export function fill(template: string, values: SlotValues): string {
48
+ return template.replace(SLOT_RE, (whole) => values.title ?? whole);
49
+ }
50
+
51
+ /**
52
+ * True when `line` is `template` with anything in its slots: the fixed text before,
53
+ * between, and after the slots must appear in order, at the ends where the template
54
+ * has them. A template with no slot matches only itself.
55
+ */
56
+ export function matchesTemplate(line: string, template: string): boolean {
57
+ const parts = template.split(SLOT_RE).filter((_, index) => index % 2 === 0);
58
+ if (parts.length === 1) return line === template;
59
+ const first = parts[0] as string;
60
+ const last = parts[parts.length - 1] as string;
61
+ if (!line.startsWith(first) || !line.endsWith(last)) return false;
62
+ if (line.length < first.length + last.length) return false;
63
+ let cursor = first.length;
64
+ const end = line.length - last.length;
65
+ for (const part of parts.slice(1, -1)) {
66
+ const at = line.indexOf(part, cursor);
67
+ if (at === -1 || at + part.length > end) return false;
68
+ cursor = at + part.length;
69
+ }
70
+ return true;
71
+ }
72
+
73
+ // --- the statement and outcome templates (Expand's `index.md`, and Plan's) ---
74
+
75
+ /** Python `_user_story_statement`, as a template. */
76
+ export const USER_STORY_STATEMENT: readonly string[] = [
77
+ "As a user,",
78
+ "I want to {title},",
79
+ "So that I can receive the value of this story.",
80
+ ];
81
+
82
+ /** Python `_technical_story_statement`, as a template. */
83
+ export const TECHNICAL_STORY_STATEMENT: readonly string[] = [
84
+ "In order to support the delivery capability,",
85
+ "As an engineering team/system component,",
86
+ "I want to {title},",
87
+ "So that the expected technical outcome is available.",
88
+ ];
89
+
90
+ /** Python `_user_story_outcome`, as a template. */
91
+ export const STORY_OUTCOME = "Navigator can validate {title} as an observable behavior.";
92
+
93
+ /** The acceptance block Expand writes for a User Story. */
94
+ export const USER_STORY_ACCEPTANCE: readonly string[] = [
95
+ "Given the user is ready for {title}",
96
+ "When the user performs the planned action",
97
+ "Then the expected observable behavior is visible",
98
+ "And unrelated Delivery Story scope remains untouched",
99
+ ];
100
+
101
+ /** The acceptance block Expand writes for a Technical Story. */
102
+ export const TECHNICAL_STORY_ACCEPTANCE: readonly string[] = [
103
+ "Given the system is ready for {title}",
104
+ "When the planned technical change is applied",
105
+ "Then the expected technical outcome is observable",
106
+ "And unrelated Delivery Story scope remains untouched",
107
+ ];
108
+
109
+ // --- the Plan vocabularies ---
110
+
111
+ /** The sentences a Plan scaffold carries, before its slots are filled. */
112
+ export interface PlanVocabulary {
113
+ readonly objective: string;
114
+ readonly scope: readonly string[];
115
+ readonly nonGoals: readonly string[];
116
+ readonly acceptanceBehavior: readonly string[];
117
+ readonly validationRoute: readonly string[];
118
+ readonly e2eDecision: string;
119
+ }
120
+
121
+ /** The Plan scaffold's sentences: Python `cmd_plan_item`'s roadmap context. */
122
+ export const PRODUCT_PLAN: PlanVocabulary = {
123
+ objective: "Plan the smallest coherent, testable slice for {title}.",
124
+ scope: [
125
+ "Deliver {title} as an observable slice.",
126
+ "Keep the implementation narrow enough to validate at the Plan-defined checkpoint.",
127
+ ],
128
+ nonGoals: ["Do not silently absorb adjacent roadmap work."],
129
+ acceptanceBehavior: [
130
+ "Given the starting state needed for {title}",
131
+ "When the Navigator exercises {title}",
132
+ "Then the planned observable behavior is visible",
133
+ "And out-of-scope sibling roadmap items remain untouched",
134
+ ],
135
+ validationRoute: [
136
+ "Run automated tests that cover the planned behavior.",
137
+ "Provide a Navigator-visible route with expected observation, pass condition, and fail condition.",
138
+ ],
139
+ e2eDecision:
140
+ "required unless Navigator explicitly accepts a narrower fixture-level validation route",
141
+ };
142
+
143
+ /** The Non-Goals line the front door writes for each sibling roadmap item. */
144
+ export const SIBLING_NON_GOAL = "Do not implement sibling roadmap item: {title}.";
145
+
146
+ /** A vocabulary with its slots filled for one item. */
147
+ export function fillPlanVocabulary(vocabulary: PlanVocabulary, values: SlotValues): PlanVocabulary {
148
+ const fillAll = (lines: readonly string[]): string[] => lines.map((line) => fill(line, values));
149
+ return {
150
+ objective: fill(vocabulary.objective, values),
151
+ scope: fillAll(vocabulary.scope),
152
+ nonGoals: fillAll(vocabulary.nonGoals),
153
+ acceptanceBehavior: fillAll(vocabulary.acceptanceBehavior),
154
+ validationRoute: fillAll(vocabulary.validationRoute),
155
+ e2eDecision: fill(vocabulary.e2eDecision, values),
156
+ };
157
+ }
158
+
159
+ /** The sentence a test guide's Navigator Validation section holds until it is authored. */
160
+ export const NAVIGATOR_VALIDATION_GUIDANCE =
161
+ "Provide the Navigator-visible route with expected observation, pass condition, and fail condition before the story can pass Validation.";
162
+
163
+ /** The sentence a test guide's Validation Evidence section holds until validation. */
164
+ export const VALIDATION_EVIDENCE_PENDING = "Pending implementation and validation.";
165
+
166
+ // --- the section tables, one per artifact ---
167
+
168
+ const FENCE_OPEN = "```text";
169
+ const FENCE_CLOSE = "```";
170
+
171
+ function bullets(lines: readonly string[]): string[] {
172
+ return lines.map((line) => `- ${line}`);
173
+ }
174
+
175
+ /** The sections of `plan.md`, in the order Plan writes them. */
176
+ export const PLAN_SECTIONS: readonly SectionSpec[] = [
177
+ { header: "Objective", kind: "placeholder", lines: [PRODUCT_PLAN.objective] },
178
+ { header: "Scope", kind: "placeholder", lines: bullets(PRODUCT_PLAN.scope) },
179
+ { header: "Non-Goals", kind: "default", lines: [] },
180
+ {
181
+ header: "Acceptance Behavior",
182
+ kind: "placeholder",
183
+ lines: [FENCE_OPEN, ...PRODUCT_PLAN.acceptanceBehavior, FENCE_CLOSE],
184
+ },
185
+ {
186
+ header: "Validation Route",
187
+ kind: "placeholder",
188
+ lines: [...bullets(PRODUCT_PLAN.validationRoute), `E2E decision: ${PRODUCT_PLAN.e2eDecision}`],
189
+ },
190
+ { header: "Implementation Contract", kind: "default", lines: [] },
191
+ { header: "Stop Conditions", kind: "default", lines: [] },
192
+ { header: "Approval Gate", kind: "default", lines: [] },
193
+ ];
194
+
195
+ /** Python `STORY_PLAN_REQUIRED_SECTIONS`, in declaration order: the Plan contract's headings. */
196
+ export const STORY_PLAN_REQUIRED_SECTIONS = [
197
+ "Scope",
198
+ "Non-Goals",
199
+ "Acceptance Behavior",
200
+ "Validation Route",
201
+ "Implementation Contract",
202
+ ] as const;
203
+
204
+ /**
205
+ * The sections a Plan approval requires authored, on either route (CR112): every
206
+ * placeholder section of the story scaffold and every section the Plan contract
207
+ * requires, in the order the plan file has them, so a refusal lists them as the reader
208
+ * will find them. A placeholder section counts until it is authored; a required
209
+ * `default` section counts until it is not empty or pending.
210
+ *
211
+ * One list for every surface that says what a `plan.md` still needs: both approval
212
+ * routes, `build show`, and the Plan checkpoint read it through `scaffoldState.ts`
213
+ * (CR111 D4). It lives here, with the sections it names, so the reader below the
214
+ * approval layer can use it without depending on that layer.
215
+ */
216
+ export const PLAN_APPROVAL_SECTIONS: readonly string[] = [
217
+ ...PLAN_SECTIONS.filter(
218
+ (section) =>
219
+ section.kind === "placeholder" ||
220
+ (STORY_PLAN_REQUIRED_SECTIONS as readonly string[]).includes(section.header),
221
+ ).map((section) => section.header),
222
+ ...STORY_PLAN_REQUIRED_SECTIONS.filter(
223
+ (header) => !PLAN_SECTIONS.some((section) => section.header === header),
224
+ ),
225
+ ];
226
+
227
+ /**
228
+ * The sections of a story `index.md`. Expand's scaffold heads the statement
229
+ * `## User Story` or `## Technical Story`; Plan's heads it `## Story Statement` and
230
+ * puts the objective under `## Outcome`. A file carries one of the three statement
231
+ * headings; the reader judges whichever it finds.
232
+ */
233
+ export const STORY_INDEX_SECTIONS: readonly SectionSpec[] = [
234
+ { header: "User Story", kind: "placeholder", lines: USER_STORY_STATEMENT },
235
+ { header: "Technical Story", kind: "placeholder", lines: TECHNICAL_STORY_STATEMENT },
236
+ {
237
+ header: "Story Statement",
238
+ kind: "placeholder",
239
+ lines: [...USER_STORY_STATEMENT, ...TECHNICAL_STORY_STATEMENT],
240
+ },
241
+ {
242
+ header: "Outcome",
243
+ kind: "placeholder",
244
+ lines: [STORY_OUTCOME, PRODUCT_PLAN.objective],
245
+ },
246
+ {
247
+ header: "Acceptance Behavior",
248
+ kind: "placeholder",
249
+ lines: [
250
+ FENCE_OPEN,
251
+ ...USER_STORY_ACCEPTANCE,
252
+ ...TECHNICAL_STORY_ACCEPTANCE,
253
+ ...PRODUCT_PLAN.acceptanceBehavior,
254
+ FENCE_CLOSE,
255
+ ],
256
+ },
257
+ { header: "Scope", kind: "default", lines: [] },
258
+ { header: "Out Of Scope", kind: "default", lines: [] },
259
+ { header: "Validation", kind: "default", lines: [] },
260
+ { header: "Artifacts", kind: "default", lines: [] },
261
+ ];
262
+
263
+ /** The sections of `test-guide.md`, in the order Plan writes them. */
264
+ export const TEST_GUIDE_SECTIONS: readonly SectionSpec[] = [
265
+ {
266
+ header: "Automated Validation",
267
+ kind: "placeholder",
268
+ lines: bullets(PRODUCT_PLAN.validationRoute),
269
+ },
270
+ { header: "E2E Decision", kind: "default", lines: [] },
271
+ { header: "Navigator Validation", kind: "placeholder", lines: [NAVIGATOR_VALIDATION_GUIDANCE] },
272
+ { header: "Validation Evidence", kind: "default", lines: [] },
273
+ ];