trail-code 0.0.0-stage → 0.28.0-semantic.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (593) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +567 -2
  3. package/dist/ai/crux.d.ts +88 -0
  4. package/dist/ai/crux.d.ts.map +1 -0
  5. package/dist/ai/crux.js +219 -0
  6. package/dist/ai/crux.js.map +1 -0
  7. package/dist/ai/failure.d.ts +60 -0
  8. package/dist/ai/failure.d.ts.map +1 -0
  9. package/dist/ai/failure.js +86 -0
  10. package/dist/ai/failure.js.map +1 -0
  11. package/dist/ai/llm/anthropic.d.ts +37 -0
  12. package/dist/ai/llm/anthropic.d.ts.map +1 -0
  13. package/dist/ai/llm/anthropic.js +144 -0
  14. package/dist/ai/llm/anthropic.js.map +1 -0
  15. package/dist/ai/llm/factory.d.ts +28 -0
  16. package/dist/ai/llm/factory.d.ts.map +1 -0
  17. package/dist/ai/llm/factory.js +36 -0
  18. package/dist/ai/llm/factory.js.map +1 -0
  19. package/dist/ai/llm/litellm.d.ts +34 -0
  20. package/dist/ai/llm/litellm.d.ts.map +1 -0
  21. package/dist/ai/llm/litellm.js +45 -0
  22. package/dist/ai/llm/litellm.js.map +1 -0
  23. package/dist/ai/llm/openai.d.ts +145 -0
  24. package/dist/ai/llm/openai.d.ts.map +1 -0
  25. package/dist/ai/llm/openai.js +629 -0
  26. package/dist/ai/llm/openai.js.map +1 -0
  27. package/dist/ai/llm/orcarouter.d.ts +34 -0
  28. package/dist/ai/llm/orcarouter.d.ts.map +1 -0
  29. package/dist/ai/llm/orcarouter.js +45 -0
  30. package/dist/ai/llm/orcarouter.js.map +1 -0
  31. package/dist/ai/llm/recover-tool.d.ts +21 -0
  32. package/dist/ai/llm/recover-tool.d.ts.map +1 -0
  33. package/dist/ai/llm/recover-tool.js +109 -0
  34. package/dist/ai/llm/recover-tool.js.map +1 -0
  35. package/dist/ai/llm/types.d.ts +122 -0
  36. package/dist/ai/llm/types.d.ts.map +1 -0
  37. package/dist/ai/llm/types.js +33 -0
  38. package/dist/ai/llm/types.js.map +1 -0
  39. package/dist/ai/providers.d.ts +59 -0
  40. package/dist/ai/providers.d.ts.map +1 -0
  41. package/dist/ai/providers.js +54 -0
  42. package/dist/ai/providers.js.map +1 -0
  43. package/dist/ai/summarize.d.ts +25 -0
  44. package/dist/ai/summarize.d.ts.map +1 -0
  45. package/dist/ai/summarize.js +34 -0
  46. package/dist/ai/summarize.js.map +1 -0
  47. package/dist/ai/synthesize.d.ts +40 -0
  48. package/dist/ai/synthesize.d.ts.map +1 -0
  49. package/dist/ai/synthesize.js +230 -0
  50. package/dist/ai/synthesize.js.map +1 -0
  51. package/dist/ask/ask.d.ts +199 -0
  52. package/dist/ask/ask.d.ts.map +1 -0
  53. package/dist/ask/ask.js +1291 -0
  54. package/dist/ask/ask.js.map +1 -0
  55. package/dist/ask/file-rank.d.ts +72 -0
  56. package/dist/ask/file-rank.d.ts.map +1 -0
  57. package/dist/ask/file-rank.js +160 -0
  58. package/dist/ask/file-rank.js.map +1 -0
  59. package/dist/ask/file-selection.d.ts +22 -0
  60. package/dist/ask/file-selection.d.ts.map +1 -0
  61. package/dist/ask/file-selection.js +66 -0
  62. package/dist/ask/file-selection.js.map +1 -0
  63. package/dist/ask/fuse.d.ts +195 -0
  64. package/dist/ask/fuse.d.ts.map +1 -0
  65. package/dist/ask/fuse.js +344 -0
  66. package/dist/ask/fuse.js.map +1 -0
  67. package/dist/ask/graphrank.d.ts +61 -0
  68. package/dist/ask/graphrank.d.ts.map +1 -0
  69. package/dist/ask/graphrank.js +130 -0
  70. package/dist/ask/graphrank.js.map +1 -0
  71. package/dist/ask/index-file.d.ts +44 -0
  72. package/dist/ask/index-file.d.ts.map +1 -0
  73. package/dist/ask/index-file.js +128 -0
  74. package/dist/ask/index-file.js.map +1 -0
  75. package/dist/ask/semantic.d.ts +42 -0
  76. package/dist/ask/semantic.d.ts.map +1 -0
  77. package/dist/ask/semantic.js +293 -0
  78. package/dist/ask/semantic.js.map +1 -0
  79. package/dist/bin/graft.d.ts +3 -0
  80. package/dist/bin/graft.d.ts.map +1 -0
  81. package/dist/bin/graft.js +14 -0
  82. package/dist/bin/graft.js.map +1 -0
  83. package/dist/bin/trail.d.ts +3 -0
  84. package/dist/bin/trail.d.ts.map +1 -0
  85. package/dist/bin/trail.js +13 -0
  86. package/dist/bin/trail.js.map +1 -0
  87. package/dist/blast/blast-cli.d.ts +35 -0
  88. package/dist/blast/blast-cli.d.ts.map +1 -0
  89. package/dist/blast/blast-cli.js +155 -0
  90. package/dist/blast/blast-cli.js.map +1 -0
  91. package/dist/blast/blast.d.ts +128 -0
  92. package/dist/blast/blast.d.ts.map +1 -0
  93. package/dist/blast/blast.js +383 -0
  94. package/dist/blast/blast.js.map +1 -0
  95. package/dist/blast/diff.d.ts +53 -0
  96. package/dist/blast/diff.d.ts.map +1 -0
  97. package/dist/blast/diff.js +193 -0
  98. package/dist/blast/diff.js.map +1 -0
  99. package/dist/blast/evidence.d.ts +51 -0
  100. package/dist/blast/evidence.d.ts.map +1 -0
  101. package/dist/blast/evidence.js +162 -0
  102. package/dist/blast/evidence.js.map +1 -0
  103. package/dist/blast/modules.d.ts +33 -0
  104. package/dist/blast/modules.d.ts.map +1 -0
  105. package/dist/blast/modules.js +83 -0
  106. package/dist/blast/modules.js.map +1 -0
  107. package/dist/blast/name.d.ts +74 -0
  108. package/dist/blast/name.d.ts.map +1 -0
  109. package/dist/blast/name.js +269 -0
  110. package/dist/blast/name.js.map +1 -0
  111. package/dist/blast/owners.d.ts +85 -0
  112. package/dist/blast/owners.d.ts.map +1 -0
  113. package/dist/blast/owners.js +272 -0
  114. package/dist/blast/owners.js.map +1 -0
  115. package/dist/blast/render.d.ts +46 -0
  116. package/dist/blast/render.d.ts.map +1 -0
  117. package/dist/blast/render.js +422 -0
  118. package/dist/blast/render.js.map +1 -0
  119. package/dist/blast/viz.d.ts +37 -0
  120. package/dist/blast/viz.d.ts.map +1 -0
  121. package/dist/blast/viz.js +180 -0
  122. package/dist/blast/viz.js.map +1 -0
  123. package/dist/brand.d.ts +111 -0
  124. package/dist/brand.d.ts.map +1 -0
  125. package/dist/brand.js +282 -0
  126. package/dist/brand.js.map +1 -0
  127. package/dist/claude/build-progress.d.ts +30 -0
  128. package/dist/claude/build-progress.d.ts.map +1 -0
  129. package/dist/claude/build-progress.js +81 -0
  130. package/dist/claude/build-progress.js.map +1 -0
  131. package/dist/claude/hermes-skill-template.d.ts +16 -0
  132. package/dist/claude/hermes-skill-template.d.ts.map +1 -0
  133. package/dist/claude/hermes-skill-template.js +154 -0
  134. package/dist/claude/hermes-skill-template.js.map +1 -0
  135. package/dist/claude/init.d.ts +65 -0
  136. package/dist/claude/init.d.ts.map +1 -0
  137. package/dist/claude/init.js +258 -0
  138. package/dist/claude/init.js.map +1 -0
  139. package/dist/claude/paths.d.ts +9 -0
  140. package/dist/claude/paths.d.ts.map +1 -0
  141. package/dist/claude/paths.js +22 -0
  142. package/dist/claude/paths.js.map +1 -0
  143. package/dist/claude/session-metrics.d.ts +73 -0
  144. package/dist/claude/session-metrics.d.ts.map +1 -0
  145. package/dist/claude/session-metrics.js +209 -0
  146. package/dist/claude/session-metrics.js.map +1 -0
  147. package/dist/claude/settings-merge.d.ts +76 -0
  148. package/dist/claude/settings-merge.d.ts.map +1 -0
  149. package/dist/claude/settings-merge.js +283 -0
  150. package/dist/claude/settings-merge.js.map +1 -0
  151. package/dist/claude/skill-template.d.ts +13 -0
  152. package/dist/claude/skill-template.d.ts.map +1 -0
  153. package/dist/claude/skill-template.js +290 -0
  154. package/dist/claude/skill-template.js.map +1 -0
  155. package/dist/claude/state.d.ts +85 -0
  156. package/dist/claude/state.d.ts.map +1 -0
  157. package/dist/claude/state.js +88 -0
  158. package/dist/claude/state.js.map +1 -0
  159. package/dist/claude/stats.d.ts +5 -0
  160. package/dist/claude/stats.d.ts.map +1 -0
  161. package/dist/claude/stats.js +24 -0
  162. package/dist/claude/stats.js.map +1 -0
  163. package/dist/cli-epilogue.d.ts +12 -0
  164. package/dist/cli-epilogue.d.ts.map +1 -0
  165. package/dist/cli-epilogue.js +72 -0
  166. package/dist/cli-epilogue.js.map +1 -0
  167. package/dist/cli-meta.d.ts +82 -0
  168. package/dist/cli-meta.d.ts.map +1 -0
  169. package/dist/cli-meta.js +238 -0
  170. package/dist/cli-meta.js.map +1 -0
  171. package/dist/cli-picker.d.ts +139 -0
  172. package/dist/cli-picker.d.ts.map +1 -0
  173. package/dist/cli-picker.js +439 -0
  174. package/dist/cli-picker.js.map +1 -0
  175. package/dist/cli.d.ts +3 -0
  176. package/dist/cli.d.ts.map +1 -0
  177. package/dist/cli.js +1638 -0
  178. package/dist/cli.js.map +1 -0
  179. package/dist/context/batches.d.ts +29 -0
  180. package/dist/context/batches.d.ts.map +1 -0
  181. package/dist/context/batches.js +130 -0
  182. package/dist/context/batches.js.map +1 -0
  183. package/dist/context/build.d.ts +57 -0
  184. package/dist/context/build.d.ts.map +1 -0
  185. package/dist/context/build.js +396 -0
  186. package/dist/context/build.js.map +1 -0
  187. package/dist/context/check.d.ts +42 -0
  188. package/dist/context/check.d.ts.map +1 -0
  189. package/dist/context/check.js +162 -0
  190. package/dist/context/check.js.map +1 -0
  191. package/dist/context/map-dir.d.ts +13 -0
  192. package/dist/context/map-dir.d.ts.map +1 -0
  193. package/dist/context/map-dir.js +81 -0
  194. package/dist/context/map-dir.js.map +1 -0
  195. package/dist/context/node-file.d.ts +109 -0
  196. package/dist/context/node-file.d.ts.map +1 -0
  197. package/dist/context/node-file.js +390 -0
  198. package/dist/context/node-file.js.map +1 -0
  199. package/dist/context/price.d.ts +49 -0
  200. package/dist/context/price.d.ts.map +1 -0
  201. package/dist/context/price.js +83 -0
  202. package/dist/context/price.js.map +1 -0
  203. package/dist/context/savings.d.ts +67 -0
  204. package/dist/context/savings.d.ts.map +1 -0
  205. package/dist/context/savings.js +125 -0
  206. package/dist/context/savings.js.map +1 -0
  207. package/dist/engine.d.ts +85 -0
  208. package/dist/engine.d.ts.map +1 -0
  209. package/dist/engine.js +122 -0
  210. package/dist/engine.js.map +1 -0
  211. package/dist/graph/bindings.d.ts +64 -0
  212. package/dist/graph/bindings.d.ts.map +1 -0
  213. package/dist/graph/bindings.js +713 -0
  214. package/dist/graph/bindings.js.map +1 -0
  215. package/dist/graph/build-run.d.ts +25 -0
  216. package/dist/graph/build-run.d.ts.map +1 -0
  217. package/dist/graph/build-run.js +121 -0
  218. package/dist/graph/build-run.js.map +1 -0
  219. package/dist/graph/build.d.ts +88 -0
  220. package/dist/graph/build.d.ts.map +1 -0
  221. package/dist/graph/build.js +386 -0
  222. package/dist/graph/build.js.map +1 -0
  223. package/dist/graph/cards.d.ts +46 -0
  224. package/dist/graph/cards.d.ts.map +1 -0
  225. package/dist/graph/cards.js +280 -0
  226. package/dist/graph/cards.js.map +1 -0
  227. package/dist/graph/check.d.ts +25 -0
  228. package/dist/graph/check.d.ts.map +1 -0
  229. package/dist/graph/check.js +192 -0
  230. package/dist/graph/check.js.map +1 -0
  231. package/dist/graph/container.d.ts +63 -0
  232. package/dist/graph/container.d.ts.map +1 -0
  233. package/dist/graph/container.js +191 -0
  234. package/dist/graph/container.js.map +1 -0
  235. package/dist/graph/depth-parser.d.ts +61 -0
  236. package/dist/graph/depth-parser.d.ts.map +1 -0
  237. package/dist/graph/depth-parser.js +153 -0
  238. package/dist/graph/depth-parser.js.map +1 -0
  239. package/dist/graph/enrich.d.ts +62 -0
  240. package/dist/graph/enrich.d.ts.map +1 -0
  241. package/dist/graph/enrich.js +258 -0
  242. package/dist/graph/enrich.js.map +1 -0
  243. package/dist/graph/extract-cache.d.ts +101 -0
  244. package/dist/graph/extract-cache.d.ts.map +1 -0
  245. package/dist/graph/extract-cache.js +199 -0
  246. package/dist/graph/extract-cache.js.map +1 -0
  247. package/dist/graph/extract.d.ts +85 -0
  248. package/dist/graph/extract.d.ts.map +1 -0
  249. package/dist/graph/extract.js +2377 -0
  250. package/dist/graph/extract.js.map +1 -0
  251. package/dist/graph/fingerprint.d.ts +76 -0
  252. package/dist/graph/fingerprint.d.ts.map +1 -0
  253. package/dist/graph/fingerprint.js +160 -0
  254. package/dist/graph/fingerprint.js.map +1 -0
  255. package/dist/graph/generic.d.ts +74 -0
  256. package/dist/graph/generic.d.ts.map +1 -0
  257. package/dist/graph/generic.js +773 -0
  258. package/dist/graph/generic.js.map +1 -0
  259. package/dist/graph/invariants.d.ts +33 -0
  260. package/dist/graph/invariants.d.ts.map +1 -0
  261. package/dist/graph/invariants.js +52 -0
  262. package/dist/graph/invariants.js.map +1 -0
  263. package/dist/graph/load.d.ts +29 -0
  264. package/dist/graph/load.d.ts.map +1 -0
  265. package/dist/graph/load.js +97 -0
  266. package/dist/graph/load.js.map +1 -0
  267. package/dist/graph/lsp/client.d.ts +61 -0
  268. package/dist/graph/lsp/client.d.ts.map +1 -0
  269. package/dist/graph/lsp/client.js +217 -0
  270. package/dist/graph/lsp/client.js.map +1 -0
  271. package/dist/graph/lsp/enrich.d.ts +11 -0
  272. package/dist/graph/lsp/enrich.d.ts.map +1 -0
  273. package/dist/graph/lsp/enrich.js +163 -0
  274. package/dist/graph/lsp/enrich.js.map +1 -0
  275. package/dist/graph/lsp/registry.d.ts +22 -0
  276. package/dist/graph/lsp/registry.d.ts.map +1 -0
  277. package/dist/graph/lsp/registry.js +71 -0
  278. package/dist/graph/lsp/registry.js.map +1 -0
  279. package/dist/graph/map.d.ts +107 -0
  280. package/dist/graph/map.d.ts.map +1 -0
  281. package/dist/graph/map.js +239 -0
  282. package/dist/graph/map.js.map +1 -0
  283. package/dist/graph/markdown.d.ts +22 -0
  284. package/dist/graph/markdown.d.ts.map +1 -0
  285. package/dist/graph/markdown.js +143 -0
  286. package/dist/graph/markdown.js.map +1 -0
  287. package/dist/graph/native.d.ts +46 -0
  288. package/dist/graph/native.d.ts.map +1 -0
  289. package/dist/graph/native.js +169 -0
  290. package/dist/graph/native.js.map +1 -0
  291. package/dist/graph/queries/c.scm +13 -0
  292. package/dist/graph/queries/c_sharp.scm +19 -0
  293. package/dist/graph/queries/clojure.scm +58 -0
  294. package/dist/graph/queries/cpp.scm +23 -0
  295. package/dist/graph/queries/dart.scm +42 -0
  296. package/dist/graph/queries/elixir.scm +54 -0
  297. package/dist/graph/queries/gleam.scm +51 -0
  298. package/dist/graph/queries/java.scm +20 -0
  299. package/dist/graph/queries/kotlin.scm +43 -0
  300. package/dist/graph/queries/lua.scm +36 -0
  301. package/dist/graph/queries/nix.scm +32 -0
  302. package/dist/graph/queries/php.scm +40 -0
  303. package/dist/graph/queries/ruby.scm +65 -0
  304. package/dist/graph/queries/rust.scm +41 -0
  305. package/dist/graph/queries/scala.scm +66 -0
  306. package/dist/graph/queries/solidity.scm +43 -0
  307. package/dist/graph/queries/swift.scm +51 -0
  308. package/dist/graph/refresh.d.ts +106 -0
  309. package/dist/graph/refresh.d.ts.map +1 -0
  310. package/dist/graph/refresh.js +430 -0
  311. package/dist/graph/refresh.js.map +1 -0
  312. package/dist/graph/relations.d.ts +14 -0
  313. package/dist/graph/relations.d.ts.map +1 -0
  314. package/dist/graph/relations.js +8 -0
  315. package/dist/graph/relations.js.map +1 -0
  316. package/dist/graph/resolve.d.ts +17 -0
  317. package/dist/graph/resolve.d.ts.map +1 -0
  318. package/dist/graph/resolve.js +716 -0
  319. package/dist/graph/resolve.js.map +1 -0
  320. package/dist/graph/root.d.ts +11 -0
  321. package/dist/graph/root.d.ts.map +1 -0
  322. package/dist/graph/root.js +40 -0
  323. package/dist/graph/root.js.map +1 -0
  324. package/dist/graph/scopes.d.ts +40 -0
  325. package/dist/graph/scopes.d.ts.map +1 -0
  326. package/dist/graph/scopes.js +383 -0
  327. package/dist/graph/scopes.js.map +1 -0
  328. package/dist/graph/seed.d.ts +38 -0
  329. package/dist/graph/seed.d.ts.map +1 -0
  330. package/dist/graph/seed.js +229 -0
  331. package/dist/graph/seed.js.map +1 -0
  332. package/dist/graph/source-files.d.ts +46 -0
  333. package/dist/graph/source-files.d.ts.map +1 -0
  334. package/dist/graph/source-files.js +118 -0
  335. package/dist/graph/source-files.js.map +1 -0
  336. package/dist/graph/traverse-cli.d.ts +55 -0
  337. package/dist/graph/traverse-cli.d.ts.map +1 -0
  338. package/dist/graph/traverse-cli.js +189 -0
  339. package/dist/graph/traverse-cli.js.map +1 -0
  340. package/dist/graph/traverse.d.ts +112 -0
  341. package/dist/graph/traverse.d.ts.map +1 -0
  342. package/dist/graph/traverse.js +192 -0
  343. package/dist/graph/traverse.js.map +1 -0
  344. package/dist/graph/types.d.ts +78 -0
  345. package/dist/graph/types.d.ts.map +1 -0
  346. package/dist/graph/types.js +14 -0
  347. package/dist/graph/types.js.map +1 -0
  348. package/dist/graph/wasm-runtime.d.ts +19 -0
  349. package/dist/graph/wasm-runtime.d.ts.map +1 -0
  350. package/dist/graph/wasm-runtime.js +38 -0
  351. package/dist/graph/wasm-runtime.js.map +1 -0
  352. package/dist/graph/workspace-cli.d.ts +56 -0
  353. package/dist/graph/workspace-cli.d.ts.map +1 -0
  354. package/dist/graph/workspace-cli.js +111 -0
  355. package/dist/graph/workspace-cli.js.map +1 -0
  356. package/dist/graph/workspace.d.ts +172 -0
  357. package/dist/graph/workspace.d.ts.map +1 -0
  358. package/dist/graph/workspace.js +714 -0
  359. package/dist/graph/workspace.js.map +1 -0
  360. package/dist/graph/write.d.ts +13 -0
  361. package/dist/graph/write.d.ts.map +1 -0
  362. package/dist/graph/write.js +86 -0
  363. package/dist/graph/write.js.map +1 -0
  364. package/dist/hosts/antigravity.d.ts +14 -0
  365. package/dist/hosts/antigravity.d.ts.map +1 -0
  366. package/dist/hosts/antigravity.js +59 -0
  367. package/dist/hosts/antigravity.js.map +1 -0
  368. package/dist/hosts/auto.d.ts +37 -0
  369. package/dist/hosts/auto.d.ts.map +1 -0
  370. package/dist/hosts/auto.js +141 -0
  371. package/dist/hosts/auto.js.map +1 -0
  372. package/dist/hosts/claude-global.d.ts +72 -0
  373. package/dist/hosts/claude-global.d.ts.map +1 -0
  374. package/dist/hosts/claude-global.js +230 -0
  375. package/dist/hosts/claude-global.js.map +1 -0
  376. package/dist/hosts/config-write.d.ts +36 -0
  377. package/dist/hosts/config-write.d.ts.map +1 -0
  378. package/dist/hosts/config-write.js +64 -0
  379. package/dist/hosts/config-write.js.map +1 -0
  380. package/dist/hosts/init.d.ts +28 -0
  381. package/dist/hosts/init.d.ts.map +1 -0
  382. package/dist/hosts/init.js +89 -0
  383. package/dist/hosts/init.js.map +1 -0
  384. package/dist/hosts/instructions.d.ts +14 -0
  385. package/dist/hosts/instructions.d.ts.map +1 -0
  386. package/dist/hosts/instructions.js +95 -0
  387. package/dist/hosts/instructions.js.map +1 -0
  388. package/dist/hosts/mcp-config.d.ts +78 -0
  389. package/dist/hosts/mcp-config.d.ts.map +1 -0
  390. package/dist/hosts/mcp-config.js +251 -0
  391. package/dist/hosts/mcp-config.js.map +1 -0
  392. package/dist/hosts/plan.d.ts +32 -0
  393. package/dist/hosts/plan.d.ts.map +1 -0
  394. package/dist/hosts/plan.js +73 -0
  395. package/dist/hosts/plan.js.map +1 -0
  396. package/dist/hosts/registry.d.ts +41 -0
  397. package/dist/hosts/registry.d.ts.map +1 -0
  398. package/dist/hosts/registry.js +164 -0
  399. package/dist/hosts/registry.js.map +1 -0
  400. package/dist/hosts/retract.d.ts +47 -0
  401. package/dist/hosts/retract.d.ts.map +1 -0
  402. package/dist/hosts/retract.js +520 -0
  403. package/dist/hosts/retract.js.map +1 -0
  404. package/dist/hosts/sections.d.ts +47 -0
  405. package/dist/hosts/sections.d.ts.map +1 -0
  406. package/dist/hosts/sections.js +127 -0
  407. package/dist/hosts/sections.js.map +1 -0
  408. package/dist/index.d.ts +41 -0
  409. package/dist/index.d.ts.map +1 -0
  410. package/dist/index.js +32 -0
  411. package/dist/index.js.map +1 -0
  412. package/dist/ingest/fs.d.ts +79 -0
  413. package/dist/ingest/fs.d.ts.map +1 -0
  414. package/dist/ingest/fs.js +306 -0
  415. package/dist/ingest/fs.js.map +1 -0
  416. package/dist/init-guard.d.ts +16 -0
  417. package/dist/init-guard.d.ts.map +1 -0
  418. package/dist/init-guard.js +27 -0
  419. package/dist/init-guard.js.map +1 -0
  420. package/dist/mcp/instructions.d.ts +5 -0
  421. package/dist/mcp/instructions.d.ts.map +1 -0
  422. package/dist/mcp/instructions.js +64 -0
  423. package/dist/mcp/instructions.js.map +1 -0
  424. package/dist/mcp/kept-listing.d.ts +27 -0
  425. package/dist/mcp/kept-listing.d.ts.map +1 -0
  426. package/dist/mcp/kept-listing.js +63 -0
  427. package/dist/mcp/kept-listing.js.map +1 -0
  428. package/dist/mcp/server.d.ts +4 -0
  429. package/dist/mcp/server.d.ts.map +1 -0
  430. package/dist/mcp/server.js +147 -0
  431. package/dist/mcp/server.js.map +1 -0
  432. package/dist/mcp/tool-names.d.ts +27 -0
  433. package/dist/mcp/tool-names.d.ts.map +1 -0
  434. package/dist/mcp/tool-names.js +47 -0
  435. package/dist/mcp/tool-names.js.map +1 -0
  436. package/dist/mcp/tools.d.ts +22 -0
  437. package/dist/mcp/tools.d.ts.map +1 -0
  438. package/dist/mcp/tools.js +440 -0
  439. package/dist/mcp/tools.js.map +1 -0
  440. package/dist/node-version.d.ts +15 -0
  441. package/dist/node-version.d.ts.map +1 -0
  442. package/dist/node-version.js +23 -0
  443. package/dist/node-version.js.map +1 -0
  444. package/dist/search/grep-cli.d.ts +35 -0
  445. package/dist/search/grep-cli.d.ts.map +1 -0
  446. package/dist/search/grep-cli.js +115 -0
  447. package/dist/search/grep-cli.js.map +1 -0
  448. package/dist/search/grep.d.ts +60 -0
  449. package/dist/search/grep.d.ts.map +1 -0
  450. package/dist/search/grep.js +143 -0
  451. package/dist/search/grep.js.map +1 -0
  452. package/dist/search/ignored-code.d.ts +9 -0
  453. package/dist/search/ignored-code.d.ts.map +1 -0
  454. package/dist/search/ignored-code.js +73 -0
  455. package/dist/search/ignored-code.js.map +1 -0
  456. package/dist/search/user-regexp.d.ts +26 -0
  457. package/dist/search/user-regexp.d.ts.map +1 -0
  458. package/dist/search/user-regexp.js +150 -0
  459. package/dist/search/user-regexp.js.map +1 -0
  460. package/dist/telemetry/contract.d.ts +117 -0
  461. package/dist/telemetry/contract.d.ts.map +1 -0
  462. package/dist/telemetry/contract.js +341 -0
  463. package/dist/telemetry/contract.js.map +1 -0
  464. package/dist/telemetry/flush.d.ts +21 -0
  465. package/dist/telemetry/flush.d.ts.map +1 -0
  466. package/dist/telemetry/flush.js +85 -0
  467. package/dist/telemetry/flush.js.map +1 -0
  468. package/dist/telemetry/gate.d.ts +30 -0
  469. package/dist/telemetry/gate.d.ts.map +1 -0
  470. package/dist/telemetry/gate.js +81 -0
  471. package/dist/telemetry/gate.js.map +1 -0
  472. package/dist/telemetry/identity.d.ts +40 -0
  473. package/dist/telemetry/identity.d.ts.map +1 -0
  474. package/dist/telemetry/identity.js +80 -0
  475. package/dist/telemetry/identity.js.map +1 -0
  476. package/dist/telemetry/index.d.ts +18 -0
  477. package/dist/telemetry/index.d.ts.map +1 -0
  478. package/dist/telemetry/index.js +16 -0
  479. package/dist/telemetry/index.js.map +1 -0
  480. package/dist/telemetry/key.d.ts +21 -0
  481. package/dist/telemetry/key.d.ts.map +1 -0
  482. package/dist/telemetry/key.js +49 -0
  483. package/dist/telemetry/key.js.map +1 -0
  484. package/dist/telemetry/notice.d.ts +19 -0
  485. package/dist/telemetry/notice.d.ts.map +1 -0
  486. package/dist/telemetry/notice.js +93 -0
  487. package/dist/telemetry/notice.js.map +1 -0
  488. package/dist/telemetry/queue.d.ts +35 -0
  489. package/dist/telemetry/queue.d.ts.map +1 -0
  490. package/dist/telemetry/queue.js +162 -0
  491. package/dist/telemetry/queue.js.map +1 -0
  492. package/dist/telemetry/send.d.ts +19 -0
  493. package/dist/telemetry/send.d.ts.map +1 -0
  494. package/dist/telemetry/send.js +84 -0
  495. package/dist/telemetry/send.js.map +1 -0
  496. package/dist/telemetry/sessions.d.ts +25 -0
  497. package/dist/telemetry/sessions.d.ts.map +1 -0
  498. package/dist/telemetry/sessions.js +104 -0
  499. package/dist/telemetry/sessions.js.map +1 -0
  500. package/dist/telemetry/track.d.ts +62 -0
  501. package/dist/telemetry/track.d.ts.map +1 -0
  502. package/dist/telemetry/track.js +143 -0
  503. package/dist/telemetry/track.js.map +1 -0
  504. package/dist/upkeep-run.d.ts +22 -0
  505. package/dist/upkeep-run.d.ts.map +1 -0
  506. package/dist/upkeep-run.js +85 -0
  507. package/dist/upkeep-run.js.map +1 -0
  508. package/dist/upkeep.d.ts +127 -0
  509. package/dist/upkeep.d.ts.map +1 -0
  510. package/dist/upkeep.js +252 -0
  511. package/dist/upkeep.js.map +1 -0
  512. package/dist/util/actions-folder.d.ts +2 -0
  513. package/dist/util/actions-folder.d.ts.map +1 -0
  514. package/dist/util/actions-folder.js +9 -0
  515. package/dist/util/actions-folder.js.map +1 -0
  516. package/dist/util/browser.d.ts +3 -0
  517. package/dist/util/browser.d.ts.map +1 -0
  518. package/dist/util/browser.js +14 -0
  519. package/dist/util/browser.js.map +1 -0
  520. package/dist/util/child-process.d.ts +15 -0
  521. package/dist/util/child-process.d.ts.map +1 -0
  522. package/dist/util/child-process.js +15 -0
  523. package/dist/util/child-process.js.map +1 -0
  524. package/dist/util/front-matter.d.ts +46 -0
  525. package/dist/util/front-matter.d.ts.map +1 -0
  526. package/dist/util/front-matter.js +113 -0
  527. package/dist/util/front-matter.js.map +1 -0
  528. package/dist/util/id.d.ts +7 -0
  529. package/dist/util/id.d.ts.map +1 -0
  530. package/dist/util/id.js +14 -0
  531. package/dist/util/id.js.map +1 -0
  532. package/dist/util/paths.d.ts +29 -0
  533. package/dist/util/paths.d.ts.map +1 -0
  534. package/dist/util/paths.js +71 -0
  535. package/dist/util/paths.js.map +1 -0
  536. package/dist/util/private-file.d.ts +14 -0
  537. package/dist/util/private-file.d.ts.map +1 -0
  538. package/dist/util/private-file.js +82 -0
  539. package/dist/util/private-file.js.map +1 -0
  540. package/dist/util/source.d.ts +4 -0
  541. package/dist/util/source.d.ts.map +1 -0
  542. package/dist/util/source.js +12 -0
  543. package/dist/util/source.js.map +1 -0
  544. package/dist/util/spinner.d.ts +15 -0
  545. package/dist/util/spinner.d.ts.map +1 -0
  546. package/dist/util/spinner.js +52 -0
  547. package/dist/util/spinner.js.map +1 -0
  548. package/dist/util/state.d.ts +120 -0
  549. package/dist/util/state.d.ts.map +1 -0
  550. package/dist/util/state.js +264 -0
  551. package/dist/util/state.js.map +1 -0
  552. package/dist/vendor/grammars/tree-sitter-go.LICENSE +21 -0
  553. package/dist/vendor/grammars/tree-sitter-go.wasm +0 -0
  554. package/dist/vendor/grammars/tree-sitter-java.LICENSE +21 -0
  555. package/dist/vendor/grammars/tree-sitter-java.wasm +0 -0
  556. package/dist/vendor/grammars/tree-sitter-kotlin.LICENSE +9 -0
  557. package/dist/vendor/grammars/tree-sitter-kotlin.wasm +0 -0
  558. package/dist/vendor/grammars/tree-sitter-php.LICENSE +22 -0
  559. package/dist/vendor/grammars/tree-sitter-php.wasm +0 -0
  560. package/dist/vendor/grammars/tree-sitter-python.LICENSE +21 -0
  561. package/dist/vendor/grammars/tree-sitter-python.wasm +0 -0
  562. package/dist/vendor/grammars/tree-sitter-r.LICENSE +9 -0
  563. package/dist/vendor/grammars/tree-sitter-r.wasm +0 -0
  564. package/dist/vendor/grammars/tree-sitter-swift.LICENSE +21 -0
  565. package/dist/vendor/grammars/tree-sitter-swift.wasm +0 -0
  566. package/dist/vendor/grammars/tree-sitter-tsx.wasm +0 -0
  567. package/dist/vendor/grammars/tree-sitter-typescript.LICENSE +21 -0
  568. package/dist/vendor/grammars/tree-sitter-typescript.wasm +0 -0
  569. package/dist/viewer/app.js +2 -0
  570. package/dist/viewer/index.html +49 -0
  571. package/dist/viewer/style.css +154 -0
  572. package/dist/viz/assemble.d.ts +83 -0
  573. package/dist/viz/assemble.d.ts.map +1 -0
  574. package/dist/viz/assemble.js +101 -0
  575. package/dist/viz/assemble.js.map +1 -0
  576. package/dist/viz/export.d.ts +39 -0
  577. package/dist/viz/export.d.ts.map +1 -0
  578. package/dist/viz/export.js +98 -0
  579. package/dist/viz/export.js.map +1 -0
  580. package/dist/viz/serve.d.ts +13 -0
  581. package/dist/viz/serve.d.ts.map +1 -0
  582. package/dist/viz/serve.js +130 -0
  583. package/dist/viz/serve.js.map +1 -0
  584. package/package.json +115 -4
  585. package/scripts/build-grammar-wasm.mjs +112 -0
  586. package/scripts/build-viewer.mjs +44 -0
  587. package/scripts/graph-quality.mjs +117 -0
  588. package/scripts/pack-trail.mjs +53 -0
  589. package/scripts/postinstall.mjs +65 -0
  590. package/scripts/run-tests.mjs +72 -0
  591. package/scripts/stamp-telemetry-key.mjs +56 -0
  592. package/scripts/tally-audit.mjs +140 -0
  593. package/scripts/vendor-grammars.mjs +53 -0
@@ -0,0 +1,49 @@
1
+ /**
2
+ * What a saved token was actually worth, in dollars.
3
+ *
4
+ * `savings.ts` answers "how many input tokens did graft keep out of the
5
+ * context"; this answers "what does an input token cost here". The two are
6
+ * deliberately separate: the token count is arithmetic over file sizes and is
7
+ * true everywhere, while the price depends on which model the session ran and
8
+ * how much of its context was served from cache — facts only the host's
9
+ * transcript knows.
10
+ *
11
+ * Nothing here guesses. There is no default rate and no env override: a model
12
+ * we don't have a price for yields null, and the callers then render the token
13
+ * count alone rather than a dollar figure we made up. A wrong number on the
14
+ * statusline is worse than no number.
15
+ */
16
+ /** List input price for a model id, or null when we don't know it — a model
17
+ * released after this table was written, or a host reporting something else
18
+ * entirely. Null propagates all the way to "render tokens only". */
19
+ export declare function inputUsdPerMtok(model: unknown): number | null;
20
+ /** One turn's input-token usage, as the host's transcript reports it. */
21
+ export interface TurnUsage {
22
+ model: string;
23
+ /** Fresh tokens, billed at the list rate. */
24
+ input: number;
25
+ /** Written to the cache this turn — a 25% premium over list. */
26
+ cacheCreate: number;
27
+ /** Served from cache — a tenth of list, and usually the bulk of a long turn. */
28
+ cacheRead: number;
29
+ }
30
+ /** What this turn's input tokens cost, in micro-dollars, or null on a model we
31
+ * have no price for. */
32
+ export declare function turnInputCostMicros(usage: TurnUsage): number | null;
33
+ /** Every input token this turn was billed for, cached or not — the denominator
34
+ * of the blended rate. */
35
+ export declare function turnInputTokens(usage: TurnUsage): number;
36
+ /**
37
+ * Dollars saved, at the rate the session has actually been paying.
38
+ *
39
+ * `costMicros / tokensBilled` is the blended price of one input token here —
40
+ * model and cache-hit ratio already folded in — so this re-blends as the
41
+ * session goes rather than freezing turn one's rate. Returns null when nothing
42
+ * has been sampled yet (turn one, or a host whose hooks name no transcript).
43
+ */
44
+ export declare function dollarsSaved(savedTokens: number, costMicros: number | undefined, tokensBilled: number | undefined): number | null;
45
+ /** `$1.23`, or `<$0.01` for a real but sub-cent saving. Never `$0.00`: a
46
+ * rounded-to-nothing number reads as "graft saved you nothing", which is a
47
+ * different claim from "graft saved you less than a cent". */
48
+ export declare function formatDollars(usd: number): string;
49
+ //# sourceMappingURL=price.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"price.d.ts","sourceRoot":"","sources":["../../src/context/price.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;GAcG;AAYH;;oEAEoE;AACpE,wBAAgB,eAAe,CAAC,KAAK,EAAE,OAAO,GAAG,MAAM,GAAG,IAAI,CAI7D;AAED,yEAAyE;AACzE,MAAM,WAAW,SAAS;IACxB,KAAK,EAAE,MAAM,CAAC;IACd,6CAA6C;IAC7C,KAAK,EAAE,MAAM,CAAC;IACd,gEAAgE;IAChE,WAAW,EAAE,MAAM,CAAC;IACpB,gFAAgF;IAChF,SAAS,EAAE,MAAM,CAAC;CACnB;AAWD;wBACwB;AACxB,wBAAgB,mBAAmB,CAAC,KAAK,EAAE,SAAS,GAAG,MAAM,GAAG,IAAI,CAQnE;AAED;0BAC0B;AAC1B,wBAAgB,eAAe,CAAC,KAAK,EAAE,SAAS,GAAG,MAAM,CAExD;AAED;;;;;;;GAOG;AACH,wBAAgB,YAAY,CAC1B,WAAW,EAAE,MAAM,EACnB,UAAU,EAAE,MAAM,GAAG,SAAS,EAC9B,YAAY,EAAE,MAAM,GAAG,SAAS,GAC/B,MAAM,GAAG,IAAI,CAMf;AAED;;8DAE8D;AAC9D,wBAAgB,aAAa,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,CAGjD"}
@@ -0,0 +1,83 @@
1
+ /**
2
+ * What a saved token was actually worth, in dollars.
3
+ *
4
+ * `savings.ts` answers "how many input tokens did graft keep out of the
5
+ * context"; this answers "what does an input token cost here". The two are
6
+ * deliberately separate: the token count is arithmetic over file sizes and is
7
+ * true everywhere, while the price depends on which model the session ran and
8
+ * how much of its context was served from cache — facts only the host's
9
+ * transcript knows.
10
+ *
11
+ * Nothing here guesses. There is no default rate and no env override: a model
12
+ * we don't have a price for yields null, and the callers then render the token
13
+ * count alone rather than a dollar figure we made up. A wrong number on the
14
+ * statusline is worse than no number.
15
+ */
16
+ /** Input $/Mtok, list price, per model family. Output tokens are irrelevant —
17
+ * what graft saves is context the agent would otherwise have read IN. */
18
+ const INPUT_USD_PER_MTOK = [
19
+ [/^claude-(fable|mythos)-5/, 10],
20
+ [/^claude-opus-(5|4-[678])/, 5],
21
+ [/^claude-sonnet-5/, 2],
22
+ [/^claude-sonnet-4-6/, 3],
23
+ [/^claude-haiku-4-5/, 1],
24
+ ];
25
+ /** List input price for a model id, or null when we don't know it — a model
26
+ * released after this table was written, or a host reporting something else
27
+ * entirely. Null propagates all the way to "render tokens only". */
28
+ export function inputUsdPerMtok(model) {
29
+ if (typeof model !== 'string')
30
+ return null;
31
+ for (const [pattern, usd] of INPUT_USD_PER_MTOK)
32
+ if (pattern.test(model))
33
+ return usd;
34
+ return null;
35
+ }
36
+ /** Cache-write costs 1.25x list, a cache read a tenth of it. The multipliers are
37
+ * why a measured rate beats an assumed one: a session deep into a long
38
+ * conversation pays nearer $0.50/Mtok than the $5.00 its model lists at. */
39
+ const CACHE_CREATE_MULTIPLIER = 1.25;
40
+ const CACHE_READ_MULTIPLIER = 0.1;
41
+ /** Micro-dollars, so a running total stays an integer and never drifts. */
42
+ const MICROS_PER_USD = 1_000_000;
43
+ /** What this turn's input tokens cost, in micro-dollars, or null on a model we
44
+ * have no price for. */
45
+ export function turnInputCostMicros(usage) {
46
+ const list = inputUsdPerMtok(usage.model);
47
+ if (list === null)
48
+ return null;
49
+ const weighted = usage.input +
50
+ usage.cacheCreate * CACHE_CREATE_MULTIPLIER +
51
+ usage.cacheRead * CACHE_READ_MULTIPLIER;
52
+ return Math.round((weighted * list * MICROS_PER_USD) / 1_000_000);
53
+ }
54
+ /** Every input token this turn was billed for, cached or not — the denominator
55
+ * of the blended rate. */
56
+ export function turnInputTokens(usage) {
57
+ return usage.input + usage.cacheCreate + usage.cacheRead;
58
+ }
59
+ /**
60
+ * Dollars saved, at the rate the session has actually been paying.
61
+ *
62
+ * `costMicros / tokensBilled` is the blended price of one input token here —
63
+ * model and cache-hit ratio already folded in — so this re-blends as the
64
+ * session goes rather than freezing turn one's rate. Returns null when nothing
65
+ * has been sampled yet (turn one, or a host whose hooks name no transcript).
66
+ */
67
+ export function dollarsSaved(savedTokens, costMicros, tokensBilled) {
68
+ if (!costMicros || !tokensBilled || savedTokens <= 0)
69
+ return null;
70
+ const usd = (savedTokens * (costMicros / tokensBilled)) / MICROS_PER_USD;
71
+ // Belt and braces against a non-finite accumulator reaching a rendered
72
+ // surface: "$NaN" on the statusline is worse than no dollar figure at all.
73
+ return Number.isFinite(usd) ? usd : null;
74
+ }
75
+ /** `$1.23`, or `<$0.01` for a real but sub-cent saving. Never `$0.00`: a
76
+ * rounded-to-nothing number reads as "graft saved you nothing", which is a
77
+ * different claim from "graft saved you less than a cent". */
78
+ export function formatDollars(usd) {
79
+ if (usd < 0.01)
80
+ return '<$0.01';
81
+ return `$${usd.toFixed(2)}`;
82
+ }
83
+ //# sourceMappingURL=price.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"price.js","sourceRoot":"","sources":["../../src/context/price.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;GAcG;AAEH;yEACyE;AACzE,MAAM,kBAAkB,GAA6C;IACnE,CAAC,0BAA0B,EAAE,EAAE,CAAC;IAChC,CAAC,0BAA0B,EAAE,CAAC,CAAC;IAC/B,CAAC,kBAAkB,EAAE,CAAC,CAAC;IACvB,CAAC,oBAAoB,EAAE,CAAC,CAAC;IACzB,CAAC,mBAAmB,EAAE,CAAC,CAAC;CACzB,CAAC;AAEF;;oEAEoE;AACpE,MAAM,UAAU,eAAe,CAAC,KAAc;IAC5C,IAAI,OAAO,KAAK,KAAK,QAAQ;QAAE,OAAO,IAAI,CAAC;IAC3C,KAAK,MAAM,CAAC,OAAO,EAAE,GAAG,CAAC,IAAI,kBAAkB;QAAE,IAAI,OAAO,CAAC,IAAI,CAAC,KAAK,CAAC;YAAE,OAAO,GAAG,CAAC;IACrF,OAAO,IAAI,CAAC;AACd,CAAC;AAaD;;4EAE4E;AAC5E,MAAM,uBAAuB,GAAG,IAAI,CAAC;AACrC,MAAM,qBAAqB,GAAG,GAAG,CAAC;AAElC,2EAA2E;AAC3E,MAAM,cAAc,GAAG,SAAS,CAAC;AAEjC;wBACwB;AACxB,MAAM,UAAU,mBAAmB,CAAC,KAAgB;IAClD,MAAM,IAAI,GAAG,eAAe,CAAC,KAAK,CAAC,KAAK,CAAC,CAAC;IAC1C,IAAI,IAAI,KAAK,IAAI;QAAE,OAAO,IAAI,CAAC;IAC/B,MAAM,QAAQ,GACZ,KAAK,CAAC,KAAK;QACX,KAAK,CAAC,WAAW,GAAG,uBAAuB;QAC3C,KAAK,CAAC,SAAS,GAAG,qBAAqB,CAAC;IAC1C,OAAO,IAAI,CAAC,KAAK,CAAC,CAAC,QAAQ,GAAG,IAAI,GAAG,cAAc,CAAC,GAAG,SAAS,CAAC,CAAC;AACpE,CAAC;AAED;0BAC0B;AAC1B,MAAM,UAAU,eAAe,CAAC,KAAgB;IAC9C,OAAO,KAAK,CAAC,KAAK,GAAG,KAAK,CAAC,WAAW,GAAG,KAAK,CAAC,SAAS,CAAC;AAC3D,CAAC;AAED;;;;;;;GAOG;AACH,MAAM,UAAU,YAAY,CAC1B,WAAmB,EACnB,UAA8B,EAC9B,YAAgC;IAEhC,IAAI,CAAC,UAAU,IAAI,CAAC,YAAY,IAAI,WAAW,IAAI,CAAC;QAAE,OAAO,IAAI,CAAC;IAClE,MAAM,GAAG,GAAG,CAAC,WAAW,GAAG,CAAC,UAAU,GAAG,YAAY,CAAC,CAAC,GAAG,cAAc,CAAC;IACzE,uEAAuE;IACvE,2EAA2E;IAC3E,OAAO,MAAM,CAAC,QAAQ,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,IAAI,CAAC;AAC3C,CAAC;AAED;;8DAE8D;AAC9D,MAAM,UAAU,aAAa,CAAC,GAAW;IACvC,IAAI,GAAG,GAAG,IAAI;QAAE,OAAO,QAAQ,CAAC;IAChC,OAAO,IAAI,GAAG,CAAC,OAAO,CAAC,CAAC,CAAC,EAAE,CAAC;AAC9B,CAAC"}
@@ -0,0 +1,67 @@
1
+ /**
2
+ * Shared "tokens saved" estimate for every retrieval-style graft command.
3
+ *
4
+ * The model is always the same: baseline (what you'd have read otherwise, in
5
+ * full) − this output (what graft handed you). The baseline is measured from
6
+ * the `chars` the build stored on each file node, so it costs nothing and is
7
+ * honest about the alternative — opening the files whole. When no file in the
8
+ * baseline has a known size (a pre-`chars` graph), the estimate is omitted
9
+ * rather than faked.
10
+ *
11
+ * `graft ask` keeps its own footer (it carries an escalation nudge and feeds
12
+ * the session saved-token counter); everything else — skeleton, grep, callers,
13
+ * map — routes through {@link savingsFor} + {@link withSavings} here.
14
+ */
15
+ import type { GraphV1 } from '../graph/types.js';
16
+ export interface Savings {
17
+ /** How many source files the baseline covers. */
18
+ files: number;
19
+ /** Total chars of those files — the "read them whole" cost. */
20
+ baselineChars: number;
21
+ }
22
+ /** Rough tokens for a byte length (≈ 4 chars/token; good enough for an estimate). */
23
+ export declare function toTokens(chars: number): number;
24
+ /** Baseline = whole size of the distinct `paths`, summed from file-node sizes.
25
+ * Returns undefined when not a single path has a known size — the caller then
26
+ * omits the estimate instead of claiming a bogus one. */
27
+ export declare function savingsFor(graph: GraphV1, paths: Iterable<string>): Savings | undefined;
28
+ /** Tell this module what an input token costs here. Null clears it, and so does
29
+ * anything that isn't a positive finite number — a NaN from a zero-denominator
30
+ * rate must render as "no dollars known", never as `$NaN` in the agent's face. */
31
+ export declare function setInputRate(usdPerMtok: number | null): void;
32
+ /** Appended to every retrieval footer so the agent reports the turn's running
33
+ * total even when SKILL.md isn't loaded — the instruction rides along in the
34
+ * tool output itself. Deliberately free of the `[graft] tokens saved ≈ <n>`
35
+ * pattern so the PostToolUse accumulator that parses these footers never
36
+ * mistakes the nudge (or its example) for a second number to count.
37
+ *
38
+ * Carries this call's dollar value once a rate has been measured, because the
39
+ * agent has no way to price a token itself — the ask it's given has to contain
40
+ * the number, not just request one. The example phrasing stays inside what
41
+ * `hasSavingsTally` (claude/tally.ts) recognises, so adding money here does not
42
+ * quietly zero the reported-turns metric. */
43
+ export declare function savingsTurnNudge(savedTokens: number): string;
44
+ /** The one-line savings estimate for a command's text output, so the agent gets
45
+ * the number for free — no extra tool call. `body` is the exact rendered output
46
+ * the agent reads (the pack). Returns "" when there's nothing honest to claim:
47
+ * no baseline, or the output isn't actually smaller than reading the files
48
+ * (tiny files, where the pointers cost more than the source). */
49
+ export declare function savingsLine(body: string, saved: Savings | undefined): string;
50
+ /**
51
+ * Sum every `[graft] tokens saved ≈ N` footer in a blob of text — the reader
52
+ * half of {@link savingsLine}, kept next to the writer so the two never drift.
53
+ * A single blob can carry several (an agent that made two graft calls in one
54
+ * turn); the nudge from `savingsTurnNudge` deliberately omits the pattern, so its example
55
+ * text is not miscounted here.
56
+ */
57
+ export declare function sumSavingsFooters(text: string): number;
58
+ /** Render `body` with the savings line on TOP.
59
+ *
60
+ * Deliberately a header, not a footer: agents routinely pipe graft through
61
+ * `head -N` (and hosts truncate long tool output from the end), which silently
62
+ * ate the number and, with it, the PostToolUse accumulator that feeds the
63
+ * statusline's `~N tok saved`. Every clipper keeps the head, so the number
64
+ * survives. Emitted once — a second copy at the bottom would be double-counted
65
+ * by that accumulator's `matchAll`. */
66
+ export declare function withSavings(body: string, saved: Savings | undefined): string;
67
+ //# sourceMappingURL=savings.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"savings.d.ts","sourceRoot":"","sources":["../../src/context/savings.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;GAaG;AACH,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,mBAAmB,CAAC;AAIjD,MAAM,WAAW,OAAO;IACtB,iDAAiD;IACjD,KAAK,EAAE,MAAM,CAAC;IACd,+DAA+D;IAC/D,aAAa,EAAE,MAAM,CAAC;CACvB;AAED,qFAAqF;AACrF,wBAAgB,QAAQ,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM,CAE9C;AAYD;;yDAEyD;AACzD,wBAAgB,UAAU,CAAC,KAAK,EAAE,OAAO,EAAE,KAAK,EAAE,QAAQ,CAAC,MAAM,CAAC,GAAG,OAAO,GAAG,SAAS,CAWvF;AAgBD;;kFAEkF;AAClF,wBAAgB,YAAY,CAAC,UAAU,EAAE,MAAM,GAAG,IAAI,GAAG,IAAI,CAK5D;AAED;;;;;;;;;;6CAU6C;AAC7C,wBAAgB,gBAAgB,CAAC,WAAW,EAAE,MAAM,GAAG,MAAM,CAgB5D;AAED;;;;iEAIiE;AACjE,wBAAgB,WAAW,CAAC,IAAI,EAAE,MAAM,EAAE,KAAK,EAAE,OAAO,GAAG,SAAS,GAAG,MAAM,CAa5E;AAED;;;;;;GAMG;AACH,wBAAgB,iBAAiB,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,CAOtD;AAED;;;;;;;uCAOuC;AACvC,wBAAgB,WAAW,CAAC,IAAI,EAAE,MAAM,EAAE,KAAK,EAAE,OAAO,GAAG,SAAS,GAAG,MAAM,CAG5E"}
@@ -0,0 +1,125 @@
1
+ import { formatDollars } from './price.js';
2
+ import { brand, tag } from "../brand.js";
3
+ /** Rough tokens for a byte length (≈ 4 chars/token; good enough for an estimate). */
4
+ export function toTokens(chars) {
5
+ return Math.round(chars / 4);
6
+ }
7
+ /** path → char size, from the file nodes the build sized. Skips nodes with no
8
+ * `chars` (pre-upgrade graphs), so an old index just yields a smaller baseline
9
+ * rather than a wrong one. */
10
+ function fileSizes(graph) {
11
+ const m = new Map();
12
+ for (const n of graph.nodes)
13
+ if (n.kind === 'file' && typeof n.chars === 'number')
14
+ m.set(n.path, n.chars);
15
+ return m;
16
+ }
17
+ /** Baseline = whole size of the distinct `paths`, summed from file-node sizes.
18
+ * Returns undefined when not a single path has a known size — the caller then
19
+ * omits the estimate instead of claiming a bogus one. */
20
+ export function savingsFor(graph, paths) {
21
+ const sizes = fileSizes(graph);
22
+ let baselineChars = 0;
23
+ let files = 0;
24
+ for (const p of new Set(paths)) {
25
+ const c = sizes.get(p);
26
+ if (c === undefined)
27
+ continue;
28
+ baselineChars += c;
29
+ files++;
30
+ }
31
+ return files > 0 ? { files, baselineChars } : undefined;
32
+ }
33
+ /**
34
+ * The blended input rate this session is paying, in $/Mtok, or null when nobody
35
+ * has measured one.
36
+ *
37
+ * Process-level because it is a process-level fact: one CLI invocation answers
38
+ * one query for one session, and the alternative — threading a rate through
39
+ * `withSavings` and all seven of its callers — would put a billing parameter in
40
+ * the signature of every retrieval formatter for no gain. Set by the CLI's
41
+ * `noteQuery` and by the MCP dispatch, both of which already resolve the repo
42
+ * root; unset everywhere else, which is why every consumer treats null as
43
+ * "report tokens only" rather than as zero.
44
+ */
45
+ let inputRateUsdPerMtok = null;
46
+ /** Tell this module what an input token costs here. Null clears it, and so does
47
+ * anything that isn't a positive finite number — a NaN from a zero-denominator
48
+ * rate must render as "no dollars known", never as `$NaN` in the agent's face. */
49
+ export function setInputRate(usdPerMtok) {
50
+ inputRateUsdPerMtok =
51
+ typeof usdPerMtok === 'number' && Number.isFinite(usdPerMtok) && usdPerMtok > 0
52
+ ? usdPerMtok
53
+ : null;
54
+ }
55
+ /** Appended to every retrieval footer so the agent reports the turn's running
56
+ * total even when SKILL.md isn't loaded — the instruction rides along in the
57
+ * tool output itself. Deliberately free of the `[graft] tokens saved ≈ <n>`
58
+ * pattern so the PostToolUse accumulator that parses these footers never
59
+ * mistakes the nudge (or its example) for a second number to count.
60
+ *
61
+ * Carries this call's dollar value once a rate has been measured, because the
62
+ * agent has no way to price a token itself — the ask it's given has to contain
63
+ * the number, not just request one. The example phrasing stays inside what
64
+ * `hasSavingsTally` (claude/tally.ts) recognises, so adding money here does not
65
+ * quietly zero the reported-turns metric. */
66
+ export function savingsTurnNudge(savedTokens) {
67
+ const b = brand();
68
+ const sum = ` — sum each such line across your ${b} calls — e.g. `;
69
+ if (inputRateUsdPerMtok === null || savedTokens <= 0) {
70
+ return (` At the end of your reply, tell the user the total ${b} tokens saved ` +
71
+ `this turn${sum}"🌱 ${b} saved ~N tokens this turn".`);
72
+ }
73
+ const usd = (savedTokens * inputRateUsdPerMtok) / 1_000_000;
74
+ return (` This call is worth ${formatDollars(usd)} at the rate this session is ` +
75
+ 'actually paying for input tokens. At the end of your reply, tell the user ' +
76
+ `the total ${brand()} tokens saved this turn and what they were worth${sum}` +
77
+ `"🌱 ${brand()} saved ~N tokens (~$X) this turn".`);
78
+ }
79
+ /** The one-line savings estimate for a command's text output, so the agent gets
80
+ * the number for free — no extra tool call. `body` is the exact rendered output
81
+ * the agent reads (the pack). Returns "" when there's nothing honest to claim:
82
+ * no baseline, or the output isn't actually smaller than reading the files
83
+ * (tiny files, where the pointers cost more than the source). */
84
+ export function savingsLine(body, saved) {
85
+ if (!saved || saved.baselineChars <= 0)
86
+ return '';
87
+ const pack = toTokens(body.length);
88
+ const base = toTokens(saved.baselineChars);
89
+ if (base <= pack)
90
+ return '';
91
+ const delta = base - pack;
92
+ const pct = Math.round((delta / base) * 100);
93
+ return (`${tag()} tokens saved ≈ ${delta.toLocaleString()} (${pct}%) — this output ≈ ` +
94
+ `${pack.toLocaleString()} tok vs reading the ${saved.files} file(s) it covers whole ≈ ` +
95
+ `${base.toLocaleString()} tok (estimate).` +
96
+ savingsTurnNudge(delta));
97
+ }
98
+ /**
99
+ * Sum every `[graft] tokens saved ≈ N` footer in a blob of text — the reader
100
+ * half of {@link savingsLine}, kept next to the writer so the two never drift.
101
+ * A single blob can carry several (an agent that made two graft calls in one
102
+ * turn); the nudge from `savingsTurnNudge` deliberately omits the pattern, so its example
103
+ * text is not miscounted here.
104
+ */
105
+ export function sumSavingsFooters(text) {
106
+ let total = 0;
107
+ // The code a query saved reading, and the digging a reused learning saved.
108
+ for (const m of text.matchAll(/\[(?:graft|trail)\] (?:tokens|learnings) saved ≈ ([\d,]+)/g)) {
109
+ total += Number(m[1].replace(/,/g, '')) || 0;
110
+ }
111
+ return total;
112
+ }
113
+ /** Render `body` with the savings line on TOP.
114
+ *
115
+ * Deliberately a header, not a footer: agents routinely pipe graft through
116
+ * `head -N` (and hosts truncate long tool output from the end), which silently
117
+ * ate the number and, with it, the PostToolUse accumulator that feeds the
118
+ * statusline's `~N tok saved`. Every clipper keeps the head, so the number
119
+ * survives. Emitted once — a second copy at the bottom would be double-counted
120
+ * by that accumulator's `matchAll`. */
121
+ export function withSavings(body, saved) {
122
+ const line = savingsLine(body, saved);
123
+ return line ? `${line}\n\n${body}` : body;
124
+ }
125
+ //# sourceMappingURL=savings.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"savings.js","sourceRoot":"","sources":["../../src/context/savings.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,85 @@
1
+ /**
2
+ * The Context Graph Engine.
3
+ *
4
+ * Two operations, no database:
5
+ * - {@link Graft.init} build `.context/` from a code repo.
6
+ * - {@link Graft.check} report whether `.context/` is still in
7
+ * sync with the code (for CI).
8
+ *
9
+ * The graph is a folder of linked markdown files committed to the repo; git is
10
+ * the sync. This class wires the configured LLM provider into the build/check
11
+ * pipelines; an API key is required for any LLM-backed operation.
12
+ */
13
+ import { type EngineConfig } from "./ai/providers.js";
14
+ import { CODE_EXTENSIONS, type BuildProgress, type BuildResult } from "./context/build.js";
15
+ import { type CheckResult } from "./context/check.js";
16
+ import { type GraphBuildOptions, type GraphBuildResult } from "./graph/build.js";
17
+ import { type GraphCheckResult } from "./graph/check.js";
18
+ import { type AskResult } from "./ask/ask.js";
19
+ export { CODE_EXTENSIONS };
20
+ export type { BuildResult, BuildProgress, CheckResult, GraphBuildResult, GraphCheckResult, AskResult };
21
+ export interface InitOptions {
22
+ /** Code extensions to include. Default: {@link CODE_EXTENSIONS}. */
23
+ extensions?: string[];
24
+ /** Repo-relative directory prefixes to limit the concept pass (`--only-dir`). */
25
+ onlyDirs?: string[];
26
+ /** Max concept synthesis batches in flight at once. Default 4. */
27
+ synthConcurrency?: number;
28
+ /** Progress callback for long builds. */
29
+ onProgress?: (info: BuildProgress) => void;
30
+ }
31
+ export interface CheckRunOptions {
32
+ extensions?: string[];
33
+ }
34
+ export interface GraphRunOptions {
35
+ /** Run the Tier-2 LLM meaning pass (summary + crux). Absent → Tier-1 only. */
36
+ llm?: boolean;
37
+ /** Max files summarized in parallel during the LLM pass. */
38
+ concurrency?: number;
39
+ /** Replay unchanged files from the extraction cache (default true). */
40
+ reuse?: boolean;
41
+ /** Opt-in compiler-grade LSP edge enrichment (`graft build --lsp`). */
42
+ lsp?: boolean;
43
+ /** Repo-relative directory prefixes to limit the build to (`--only-dir`). */
44
+ onlyDirs?: string[];
45
+ onProgress?: GraphBuildOptions["onProgress"];
46
+ }
47
+ export declare class Graft {
48
+ private cfg;
49
+ constructor(config?: EngineConfig);
50
+ /** Build the `.context/` graph from the repo at `dir`. */
51
+ init(dir: string, opts?: InitOptions): Promise<BuildResult>;
52
+ /** Report whether the committed `.context/` markdown graph is in sync with the code. */
53
+ check(dir: string, opts?: CheckRunOptions): CheckResult;
54
+ /** Report whether the committed `graph.json` is in sync with the code (Tier-1 diff).
55
+ * Async because the breadth tier warms WASM grammars before re-extraction. */
56
+ checkGraph(dir: string): Promise<GraphCheckResult>;
57
+ /**
58
+ * Build `.context/graph.json` — a per-symbol code graph from tree-sitter.
59
+ * Tier-1 (structure) always runs; the Tier-2 meaning layer runs only when
60
+ * `opts.llm` is set. Either way the prior meaning layer is preserved.
61
+ */
62
+ graph(dir: string, opts?: GraphRunOptions): Promise<GraphBuildResult>;
63
+ /**
64
+ * Answer a plain-words query from the committed `graft/` graph — the active
65
+ * channel. Deterministic and $0: routes structural queries to the wiring
66
+ * edges and everything else to a lexical rank over concepts + symbols.
67
+ */
68
+ ask(dir: string, query: string, opts?: {
69
+ limit?: number;
70
+ source?: boolean;
71
+ full?: boolean;
72
+ in?: string;
73
+ graphRank?: boolean;
74
+ }): AskResult;
75
+ private _chatModel?;
76
+ /** The configured transport, or a clear error telling the user how to set a key. */
77
+ private chatModel;
78
+ private synthesizer;
79
+ /** Per-node crux summarizer for the code graph's Tier-2 pass. */
80
+ private cruxSummarizer;
81
+ private summarizer;
82
+ /** Human label for the active model, recorded in the manifest. */
83
+ private modelLabel;
84
+ }
85
+ //# sourceMappingURL=engine.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"engine.d.ts","sourceRoot":"","sources":["../src/engine.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;GAWG;AACH,OAAO,EAAiB,KAAK,YAAY,EAAuB,MAAM,mBAAmB,CAAC;AAM1F,OAAO,EAAgB,eAAe,EAAE,KAAK,aAAa,EAAE,KAAK,WAAW,EAAE,MAAM,oBAAoB,CAAC;AACzG,OAAO,EAAgB,KAAK,WAAW,EAAE,MAAM,oBAAoB,CAAC;AACpE,OAAO,EAAc,KAAK,iBAAiB,EAAE,KAAK,gBAAgB,EAAE,MAAM,kBAAkB,CAAC;AAC7F,OAAO,EAAc,KAAK,gBAAgB,EAAE,MAAM,kBAAkB,CAAC;AACrE,OAAO,EAAO,KAAK,SAAS,EAAE,MAAM,cAAc,CAAC;AAGnD,OAAO,EAAE,eAAe,EAAE,CAAC;AAC3B,YAAY,EAAE,WAAW,EAAE,aAAa,EAAE,WAAW,EAAE,gBAAgB,EAAE,gBAAgB,EAAE,SAAS,EAAE,CAAC;AAEvG,MAAM,WAAW,WAAW;IAC1B,oEAAoE;IACpE,UAAU,CAAC,EAAE,MAAM,EAAE,CAAC;IACtB,iFAAiF;IACjF,QAAQ,CAAC,EAAE,MAAM,EAAE,CAAC;IACpB,kEAAkE;IAClE,gBAAgB,CAAC,EAAE,MAAM,CAAC;IAC1B,yCAAyC;IACzC,UAAU,CAAC,EAAE,CAAC,IAAI,EAAE,aAAa,KAAK,IAAI,CAAC;CAC5C;AAED,MAAM,WAAW,eAAe;IAC9B,UAAU,CAAC,EAAE,MAAM,EAAE,CAAC;CACvB;AAED,MAAM,WAAW,eAAe;IAC9B,8EAA8E;IAC9E,GAAG,CAAC,EAAE,OAAO,CAAC;IACd,4DAA4D;IAC5D,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,uEAAuE;IACvE,KAAK,CAAC,EAAE,OAAO,CAAC;IAChB,uEAAuE;IACvE,GAAG,CAAC,EAAE,OAAO,CAAC;IACd,6EAA6E;IAC7E,QAAQ,CAAC,EAAE,MAAM,EAAE,CAAC;IACpB,UAAU,CAAC,EAAE,iBAAiB,CAAC,YAAY,CAAC,CAAC;CAC9C;AAED,qBAAa,KAAK;IAChB,OAAO,CAAC,GAAG,CAAiB;gBAEhB,MAAM,GAAE,YAAiB;IAIrC,0DAA0D;IACpD,IAAI,CAAC,GAAG,EAAE,MAAM,EAAE,IAAI,GAAE,WAAgB,GAAG,OAAO,CAAC,WAAW,CAAC;IAarE,wFAAwF;IACxF,KAAK,CAAC,GAAG,EAAE,MAAM,EAAE,IAAI,GAAE,eAAoB,GAAG,WAAW;IAI3D;kFAC8E;IAC9E,UAAU,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,gBAAgB,CAAC;IAIlD;;;;OAIG;IACH,KAAK,CAAC,GAAG,EAAE,MAAM,EAAE,IAAI,GAAE,eAAoB,GAAG,OAAO,CAAC,gBAAgB,CAAC;IAYzE;;;;OAIG;IACH,GAAG,CAAC,GAAG,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,EAAE,IAAI,GAAE;QAAE,KAAK,CAAC,EAAE,MAAM,CAAC;QAAC,MAAM,CAAC,EAAE,OAAO,CAAC;QAAC,IAAI,CAAC,EAAE,OAAO,CAAC;QAAC,EAAE,CAAC,EAAE,MAAM,CAAC;QAAC,SAAS,CAAC,EAAE,OAAO,CAAA;KAAO,GAAG,SAAS;IAY7I,OAAO,CAAC,UAAU,CAAC,CAAY;IAE/B,oFAAoF;IACpF,OAAO,CAAC,SAAS;IAmBjB,OAAO,CAAC,WAAW;IAInB,iEAAiE;IACjE,OAAO,CAAC,cAAc;IAItB,OAAO,CAAC,UAAU;IAIlB,kEAAkE;IAClE,OAAO,CAAC,UAAU;CAKnB"}
package/dist/engine.js ADDED
@@ -0,0 +1,122 @@
1
+ /**
2
+ * The Context Graph Engine.
3
+ *
4
+ * Two operations, no database:
5
+ * - {@link Graft.init} build `.context/` from a code repo.
6
+ * - {@link Graft.check} report whether `.context/` is still in
7
+ * sync with the code (for CI).
8
+ *
9
+ * The graph is a folder of linked markdown files committed to the repo; git is
10
+ * the sync. This class wires the configured LLM provider into the build/check
11
+ * pipelines; an API key is required for any LLM-backed operation.
12
+ */
13
+ import { resolveConfig } from "./ai/providers.js";
14
+ import { ChatSynthesizer } from "./ai/synthesize.js";
15
+ import { ChatSummarizer } from "./ai/summarize.js";
16
+ import { ChatCruxSummarizer } from "./ai/crux.js";
17
+ import { createChatModel } from "./ai/llm/factory.js";
18
+ import { buildContext, CODE_EXTENSIONS } from "./context/build.js";
19
+ import { checkContext } from "./context/check.js";
20
+ import { buildGraph } from "./graph/build.js";
21
+ import { checkGraph } from "./graph/check.js";
22
+ import { ask } from "./ask/ask.js";
23
+ export { CODE_EXTENSIONS };
24
+ export class Graft {
25
+ cfg;
26
+ constructor(config = {}) {
27
+ this.cfg = resolveConfig(config);
28
+ }
29
+ /** Build the `.context/` graph from the repo at `dir`. */
30
+ async init(dir, opts = {}) {
31
+ return buildContext(dir, {
32
+ contextDir: this.cfg.contextDir,
33
+ extensions: opts.extensions,
34
+ onlyDirs: opts.onlyDirs,
35
+ synthConcurrency: opts.synthConcurrency,
36
+ model: this.modelLabel(),
37
+ summarizer: this.summarizer(),
38
+ synthesizer: this.synthesizer(),
39
+ onProgress: opts.onProgress,
40
+ });
41
+ }
42
+ /** Report whether the committed `.context/` markdown graph is in sync with the code. */
43
+ check(dir, opts = {}) {
44
+ return checkContext(dir, { contextDir: this.cfg.contextDir, extensions: opts.extensions });
45
+ }
46
+ /** Report whether the committed `graph.json` is in sync with the code (Tier-1 diff).
47
+ * Async because the breadth tier warms WASM grammars before re-extraction. */
48
+ checkGraph(dir) {
49
+ return checkGraph(dir, { contextDir: this.cfg.contextDir });
50
+ }
51
+ /**
52
+ * Build `.context/graph.json` — a per-symbol code graph from tree-sitter.
53
+ * Tier-1 (structure) always runs; the Tier-2 meaning layer runs only when
54
+ * `opts.llm` is set. Either way the prior meaning layer is preserved.
55
+ */
56
+ graph(dir, opts = {}) {
57
+ return buildGraph(dir, {
58
+ contextDir: this.cfg.contextDir,
59
+ summarizer: opts.llm ? this.cruxSummarizer() : undefined,
60
+ concurrency: opts.concurrency,
61
+ reuse: opts.reuse,
62
+ lsp: opts.lsp,
63
+ onlyDirs: opts.onlyDirs,
64
+ onProgress: opts.onProgress,
65
+ });
66
+ }
67
+ /**
68
+ * Answer a plain-words query from the committed `graft/` graph — the active
69
+ * channel. Deterministic and $0: routes structural queries to the wiring
70
+ * edges and everything else to a lexical rank over concepts + symbols.
71
+ */
72
+ ask(dir, query, opts = {}) {
73
+ const r = ask(dir, query, {
74
+ contextDir: this.cfg.contextDir,
75
+ limit: opts.limit,
76
+ source: opts.source,
77
+ full: opts.full,
78
+ in: opts.in,
79
+ graphRank: opts.graphRank,
80
+ });
81
+ return r;
82
+ }
83
+ _chatModel;
84
+ /** The configured transport, or a clear error telling the user how to set a key. */
85
+ chatModel() {
86
+ if (this.cfg.chatModel)
87
+ return this.cfg.chatModel;
88
+ if (this._chatModel)
89
+ return this._chatModel;
90
+ if (!this.cfg.apiKey) {
91
+ throw new Error("No API key. Set GRAFT_API_KEY (and GRAFT_PROVIDER / GRAFT_BASE_URL / GRAFT_MODEL " +
92
+ "for your provider) to build or summarize the graph.");
93
+ }
94
+ this._chatModel = createChatModel({
95
+ provider: this.cfg.provider,
96
+ apiKey: this.cfg.apiKey,
97
+ model: this.cfg.model,
98
+ baseUrl: this.cfg.baseUrl,
99
+ headers: this.cfg.headers,
100
+ });
101
+ return this._chatModel;
102
+ }
103
+ synthesizer() {
104
+ return this.cfg.synthesizer ?? new ChatSynthesizer(this.chatModel());
105
+ }
106
+ /** Per-node crux summarizer for the code graph's Tier-2 pass. */
107
+ cruxSummarizer() {
108
+ return this.cfg.cruxSummarizer ?? new ChatCruxSummarizer(this.chatModel());
109
+ }
110
+ summarizer() {
111
+ return this.cfg.summarizer ?? new ChatSummarizer(this.chatModel());
112
+ }
113
+ /** Human label for the active model, recorded in the manifest. */
114
+ modelLabel() {
115
+ if (this.cfg.chatModel)
116
+ return this.cfg.chatModel.label;
117
+ if (this.cfg.synthesizer || this.cfg.summarizer || this.cfg.cruxSummarizer)
118
+ return "custom";
119
+ return `${this.cfg.provider}:${this.cfg.model}`;
120
+ }
121
+ }
122
+ //# sourceMappingURL=engine.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"engine.js","sourceRoot":"","sources":["../src/engine.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,64 @@
1
+ /**
2
+ * Receiver-type binding pass: a pre-order walk over a parsed file that answers,
3
+ * for every local variable / parameter / class field / `self`|`this` attribute,
4
+ * "what type is this?" — so a later member-call site (`app.include_router()`)
5
+ * can look up `app`'s bound type instead of resolving on the bare method name
6
+ * alone. Pure and dependency-only: no LLM, no network, no mutation of the AST.
7
+ *
8
+ * Only `import type` from extract.ts (never a value) — extract.ts imports
9
+ * `collectBindings` from here, so a value import back would be a cycle.
10
+ */
11
+ import type { SyntaxNode } from "./depth-parser.js";
12
+ import type { Language, WalkCtx } from "./extract.js";
13
+ /** Variable/field → bare type name, keyed by scope. Scope keys mirror
14
+ * extract.ts's own scope stack (`scope.join(".")`, `""` at module level) so a
15
+ * lookup from extract.ts's walk finds exactly what was bound in the same
16
+ * lexical position. */
17
+ export declare class FileBindings {
18
+ private map;
19
+ set(scopePath: string, name: string, type: string): void;
20
+ /** Innermost-first: for scope ["a","b"] name "x", tries `a.b|x`, `a|x`, `|x`. */
21
+ lookup(scope: string[], name: string): string | null;
22
+ }
23
+ /** Definition-node types that push a new scope segment, mirroring extract.ts's
24
+ * `describe()` closely enough to keep the two scope stacks in lockstep — but
25
+ * duplicated here (not imported) to keep bindings.ts free of a value import on
26
+ * extract.ts. Returns the def's scope segment (bare name, except a Go method
27
+ * which is receiver-qualified — `Receiver.method` — exactly like extract.ts's
28
+ * `idName`, so a binding recorded inside a Go method body is stored under the
29
+ * same scope key extract.ts's walk will look it up with), or null if `node`
30
+ * isn't a definition. */
31
+ export declare function defName(node: SyntaxNode, lang: Language): string | null;
32
+ /**
33
+ * The bare name a `binary_operator` (left-assign) or `function_definition`
34
+ * (right-assign) node defines, for R's two plain-function assignment shapes —
35
+ * this file's own `defName` uses it directly. extract.ts's `describeR`
36
+ * duplicates the same op-filtering check rather than importing this (same
37
+ * reasoning as the Go receiver helpers below: bindings.ts can't take a value
38
+ * import back on extract.ts), and additionally needs to distinguish an S3
39
+ * `generic.Class` method and R6/S4 class/method shapes this function doesn't
40
+ * know about — bindings.ts has no equivalent need since no `handleR` binding
41
+ * collector exists yet (R6/S4/S3 don't get a member/receiver-type table in
42
+ * this pass; `self`/`private` resolve directly via `ctx.enclosingClass`
43
+ * instead, needing no lookup). See `describeR`'s doc comment for why
44
+ * right-assign's AST shape needs its own branch rather than mirroring
45
+ * left-assign's (empirically, not assumed — `->`'s low precedence means it's
46
+ * absorbed into the function's own `body` field, not an outer wrapper).
47
+ * Null if `node` isn't one of these two shapes.
48
+ */
49
+ export declare function rDefName(node: SyntaxNode): string | null;
50
+ /** The receiver parameter's own variable name for a Go method (`func (w *Worker) …`
51
+ * → `w`). Null if it can't be read. */
52
+ export declare function goReceiverVarOf(node: SyntaxNode): string | null;
53
+ /** Resolves a call site's receiver text (from `calleeName`) to a bound type
54
+ * name, given the enclosing walk state. `self`/`cls`/`this`/the Go receiver
55
+ * var resolve directly to the enclosing class; `super` — R6's `super$` and
56
+ * Swift's `super.` alike — resolves to the PARENT class instead
57
+ * (`ctx.rSuperClass`, not `ctx.enclosingClass` — a super call must climb past
58
+ * the current class's own same-named override, not find it); anything else is
59
+ * a bindings-map lookup, normalizing `this.` to `self.` since both are stored
60
+ * the same way. */
61
+ export declare function resolveRecvType(receiver: string | undefined, ctx: Pick<WalkCtx, "scope" | "enclosingClass" | "goReceiverVar" | "lang" | "bindings" | "rSuperClass">): string | undefined;
62
+ /** Pass 1 over a parsed file: collect variable->type bindings. Pure. */
63
+ export declare function collectBindings(root: SyntaxNode, lang: Language): FileBindings;
64
+ //# sourceMappingURL=bindings.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"bindings.d.ts","sourceRoot":"","sources":["../../src/graph/bindings.ts"],"names":[],"mappings":"AAAA;;;;;;;;;GASG;AACH,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,mBAAmB,CAAC;AACpD,OAAO,KAAK,EAAE,QAAQ,EAAE,OAAO,EAAE,MAAM,cAAc,CAAC;AAEtD;;;uBAGuB;AACvB,qBAAa,YAAY;IACvB,OAAO,CAAC,GAAG,CAA6B;IAExC,GAAG,CAAC,SAAS,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,GAAG,IAAI;IAIxD,iFAAiF;IACjF,MAAM,CAAC,KAAK,EAAE,MAAM,EAAE,EAAE,IAAI,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI;CAOrD;AAID;;;;;;;yBAOyB;AACzB,wBAAgB,OAAO,CAAC,IAAI,EAAE,UAAU,EAAE,IAAI,EAAE,QAAQ,GAAG,MAAM,GAAG,IAAI,CAsDvE;AAqCD;;;;;;;;;;;;;;;;GAgBG;AACH,wBAAgB,QAAQ,CAAC,IAAI,EAAE,UAAU,GAAG,MAAM,GAAG,IAAI,CAiBxD;AAED;uCACuC;AACvC,wBAAgB,eAAe,CAAC,IAAI,EAAE,UAAU,GAAG,MAAM,GAAG,IAAI,CAI/D;AAcD;;;;;;;mBAOmB;AACnB,wBAAgB,eAAe,CAC7B,QAAQ,EAAE,MAAM,GAAG,SAAS,EAC5B,GAAG,EAAE,IAAI,CAAC,OAAO,EAAE,OAAO,GAAG,gBAAgB,GAAG,eAAe,GAAG,MAAM,GAAG,UAAU,GAAG,aAAa,CAAC,GACrG,MAAM,GAAG,SAAS,CAuBpB;AAqCD,wEAAwE;AACxE,wBAAgB,eAAe,CAAC,IAAI,EAAE,UAAU,EAAE,IAAI,EAAE,QAAQ,GAAG,YAAY,CAM9E"}