@isaacriehm/cairn-core 0.1.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 (616) hide show
  1. package/LICENSE +21 -0
  2. package/dist/.tsbuildinfo +1 -0
  3. package/dist/claude/error.d.ts +33 -0
  4. package/dist/claude/error.js +58 -0
  5. package/dist/claude/error.js.map +1 -0
  6. package/dist/claude/index.d.ts +3 -0
  7. package/dist/claude/index.js +3 -0
  8. package/dist/claude/index.js.map +1 -0
  9. package/dist/claude/runner.d.ts +11 -0
  10. package/dist/claude/runner.js +132 -0
  11. package/dist/claude/runner.js.map +1 -0
  12. package/dist/claude/types.d.ts +52 -0
  13. package/dist/claude/types.js +14 -0
  14. package/dist/claude/types.js.map +1 -0
  15. package/dist/context/checkpoint.d.ts +10 -0
  16. package/dist/context/checkpoint.js +29 -0
  17. package/dist/context/checkpoint.js.map +1 -0
  18. package/dist/context/handoff-builder.d.ts +11 -0
  19. package/dist/context/handoff-builder.js +268 -0
  20. package/dist/context/handoff-builder.js.map +1 -0
  21. package/dist/context/index.d.ts +11 -0
  22. package/dist/context/index.js +11 -0
  23. package/dist/context/index.js.map +1 -0
  24. package/dist/context/spec-delta.d.ts +47 -0
  25. package/dist/context/spec-delta.js +237 -0
  26. package/dist/context/spec-delta.js.map +1 -0
  27. package/dist/decision-capture/capture.d.ts +57 -0
  28. package/dist/decision-capture/capture.js +186 -0
  29. package/dist/decision-capture/capture.js.map +1 -0
  30. package/dist/decision-capture/extractor.d.ts +20 -0
  31. package/dist/decision-capture/extractor.js +103 -0
  32. package/dist/decision-capture/extractor.js.map +1 -0
  33. package/dist/decision-capture/id.d.ts +21 -0
  34. package/dist/decision-capture/id.js +60 -0
  35. package/dist/decision-capture/id.js.map +1 -0
  36. package/dist/decision-capture/index.d.ts +25 -0
  37. package/dist/decision-capture/index.js +21 -0
  38. package/dist/decision-capture/index.js.map +1 -0
  39. package/dist/decision-capture/prompt.d.ts +15 -0
  40. package/dist/decision-capture/prompt.js +68 -0
  41. package/dist/decision-capture/prompt.js.map +1 -0
  42. package/dist/decision-capture/refinement-prompt.d.ts +25 -0
  43. package/dist/decision-capture/refinement-prompt.js +146 -0
  44. package/dist/decision-capture/refinement-prompt.js.map +1 -0
  45. package/dist/decision-capture/refinement-schema.d.ts +52 -0
  46. package/dist/decision-capture/refinement-schema.js +61 -0
  47. package/dist/decision-capture/refinement-schema.js.map +1 -0
  48. package/dist/decision-capture/refinement.d.ts +60 -0
  49. package/dist/decision-capture/refinement.js +439 -0
  50. package/dist/decision-capture/refinement.js.map +1 -0
  51. package/dist/decision-capture/schema.d.ts +70 -0
  52. package/dist/decision-capture/schema.js +71 -0
  53. package/dist/decision-capture/schema.js.map +1 -0
  54. package/dist/decision-capture/types.d.ts +201 -0
  55. package/dist/decision-capture/types.js +20 -0
  56. package/dist/decision-capture/types.js.map +1 -0
  57. package/dist/decision-capture/writer.d.ts +90 -0
  58. package/dist/decision-capture/writer.js +267 -0
  59. package/dist/decision-capture/writer.js.map +1 -0
  60. package/dist/doctor/index.d.ts +48 -0
  61. package/dist/doctor/index.js +460 -0
  62. package/dist/doctor/index.js.map +1 -0
  63. package/dist/events/index.d.ts +15 -0
  64. package/dist/events/index.js +14 -0
  65. package/dist/events/index.js.map +1 -0
  66. package/dist/events/paths.d.ts +2 -0
  67. package/dist/events/paths.js +6 -0
  68. package/dist/events/paths.js.map +1 -0
  69. package/dist/events/reader.d.ts +40 -0
  70. package/dist/events/reader.js +139 -0
  71. package/dist/events/reader.js.map +1 -0
  72. package/dist/events/writer.d.ts +61 -0
  73. package/dist/events/writer.js +68 -0
  74. package/dist/events/writer.js.map +1 -0
  75. package/dist/frontend-types.d.ts +243 -0
  76. package/dist/frontend-types.js +15 -0
  77. package/dist/frontend-types.js.map +1 -0
  78. package/dist/gc/apply.d.ts +26 -0
  79. package/dist/gc/apply.js +48 -0
  80. package/dist/gc/apply.js.map +1 -0
  81. package/dist/gc/canary.d.ts +42 -0
  82. package/dist/gc/canary.js +134 -0
  83. package/dist/gc/canary.js.map +1 -0
  84. package/dist/gc/citation-integrity.d.ts +24 -0
  85. package/dist/gc/citation-integrity.js +151 -0
  86. package/dist/gc/citation-integrity.js.map +1 -0
  87. package/dist/gc/classify.d.ts +25 -0
  88. package/dist/gc/classify.js +89 -0
  89. package/dist/gc/classify.js.map +1 -0
  90. package/dist/gc/completion-integrity.d.ts +22 -0
  91. package/dist/gc/completion-integrity.js +165 -0
  92. package/dist/gc/completion-integrity.js.map +1 -0
  93. package/dist/gc/doc-gardening.d.ts +29 -0
  94. package/dist/gc/doc-gardening.js +146 -0
  95. package/dist/gc/doc-gardening.js.map +1 -0
  96. package/dist/gc/frontmatter.d.ts +35 -0
  97. package/dist/gc/frontmatter.js +105 -0
  98. package/dist/gc/frontmatter.js.map +1 -0
  99. package/dist/gc/generator-drift.d.ts +28 -0
  100. package/dist/gc/generator-drift.js +53 -0
  101. package/dist/gc/generator-drift.js.map +1 -0
  102. package/dist/gc/index.d.ts +42 -0
  103. package/dist/gc/index.js +30 -0
  104. package/dist/gc/index.js.map +1 -0
  105. package/dist/gc/quality-update.d.ts +23 -0
  106. package/dist/gc/quality-update.js +69 -0
  107. package/dist/gc/quality-update.js.map +1 -0
  108. package/dist/gc/scope-coverage.d.ts +20 -0
  109. package/dist/gc/scope-coverage.js +70 -0
  110. package/dist/gc/scope-coverage.js.map +1 -0
  111. package/dist/gc/stub-hits.d.ts +31 -0
  112. package/dist/gc/stub-hits.js +78 -0
  113. package/dist/gc/stub-hits.js.map +1 -0
  114. package/dist/gc/sweep.d.ts +56 -0
  115. package/dist/gc/sweep.js +205 -0
  116. package/dist/gc/sweep.js.map +1 -0
  117. package/dist/gc/types.d.ts +129 -0
  118. package/dist/gc/types.js +26 -0
  119. package/dist/gc/types.js.map +1 -0
  120. package/dist/gc/walk-source.d.ts +14 -0
  121. package/dist/gc/walk-source.js +59 -0
  122. package/dist/gc/walk-source.js.map +1 -0
  123. package/dist/ground/drift.d.ts +8 -0
  124. package/dist/ground/drift.js +23 -0
  125. package/dist/ground/drift.js.map +1 -0
  126. package/dist/ground/frontmatter.d.ts +20 -0
  127. package/dist/ground/frontmatter.js +49 -0
  128. package/dist/ground/frontmatter.js.map +1 -0
  129. package/dist/ground/glob.d.ts +10 -0
  130. package/dist/ground/glob.js +46 -0
  131. package/dist/ground/glob.js.map +1 -0
  132. package/dist/ground/index.d.ts +16 -0
  133. package/dist/ground/index.js +11 -0
  134. package/dist/ground/index.js.map +1 -0
  135. package/dist/ground/ledgers.d.ts +18 -0
  136. package/dist/ground/ledgers.js +103 -0
  137. package/dist/ground/ledgers.js.map +1 -0
  138. package/dist/ground/manifest.d.ts +10 -0
  139. package/dist/ground/manifest.js +88 -0
  140. package/dist/ground/manifest.js.map +1 -0
  141. package/dist/ground/paths.d.ts +20 -0
  142. package/dist/ground/paths.js +61 -0
  143. package/dist/ground/paths.js.map +1 -0
  144. package/dist/ground/quality-grades.d.ts +11 -0
  145. package/dist/ground/quality-grades.js +98 -0
  146. package/dist/ground/quality-grades.js.map +1 -0
  147. package/dist/ground/schemas.d.ts +306 -0
  148. package/dist/ground/schemas.js +188 -0
  149. package/dist/ground/schemas.js.map +1 -0
  150. package/dist/ground/scope-index.d.ts +48 -0
  151. package/dist/ground/scope-index.js +120 -0
  152. package/dist/ground/scope-index.js.map +1 -0
  153. package/dist/ground/walk.d.ts +7 -0
  154. package/dist/ground/walk.js +53 -0
  155. package/dist/ground/walk.js.map +1 -0
  156. package/dist/hooks/bypass-detection.d.ts +28 -0
  157. package/dist/hooks/bypass-detection.js +106 -0
  158. package/dist/hooks/bypass-detection.js.map +1 -0
  159. package/dist/hooks/index.d.ts +12 -0
  160. package/dist/hooks/index.js +13 -0
  161. package/dist/hooks/index.js.map +1 -0
  162. package/dist/hooks/post-tool-use/allowlist-reader.d.ts +14 -0
  163. package/dist/hooks/post-tool-use/allowlist-reader.js +69 -0
  164. package/dist/hooks/post-tool-use/allowlist-reader.js.map +1 -0
  165. package/dist/hooks/post-tool-use/citation-scanner.d.ts +23 -0
  166. package/dist/hooks/post-tool-use/citation-scanner.js +59 -0
  167. package/dist/hooks/post-tool-use/citation-scanner.js.map +1 -0
  168. package/dist/hooks/post-tool-use/copy-scanner.d.ts +25 -0
  169. package/dist/hooks/post-tool-use/copy-scanner.js +192 -0
  170. package/dist/hooks/post-tool-use/copy-scanner.js.map +1 -0
  171. package/dist/hooks/post-tool-use/index.d.ts +19 -0
  172. package/dist/hooks/post-tool-use/index.js +15 -0
  173. package/dist/hooks/post-tool-use/index.js.map +1 -0
  174. package/dist/hooks/post-tool-use/ledger-cache.d.ts +32 -0
  175. package/dist/hooks/post-tool-use/ledger-cache.js +236 -0
  176. package/dist/hooks/post-tool-use/ledger-cache.js.map +1 -0
  177. package/dist/hooks/post-tool-use/legend-builder.d.ts +15 -0
  178. package/dist/hooks/post-tool-use/legend-builder.js +84 -0
  179. package/dist/hooks/post-tool-use/legend-builder.js.map +1 -0
  180. package/dist/hooks/post-tool-use/read-enricher.d.ts +13 -0
  181. package/dist/hooks/post-tool-use/read-enricher.js +157 -0
  182. package/dist/hooks/post-tool-use/read-enricher.js.map +1 -0
  183. package/dist/hooks/post-tool-use/write-guardian.d.ts +17 -0
  184. package/dist/hooks/post-tool-use/write-guardian.js +176 -0
  185. package/dist/hooks/post-tool-use/write-guardian.js.map +1 -0
  186. package/dist/hooks/read-enrich.d.ts +6 -0
  187. package/dist/hooks/read-enrich.js +11 -0
  188. package/dist/hooks/read-enrich.js.map +1 -0
  189. package/dist/hooks/runners/index.d.ts +12 -0
  190. package/dist/hooks/runners/index.js +11 -0
  191. package/dist/hooks/runners/index.js.map +1 -0
  192. package/dist/hooks/runners/payload.d.ts +32 -0
  193. package/dist/hooks/runners/payload.js +70 -0
  194. package/dist/hooks/runners/payload.js.map +1 -0
  195. package/dist/hooks/runners/session-end.d.ts +7 -0
  196. package/dist/hooks/runners/session-end.js +42 -0
  197. package/dist/hooks/runners/session-end.js.map +1 -0
  198. package/dist/hooks/runners/session-start.d.ts +10 -0
  199. package/dist/hooks/runners/session-start.js +167 -0
  200. package/dist/hooks/runners/session-start.js.map +1 -0
  201. package/dist/hooks/runners/stop.d.ts +18 -0
  202. package/dist/hooks/runners/stop.js +165 -0
  203. package/dist/hooks/runners/stop.js.map +1 -0
  204. package/dist/hooks/session-end.d.ts +5 -0
  205. package/dist/hooks/session-end.js +10 -0
  206. package/dist/hooks/session-end.js.map +1 -0
  207. package/dist/hooks/session-start.d.ts +7 -0
  208. package/dist/hooks/session-start.js +12 -0
  209. package/dist/hooks/session-start.js.map +1 -0
  210. package/dist/hooks/stop.d.ts +5 -0
  211. package/dist/hooks/stop.js +10 -0
  212. package/dist/hooks/stop.js.map +1 -0
  213. package/dist/hooks/write-guard.d.ts +6 -0
  214. package/dist/hooks/write-guard.js +11 -0
  215. package/dist/hooks/write-guard.js.map +1 -0
  216. package/dist/inbox.d.ts +17 -0
  217. package/dist/inbox.js +30 -0
  218. package/dist/inbox.js.map +1 -0
  219. package/dist/index.d.ts +33 -0
  220. package/dist/index.js +32 -0
  221. package/dist/index.js.map +1 -0
  222. package/dist/init/baseline-audit.d.ts +71 -0
  223. package/dist/init/baseline-audit.js +377 -0
  224. package/dist/init/baseline-audit.js.map +1 -0
  225. package/dist/init/brand-setup.d.ts +44 -0
  226. package/dist/init/brand-setup.js +201 -0
  227. package/dist/init/brand-setup.js.map +1 -0
  228. package/dist/init/daemon-autostart.d.ts +16 -0
  229. package/dist/init/daemon-autostart.js +95 -0
  230. package/dist/init/daemon-autostart.js.map +1 -0
  231. package/dist/init/detect.d.ts +25 -0
  232. package/dist/init/detect.js +319 -0
  233. package/dist/init/detect.js.map +1 -0
  234. package/dist/init/index.d.ts +32 -0
  235. package/dist/init/index.js +18 -0
  236. package/dist/init/index.js.map +1 -0
  237. package/dist/init/ingest-docs.d.ts +74 -0
  238. package/dist/init/ingest-docs.js +499 -0
  239. package/dist/init/ingest-docs.js.map +1 -0
  240. package/dist/init/init.d.ts +165 -0
  241. package/dist/init/init.js +1166 -0
  242. package/dist/init/init.js.map +1 -0
  243. package/dist/init/mapper-legacy.d.ts +148 -0
  244. package/dist/init/mapper-legacy.js +238 -0
  245. package/dist/init/mapper-legacy.js.map +1 -0
  246. package/dist/init/mapper-merge.d.ts +38 -0
  247. package/dist/init/mapper-merge.js +238 -0
  248. package/dist/init/mapper-merge.js.map +1 -0
  249. package/dist/init/mapper-parallel.d.ts +48 -0
  250. package/dist/init/mapper-parallel.js +409 -0
  251. package/dist/init/mapper-parallel.js.map +1 -0
  252. package/dist/init/mapper-prompts.d.ts +135 -0
  253. package/dist/init/mapper-prompts.js +189 -0
  254. package/dist/init/mapper-prompts.js.map +1 -0
  255. package/dist/init/mapper.d.ts +211 -0
  256. package/dist/init/mapper.js +151 -0
  257. package/dist/init/mapper.js.map +1 -0
  258. package/dist/init/module-slicer.d.ts +39 -0
  259. package/dist/init/module-slicer.js +809 -0
  260. package/dist/init/module-slicer.js.map +1 -0
  261. package/dist/init/multi-dev/index.d.ts +2 -0
  262. package/dist/init/multi-dev/index.js +2 -0
  263. package/dist/init/multi-dev/index.js.map +1 -0
  264. package/dist/init/multi-dev/install.d.ts +40 -0
  265. package/dist/init/multi-dev/install.js +139 -0
  266. package/dist/init/multi-dev/install.js.map +1 -0
  267. package/dist/init/preflight-guards.d.ts +42 -0
  268. package/dist/init/preflight-guards.js +108 -0
  269. package/dist/init/preflight-guards.js.map +1 -0
  270. package/dist/init/prompts.d.ts +61 -0
  271. package/dist/init/prompts.js +66 -0
  272. package/dist/init/prompts.js.map +1 -0
  273. package/dist/init/rules-merge/discover.d.ts +21 -0
  274. package/dist/init/rules-merge/discover.js +78 -0
  275. package/dist/init/rules-merge/discover.js.map +1 -0
  276. package/dist/init/rules-merge/index.d.ts +10 -0
  277. package/dist/init/rules-merge/index.js +6 -0
  278. package/dist/init/rules-merge/index.js.map +1 -0
  279. package/dist/init/rules-merge/ingest.d.ts +56 -0
  280. package/dist/init/rules-merge/ingest.js +336 -0
  281. package/dist/init/rules-merge/ingest.js.map +1 -0
  282. package/dist/init/rules-merge/keep-markers.d.ts +39 -0
  283. package/dist/init/rules-merge/keep-markers.js +97 -0
  284. package/dist/init/rules-merge/keep-markers.js.map +1 -0
  285. package/dist/init/rules-merge/parse-sections.d.ts +24 -0
  286. package/dist/init/rules-merge/parse-sections.js +71 -0
  287. package/dist/init/rules-merge/parse-sections.js.map +1 -0
  288. package/dist/init/rules-merge/regenerate.d.ts +33 -0
  289. package/dist/init/rules-merge/regenerate.js +163 -0
  290. package/dist/init/rules-merge/regenerate.js.map +1 -0
  291. package/dist/init/secrets.d.ts +18 -0
  292. package/dist/init/secrets.js +76 -0
  293. package/dist/init/secrets.js.map +1 -0
  294. package/dist/init/seed.d.ts +21 -0
  295. package/dist/init/seed.js +96 -0
  296. package/dist/init/seed.js.map +1 -0
  297. package/dist/init/setup-runners.d.ts +15 -0
  298. package/dist/init/setup-runners.js +143 -0
  299. package/dist/init/setup-runners.js.map +1 -0
  300. package/dist/init/source-comments/classify.d.ts +98 -0
  301. package/dist/init/source-comments/classify.js +244 -0
  302. package/dist/init/source-comments/classify.js.map +1 -0
  303. package/dist/init/source-comments/index.d.ts +8 -0
  304. package/dist/init/source-comments/index.js +5 -0
  305. package/dist/init/source-comments/index.js.map +1 -0
  306. package/dist/init/source-comments/ingest.d.ts +51 -0
  307. package/dist/init/source-comments/ingest.js +236 -0
  308. package/dist/init/source-comments/ingest.js.map +1 -0
  309. package/dist/init/source-comments/strip-replace.d.ts +106 -0
  310. package/dist/init/source-comments/strip-replace.js +284 -0
  311. package/dist/init/source-comments/strip-replace.js.map +1 -0
  312. package/dist/init/source-comments/walker.d.ts +65 -0
  313. package/dist/init/source-comments/walker.js +777 -0
  314. package/dist/init/source-comments/walker.js.map +1 -0
  315. package/dist/init/submodules.d.ts +48 -0
  316. package/dist/init/submodules.js +149 -0
  317. package/dist/init/submodules.js.map +1 -0
  318. package/dist/init/types.d.ts +55 -0
  319. package/dist/init/types.js +10 -0
  320. package/dist/init/types.js.map +1 -0
  321. package/dist/init/visual.d.ts +69 -0
  322. package/dist/init/visual.js +265 -0
  323. package/dist/init/visual.js.map +1 -0
  324. package/dist/init/walker.d.ts +82 -0
  325. package/dist/init/walker.js +585 -0
  326. package/dist/init/walker.js.map +1 -0
  327. package/dist/init/workflow-block.d.ts +34 -0
  328. package/dist/init/workflow-block.js +110 -0
  329. package/dist/init/workflow-block.js.map +1 -0
  330. package/dist/join/index.d.ts +67 -0
  331. package/dist/join/index.js +256 -0
  332. package/dist/join/index.js.map +1 -0
  333. package/dist/lock.d.ts +39 -0
  334. package/dist/lock.js +129 -0
  335. package/dist/lock.js.map +1 -0
  336. package/dist/logger.d.ts +13 -0
  337. package/dist/logger.js +78 -0
  338. package/dist/logger.js.map +1 -0
  339. package/dist/mcp/bootstrap-guard.d.ts +29 -0
  340. package/dist/mcp/bootstrap-guard.js +47 -0
  341. package/dist/mcp/bootstrap-guard.js.map +1 -0
  342. package/dist/mcp/context.d.ts +23 -0
  343. package/dist/mcp/context.js +9 -0
  344. package/dist/mcp/context.js.map +1 -0
  345. package/dist/mcp/errors.d.ts +17 -0
  346. package/dist/mcp/errors.js +23 -0
  347. package/dist/mcp/errors.js.map +1 -0
  348. package/dist/mcp/history/index.d.ts +6 -0
  349. package/dist/mcp/history/index.js +5 -0
  350. package/dist/mcp/history/index.js.map +1 -0
  351. package/dist/mcp/history/prompt.d.ts +32 -0
  352. package/dist/mcp/history/prompt.js +99 -0
  353. package/dist/mcp/history/prompt.js.map +1 -0
  354. package/dist/mcp/history/schema.d.ts +58 -0
  355. package/dist/mcp/history/schema.js +41 -0
  356. package/dist/mcp/history/schema.js.map +1 -0
  357. package/dist/mcp/history/summarizer.d.ts +81 -0
  358. package/dist/mcp/history/summarizer.js +196 -0
  359. package/dist/mcp/history/summarizer.js.map +1 -0
  360. package/dist/mcp/history/walker.d.ts +57 -0
  361. package/dist/mcp/history/walker.js +156 -0
  362. package/dist/mcp/history/walker.js.map +1 -0
  363. package/dist/mcp/index.d.ts +13 -0
  364. package/dist/mcp/index.js +9 -0
  365. package/dist/mcp/index.js.map +1 -0
  366. package/dist/mcp/path-allowlist.d.ts +29 -0
  367. package/dist/mcp/path-allowlist.js +71 -0
  368. package/dist/mcp/path-allowlist.js.map +1 -0
  369. package/dist/mcp/result.d.ts +8 -0
  370. package/dist/mcp/result.js +18 -0
  371. package/dist/mcp/result.js.map +1 -0
  372. package/dist/mcp/schemas.d.ts +192 -0
  373. package/dist/mcp/schemas.js +174 -0
  374. package/dist/mcp/schemas.js.map +1 -0
  375. package/dist/mcp/serve.d.ts +15 -0
  376. package/dist/mcp/serve.js +71 -0
  377. package/dist/mcp/serve.js.map +1 -0
  378. package/dist/mcp/server.d.ts +11 -0
  379. package/dist/mcp/server.js +58 -0
  380. package/dist/mcp/server.js.map +1 -0
  381. package/dist/mcp/telemetry.d.ts +15 -0
  382. package/dist/mcp/telemetry.js +13 -0
  383. package/dist/mcp/telemetry.js.map +1 -0
  384. package/dist/mcp/tools/append-run-note.d.ts +18 -0
  385. package/dist/mcp/tools/append-run-note.js +47 -0
  386. package/dist/mcp/tools/append-run-note.js.map +1 -0
  387. package/dist/mcp/tools/append.d.ts +8 -0
  388. package/dist/mcp/tools/append.js +37 -0
  389. package/dist/mcp/tools/append.js.map +1 -0
  390. package/dist/mcp/tools/archive.d.ts +8 -0
  391. package/dist/mcp/tools/archive.js +72 -0
  392. package/dist/mcp/tools/archive.js.map +1 -0
  393. package/dist/mcp/tools/ask-operator.d.ts +34 -0
  394. package/dist/mcp/tools/ask-operator.js +97 -0
  395. package/dist/mcp/tools/ask-operator.js.map +1 -0
  396. package/dist/mcp/tools/canonical-for-topic.d.ts +6 -0
  397. package/dist/mcp/tools/canonical-for-topic.js +40 -0
  398. package/dist/mcp/tools/canonical-for-topic.js.map +1 -0
  399. package/dist/mcp/tools/decision-get.d.ts +6 -0
  400. package/dist/mcp/tools/decision-get.js +49 -0
  401. package/dist/mcp/tools/decision-get.js.map +1 -0
  402. package/dist/mcp/tools/decisions-for-symbol.d.ts +7 -0
  403. package/dist/mcp/tools/decisions-for-symbol.js +42 -0
  404. package/dist/mcp/tools/decisions-for-symbol.js.map +1 -0
  405. package/dist/mcp/tools/decisions-in-scope.d.ts +7 -0
  406. package/dist/mcp/tools/decisions-in-scope.js +47 -0
  407. package/dist/mcp/tools/decisions-in-scope.js.map +1 -0
  408. package/dist/mcp/tools/drop-task.d.ts +12 -0
  409. package/dist/mcp/tools/drop-task.js +68 -0
  410. package/dist/mcp/tools/drop-task.js.map +1 -0
  411. package/dist/mcp/tools/get-full.d.ts +7 -0
  412. package/dist/mcp/tools/get-full.js +46 -0
  413. package/dist/mcp/tools/get-full.js.map +1 -0
  414. package/dist/mcp/tools/ground-get.d.ts +7 -0
  415. package/dist/mcp/tools/ground-get.js +77 -0
  416. package/dist/mcp/tools/ground-get.js.map +1 -0
  417. package/dist/mcp/tools/index.d.ts +3 -0
  418. package/dist/mcp/tools/index.js +40 -0
  419. package/dist/mcp/tools/index.js.map +1 -0
  420. package/dist/mcp/tools/invariant-get.d.ts +6 -0
  421. package/dist/mcp/tools/invariant-get.js +49 -0
  422. package/dist/mcp/tools/invariant-get.js.map +1 -0
  423. package/dist/mcp/tools/invariants-in-scope.d.ts +7 -0
  424. package/dist/mcp/tools/invariants-in-scope.js +62 -0
  425. package/dist/mcp/tools/invariants-in-scope.js.map +1 -0
  426. package/dist/mcp/tools/query-history.d.ts +20 -0
  427. package/dist/mcp/tools/query-history.js +51 -0
  428. package/dist/mcp/tools/query-history.js.map +1 -0
  429. package/dist/mcp/tools/record-decision.d.ts +14 -0
  430. package/dist/mcp/tools/record-decision.js +98 -0
  431. package/dist/mcp/tools/record-decision.js.map +1 -0
  432. package/dist/mcp/tools/record-run-event.d.ts +10 -0
  433. package/dist/mcp/tools/record-run-event.js +32 -0
  434. package/dist/mcp/tools/record-run-event.js.map +1 -0
  435. package/dist/mcp/tools/resolve-attention.d.ts +31 -0
  436. package/dist/mcp/tools/resolve-attention.js +191 -0
  437. package/dist/mcp/tools/resolve-attention.js.map +1 -0
  438. package/dist/mcp/tools/search.d.ts +9 -0
  439. package/dist/mcp/tools/search.js +164 -0
  440. package/dist/mcp/tools/search.js.map +1 -0
  441. package/dist/mcp/tools/supersedes-chain.d.ts +6 -0
  442. package/dist/mcp/tools/supersedes-chain.js +66 -0
  443. package/dist/mcp/tools/supersedes-chain.js.map +1 -0
  444. package/dist/mcp/tools/timeline.d.ts +9 -0
  445. package/dist/mcp/tools/timeline.js +65 -0
  446. package/dist/mcp/tools/timeline.js.map +1 -0
  447. package/dist/mcp/tools/types.d.ts +9 -0
  448. package/dist/mcp/tools/types.js +2 -0
  449. package/dist/mcp/tools/types.js.map +1 -0
  450. package/dist/mirror/clone.d.ts +6 -0
  451. package/dist/mirror/clone.js +48 -0
  452. package/dist/mirror/clone.js.map +1 -0
  453. package/dist/mirror/dirty-overlap.d.ts +13 -0
  454. package/dist/mirror/dirty-overlap.js +42 -0
  455. package/dist/mirror/dirty-overlap.js.map +1 -0
  456. package/dist/mirror/index.d.ts +7 -0
  457. package/dist/mirror/index.js +7 -0
  458. package/dist/mirror/index.js.map +1 -0
  459. package/dist/mirror/paths.d.ts +18 -0
  460. package/dist/mirror/paths.js +45 -0
  461. package/dist/mirror/paths.js.map +1 -0
  462. package/dist/mirror/push.d.ts +9 -0
  463. package/dist/mirror/push.js +27 -0
  464. package/dist/mirror/push.js.map +1 -0
  465. package/dist/mirror/state.d.ts +4 -0
  466. package/dist/mirror/state.js +36 -0
  467. package/dist/mirror/state.js.map +1 -0
  468. package/dist/mirror/sync.d.ts +9 -0
  469. package/dist/mirror/sync.js +33 -0
  470. package/dist/mirror/sync.js.map +1 -0
  471. package/dist/mirror/types.d.ts +77 -0
  472. package/dist/mirror/types.js +2 -0
  473. package/dist/mirror/types.js.map +1 -0
  474. package/dist/paths/index.d.ts +23 -0
  475. package/dist/paths/index.js +50 -0
  476. package/dist/paths/index.js.map +1 -0
  477. package/dist/profiles/index.d.ts +3 -0
  478. package/dist/profiles/index.js +3 -0
  479. package/dist/profiles/index.js.map +1 -0
  480. package/dist/profiles/registry.d.ts +5 -0
  481. package/dist/profiles/registry.js +31 -0
  482. package/dist/profiles/registry.js.map +1 -0
  483. package/dist/profiles/types.d.ts +48 -0
  484. package/dist/profiles/types.js +11 -0
  485. package/dist/profiles/types.js.map +1 -0
  486. package/dist/profiles/unknown.d.ts +9 -0
  487. package/dist/profiles/unknown.js +17 -0
  488. package/dist/profiles/unknown.js.map +1 -0
  489. package/dist/prompt.d.ts +19 -0
  490. package/dist/prompt.js +50 -0
  491. package/dist/prompt.js.map +1 -0
  492. package/dist/sensors/attestation.d.ts +44 -0
  493. package/dist/sensors/attestation.js +262 -0
  494. package/dist/sensors/attestation.js.map +1 -0
  495. package/dist/sensors/catalog.d.ts +41 -0
  496. package/dist/sensors/catalog.js +123 -0
  497. package/dist/sensors/catalog.js.map +1 -0
  498. package/dist/sensors/decisions.d.ts +30 -0
  499. package/dist/sensors/decisions.js +393 -0
  500. package/dist/sensors/decisions.js.map +1 -0
  501. package/dist/sensors/diff.d.ts +27 -0
  502. package/dist/sensors/diff.js +148 -0
  503. package/dist/sensors/diff.js.map +1 -0
  504. package/dist/sensors/index.d.ts +13 -0
  505. package/dist/sensors/index.js +9 -0
  506. package/dist/sensors/index.js.map +1 -0
  507. package/dist/sensors/remediation.d.ts +20 -0
  508. package/dist/sensors/remediation.js +65 -0
  509. package/dist/sensors/remediation.js.map +1 -0
  510. package/dist/sensors/runner.d.ts +44 -0
  511. package/dist/sensors/runner.js +95 -0
  512. package/dist/sensors/runner.js.map +1 -0
  513. package/dist/sensors/structural.d.ts +30 -0
  514. package/dist/sensors/structural.js +204 -0
  515. package/dist/sensors/structural.js.map +1 -0
  516. package/dist/sensors/stub-catalog.d.ts +39 -0
  517. package/dist/sensors/stub-catalog.js +115 -0
  518. package/dist/sensors/stub-catalog.js.map +1 -0
  519. package/dist/sensors/types.d.ts +135 -0
  520. package/dist/sensors/types.js +14 -0
  521. package/dist/sensors/types.js.map +1 -0
  522. package/dist/session/events-marker.d.ts +39 -0
  523. package/dist/session/events-marker.js +74 -0
  524. package/dist/session/events-marker.js.map +1 -0
  525. package/dist/session/id.d.ts +83 -0
  526. package/dist/session/id.js +166 -0
  527. package/dist/session/id.js.map +1 -0
  528. package/dist/session/index.d.ts +14 -0
  529. package/dist/session/index.js +13 -0
  530. package/dist/session/index.js.map +1 -0
  531. package/dist/session-start/build.d.ts +53 -0
  532. package/dist/session-start/build.js +645 -0
  533. package/dist/session-start/build.js.map +1 -0
  534. package/dist/session-start/index.d.ts +18 -0
  535. package/dist/session-start/index.js +18 -0
  536. package/dist/session-start/index.js.map +1 -0
  537. package/dist/session-start/templates.d.ts +6 -0
  538. package/dist/session-start/templates.js +38 -0
  539. package/dist/session-start/templates.js.map +1 -0
  540. package/dist/status-line/format.d.ts +14 -0
  541. package/dist/status-line/format.js +40 -0
  542. package/dist/status-line/format.js.map +1 -0
  543. package/dist/status-line/index.d.ts +29 -0
  544. package/dist/status-line/index.js +14 -0
  545. package/dist/status-line/index.js.map +1 -0
  546. package/dist/status-line/reader.d.ts +13 -0
  547. package/dist/status-line/reader.js +76 -0
  548. package/dist/status-line/reader.js.map +1 -0
  549. package/dist/status-line/writer.d.ts +33 -0
  550. package/dist/status-line/writer.js +72 -0
  551. package/dist/status-line/writer.js.map +1 -0
  552. package/dist/tier0/classify.d.ts +10 -0
  553. package/dist/tier0/classify.js +110 -0
  554. package/dist/tier0/classify.js.map +1 -0
  555. package/dist/tier0/index.d.ts +2 -0
  556. package/dist/tier0/index.js +2 -0
  557. package/dist/tier0/index.js.map +1 -0
  558. package/dist/tier0/ollama.d.ts +22 -0
  559. package/dist/tier0/ollama.js +63 -0
  560. package/dist/tier0/ollama.js.map +1 -0
  561. package/dist/tier0/types.d.ts +24 -0
  562. package/dist/tier0/types.js +9 -0
  563. package/dist/tier0/types.js.map +1 -0
  564. package/dist/tightener/index.d.ts +4 -0
  565. package/dist/tightener/index.js +4 -0
  566. package/dist/tightener/index.js.map +1 -0
  567. package/dist/tightener/prompt.d.ts +3 -0
  568. package/dist/tightener/prompt.js +67 -0
  569. package/dist/tightener/prompt.js.map +1 -0
  570. package/dist/tightener/schema.d.ts +68 -0
  571. package/dist/tightener/schema.js +44 -0
  572. package/dist/tightener/schema.js.map +1 -0
  573. package/dist/tightener/tighten.d.ts +2 -0
  574. package/dist/tightener/tighten.js +66 -0
  575. package/dist/tightener/tighten.js.map +1 -0
  576. package/dist/tightener/types.d.ts +74 -0
  577. package/dist/tightener/types.js +6 -0
  578. package/dist/tightener/types.js.map +1 -0
  579. package/dist/voice/index.d.ts +4 -0
  580. package/dist/voice/index.js +4 -0
  581. package/dist/voice/index.js.map +1 -0
  582. package/dist/voice/model.d.ts +23 -0
  583. package/dist/voice/model.js +46 -0
  584. package/dist/voice/model.js.map +1 -0
  585. package/dist/voice/pipe.d.ts +9 -0
  586. package/dist/voice/pipe.js +47 -0
  587. package/dist/voice/pipe.js.map +1 -0
  588. package/dist/voice/transcribe.d.ts +3 -0
  589. package/dist/voice/transcribe.js +43 -0
  590. package/dist/voice/transcribe.js.map +1 -0
  591. package/dist/voice/types.d.ts +26 -0
  592. package/dist/voice/types.js +9 -0
  593. package/dist/voice/types.js.map +1 -0
  594. package/package.json +54 -0
  595. package/templates/.archive/README.md +67 -0
  596. package/templates/.cairn/JOIN.md +87 -0
  597. package/templates/.cairn/config/sensors.yaml +185 -0
  598. package/templates/.cairn/config/stub-patterns.yaml +231 -0
  599. package/templates/.cairn/config/trust-policy.yaml +95 -0
  600. package/templates/.cairn/config/workflow.md +230 -0
  601. package/templates/.cairn/git-hooks/commit-msg +17 -0
  602. package/templates/.cairn/git-hooks/post-commit +28 -0
  603. package/templates/.cairn/git-hooks/pre-commit +24 -0
  604. package/templates/.cairn/ground/brand/overview.md +24 -0
  605. package/templates/.cairn/ground/brand/voice.md +20 -0
  606. package/templates/.cairn/ground/canonical-map/topics.yaml +54 -0
  607. package/templates/.cairn/ground/capabilities/mcp-tools.yaml +4 -0
  608. package/templates/.cairn/ground/capabilities/skills.yaml +3 -0
  609. package/templates/.cairn/ground/capabilities/snippets.yaml +3 -0
  610. package/templates/.cairn/ground/manifest.yaml +16 -0
  611. package/templates/.cairn/ground/product/personas.yaml +4 -0
  612. package/templates/.cairn/ground/product/positioning.md +21 -0
  613. package/templates/.claude/settings.json +57 -0
  614. package/templates/.github/workflows/cairn-check.yml +31 -0
  615. package/templates/.mcp.json +8 -0
  616. package/templates/README.md +24 -0
@@ -0,0 +1,134 @@
1
+ /**
2
+ * Batch canary — verifies a multi-commit GC batch hasn't broken anything that
3
+ * shows only when the commits are taken together: "individually safe,
4
+ * collectively broken."
5
+ *
6
+ * Two checks run after the batch lands locally and BEFORE any push:
7
+ *
8
+ * 1. workflow.md re-render against a synthetic-task fixture.
9
+ * The orchestrator injects this template on every run; if a GC batch
10
+ * removed a placeholder section, broke a `{{var}}` token, or left
11
+ * orphaned `{{#each}}` blocks, the next live run would silently produce
12
+ * a malformed prompt. Render the template against a known-good fixture
13
+ * and assert (a) every `{{...}}` resolves and (b) the expected section
14
+ * headers (`## Task`, `## Acceptance criteria`, `## Decisions in scope`,
15
+ * `## Sensors that will run`) survive.
16
+ *
17
+ * 2. Manifest rebuild + ground-zone consistency.
18
+ * Re-run `buildManifest` against the post-batch tree. If it throws or
19
+ * produces zero entries (the canonical zone went empty), the batch
20
+ * broke ground.
21
+ *
22
+ * Both checks are pure-mechanical — no claude burn — and run in milliseconds.
23
+ * They are not exhaustive (no runtime sensor sweep against a synthetic diff
24
+ * yet; that's deferred to a richer Phase 12.x revision when the orchestrator
25
+ * exposes an "isolated sensor sweep" entry point).
26
+ */
27
+ import { existsSync, readFileSync } from "node:fs";
28
+ import { join } from "node:path";
29
+ import { buildManifest } from "../ground/manifest.js";
30
+ import { loadWorkflowTemplate, renderTemplate } from "../prompt.js";
31
+ const REQUIRED_SECTION_HEADINGS = [
32
+ "## Task",
33
+ "## Acceptance criteria",
34
+ "## Decisions in scope",
35
+ "## Off-limits paths",
36
+ "## Sensors that will run",
37
+ ];
38
+ const UNRESOLVED_TOKEN_RE = /\{\{[^}]*\}\}/;
39
+ export function buildSyntheticContext() {
40
+ return {
41
+ agent_role: "implementer",
42
+ project_name: "canary",
43
+ run_id: "canary-run",
44
+ mirror_path: "/tmp/canary-mirror",
45
+ sha_pin: "0000000000000000000000000000000000000000",
46
+ tightened_spec_body: "Canary fixture body — non-empty.",
47
+ acceptance_criteria: ["Renders workflow.md without unresolved tokens."],
48
+ in_scope_decisions: [
49
+ { id: "D-CANARY-1", title: "Canary decision", scope_summary: "fixture" },
50
+ ],
51
+ in_scope_invariants: [{ id: "V-CANARY-1", title: "Canary invariant" }],
52
+ off_limits: [".git/**", ".archive/**"],
53
+ scoped_sensors: [
54
+ { id: "stub-pattern-catalog", description: "Layer A stub catalog" },
55
+ { id: "attestation-cross-check", description: "Layer B attestation cross-check" },
56
+ ],
57
+ };
58
+ }
59
+ export function verifyBatchCanary(opts) {
60
+ const failures = [];
61
+ const ctx = opts.syntheticContext ?? buildSyntheticContext();
62
+ // 1. Workflow template re-render.
63
+ let template = "";
64
+ let rendered = "";
65
+ try {
66
+ template = loadWorkflowTemplate(opts.repoRoot);
67
+ }
68
+ catch (err) {
69
+ failures.push(`workflow.md template missing or unreadable: ${err.message}`);
70
+ }
71
+ if (template.length === 0) {
72
+ failures.push("workflow.md template is empty after frontmatter strip");
73
+ }
74
+ else {
75
+ rendered = renderTemplate(template, {
76
+ agent_role: ctx.agent_role,
77
+ project_name: ctx.project_name,
78
+ run_id: ctx.run_id,
79
+ mirror_path: ctx.mirror_path,
80
+ sha_pin: ctx.sha_pin,
81
+ tightened_spec_body: ctx.tightened_spec_body,
82
+ acceptance_criteria: ctx.acceptance_criteria,
83
+ in_scope_decisions: ctx.in_scope_decisions,
84
+ in_scope_invariants: ctx.in_scope_invariants,
85
+ off_limits: ctx.off_limits,
86
+ scoped_sensors: ctx.scoped_sensors,
87
+ });
88
+ if (UNRESOLVED_TOKEN_RE.test(rendered)) {
89
+ const m = rendered.match(UNRESOLVED_TOKEN_RE);
90
+ failures.push(`workflow.md rendered prompt contains unresolved token: ${m?.[0] ?? "<unknown>"}`);
91
+ }
92
+ for (const heading of REQUIRED_SECTION_HEADINGS) {
93
+ if (!rendered.includes(heading)) {
94
+ failures.push(`workflow.md rendered prompt missing section: \`${heading}\``);
95
+ }
96
+ }
97
+ }
98
+ // 2. Manifest rebuild (canonical-zone integrity).
99
+ let manifestFiles = 0;
100
+ try {
101
+ const manifest = buildManifest({ repoRoot: opts.repoRoot, generator: "gc.canary" });
102
+ manifestFiles = manifest.files.length;
103
+ if (manifestFiles === 0) {
104
+ failures.push("manifest rebuild produced zero canonical-zone files");
105
+ }
106
+ }
107
+ catch (err) {
108
+ failures.push(`manifest rebuild threw: ${err.message}`);
109
+ }
110
+ // 3. Sanity: workflow.md exists at the expected path (loadWorkflowTemplate
111
+ // already throws when missing, but a missing template yields the more
112
+ // detailed failure above; this check ensures the path itself is right).
113
+ const workflowPath = join(opts.repoRoot, ".cairn", "config", "workflow.md");
114
+ if (!existsSync(workflowPath)) {
115
+ failures.push(`workflow.md not found at .cairn/config/workflow.md`);
116
+ }
117
+ else {
118
+ // Cheap re-read to ensure we can read it post-batch (catches an edit that
119
+ // wrote invalid utf-8 etc).
120
+ try {
121
+ readFileSync(workflowPath, "utf8");
122
+ }
123
+ catch (err) {
124
+ failures.push(`workflow.md unreadable post-batch: ${err.message}`);
125
+ }
126
+ }
127
+ return {
128
+ ok: failures.length === 0,
129
+ failures,
130
+ manifest_files: manifestFiles,
131
+ rendered_length: rendered.length,
132
+ };
133
+ }
134
+ //# sourceMappingURL=canary.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"canary.js","sourceRoot":"","sources":["../../src/gc/canary.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,24 @@
1
+ /**
2
+ * GC pass — citation integrity.
3
+ *
4
+ * Walks every source file in the repo and scans for cairn citations
5
+ * (§V invariants, TODO(TSK-...) linked todos, banned DEC-N comments).
6
+ * Each citation is resolved against the appropriate source of truth:
7
+ * - §V<N> → invariants.ledger.yaml. Missing → orphaned. superseded_by set
8
+ * anywhere in the ledger → superseded citation.
9
+ * - DEC-<N> → always a policy violation per PRIMER §10 (DEC-id inline
10
+ * comments are banned).
11
+ * - TODO(TSK-<id>) → tasks/{active,done}/<id>/. Missing → orphan; "done"
12
+ * isn't a finding (TODO will be removed when the agent
13
+ * gets to it; flagging is noisy).
14
+ */
15
+ import type { GcFinding } from "./types.js";
16
+ export interface CitationIntegrityOptions {
17
+ repoRoot: string;
18
+ /** Cap on file size to scan (bytes). Default 256 KB. */
19
+ maxFileBytes?: number;
20
+ }
21
+ export interface CitationIntegrityResult {
22
+ findings: GcFinding[];
23
+ }
24
+ export declare function runCitationIntegrity(opts: CitationIntegrityOptions): CitationIntegrityResult;
@@ -0,0 +1,151 @@
1
+ /**
2
+ * GC pass — citation integrity.
3
+ *
4
+ * Walks every source file in the repo and scans for cairn citations
5
+ * (§V invariants, TODO(TSK-...) linked todos, banned DEC-N comments).
6
+ * Each citation is resolved against the appropriate source of truth:
7
+ * - §V<N> → invariants.ledger.yaml. Missing → orphaned. superseded_by set
8
+ * anywhere in the ledger → superseded citation.
9
+ * - DEC-<N> → always a policy violation per PRIMER §10 (DEC-id inline
10
+ * comments are banned).
11
+ * - TODO(TSK-<id>) → tasks/{active,done}/<id>/. Missing → orphan; "done"
12
+ * isn't a finding (TODO will be removed when the agent
13
+ * gets to it; flagging is noisy).
14
+ */
15
+ import { existsSync, readFileSync, statSync } from "node:fs";
16
+ import { join } from "node:path";
17
+ import { parse as parseYaml } from "yaml";
18
+ import { buildInvariantsLedger } from "../ground/index.js";
19
+ import { invariantsLedgerPath } from "../ground/paths.js";
20
+ import { scanCitations } from "../hooks/post-tool-use/citation-scanner.js";
21
+ import { walkSourceTree } from "./walk-source.js";
22
+ const PASS_ID = "citation-integrity";
23
+ const TEXT_EXTS = new Set([
24
+ ".ts", ".tsx", ".js", ".jsx", ".mjs", ".cjs",
25
+ ".py", ".rb", ".go", ".rs", ".java", ".c", ".cc", ".cpp", ".h", ".hpp",
26
+ ".swift", ".kt", ".sh", ".bash", ".zsh",
27
+ ".sql", ".html", ".vue", ".svelte", ".css", ".scss",
28
+ ]);
29
+ function loadInvariants(repoRoot) {
30
+ const active = new Set();
31
+ for (const e of buildInvariantsLedger({ repoRoot })) {
32
+ active.add(e.id);
33
+ }
34
+ const superseded = new Map();
35
+ const path = invariantsLedgerPath(repoRoot);
36
+ if (!existsSync(path)) {
37
+ return { active, superseded };
38
+ }
39
+ let parsed;
40
+ try {
41
+ parsed = parseYaml(readFileSync(path, "utf8"));
42
+ }
43
+ catch {
44
+ return { active, superseded };
45
+ }
46
+ if (!Array.isArray(parsed))
47
+ return { active, superseded };
48
+ for (const entry of parsed) {
49
+ if (typeof entry !== "object" || entry === null)
50
+ continue;
51
+ const e = entry;
52
+ const id = typeof e["id"] === "string" ? e["id"] : null;
53
+ const supBy = typeof e["superseded_by"] === "string" ? e["superseded_by"] : null;
54
+ if (id !== null && supBy !== null && supBy.length > 0) {
55
+ superseded.set(id, supBy);
56
+ }
57
+ }
58
+ return { active, superseded };
59
+ }
60
+ function fileExt(path) {
61
+ const idx = path.lastIndexOf(".");
62
+ if (idx === -1)
63
+ return "";
64
+ return path.slice(idx).toLowerCase();
65
+ }
66
+ export function runCitationIntegrity(opts) {
67
+ const findings = [];
68
+ const maxBytes = opts.maxFileBytes ?? 256 * 1024;
69
+ const invariants = loadInvariants(opts.repoRoot);
70
+ const files = walkSourceTree(opts.repoRoot);
71
+ for (const rel of files) {
72
+ if (!TEXT_EXTS.has(fileExt(rel)))
73
+ continue;
74
+ const abs = join(opts.repoRoot, rel);
75
+ let size;
76
+ try {
77
+ size = statSync(abs).size;
78
+ }
79
+ catch {
80
+ continue;
81
+ }
82
+ if (size > maxBytes)
83
+ continue;
84
+ let content;
85
+ try {
86
+ content = readFileSync(abs, "utf8");
87
+ }
88
+ catch {
89
+ continue;
90
+ }
91
+ if (content.length === 0)
92
+ continue;
93
+ const matches = scanCitations(content);
94
+ // §V invariants
95
+ for (const m of matches.invariants) {
96
+ if (invariants.superseded.has(m.id)) {
97
+ const supBy = invariants.superseded.get(m.id) ?? "(unknown)";
98
+ findings.push({
99
+ pass: PASS_ID,
100
+ kind: "superseded_citation",
101
+ path: rel,
102
+ detail: `${rel}:${m.line} cites §${m.id}, which is superseded by §${supBy}`,
103
+ severity: "warn",
104
+ line: m.line,
105
+ });
106
+ continue;
107
+ }
108
+ if (!invariants.active.has(m.id)) {
109
+ findings.push({
110
+ pass: PASS_ID,
111
+ kind: "orphaned_citation",
112
+ path: rel,
113
+ detail: `${rel}:${m.line} cites §${m.id}, which is not in the invariants ledger`,
114
+ severity: "warn",
115
+ line: m.line,
116
+ });
117
+ }
118
+ }
119
+ // DEC-N inline comments — always a policy violation per PRIMER §10
120
+ for (const m of matches.decIds) {
121
+ findings.push({
122
+ pass: PASS_ID,
123
+ kind: "banned_dec_comment",
124
+ path: rel,
125
+ detail: `${rel}:${m.line} contains ${m.id} inline comment — DEC-id citations are banned per PRIMER §10`,
126
+ severity: "warn",
127
+ line: m.line,
128
+ });
129
+ }
130
+ // TODO(TSK-...) — check active/done dirs
131
+ for (const m of matches.todos) {
132
+ const taskId = m.id; // already "TSK-..."
133
+ const activeDir = join(opts.repoRoot, ".cairn", "tasks", "active", taskId);
134
+ const doneDir = join(opts.repoRoot, ".cairn", "tasks", "done", taskId);
135
+ if (existsSync(activeDir))
136
+ continue; // active TODO — fine
137
+ if (existsSync(doneDir))
138
+ continue; // done — agent will remove eventually; not a finding
139
+ findings.push({
140
+ pass: PASS_ID,
141
+ kind: "orphaned_citation",
142
+ path: rel,
143
+ detail: `${rel}:${m.line} references ${taskId}, which is not in tasks/{active,done}/`,
144
+ severity: "warn",
145
+ line: m.line,
146
+ });
147
+ }
148
+ }
149
+ return { findings };
150
+ }
151
+ //# sourceMappingURL=citation-integrity.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"citation-integrity.js","sourceRoot":"","sources":["../../src/gc/citation-integrity.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,25 @@
1
+ /**
2
+ * Auto-merge classification per PRIMER §12.2.
3
+ *
4
+ * Given a set of repo-relative paths a commit will touch, return one of:
5
+ * safe — formatting, doc regen, frontmatter refresh, generated content,
6
+ * archive moves, stub-catalog additions, .cairn/ground/* writes
7
+ * code — touches *.ts / *.tsx / *.js outside generator-managed files
8
+ * high-stakes — any path matches projectGlobs.high_stakes_globs
9
+ *
10
+ * The classifier is deliberately conservative: when in doubt, escalate. A
11
+ * single high-stakes hit dominates the result. A single code hit dominates
12
+ * over safe.
13
+ */
14
+ import type { ProjectGlobs } from "../sensors/types.js";
15
+ import type { GcAutoMergeClass } from "./types.js";
16
+ export interface ClassifyArgs {
17
+ paths: readonly string[];
18
+ projectGlobs?: ProjectGlobs;
19
+ /**
20
+ * Globs of paths the cairn considers generator-managed — touching these
21
+ * stays safe-class even when the extension is .ts. Default: empty.
22
+ */
23
+ generatorManagedGlobs?: readonly string[];
24
+ }
25
+ export declare function classifyAutoMerge(args: ClassifyArgs): GcAutoMergeClass;
@@ -0,0 +1,89 @@
1
+ /**
2
+ * Auto-merge classification per PRIMER §12.2.
3
+ *
4
+ * Given a set of repo-relative paths a commit will touch, return one of:
5
+ * safe — formatting, doc regen, frontmatter refresh, generated content,
6
+ * archive moves, stub-catalog additions, .cairn/ground/* writes
7
+ * code — touches *.ts / *.tsx / *.js outside generator-managed files
8
+ * high-stakes — any path matches projectGlobs.high_stakes_globs
9
+ *
10
+ * The classifier is deliberately conservative: when in doubt, escalate. A
11
+ * single high-stakes hit dominates the result. A single code hit dominates
12
+ * over safe.
13
+ */
14
+ import { matchAnyGlob } from "../ground/glob.js";
15
+ /** Patterns the classifier always treats as safe regardless of file type. */
16
+ const SAFE_PATH_PREFIXES = [
17
+ ".cairn/ground/",
18
+ ".cairn/staleness/",
19
+ ".cairn/runs/terminal/",
20
+ ".archive/",
21
+ ];
22
+ /** Doc / config / generated extensions. Not safe by themselves; combined with
23
+ * off-source-tree location they are. */
24
+ const DOC_LIKE_EXTS = [".md", ".yaml", ".yml", ".json", ".txt"];
25
+ /** Source-code extensions that escalate to code-class. */
26
+ const CODE_EXTS = [
27
+ ".ts",
28
+ ".tsx",
29
+ ".cts",
30
+ ".mts",
31
+ ".js",
32
+ ".jsx",
33
+ ".cjs",
34
+ ".mjs",
35
+ ".py",
36
+ ".rb",
37
+ ".go",
38
+ ".rs",
39
+ ];
40
+ export function classifyAutoMerge(args) {
41
+ const highStakes = args.projectGlobs?.high_stakes_globs ?? [];
42
+ const generated = args.generatorManagedGlobs ?? args.projectGlobs?.generator_source_globs ?? [];
43
+ let cls = "safe";
44
+ for (const path of args.paths) {
45
+ if (highStakes.length > 0 && matchAnyGlob(path, highStakes)) {
46
+ return "high-stakes";
47
+ }
48
+ if (cls === "code")
49
+ continue; // already escalated; only high-stakes upgrade further
50
+ if (isSafePath(path, generated))
51
+ continue;
52
+ if (isCodePath(path)) {
53
+ cls = "code";
54
+ continue;
55
+ }
56
+ // Unknown extension under the canonical zone — keep as safe; .archive
57
+ // moves or yaml writes etc.
58
+ }
59
+ return cls;
60
+ }
61
+ function isSafePath(path, generatorManagedGlobs) {
62
+ for (const prefix of SAFE_PATH_PREFIXES) {
63
+ if (path.startsWith(prefix))
64
+ return true;
65
+ }
66
+ if (generatorManagedGlobs.length > 0 && matchAnyGlob(path, generatorManagedGlobs)) {
67
+ return true;
68
+ }
69
+ // Documentation files are safe.
70
+ if (path.startsWith("docs/"))
71
+ return true;
72
+ if (path === "AGENTS.md" || path === "CLAUDE.md" || path === "README.md")
73
+ return true;
74
+ // Frontmatter / config under .cairn/config/* is safe (the GC pass that
75
+ // writes there is doing config maintenance, not source change).
76
+ if (path.startsWith(".cairn/config/") || path.startsWith(".claude/"))
77
+ return true;
78
+ // Generic doc-extension files outside the source tree fall here.
79
+ for (const ext of DOC_LIKE_EXTS) {
80
+ if (path.endsWith(ext))
81
+ return true;
82
+ }
83
+ return false;
84
+ }
85
+ function isCodePath(path) {
86
+ const lower = path.toLowerCase();
87
+ return CODE_EXTS.some((e) => lower.endsWith(e));
88
+ }
89
+ //# sourceMappingURL=classify.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"classify.js","sourceRoot":"","sources":["../../src/gc/classify.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;GAYG;AAEH,OAAO,EAAE,YAAY,EAAE,MAAM,mBAAmB,CAAC;AAIjD,6EAA6E;AAC7E,MAAM,kBAAkB,GAAG;IACzB,gBAAgB;IAChB,mBAAmB;IACnB,uBAAuB;IACvB,WAAW;CACZ,CAAC;AAEF;yCACyC;AACzC,MAAM,aAAa,GAAG,CAAC,KAAK,EAAE,OAAO,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,CAAC,CAAC;AAEhE,0DAA0D;AAC1D,MAAM,SAAS,GAAG;IAChB,KAAK;IACL,MAAM;IACN,MAAM;IACN,MAAM;IACN,KAAK;IACL,MAAM;IACN,MAAM;IACN,MAAM;IACN,KAAK;IACL,KAAK;IACL,KAAK;IACL,KAAK;CACN,CAAC;AAYF,MAAM,UAAU,iBAAiB,CAAC,IAAkB;IAClD,MAAM,UAAU,GAAG,IAAI,CAAC,YAAY,EAAE,iBAAiB,IAAI,EAAE,CAAC;IAC9D,MAAM,SAAS,GAAG,IAAI,CAAC,qBAAqB,IAAI,IAAI,CAAC,YAAY,EAAE,sBAAsB,IAAI,EAAE,CAAC;IAEhG,IAAI,GAAG,GAAqB,MAAM,CAAC;IACnC,KAAK,MAAM,IAAI,IAAI,IAAI,CAAC,KAAK,EAAE,CAAC;QAC9B,IAAI,UAAU,CAAC,MAAM,GAAG,CAAC,IAAI,YAAY,CAAC,IAAI,EAAE,UAAU,CAAC,EAAE,CAAC;YAC5D,OAAO,aAAa,CAAC;QACvB,CAAC;QACD,IAAI,GAAG,KAAK,MAAM;YAAE,SAAS,CAAC,sDAAsD;QACpF,IAAI,UAAU,CAAC,IAAI,EAAE,SAAS,CAAC;YAAE,SAAS;QAC1C,IAAI,UAAU,CAAC,IAAI,CAAC,EAAE,CAAC;YACrB,GAAG,GAAG,MAAM,CAAC;YACb,SAAS;QACX,CAAC;QACD,sEAAsE;QACtE,4BAA4B;IAC9B,CAAC;IACD,OAAO,GAAG,CAAC;AACb,CAAC;AAED,SAAS,UAAU,CAAC,IAAY,EAAE,qBAAwC;IACxE,KAAK,MAAM,MAAM,IAAI,kBAAkB,EAAE,CAAC;QACxC,IAAI,IAAI,CAAC,UAAU,CAAC,MAAM,CAAC;YAAE,OAAO,IAAI,CAAC;IAC3C,CAAC;IACD,IAAI,qBAAqB,CAAC,MAAM,GAAG,CAAC,IAAI,YAAY,CAAC,IAAI,EAAE,qBAAqB,CAAC,EAAE,CAAC;QAClF,OAAO,IAAI,CAAC;IACd,CAAC;IACD,gCAAgC;IAChC,IAAI,IAAI,CAAC,UAAU,CAAC,OAAO,CAAC;QAAE,OAAO,IAAI,CAAC;IAC1C,IAAI,IAAI,KAAK,WAAW,IAAI,IAAI,KAAK,WAAW,IAAI,IAAI,KAAK,WAAW;QAAE,OAAO,IAAI,CAAC;IACtF,uEAAuE;IACvE,gEAAgE;IAChE,IAAI,IAAI,CAAC,UAAU,CAAC,gBAAgB,CAAC,IAAI,IAAI,CAAC,UAAU,CAAC,UAAU,CAAC;QAAE,OAAO,IAAI,CAAC;IAClF,iEAAiE;IACjE,KAAK,MAAM,GAAG,IAAI,aAAa,EAAE,CAAC;QAChC,IAAI,IAAI,CAAC,QAAQ,CAAC,GAAG,CAAC;YAAE,OAAO,IAAI,CAAC;IACtC,CAAC;IACD,OAAO,KAAK,CAAC;AACf,CAAC;AAED,SAAS,UAAU,CAAC,IAAY;IAC9B,MAAM,KAAK,GAAG,IAAI,CAAC,WAAW,EAAE,CAAC;IACjC,OAAO,SAAS,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,KAAK,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC,CAAC;AAClD,CAAC"}
@@ -0,0 +1,22 @@
1
+ /**
2
+ * GC pass — completion integrity.
3
+ *
4
+ * For every task in `.cairn/tasks/done/`, validate that:
5
+ * - status.yaml indicates phase: succeeded
6
+ * - related_run_ids has at least one entry (last entry is "the run")
7
+ * - the linked run dir exists in either runs/active/ or runs/terminal/
8
+ * - meta.json is present and parseable, with a sha_pin string
9
+ * - attestation.yaml is present
10
+ * - sensor-results.yaml is present and contains no failed entries
11
+ * - the attested sha_pin is reachable in the current git history
12
+ *
13
+ * All findings are kind: "task_integrity_error" with severity: "warn".
14
+ */
15
+ import type { GcFinding } from "./types.js";
16
+ export interface CompletionIntegrityOptions {
17
+ repoRoot: string;
18
+ }
19
+ export interface CompletionIntegrityResult {
20
+ findings: GcFinding[];
21
+ }
22
+ export declare function runCompletionIntegrity(opts: CompletionIntegrityOptions): Promise<CompletionIntegrityResult>;
@@ -0,0 +1,165 @@
1
+ /**
2
+ * GC pass — completion integrity.
3
+ *
4
+ * For every task in `.cairn/tasks/done/`, validate that:
5
+ * - status.yaml indicates phase: succeeded
6
+ * - related_run_ids has at least one entry (last entry is "the run")
7
+ * - the linked run dir exists in either runs/active/ or runs/terminal/
8
+ * - meta.json is present and parseable, with a sha_pin string
9
+ * - attestation.yaml is present
10
+ * - sensor-results.yaml is present and contains no failed entries
11
+ * - the attested sha_pin is reachable in the current git history
12
+ *
13
+ * All findings are kind: "task_integrity_error" with severity: "warn".
14
+ */
15
+ import { existsSync, readdirSync, readFileSync } from "node:fs";
16
+ import { join } from "node:path";
17
+ import { simpleGit } from "simple-git";
18
+ import { parse as parseYaml } from "yaml";
19
+ const PASS_ID = "completion-integrity";
20
+ export async function runCompletionIntegrity(opts) {
21
+ const findings = [];
22
+ const doneDir = join(opts.repoRoot, ".cairn", "tasks", "done");
23
+ if (!existsSync(doneDir))
24
+ return { findings };
25
+ let dirents;
26
+ try {
27
+ dirents = readdirSync(doneDir, { withFileTypes: true, encoding: "utf8" });
28
+ }
29
+ catch {
30
+ return { findings };
31
+ }
32
+ // Lazily-constructed git client; only needed if any task makes it past the
33
+ // attestation checks.
34
+ let git = null;
35
+ function ensureGit() {
36
+ if (git === null)
37
+ git = simpleGit({ baseDir: opts.repoRoot });
38
+ return git;
39
+ }
40
+ for (const entry of dirents) {
41
+ if (!entry.isDirectory())
42
+ continue;
43
+ const taskId = entry.name;
44
+ const taskDir = join(doneDir, taskId);
45
+ const statusPath = join(taskDir, "status.yaml");
46
+ if (!existsSync(statusPath)) {
47
+ findings.push(makeFinding(taskId, `tasks/done/${taskId}/status.yaml missing`));
48
+ continue;
49
+ }
50
+ let statusParsed;
51
+ try {
52
+ statusParsed = parseYaml(readFileSync(statusPath, "utf8"));
53
+ }
54
+ catch (err) {
55
+ findings.push(makeFinding(taskId, `tasks/done/${taskId}/status.yaml unparseable: ${stringifyErr(err)}`));
56
+ continue;
57
+ }
58
+ if (typeof statusParsed !== "object" || statusParsed === null) {
59
+ findings.push(makeFinding(taskId, `tasks/done/${taskId}/status.yaml is not an object`));
60
+ continue;
61
+ }
62
+ const status = statusParsed;
63
+ const phase = typeof status["phase"] === "string" ? status["phase"] : null;
64
+ if (phase !== "succeeded") {
65
+ // Tasks in done/ that aren't succeeded are presumably archived for
66
+ // another reason; skip — the pass is about completion integrity, not
67
+ // categorization.
68
+ continue;
69
+ }
70
+ const runIds = Array.isArray(status["related_run_ids"])
71
+ ? status["related_run_ids"].filter((x) => typeof x === "string")
72
+ : [];
73
+ const runId = runIds.length > 0 ? runIds[runIds.length - 1] : undefined;
74
+ if (runId === undefined) {
75
+ findings.push(makeFinding(taskId, `task ${taskId} in tasks/done/ has no related_run_ids`));
76
+ continue;
77
+ }
78
+ // Look in runs/terminal/ first (succeeded runs typically end up here),
79
+ // then fall back to runs/active/.
80
+ const terminalDir = join(opts.repoRoot, ".cairn", "runs", "terminal", runId);
81
+ const activeDir = join(opts.repoRoot, ".cairn", "runs", "active", runId);
82
+ let runDir = null;
83
+ if (existsSync(terminalDir))
84
+ runDir = terminalDir;
85
+ else if (existsSync(activeDir))
86
+ runDir = activeDir;
87
+ if (runDir === null) {
88
+ findings.push(makeFinding(taskId, `linked run dir not found for ${runId} (checked runs/{active,terminal}/)`));
89
+ continue;
90
+ }
91
+ const metaPath = join(runDir, "meta.json");
92
+ if (!existsSync(metaPath)) {
93
+ findings.push(makeFinding(taskId, `meta.json missing in ${relPathOf(opts.repoRoot, runDir)}`));
94
+ continue;
95
+ }
96
+ let meta;
97
+ try {
98
+ const raw = JSON.parse(readFileSync(metaPath, "utf8"));
99
+ if (typeof raw !== "object" || raw === null) {
100
+ findings.push(makeFinding(taskId, `meta.json malformed in ${relPathOf(opts.repoRoot, runDir)}`));
101
+ continue;
102
+ }
103
+ meta = raw;
104
+ }
105
+ catch (err) {
106
+ findings.push(makeFinding(taskId, `meta.json unparseable in ${relPathOf(opts.repoRoot, runDir)}: ${stringifyErr(err)}`));
107
+ continue;
108
+ }
109
+ const attestationPath = join(runDir, "attestation.yaml");
110
+ if (!existsSync(attestationPath)) {
111
+ findings.push(makeFinding(taskId, `attestation.yaml missing in ${relPathOf(opts.repoRoot, runDir)}`));
112
+ continue;
113
+ }
114
+ const sensorResultsPath = join(runDir, "sensor-results.yaml");
115
+ if (existsSync(sensorResultsPath)) {
116
+ let sensorParsed;
117
+ try {
118
+ sensorParsed = parseYaml(readFileSync(sensorResultsPath, "utf8"));
119
+ }
120
+ catch (err) {
121
+ findings.push(makeFinding(taskId, `sensor-results.yaml unparseable in ${relPathOf(opts.repoRoot, runDir)}: ${stringifyErr(err)}`));
122
+ continue;
123
+ }
124
+ if (Array.isArray(sensorParsed)) {
125
+ for (const r of sensorParsed) {
126
+ if (typeof r !== "object" || r === null)
127
+ continue;
128
+ const rr = r;
129
+ if (typeof rr["status"] === "string" && rr["status"] !== "pass") {
130
+ findings.push(makeFinding(taskId, `sensor failures present in completed task ${taskId} (sensor: ${typeof rr["sensor"] === "string" ? rr["sensor"] : "unknown"})`));
131
+ // Don't break — surface every failed sensor as its own finding.
132
+ }
133
+ }
134
+ }
135
+ }
136
+ // SHA reachability — skip if no sha_pin field.
137
+ const shaPin = typeof meta["sha_pin"] === "string" ? meta["sha_pin"] : null;
138
+ if (shaPin === null || shaPin.length === 0)
139
+ continue;
140
+ try {
141
+ await ensureGit().catFile(["-e", shaPin]);
142
+ // No throw → SHA reachable; nothing to surface.
143
+ }
144
+ catch {
145
+ findings.push(makeFinding(taskId, `attested SHA ${shaPin.slice(0, 7)} not found in git history (task ${taskId})`));
146
+ }
147
+ }
148
+ return { findings };
149
+ }
150
+ function makeFinding(taskId, detail) {
151
+ return {
152
+ pass: PASS_ID,
153
+ kind: "task_integrity_error",
154
+ path: `.cairn/tasks/done/${taskId}/`,
155
+ detail,
156
+ severity: "warn",
157
+ };
158
+ }
159
+ function stringifyErr(err) {
160
+ return err instanceof Error ? err.message : String(err);
161
+ }
162
+ function relPathOf(repoRoot, abs) {
163
+ return abs.startsWith(repoRoot) ? abs.slice(repoRoot.length + 1) : abs;
164
+ }
165
+ //# sourceMappingURL=completion-integrity.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"completion-integrity.js","sourceRoot":"","sources":["../../src/gc/completion-integrity.ts"],"names":[],"mappings":"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"}