@cavelang/cli 0.27.3 → 0.29.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 (321) hide show
  1. package/Authors.md +5 -0
  2. package/License.md +6 -0
  3. package/README.md +122 -24
  4. package/dist/internal/act/action.d.ts +69 -0
  5. package/dist/internal/act/action.d.ts.map +1 -0
  6. package/dist/internal/act/action.js +201 -0
  7. package/dist/internal/act/action.js.map +1 -0
  8. package/dist/internal/act/declare.d.ts +102 -0
  9. package/dist/internal/act/declare.d.ts.map +1 -0
  10. package/dist/internal/act/declare.js +270 -0
  11. package/dist/internal/act/declare.js.map +1 -0
  12. package/dist/internal/act/engine.d.ts +103 -0
  13. package/dist/internal/act/engine.d.ts.map +1 -0
  14. package/dist/internal/act/engine.js +298 -0
  15. package/dist/internal/act/engine.js.map +1 -0
  16. package/dist/internal/act/index.d.ts +27 -0
  17. package/dist/internal/act/index.d.ts.map +1 -0
  18. package/dist/internal/act/index.js +25 -0
  19. package/dist/internal/act/index.js.map +1 -0
  20. package/dist/internal/automate/automation.d.ts +78 -0
  21. package/dist/internal/automate/automation.d.ts.map +1 -0
  22. package/dist/internal/automate/automation.js +135 -0
  23. package/dist/internal/automate/automation.js.map +1 -0
  24. package/dist/internal/automate/declare.d.ts +84 -0
  25. package/dist/internal/automate/declare.d.ts.map +1 -0
  26. package/dist/internal/automate/declare.js +233 -0
  27. package/dist/internal/automate/declare.js.map +1 -0
  28. package/dist/internal/automate/engine.d.ts +125 -0
  29. package/dist/internal/automate/engine.d.ts.map +1 -0
  30. package/dist/internal/automate/engine.js +388 -0
  31. package/dist/internal/automate/engine.js.map +1 -0
  32. package/dist/internal/automate/index.d.ts +28 -0
  33. package/dist/internal/automate/index.d.ts.map +1 -0
  34. package/dist/internal/automate/index.js +26 -0
  35. package/dist/internal/automate/index.js.map +1 -0
  36. package/dist/internal/automate/main.d.ts +26 -0
  37. package/dist/internal/automate/main.d.ts.map +1 -0
  38. package/dist/internal/automate/main.js +298 -0
  39. package/dist/internal/automate/main.js.map +1 -0
  40. package/dist/internal/connect/index.d.ts +26 -0
  41. package/dist/internal/connect/index.d.ts.map +1 -0
  42. package/dist/internal/connect/index.js +24 -0
  43. package/dist/internal/connect/index.js.map +1 -0
  44. package/dist/internal/connect/main.d.ts +23 -0
  45. package/dist/internal/connect/main.d.ts.map +1 -0
  46. package/dist/internal/connect/main.js +330 -0
  47. package/dist/internal/connect/main.js.map +1 -0
  48. package/dist/internal/connect/run.d.ts +85 -0
  49. package/dist/internal/connect/run.d.ts.map +1 -0
  50. package/dist/internal/connect/run.js +242 -0
  51. package/dist/internal/connect/run.js.map +1 -0
  52. package/dist/internal/connect/source.d.ts +44 -0
  53. package/dist/internal/connect/source.d.ts.map +1 -0
  54. package/dist/internal/connect/source.js +215 -0
  55. package/dist/internal/connect/source.js.map +1 -0
  56. package/dist/internal/connect/template.d.ts +69 -0
  57. package/dist/internal/connect/template.d.ts.map +1 -0
  58. package/dist/internal/connect/template.js +221 -0
  59. package/dist/internal/connect/template.js.map +1 -0
  60. package/dist/internal/eval/index.d.ts +28 -0
  61. package/dist/internal/eval/index.d.ts.map +1 -0
  62. package/dist/internal/eval/index.js +27 -0
  63. package/dist/internal/eval/index.js.map +1 -0
  64. package/dist/internal/eval/judge.d.ts +30 -0
  65. package/dist/internal/eval/judge.d.ts.map +1 -0
  66. package/dist/internal/eval/judge.js +101 -0
  67. package/dist/internal/eval/judge.js.map +1 -0
  68. package/dist/internal/eval/loop.d.ts +64 -0
  69. package/dist/internal/eval/loop.d.ts.map +1 -0
  70. package/dist/internal/eval/loop.js +123 -0
  71. package/dist/internal/eval/loop.js.map +1 -0
  72. package/dist/internal/eval/main.d.ts +17 -0
  73. package/dist/internal/eval/main.d.ts.map +1 -0
  74. package/dist/internal/eval/main.js +236 -0
  75. package/dist/internal/eval/main.js.map +1 -0
  76. package/dist/internal/eval/queries.d.ts +74 -0
  77. package/dist/internal/eval/queries.d.ts.map +1 -0
  78. package/dist/internal/eval/queries.js +161 -0
  79. package/dist/internal/eval/queries.js.map +1 -0
  80. package/dist/internal/eval/run.d.ts +143 -0
  81. package/dist/internal/eval/run.d.ts.map +1 -0
  82. package/dist/internal/eval/run.js +376 -0
  83. package/dist/internal/eval/run.js.map +1 -0
  84. package/dist/internal/eval/score.d.ts +81 -0
  85. package/dist/internal/eval/score.d.ts.map +1 -0
  86. package/dist/internal/eval/score.js +126 -0
  87. package/dist/internal/eval/score.js.map +1 -0
  88. package/dist/internal/eval/suite.d.ts +66 -0
  89. package/dist/internal/eval/suite.d.ts.map +1 -0
  90. package/dist/internal/eval/suite.js +130 -0
  91. package/dist/internal/eval/suite.js.map +1 -0
  92. package/dist/internal/ingest/context.d.ts +20 -0
  93. package/dist/internal/ingest/context.d.ts.map +1 -0
  94. package/dist/internal/ingest/context.js +59 -0
  95. package/dist/internal/ingest/context.js.map +1 -0
  96. package/dist/internal/ingest/files.d.ts +46 -0
  97. package/dist/internal/ingest/files.d.ts.map +1 -0
  98. package/dist/internal/ingest/files.js +115 -0
  99. package/dist/internal/ingest/files.js.map +1 -0
  100. package/dist/internal/ingest/index.d.ts +31 -0
  101. package/dist/internal/ingest/index.d.ts.map +1 -0
  102. package/dist/internal/ingest/index.js +29 -0
  103. package/dist/internal/ingest/index.js.map +1 -0
  104. package/dist/internal/ingest/main.d.ts +12 -0
  105. package/dist/internal/ingest/main.d.ts.map +1 -0
  106. package/dist/internal/ingest/main.js +180 -0
  107. package/dist/internal/ingest/main.js.map +1 -0
  108. package/dist/internal/ingest/prompt.d.ts +32 -0
  109. package/dist/internal/ingest/prompt.d.ts.map +1 -0
  110. package/dist/internal/ingest/prompt.js +75 -0
  111. package/dist/internal/ingest/prompt.js.map +1 -0
  112. package/dist/internal/ingest/run.d.ts +142 -0
  113. package/dist/internal/ingest/run.d.ts.map +1 -0
  114. package/dist/internal/ingest/run.js +350 -0
  115. package/dist/internal/ingest/run.js.map +1 -0
  116. package/dist/internal/ingest/web.d.ts +48 -0
  117. package/dist/internal/ingest/web.d.ts.map +1 -0
  118. package/dist/internal/ingest/web.js +140 -0
  119. package/dist/internal/ingest/web.js.map +1 -0
  120. package/dist/internal/loop/demo.d.ts +22 -0
  121. package/dist/internal/loop/demo.d.ts.map +1 -0
  122. package/dist/internal/loop/demo.js +67 -0
  123. package/dist/internal/loop/demo.js.map +1 -0
  124. package/dist/internal/loop/index.d.ts +20 -0
  125. package/dist/internal/loop/index.d.ts.map +1 -0
  126. package/dist/internal/loop/index.js +17 -0
  127. package/dist/internal/loop/index.js.map +1 -0
  128. package/dist/internal/loop/llm.d.ts +99 -0
  129. package/dist/internal/loop/llm.d.ts.map +1 -0
  130. package/dist/internal/loop/llm.js +231 -0
  131. package/dist/internal/loop/llm.js.map +1 -0
  132. package/dist/internal/loop/reconstruct.d.ts +87 -0
  133. package/dist/internal/loop/reconstruct.d.ts.map +1 -0
  134. package/dist/internal/loop/reconstruct.js +157 -0
  135. package/dist/internal/loop/reconstruct.js.map +1 -0
  136. package/dist/internal/loop/sqlite.d.ts +13 -0
  137. package/dist/internal/loop/sqlite.d.ts.map +1 -0
  138. package/dist/internal/loop/sqlite.js +33 -0
  139. package/dist/internal/loop/sqlite.js.map +1 -0
  140. package/dist/internal/loop/store.d.ts +50 -0
  141. package/dist/internal/loop/store.d.ts.map +1 -0
  142. package/dist/internal/loop/store.js +100 -0
  143. package/dist/internal/loop/store.js.map +1 -0
  144. package/dist/internal/mcp/bin.d.ts +7 -0
  145. package/dist/internal/mcp/bin.d.ts.map +1 -0
  146. package/dist/internal/mcp/bin.js +8 -0
  147. package/dist/internal/mcp/bin.js.map +1 -0
  148. package/dist/internal/mcp/index.d.ts +25 -0
  149. package/dist/internal/mcp/index.d.ts.map +1 -0
  150. package/dist/internal/mcp/index.js +23 -0
  151. package/dist/internal/mcp/index.js.map +1 -0
  152. package/dist/internal/mcp/main.d.ts +23 -0
  153. package/dist/internal/mcp/main.d.ts.map +1 -0
  154. package/dist/internal/mcp/main.js +156 -0
  155. package/dist/internal/mcp/main.js.map +1 -0
  156. package/dist/internal/mcp/server.d.ts +92 -0
  157. package/dist/internal/mcp/server.d.ts.map +1 -0
  158. package/dist/internal/mcp/server.js +251 -0
  159. package/dist/internal/mcp/server.js.map +1 -0
  160. package/dist/internal/mcp/tools.d.ts +91 -0
  161. package/dist/internal/mcp/tools.d.ts.map +1 -0
  162. package/dist/internal/mcp/tools.js +584 -0
  163. package/dist/internal/mcp/tools.js.map +1 -0
  164. package/dist/internal/rules/declare.d.ts +58 -0
  165. package/dist/internal/rules/declare.d.ts.map +1 -0
  166. package/dist/internal/rules/declare.js +152 -0
  167. package/dist/internal/rules/declare.js.map +1 -0
  168. package/dist/internal/rules/engine.d.ts +125 -0
  169. package/dist/internal/rules/engine.d.ts.map +1 -0
  170. package/dist/internal/rules/engine.js +575 -0
  171. package/dist/internal/rules/engine.js.map +1 -0
  172. package/dist/internal/rules/index.d.ts +23 -0
  173. package/dist/internal/rules/index.d.ts.map +1 -0
  174. package/dist/internal/rules/index.js +21 -0
  175. package/dist/internal/rules/index.js.map +1 -0
  176. package/dist/internal/rules/rule.d.ts +88 -0
  177. package/dist/internal/rules/rule.d.ts.map +1 -0
  178. package/dist/internal/rules/rule.js +221 -0
  179. package/dist/internal/rules/rule.js.map +1 -0
  180. package/dist/internal/shape/check.d.ts +118 -0
  181. package/dist/internal/shape/check.d.ts.map +1 -0
  182. package/dist/internal/shape/check.js +331 -0
  183. package/dist/internal/shape/check.js.map +1 -0
  184. package/dist/internal/shape/client.d.ts +31 -0
  185. package/dist/internal/shape/client.d.ts.map +1 -0
  186. package/dist/internal/shape/client.js +170 -0
  187. package/dist/internal/shape/client.js.map +1 -0
  188. package/dist/internal/shape/gate.d.ts +33 -0
  189. package/dist/internal/shape/gate.d.ts.map +1 -0
  190. package/dist/internal/shape/gate.js +0 -0
  191. package/dist/internal/shape/gate.js.map +1 -0
  192. package/dist/internal/shape/index.d.ts +27 -0
  193. package/dist/internal/shape/index.d.ts.map +1 -0
  194. package/dist/internal/shape/index.js +23 -0
  195. package/dist/internal/shape/index.js.map +1 -0
  196. package/dist/internal/shape/suggest.d.ts +82 -0
  197. package/dist/internal/shape/suggest.d.ts.map +1 -0
  198. package/dist/internal/shape/suggest.js +374 -0
  199. package/dist/internal/shape/suggest.js.map +1 -0
  200. package/dist/internal/sync/index.d.ts +22 -0
  201. package/dist/internal/sync/index.d.ts.map +1 -0
  202. package/dist/internal/sync/index.js +21 -0
  203. package/dist/internal/sync/index.js.map +1 -0
  204. package/dist/internal/sync/sync.d.ts +95 -0
  205. package/dist/internal/sync/sync.d.ts.map +1 -0
  206. package/dist/internal/sync/sync.js +342 -0
  207. package/dist/internal/sync/sync.js.map +1 -0
  208. package/dist/internal/view/api.d.ts +196 -0
  209. package/dist/internal/view/api.d.ts.map +1 -0
  210. package/dist/internal/view/api.js +189 -0
  211. package/dist/internal/view/api.js.map +1 -0
  212. package/dist/internal/view/index.d.ts +33 -0
  213. package/dist/internal/view/index.d.ts.map +1 -0
  214. package/dist/internal/view/index.js +30 -0
  215. package/dist/internal/view/index.js.map +1 -0
  216. package/dist/internal/view/main.d.ts +11 -0
  217. package/dist/internal/view/main.d.ts.map +1 -0
  218. package/dist/internal/view/main.js +98 -0
  219. package/dist/internal/view/main.js.map +1 -0
  220. package/dist/internal/view/page.d.ts +14 -0
  221. package/dist/internal/view/page.d.ts.map +1 -0
  222. package/dist/internal/view/page.js +370 -0
  223. package/dist/internal/view/page.js.map +1 -0
  224. package/dist/internal/view/report.d.ts +52 -0
  225. package/dist/internal/view/report.d.ts.map +1 -0
  226. package/dist/internal/view/report.js +367 -0
  227. package/dist/internal/view/report.js.map +1 -0
  228. package/dist/internal/view/scope.d.ts +11 -0
  229. package/dist/internal/view/scope.d.ts.map +1 -0
  230. package/dist/internal/view/scope.js +41 -0
  231. package/dist/internal/view/scope.js.map +1 -0
  232. package/dist/internal/view/server.d.ts +35 -0
  233. package/dist/internal/view/server.d.ts.map +1 -0
  234. package/dist/internal/view/server.js +141 -0
  235. package/dist/internal/view/server.js.map +1 -0
  236. package/dist/src/act.d.ts +3 -0
  237. package/dist/src/act.d.ts.map +1 -0
  238. package/dist/src/act.js +3 -0
  239. package/dist/src/act.js.map +1 -0
  240. package/dist/src/automate.d.ts +3 -0
  241. package/dist/src/automate.d.ts.map +1 -0
  242. package/dist/src/automate.js +3 -0
  243. package/dist/src/automate.js.map +1 -0
  244. package/dist/src/cli.d.ts +24 -17
  245. package/dist/src/cli.d.ts.map +1 -1
  246. package/dist/src/cli.js +416 -109
  247. package/dist/src/cli.js.map +1 -1
  248. package/dist/src/commands.d.ts +104 -0
  249. package/dist/src/commands.d.ts.map +1 -0
  250. package/dist/src/commands.js +33 -0
  251. package/dist/src/commands.js.map +1 -0
  252. package/dist/src/connect.d.ts +3 -0
  253. package/dist/src/connect.d.ts.map +1 -0
  254. package/dist/src/connect.js +3 -0
  255. package/dist/src/connect.js.map +1 -0
  256. package/dist/src/dispatch.d.ts +14 -0
  257. package/dist/src/dispatch.d.ts.map +1 -0
  258. package/dist/src/dispatch.js +116 -0
  259. package/dist/src/dispatch.js.map +1 -0
  260. package/dist/src/doctor.d.ts +45 -0
  261. package/dist/src/doctor.d.ts.map +1 -0
  262. package/dist/src/doctor.js +284 -0
  263. package/dist/src/doctor.js.map +1 -0
  264. package/dist/src/eval.d.ts +3 -0
  265. package/dist/src/eval.d.ts.map +1 -0
  266. package/dist/src/eval.js +3 -0
  267. package/dist/src/eval.js.map +1 -0
  268. package/dist/src/index.d.ts +9 -2
  269. package/dist/src/index.d.ts.map +1 -1
  270. package/dist/src/index.js +6 -2
  271. package/dist/src/index.js.map +1 -1
  272. package/dist/src/ingest.d.ts +3 -0
  273. package/dist/src/ingest.d.ts.map +1 -0
  274. package/dist/src/ingest.js +3 -0
  275. package/dist/src/ingest.js.map +1 -0
  276. package/dist/src/loop.d.ts +3 -0
  277. package/dist/src/loop.d.ts.map +1 -0
  278. package/dist/src/loop.js +3 -0
  279. package/dist/src/loop.js.map +1 -0
  280. package/dist/src/main.d.ts +1 -1
  281. package/dist/src/main.d.ts.map +1 -1
  282. package/dist/src/main.js +3 -75
  283. package/dist/src/main.js.map +1 -1
  284. package/dist/src/mcp.d.ts +3 -0
  285. package/dist/src/mcp.d.ts.map +1 -0
  286. package/dist/src/mcp.js +3 -0
  287. package/dist/src/mcp.js.map +1 -0
  288. package/dist/src/rules.d.ts +3 -0
  289. package/dist/src/rules.d.ts.map +1 -0
  290. package/dist/src/rules.js +3 -0
  291. package/dist/src/rules.js.map +1 -0
  292. package/dist/src/shape.d.ts +3 -0
  293. package/dist/src/shape.d.ts.map +1 -0
  294. package/dist/src/shape.js +3 -0
  295. package/dist/src/shape.js.map +1 -0
  296. package/dist/src/sync.d.ts +3 -0
  297. package/dist/src/sync.d.ts.map +1 -0
  298. package/dist/src/sync.js +3 -0
  299. package/dist/src/sync.js.map +1 -0
  300. package/dist/src/view.d.ts +3 -0
  301. package/dist/src/view.d.ts.map +1 -0
  302. package/dist/src/view.js +3 -0
  303. package/dist/src/view.js.map +1 -0
  304. package/package.json +81 -21
  305. package/src/act.ts +2 -0
  306. package/src/automate.ts +2 -0
  307. package/src/cli.ts +423 -104
  308. package/src/commands.ts +48 -0
  309. package/src/connect.ts +2 -0
  310. package/src/dispatch.ts +141 -0
  311. package/src/doctor.ts +370 -0
  312. package/src/eval.ts +2 -0
  313. package/src/index.ts +9 -2
  314. package/src/ingest.ts +2 -0
  315. package/src/loop.ts +2 -0
  316. package/src/main.ts +3 -66
  317. package/src/mcp.ts +2 -0
  318. package/src/rules.ts +2 -0
  319. package/src/shape.ts +2 -0
  320. package/src/sync.ts +2 -0
  321. package/src/view.ts +2 -0
@@ -0,0 +1,126 @@
1
+ /**
2
+ * Claim scoring — the produced extraction against the golden (roadmap
3
+ * item 9).
4
+ *
5
+ * Both sides run through the same pipeline: parse → canonicalize → strip
6
+ * actor stamps → re-key → keep the last claim per key. Actor stamps are
7
+ * the `@src:` contexts appended by the engine itself under spec §9.5
8
+ * (`@src:cli`, `@src:agent/<name>`, `@src:ingest`) — which actor
9
+ * happened to write a claim must not shift its key away from the golden's,
10
+ * while *content* sources the fixture author wrote (`@src:maria`,
11
+ * `@src:notes.md`) stay part of claim identity: the golden decides which
12
+ * contexts extraction is expected to produce.
13
+ *
14
+ * A golden claim *matches* a produced claim when their normalized keys are
15
+ * equal and their values agree — numerically within a relative tolerance
16
+ * (units must agree; `~` approximation is metadata), textually otherwise.
17
+ * Relation and existence claims carry their object in the key, so the key
18
+ * alone decides. Confidence, tags, `+/-` uncertainty, importance and
19
+ * comments are metadata and never scored; a key that matches with a
20
+ * disagreeing value is counted separately (`valueOff`) — the right fact,
21
+ * the wrong value.
22
+ */
23
+ import { Claim, Key, Value } from '@cavelang/core';
24
+ import { canonicalizeText, emitClaim, standardRegistry } from '@cavelang/canonical';
25
+ import { Files } from '@cavelang/cli/ingest';
26
+ /** Actor-stamp sources appended by the engine (spec §9.5), ignored in scoring. */
27
+ const actorStampRe = /^src:(?:cli$|agent\/|ingest$)/;
28
+ /** @returns the claim without engine-appended actor stamps. */
29
+ export const normalize = (claim) => {
30
+ const contexts = claim.contexts.filter(context => !actorStampRe.test(context));
31
+ return contexts.length === claim.contexts.length ? claim : { ...claim, contexts };
32
+ };
33
+ /** @returns the claim key of the normalized claim. */
34
+ export const keyOf = (claim) => Key.of(normalize(claim));
35
+ /**
36
+ * @returns one fact per normalized key, the last claim winning — the same
37
+ * latest-wins semantics the store gives a belief series (spec §9.1).
38
+ */
39
+ export const factsOf = (claims) => {
40
+ const byKey = new Map();
41
+ for (const claim of claims) {
42
+ byKey.set(keyOf(claim), claim);
43
+ }
44
+ return [...byKey].map(([key, claim]) => ({ key, claim }));
45
+ };
46
+ /** Parses a golden document into facts; parse problems are fixture problems. */
47
+ export const goldenFacts = (text, registry = standardRegistry) => {
48
+ const result = canonicalizeText(text, registry);
49
+ return {
50
+ facts: factsOf(result.claims.map(entry => entry.claim)),
51
+ problems: result.problems.map(problem => `golden line ${problem.line}: ${problem.message}`)
52
+ };
53
+ };
54
+ /**
55
+ * @returns the facts an extraction run produced — the store's current
56
+ * beliefs minus the orchestrator's own `ingest-digest` provenance claims
57
+ * (`@cavelang/cli/ingest` bookkeeping, not extracted knowledge).
58
+ */
59
+ export const producedFacts = (store) => factsOf(store.currentBeliefs()
60
+ .filter(row => row.attribute !== Files.digestAttribute)
61
+ .map(row => store.toClaim(row)));
62
+ const valueOf = (claim) => claim.payload.kind === 'attribute' ? claim.payload.value :
63
+ claim.payload.kind === 'metric' ? claim.payload.value :
64
+ undefined;
65
+ /**
66
+ * @returns whether the produced value agrees with the golden's: equal
67
+ * numbers (within `tolerance`, relative to the golden) under equal units,
68
+ * or the exact same canonical text. Claims without a value (relations,
69
+ * existence) always agree — their key already carries the object.
70
+ */
71
+ export const valueAgrees = (golden, produced, tolerance = 0) => {
72
+ const goldenValue = valueOf(golden);
73
+ const producedValue = valueOf(produced);
74
+ if (goldenValue === undefined || producedValue === undefined) {
75
+ return goldenValue === producedValue;
76
+ }
77
+ if (goldenValue.num !== undefined && producedValue.num !== undefined) {
78
+ if ((goldenValue.unit ?? '') !== (producedValue.unit ?? '')) {
79
+ return false;
80
+ }
81
+ return goldenValue.num === producedValue.num ||
82
+ Math.abs(producedValue.num - goldenValue.num) <= tolerance * Math.abs(goldenValue.num);
83
+ }
84
+ return Value.format(goldenValue) === Value.format(producedValue);
85
+ };
86
+ const ratio = (numerator, denominator) => denominator === 0 ? 0 : numerator / denominator;
87
+ /** @returns the F1 of a precision/recall pair, 0 when both are 0. */
88
+ export const f1Of = (precision, recall) => precision + recall === 0 ? 0 : (2 * precision * recall) / (precision + recall);
89
+ /** Compares produced facts against golden facts. */
90
+ export const compare = (golden, produced, options = {}) => {
91
+ const byKey = new Map(produced.map(fact => [fact.key, fact]));
92
+ const misses = [];
93
+ const matchedKeys = new Set();
94
+ let matched = 0;
95
+ let valueOff = 0;
96
+ for (const fact of golden) {
97
+ const candidate = byKey.get(fact.key);
98
+ if (candidate !== undefined && valueAgrees(fact.claim, candidate.claim, options.tolerance)) {
99
+ matched += 1;
100
+ matchedKeys.add(fact.key);
101
+ }
102
+ else {
103
+ if (candidate !== undefined) {
104
+ valueOff += 1;
105
+ }
106
+ misses.push(fact);
107
+ }
108
+ }
109
+ const extras = produced.filter(fact => !matchedKeys.has(fact.key));
110
+ const precision = ratio(matched, produced.length);
111
+ const recall = ratio(matched, golden.length);
112
+ return {
113
+ golden: golden.length,
114
+ produced: produced.length,
115
+ matched,
116
+ valueOff,
117
+ misses,
118
+ extras,
119
+ precision,
120
+ recall,
121
+ f1: f1Of(precision, recall)
122
+ };
123
+ };
124
+ /** @returns the canonical line of a fact, for reports and judge prompts. */
125
+ export const lineOf = (fact) => emitClaim(normalize(fact.claim));
126
+ //# sourceMappingURL=score.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"score.js","sourceRoot":"","sources":["../../src/score.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,66 @@
1
+ /**
2
+ * Suite discovery — eval fixtures as plain files.
3
+ *
4
+ * A suite is any directory; a *case* is named by its golden file:
5
+ *
6
+ * ```
7
+ * suite/
8
+ * instructions.md (optional, shared by the suite)
9
+ * family-history.md the source the agent extracts from
10
+ * family-history.golden.cave the expected extraction
11
+ * family-history.queries.cave (optional) CAVE-Q behavioral checks
12
+ * ```
13
+ *
14
+ * For `<stem>.golden.cave` the source is the single sibling `<stem>.<ext>`
15
+ * whose extension has no further dots — so goldens, queries and
16
+ * instructions of this or other cases never masquerade as sources, while
17
+ * `design.notes.md` still pairs with `design.notes.golden.cave`. Zero or
18
+ * several candidates is a fixture problem, reported instead of guessed.
19
+ *
20
+ * A `<stem>.loop.cave` sibling makes the case a *reconstruction* case
21
+ * (spec §18): the source is the knowledge (CAVE text), the loop
22
+ * file declares seeds and budgets, and the golden is the expected
23
+ * reconstruction — see `loop.ts`.
24
+ *
25
+ * Instructions resolve nearest-first: an explicit path (CLI `--instructions`)
26
+ * beats `<stem>.instructions.md` beats the case directory's
27
+ * `instructions.md` beats the suite root's.
28
+ */
29
+ export declare const goldenSuffix = ".golden.cave";
30
+ export declare const queriesSuffix = ".queries.cave";
31
+ export declare const loopSuffix = ".loop.cave";
32
+ export declare const instructionsSuffix = ".instructions.md";
33
+ /** Suite-shared instructions file name. */
34
+ export declare const sharedInstructions = "instructions.md";
35
+ export type Case = {
36
+ /** Display name — the golden's path relative to `cwd`, suffix dropped. */
37
+ readonly name: string;
38
+ /**
39
+ * Absolute source file: what the agent extracts from — or, for a
40
+ * reconstruction case, the knowledge the loop runs over.
41
+ */
42
+ readonly source: string;
43
+ /** Absolute golden `.cave` path. */
44
+ readonly golden: string;
45
+ /** Absolute queries file path, when the case has one. */
46
+ readonly queries?: string;
47
+ /** Absolute loop file path — present on reconstruction cases (item 10). */
48
+ readonly loop?: string;
49
+ /** Absolute instructions markdown path, when one resolves. */
50
+ readonly instructions?: string;
51
+ };
52
+ export type Suite = {
53
+ /** Discovered cases, sorted by name. */
54
+ readonly cases: readonly Case[];
55
+ /** Fixture problems — goldens that could not become cases. */
56
+ readonly problems: readonly string[];
57
+ };
58
+ /**
59
+ * Discovers the cases of one or more suites. Each root may be a directory
60
+ * (searched recursively for `*.golden.cave`) or a single golden file.
61
+ */
62
+ export declare const discover: (roots: readonly string[], options?: {
63
+ instructions?: string;
64
+ cwd?: string;
65
+ }) => Suite;
66
+ //# sourceMappingURL=suite.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"suite.d.ts","sourceRoot":"","sources":["../../src/suite.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;GA2BG;AAKH,eAAO,MAAM,YAAY,iBAAiB,CAAA;AAC1C,eAAO,MAAM,aAAa,kBAAkB,CAAA;AAC5C,eAAO,MAAM,UAAU,eAAe,CAAA;AACtC,eAAO,MAAM,kBAAkB,qBAAqB,CAAA;AAEpD,2CAA2C;AAC3C,eAAO,MAAM,kBAAkB,oBAAoB,CAAA;AAEnD,MAAM,MAAM,IAAI,GAAG;IACjB,0EAA0E;IAC1E,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAA;IACrB;;;OAGG;IACH,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAA;IACvB,oCAAoC;IACpC,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAA;IACvB,yDAAyD;IACzD,QAAQ,CAAC,OAAO,CAAC,EAAE,MAAM,CAAA;IACzB,2EAA2E;IAC3E,QAAQ,CAAC,IAAI,CAAC,EAAE,MAAM,CAAA;IACtB,8DAA8D;IAC9D,QAAQ,CAAC,YAAY,CAAC,EAAE,MAAM,CAAA;CAC/B,CAAA;AAED,MAAM,MAAM,KAAK,GAAG;IAClB,wCAAwC;IACxC,QAAQ,CAAC,KAAK,EAAE,SAAS,IAAI,EAAE,CAAA;IAC/B,8DAA8D;IAC9D,QAAQ,CAAC,QAAQ,EAAE,SAAS,MAAM,EAAE,CAAA;CACrC,CAAA;AAyDD;;;GAGG;AACH,eAAO,MAAM,QAAQ,GACnB,OAAO,SAAS,MAAM,EAAE,EACxB,UAAS;IAAE,YAAY,CAAC,EAAE,MAAM,CAAC;IAAC,GAAG,CAAC,EAAE,MAAM,CAAA;CAAO,KACpD,KAuCF,CAAA"}
@@ -0,0 +1,130 @@
1
+ /**
2
+ * Suite discovery — eval fixtures as plain files.
3
+ *
4
+ * A suite is any directory; a *case* is named by its golden file:
5
+ *
6
+ * ```
7
+ * suite/
8
+ * instructions.md (optional, shared by the suite)
9
+ * family-history.md the source the agent extracts from
10
+ * family-history.golden.cave the expected extraction
11
+ * family-history.queries.cave (optional) CAVE-Q behavioral checks
12
+ * ```
13
+ *
14
+ * For `<stem>.golden.cave` the source is the single sibling `<stem>.<ext>`
15
+ * whose extension has no further dots — so goldens, queries and
16
+ * instructions of this or other cases never masquerade as sources, while
17
+ * `design.notes.md` still pairs with `design.notes.golden.cave`. Zero or
18
+ * several candidates is a fixture problem, reported instead of guessed.
19
+ *
20
+ * A `<stem>.loop.cave` sibling makes the case a *reconstruction* case
21
+ * (spec §18): the source is the knowledge (CAVE text), the loop
22
+ * file declares seeds and budgets, and the golden is the expected
23
+ * reconstruction — see `loop.ts`.
24
+ *
25
+ * Instructions resolve nearest-first: an explicit path (CLI `--instructions`)
26
+ * beats `<stem>.instructions.md` beats the case directory's
27
+ * `instructions.md` beats the suite root's.
28
+ */
29
+ import { existsSync, globSync, readdirSync, statSync } from 'node:fs';
30
+ import { basename, dirname, join, relative, resolve } from 'node:path';
31
+ export const goldenSuffix = '.golden.cave';
32
+ export const queriesSuffix = '.queries.cave';
33
+ export const loopSuffix = '.loop.cave';
34
+ export const instructionsSuffix = '.instructions.md';
35
+ /** Suite-shared instructions file name. */
36
+ export const sharedInstructions = 'instructions.md';
37
+ /** @returns source candidates: `<stem>.<ext>` siblings with a dot-free extension. */
38
+ const sourcesOf = (golden) => {
39
+ const dir = dirname(golden);
40
+ const stem = basename(golden).slice(0, -goldenSuffix.length);
41
+ return readdirSync(dir)
42
+ .filter(name => {
43
+ if (!name.startsWith(`${stem}.`)) {
44
+ return false;
45
+ }
46
+ const extension = name.slice(stem.length + 1);
47
+ return extension !== '' && !extension.includes('.') && statSync(join(dir, name)).isFile();
48
+ })
49
+ .sort()
50
+ .map(name => join(dir, name));
51
+ };
52
+ const instructionsOf = (golden, root, explicit) => {
53
+ const candidates = [
54
+ explicit,
55
+ `${golden.slice(0, -goldenSuffix.length)}${instructionsSuffix}`,
56
+ join(dirname(golden), sharedInstructions),
57
+ join(root, sharedInstructions)
58
+ ];
59
+ return candidates.find(path => path !== undefined && existsSync(path));
60
+ };
61
+ const caseOf = (golden, root, cwd, explicit) => {
62
+ const sources = sourcesOf(golden);
63
+ const name = relative(cwd, golden).slice(0, -goldenSuffix.length);
64
+ if (sources.length === 0) {
65
+ return { problem: `${name}: no source file — expected a single ${basename(golden).slice(0, -goldenSuffix.length)}.<ext> beside ${basename(golden)}` };
66
+ }
67
+ if (sources.length > 1) {
68
+ return { problem: `${name}: ambiguous source — ${sources.map(source => basename(source)).join(', ')}` };
69
+ }
70
+ const queries = `${golden.slice(0, -goldenSuffix.length)}${queriesSuffix}`;
71
+ const loop = `${golden.slice(0, -goldenSuffix.length)}${loopSuffix}`;
72
+ const instructions = instructionsOf(golden, root, explicit);
73
+ return {
74
+ kase: {
75
+ name,
76
+ source: sources[0],
77
+ golden,
78
+ ...existsSync(queries) ? { queries } : {},
79
+ ...existsSync(loop) ? { loop } : {},
80
+ ...instructions === undefined ? {} : { instructions }
81
+ }
82
+ };
83
+ };
84
+ /**
85
+ * Discovers the cases of one or more suites. Each root may be a directory
86
+ * (searched recursively for `*.golden.cave`) or a single golden file.
87
+ */
88
+ export const discover = (roots, options = {}) => {
89
+ const cwd = options.cwd ?? process.cwd();
90
+ const explicit = options.instructions === undefined ? undefined : resolve(cwd, options.instructions);
91
+ const cases = [];
92
+ const problems = [];
93
+ for (const root of roots) {
94
+ const absolute = resolve(cwd, root);
95
+ if (!existsSync(absolute)) {
96
+ problems.push(`${root}: no such file or directory`);
97
+ continue;
98
+ }
99
+ if (statSync(absolute).isFile()) {
100
+ if (!absolute.endsWith(goldenSuffix)) {
101
+ problems.push(`${root}: not a suite directory or ${goldenSuffix} file`);
102
+ continue;
103
+ }
104
+ const outcome = caseOf(absolute, dirname(absolute), cwd, explicit);
105
+ if ('kase' in outcome) {
106
+ cases.push(outcome.kase);
107
+ }
108
+ else {
109
+ problems.push(outcome.problem);
110
+ }
111
+ continue;
112
+ }
113
+ const goldens = globSync(`**/*${goldenSuffix}`, { cwd: absolute }).sort();
114
+ if (goldens.length === 0) {
115
+ problems.push(`${root}: no ${goldenSuffix} cases found`);
116
+ continue;
117
+ }
118
+ for (const golden of goldens) {
119
+ const outcome = caseOf(join(absolute, golden), absolute, cwd, explicit);
120
+ if ('kase' in outcome) {
121
+ cases.push(outcome.kase);
122
+ }
123
+ else {
124
+ problems.push(outcome.problem);
125
+ }
126
+ }
127
+ }
128
+ return { cases: cases.sort((a, b) => a.name.localeCompare(b.name)), problems };
129
+ };
130
+ //# sourceMappingURL=suite.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"suite.js","sourceRoot":"","sources":["../../src/suite.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,20 @@
1
+ /**
2
+ * Existing-knowledge context for an ingestion batch.
3
+ *
4
+ * Neither extreme works: dumping the whole database into every prompt
5
+ * stops scaling almost immediately, and tools-only leaves the model blind
6
+ * to established naming conventions and prone to duplicates. The middle
7
+ * road injected here is a small *relevant* slice — store statistics, the
8
+ * most-connected entities (naming anchors), and claims matching the batch
9
+ * files' path tokens — while the agent keeps full API access through the
10
+ * `cave_*` MCP tools for anything deeper.
11
+ */
12
+ import type { Store } from '@cavelang/store';
13
+ /** Tokens worth searching for, derived from a file path or URL. */
14
+ export declare const pathTokens: (path: string) => string[];
15
+ /**
16
+ * @returns a compact knowledge-context block for the batch, capped at
17
+ * `limit` claim lines; `undefined` for an empty store.
18
+ */
19
+ export declare const contextFor: (store: Store, paths: readonly string[], limit?: number) => undefined | string;
20
+ //# sourceMappingURL=context.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"context.d.ts","sourceRoot":"","sources":["../../src/context.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;AAGH,OAAO,KAAK,EAAE,KAAK,EAAE,MAAM,iBAAiB,CAAA;AAE5C,mEAAmE;AACnE,eAAO,MAAM,UAAU,GAAI,MAAM,MAAM,KAAG,MAAM,EAO/C,CAAA;AAED;;;GAGG;AACH,eAAO,MAAM,UAAU,GAAI,OAAO,KAAK,EAAE,OAAO,SAAS,MAAM,EAAE,EAAE,cAAU,KAAG,SAAS,GAAG,MAgC3F,CAAA"}
@@ -0,0 +1,59 @@
1
+ /**
2
+ * Existing-knowledge context for an ingestion batch.
3
+ *
4
+ * Neither extreme works: dumping the whole database into every prompt
5
+ * stops scaling almost immediately, and tools-only leaves the model blind
6
+ * to established naming conventions and prone to duplicates. The middle
7
+ * road injected here is a small *relevant* slice — store statistics, the
8
+ * most-connected entities (naming anchors), and claims matching the batch
9
+ * files' path tokens — while the agent keeps full API access through the
10
+ * `cave_*` MCP tools for anything deeper.
11
+ */
12
+ import { emitClaim } from '@cavelang/canonical';
13
+ /** Tokens worth searching for, derived from a file path or URL. */
14
+ export const pathTokens = (path) => {
15
+ const parts = path
16
+ .split(/[/\\?#&=]/)
17
+ .flatMap(segment => segment.split('.'))
18
+ .filter(token => token.length >= 3 &&
19
+ !/^(src|test|index|json|md|ts|js|tsx|jsx|txt|yaml|yml|https?:|www|com|net|org|html|htm)$/.test(token));
20
+ return [...new Set(parts)];
21
+ };
22
+ /**
23
+ * @returns a compact knowledge-context block for the batch, capped at
24
+ * `limit` claim lines; `undefined` for an empty store.
25
+ */
26
+ export const contextFor = (store, paths, limit = 40) => {
27
+ const current = store.currentBeliefs();
28
+ if (current.length === 0) {
29
+ return undefined;
30
+ }
31
+ const degree = new Map();
32
+ for (const row of current) {
33
+ degree.set(row.subject, (degree.get(row.subject) ?? 0) + 1);
34
+ if (row.object !== null) {
35
+ degree.set(row.object, (degree.get(row.object) ?? 0) + 1);
36
+ }
37
+ }
38
+ const topEntities = [...degree.entries()]
39
+ .sort((a, b) => b[1] - a[1])
40
+ .slice(0, 15)
41
+ .map(([entity, count]) => `${entity} (${count})`);
42
+ const related = new Map();
43
+ for (const token of paths.flatMap(pathTokens)) {
44
+ for (const row of store.search(token, { limit: 5 })) {
45
+ if (related.size >= limit) {
46
+ break;
47
+ }
48
+ related.set(row.claim_key, emitClaim(store.toClaim(row)));
49
+ }
50
+ }
51
+ return [
52
+ `The database currently holds ${current.length} current belief(s).`,
53
+ `Established entities (use these names, do not invent variants): ${topEntities.join(', ')}`,
54
+ ...related.size > 0 ?
55
+ ['Existing claims related to this batch:', ...[...related.values()].map(line => ` ${line}`)] :
56
+ []
57
+ ].join('\n');
58
+ };
59
+ //# sourceMappingURL=context.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"context.js","sourceRoot":"","sources":["../../src/context.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;AAEH,OAAO,EAAE,SAAS,EAAE,MAAM,qBAAqB,CAAA;AAG/C,mEAAmE;AACnE,MAAM,CAAC,MAAM,UAAU,GAAG,CAAC,IAAY,EAAY,EAAE;IACnD,MAAM,KAAK,GAAG,IAAI;SACf,KAAK,CAAC,WAAW,CAAC;SAClB,OAAO,CAAC,OAAO,CAAC,EAAE,CAAC,OAAO,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC;SACtC,MAAM,CAAC,KAAK,CAAC,EAAE,CAAC,KAAK,CAAC,MAAM,IAAI,CAAC;QAChC,CAAC,wFAAwF,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,CAAA;IAC1G,OAAO,CAAC,GAAG,IAAI,GAAG,CAAC,KAAK,CAAC,CAAC,CAAA;AAC5B,CAAC,CAAA;AAED;;;GAGG;AACH,MAAM,CAAC,MAAM,UAAU,GAAG,CAAC,KAAY,EAAE,KAAwB,EAAE,KAAK,GAAG,EAAE,EAAsB,EAAE;IACnG,MAAM,OAAO,GAAG,KAAK,CAAC,cAAc,EAAE,CAAA;IACtC,IAAI,OAAO,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;QACzB,OAAO,SAAS,CAAA;IAClB,CAAC;IACD,MAAM,MAAM,GAAG,IAAI,GAAG,EAAkB,CAAA;IACxC,KAAK,MAAM,GAAG,IAAI,OAAO,EAAE,CAAC;QAC1B,MAAM,CAAC,GAAG,CAAC,GAAG,CAAC,OAAO,EAAE,CAAC,MAAM,CAAC,GAAG,CAAC,GAAG,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC,GAAG,CAAC,CAAC,CAAA;QAC3D,IAAI,GAAG,CAAC,MAAM,KAAK,IAAI,EAAE,CAAC;YACxB,MAAM,CAAC,GAAG,CAAC,GAAG,CAAC,MAAM,EAAE,CAAC,MAAM,CAAC,GAAG,CAAC,GAAG,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC,GAAG,CAAC,CAAC,CAAA;QAC3D,CAAC;IACH,CAAC;IACD,MAAM,WAAW,GAAG,CAAC,GAAG,MAAM,CAAC,OAAO,EAAE,CAAC;SACtC,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC;SAC3B,KAAK,CAAC,CAAC,EAAE,EAAE,CAAC;SACZ,GAAG,CAAC,CAAC,CAAC,MAAM,EAAE,KAAK,CAAC,EAAE,EAAE,CAAC,GAAG,MAAM,KAAK,KAAK,GAAG,CAAC,CAAA;IACnD,MAAM,OAAO,GAAG,IAAI,GAAG,EAAkB,CAAA;IACzC,KAAK,MAAM,KAAK,IAAI,KAAK,CAAC,OAAO,CAAC,UAAU,CAAC,EAAE,CAAC;QAC9C,KAAK,MAAM,GAAG,IAAI,KAAK,CAAC,MAAM,CAAC,KAAK,EAAE,EAAE,KAAK,EAAE,CAAC,EAAE,CAAC,EAAE,CAAC;YACpD,IAAI,OAAO,CAAC,IAAI,IAAI,KAAK,EAAE,CAAC;gBAC1B,MAAK;YACP,CAAC;YACD,OAAO,CAAC,GAAG,CAAC,GAAG,CAAC,SAAS,EAAE,SAAS,CAAC,KAAK,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC,CAAC,CAAA;QAC3D,CAAC;IACH,CAAC;IACD,OAAO;QACL,gCAAgC,OAAO,CAAC,MAAM,qBAAqB;QACnE,mEAAmE,WAAW,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE;QAC3F,GAAG,OAAO,CAAC,IAAI,GAAG,CAAC,CAAC,CAAC;YACnB,CAAC,wCAAwC,EAAE,GAAG,CAAC,GAAG,OAAO,CAAC,MAAM,EAAE,CAAC,CAAC,GAAG,CAAC,IAAI,CAAC,EAAE,CAAC,KAAK,IAAI,EAAE,CAAC,CAAC,CAAC,CAAC;YAC/F,EAAE;KACL,CAAC,IAAI,CAAC,IAAI,CAAC,CAAA;AACd,CAAC,CAAA"}
@@ -0,0 +1,46 @@
1
+ /**
2
+ * File selection for ingestion: glob expansion, batching, and the
3
+ * incremental-skip bookkeeping.
4
+ *
5
+ * Ingestion provenance is recorded as ordinary CAVE claims —
6
+ * `<path> HAS ingest-digest: <sha256/12> @src:cave-ingest` — so "which
7
+ * files are already ingested at which content version" lives in the same
8
+ * append-only store as the knowledge itself, and re-running `cave ingest`
9
+ * over a monorepo only processes files whose content changed.
10
+ */
11
+ import type { Store } from '@cavelang/store';
12
+ /** Digest attribute name used in provenance claims. */
13
+ export declare const digestAttribute = "ingest-digest";
14
+ /** Context marking provenance claims. */
15
+ export declare const provenanceContext = "src:cave-ingest";
16
+ /** @returns matching regular-file paths — globs expanded, directories dropped, deduplicated, sorted. */
17
+ export declare const expand: (patterns: readonly string[], cwd?: string) => string[];
18
+ /** @returns first 12 hex chars of the content's sha256. */
19
+ export declare const digestOf: (content: string) => string;
20
+ export type Selected = {
21
+ readonly path: string;
22
+ readonly digest: string;
23
+ /** Pre-fetched content (URL sources); files are read from disk instead. */
24
+ readonly content?: string;
25
+ };
26
+ export type Selection = {
27
+ readonly files: readonly Selected[];
28
+ /** Files skipped because their current digest claim matches. */
29
+ readonly skipped: readonly string[];
30
+ };
31
+ /** @returns whether the source's current `ingest-digest` belief matches. */
32
+ export declare const isIngested: (store: Store, path: string, digest: string) => boolean;
33
+ /**
34
+ * Reads and digests candidate files (paths relative to `cwd`), skipping
35
+ * the ones whose current `ingest-digest` belief already matches (pass
36
+ * `force` to re-ingest all).
37
+ */
38
+ export declare const select: (store: Store, paths: readonly string[], options?: {
39
+ force?: boolean;
40
+ cwd?: string;
41
+ }) => Selection;
42
+ /** Records provenance claims for successfully ingested files. */
43
+ export declare const recordDigests: (store: Store, files: readonly Selected[]) => void;
44
+ /** @returns `files` split into batches of at most `size`. */
45
+ export declare const batch: <T>(files: readonly T[], size: number) => T[][];
46
+ //# sourceMappingURL=files.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"files.d.ts","sourceRoot":"","sources":["../../src/files.ts"],"names":[],"mappings":"AAAA;;;;;;;;;GASG;AAMH,OAAO,KAAK,EAAE,KAAK,EAAE,MAAM,iBAAiB,CAAA;AAE5C,uDAAuD;AACvD,eAAO,MAAM,eAAe,kBAAkB,CAAA;AAE9C,yCAAyC;AACzC,eAAO,MAAM,iBAAiB,oBAAoB,CAAA;AAiClD,wGAAwG;AACxG,eAAO,MAAM,MAAM,GAAI,UAAU,SAAS,MAAM,EAAE,EAAE,MAAK,MAAsB,KAAG,MAAM,EAKvF,CAAA;AAED,2DAA2D;AAC3D,eAAO,MAAM,QAAQ,GAAI,SAAS,MAAM,KAAG,MACsB,CAAA;AAMjE,MAAM,MAAM,QAAQ,GAAG;IACrB,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAA;IACrB,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAA;IACvB,2EAA2E;IAC3E,QAAQ,CAAC,OAAO,CAAC,EAAE,MAAM,CAAA;CAC1B,CAAA;AAED,MAAM,MAAM,SAAS,GAAG;IACtB,QAAQ,CAAC,KAAK,EAAE,SAAS,QAAQ,EAAE,CAAA;IACnC,gEAAgE;IAChE,QAAQ,CAAC,OAAO,EAAE,SAAS,MAAM,EAAE,CAAA;CACpC,CAAA;AAED,4EAA4E;AAC5E,eAAO,MAAM,UAAU,GAAI,OAAO,KAAK,EAAE,MAAM,MAAM,EAAE,QAAQ,MAAM,KAAG,OAGvE,CAAA;AAED;;;;GAIG;AACH,eAAO,MAAM,MAAM,GACjB,OAAO,KAAK,EACZ,OAAO,SAAS,MAAM,EAAE,EACxB,UAAS;IAAE,KAAK,CAAC,EAAE,OAAO,CAAC;IAAC,GAAG,CAAC,EAAE,MAAM,CAAA;CAAO,KAC9C,SAaF,CAAA;AAED,iEAAiE;AACjE,eAAO,MAAM,aAAa,GAAI,OAAO,KAAK,EAAE,OAAO,SAAS,QAAQ,EAAE,KAAG,IAkBxE,CAAA;AAED,6DAA6D;AAC7D,eAAO,MAAM,KAAK,GAAI,CAAC,EAAE,OAAO,SAAS,CAAC,EAAE,EAAE,MAAM,MAAM,KAAG,CAAC,EAAE,EAS/D,CAAA"}
@@ -0,0 +1,115 @@
1
+ /**
2
+ * File selection for ingestion: glob expansion, batching, and the
3
+ * incremental-skip bookkeeping.
4
+ *
5
+ * Ingestion provenance is recorded as ordinary CAVE claims —
6
+ * `<path> HAS ingest-digest: <sha256/12> @src:cave-ingest` — so "which
7
+ * files are already ingested at which content version" lives in the same
8
+ * append-only store as the knowledge itself, and re-running `cave ingest`
9
+ * over a monorepo only processes files whose content changed.
10
+ */
11
+ import { createHash } from 'node:crypto';
12
+ import { globSync, readFileSync, statSync } from 'node:fs';
13
+ import { resolve as resolvePath } from 'node:path';
14
+ import { Key, Claim, Value } from '@cavelang/core';
15
+ /** Digest attribute name used in provenance claims. */
16
+ export const digestAttribute = 'ingest-digest';
17
+ /** Context marking provenance claims. */
18
+ export const provenanceContext = 'src:cave-ingest';
19
+ /**
20
+ * File paths normally remain entity atoms for compatibility with existing
21
+ * provenance. Paths that would be split or interpreted as metadata use a
22
+ * code literal so their exact spelling round-trips through CAVE text.
23
+ */
24
+ const provenanceSubject = (path) => {
25
+ const isEntityAtom = path !== '' &&
26
+ !/[\s"`;]/u.test(path) &&
27
+ !/^(?:[@#]|\+\/-|!$|\(\d+(?:\.\d+)?σ\)$)/u.test(path);
28
+ if (isEntityAtom) {
29
+ return Claim.entity(path);
30
+ }
31
+ // Prefer a code literal for path-like data; use text when the path itself
32
+ // contains a backtick. CAVE has no literal escape syntax, so a path with
33
+ // both delimiters needs a deterministic encoded representation to remain
34
+ // valid through canonical export/import.
35
+ if (path.includes('`')) {
36
+ return path.includes('"') ? Claim.code(`percent-encoded:${encodeURIComponent(path)}`) : Claim.text(path);
37
+ }
38
+ return Claim.code(path);
39
+ };
40
+ /** One construction path keeps digest lookup and storage identities identical. */
41
+ const provenanceClaim = (path, digest) => Claim.of({
42
+ subject: provenanceSubject(path),
43
+ verb: 'HAS',
44
+ payload: Claim.attribute(digestAttribute, Value.parse(digest)),
45
+ contexts: [provenanceContext]
46
+ });
47
+ /** @returns matching regular-file paths — globs expanded, directories dropped, deduplicated, sorted. */
48
+ export const expand = (patterns, cwd = process.cwd()) => {
49
+ const matched = patterns.flatMap(pattern => globSync(pattern, { cwd }));
50
+ return [...new Set(matched)]
51
+ .filter(path => statSync(resolvePath(cwd, path)).isFile())
52
+ .sort();
53
+ };
54
+ /** @returns first 12 hex chars of the content's sha256. */
55
+ export const digestOf = (content) => createHash('sha256').update(content).digest('hex').slice(0, 12);
56
+ /** Claim key of a file's provenance claim (value excluded by design, §9.2). */
57
+ const provenanceKey = (path) => Key.of(provenanceClaim(path, 'x'));
58
+ /** @returns whether the source's current `ingest-digest` belief matches. */
59
+ export const isIngested = (store, path, digest) => {
60
+ const known = store.currentBelief(provenanceKey(path));
61
+ return known !== undefined && known.value_text === digest && known.conf > 0;
62
+ };
63
+ /**
64
+ * Reads and digests candidate files (paths relative to `cwd`), skipping
65
+ * the ones whose current `ingest-digest` belief already matches (pass
66
+ * `force` to re-ingest all).
67
+ */
68
+ export const select = (store, paths, options = {}) => {
69
+ const files = [];
70
+ const skipped = [];
71
+ const cwd = options.cwd ?? process.cwd();
72
+ for (const path of paths) {
73
+ const digest = digestOf(readFileSync(resolvePath(cwd, path), 'utf8'));
74
+ if (options.force !== true && isIngested(store, path, digest)) {
75
+ skipped.push(path);
76
+ }
77
+ else {
78
+ files.push({ path, digest });
79
+ }
80
+ }
81
+ return { files, skipped };
82
+ };
83
+ /** Records provenance claims for successfully ingested files. */
84
+ export const recordDigests = (store, files) => {
85
+ if (files.length === 0) {
86
+ return;
87
+ }
88
+ try {
89
+ store.insertResult({
90
+ claims: files.map((file, index) => ({
91
+ line: index + 1,
92
+ claim: provenanceClaim(file.path, file.digest)
93
+ })),
94
+ edges: [],
95
+ registry: store.registry(),
96
+ problems: []
97
+ });
98
+ }
99
+ catch (error) {
100
+ const sources = files.map(file => JSON.stringify(file.path)).join(', ');
101
+ throw new Error(`failed to record ingest digest(s) for ${sources}`, { cause: error });
102
+ }
103
+ };
104
+ /** @returns `files` split into batches of at most `size`. */
105
+ export const batch = (files, size) => {
106
+ if (!(size >= 1)) {
107
+ throw new Error(`batch size must be >= 1, got ${size}`);
108
+ }
109
+ const batches = [];
110
+ for (let at = 0; at < files.length; at += size) {
111
+ batches.push(files.slice(at, at + size));
112
+ }
113
+ return batches;
114
+ };
115
+ //# sourceMappingURL=files.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"files.js","sourceRoot":"","sources":["../../src/files.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,31 @@
1
+ /**
2
+ * `@cavelang/cli/ingest` — LLM-driven knowledge ingestion.
3
+ *
4
+ * ```sh
5
+ * cave ingest 'src/**' https://example.com/design-notes --db k.db \
6
+ * --agent 'claude -p --mcp-config {mcp-config} --allowedTools "mcp__cave__*"'
7
+ * ```
8
+ *
9
+ * Library API for SDK scripts:
10
+ *
11
+ * ```ts
12
+ * import { run } from '@cavelang/cli/ingest'
13
+ * import { open } from '@cavelang/store'
14
+ *
15
+ * const store = open('k.db')
16
+ * await run({
17
+ * db: 'k.db', store, patterns: ['docs/**'], mode: 'stdout', embed: true,
18
+ * agent: async prompt => callYourSdk(prompt), // returns CAVE text
19
+ * // policy: 'lenient' // strict is the default
20
+ * })
21
+ * ```
22
+ */
23
+ export * as Context from './context.ts';
24
+ export * as Files from './files.ts';
25
+ export * as Web from './web.ts';
26
+ export { buildPrompt, extractionRules, readInstructions } from './prompt.ts';
27
+ export type { Mode, PromptInput } from './prompt.ts';
28
+ export { caveTextOf, promptFor, run, runShellAgent, selectBatches, writeMcpConfig } from './run.ts';
29
+ export type { Agent, AgentContext, Batch, BatchReport, Options, Policy, Report, SourceReport, SourceStatus } from './run.ts';
30
+ export { runIngest } from './main.ts';
31
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;GAqBG;AAEH,OAAO,KAAK,OAAO,MAAM,cAAc,CAAA;AACvC,OAAO,KAAK,KAAK,MAAM,YAAY,CAAA;AACnC,OAAO,KAAK,GAAG,MAAM,UAAU,CAAA;AAC/B,OAAO,EAAE,WAAW,EAAE,eAAe,EAAE,gBAAgB,EAAE,MAAM,aAAa,CAAA;AAC5E,YAAY,EAAE,IAAI,EAAE,WAAW,EAAE,MAAM,aAAa,CAAA;AACpD,OAAO,EAAE,UAAU,EAAE,SAAS,EAAE,GAAG,EAAE,aAAa,EAAE,aAAa,EAAE,cAAc,EAAE,MAAM,UAAU,CAAA;AACnG,YAAY,EACV,KAAK,EAAE,YAAY,EAAE,KAAK,EAAE,WAAW,EAAE,OAAO,EAAE,MAAM,EAAE,MAAM,EAAE,YAAY,EAAE,YAAY,EAC7F,MAAM,UAAU,CAAA;AACjB,OAAO,EAAE,SAAS,EAAE,MAAM,WAAW,CAAA"}