@specship/specship 0.11.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 (879) hide show
  1. package/.claude-plugin/plugin.json +6 -0
  2. package/LICENSE +21 -0
  3. package/README.md +583 -0
  4. package/agents/specship-explorer.md +29 -0
  5. package/commands/ss-behaviour.md +116 -0
  6. package/commands/ss-check.md +43 -0
  7. package/commands/ss-design-implement.md +84 -0
  8. package/commands/ss-design-loop.md +125 -0
  9. package/commands/ss-explore.md +43 -0
  10. package/commands/ss-spec.md +118 -0
  11. package/dist/activation/starter-prompt.d.ts +57 -0
  12. package/dist/activation/starter-prompt.d.ts.map +1 -0
  13. package/dist/activation/starter-prompt.js +164 -0
  14. package/dist/activation/starter-prompt.js.map +1 -0
  15. package/dist/analytics/specship-impact.d.ts +72 -0
  16. package/dist/analytics/specship-impact.d.ts.map +1 -0
  17. package/dist/analytics/specship-impact.js +216 -0
  18. package/dist/analytics/specship-impact.js.map +1 -0
  19. package/dist/behaviour/behaviour-surface.d.ts +59 -0
  20. package/dist/behaviour/behaviour-surface.d.ts.map +1 -0
  21. package/dist/behaviour/behaviour-surface.js +112 -0
  22. package/dist/behaviour/behaviour-surface.js.map +1 -0
  23. package/dist/bin/node-version-check.d.ts +37 -0
  24. package/dist/bin/node-version-check.d.ts.map +1 -0
  25. package/dist/bin/node-version-check.js +79 -0
  26. package/dist/bin/node-version-check.js.map +1 -0
  27. package/dist/bin/specship.d.ts +25 -0
  28. package/dist/bin/specship.d.ts.map +1 -0
  29. package/dist/bin/specship.js +2823 -0
  30. package/dist/bin/specship.js.map +1 -0
  31. package/dist/bin/uninstall.d.ts +13 -0
  32. package/dist/bin/uninstall.d.ts.map +1 -0
  33. package/dist/bin/uninstall.js +35 -0
  34. package/dist/bin/uninstall.js.map +1 -0
  35. package/dist/context/formatter.d.ts +30 -0
  36. package/dist/context/formatter.d.ts.map +1 -0
  37. package/dist/context/formatter.js +263 -0
  38. package/dist/context/formatter.js.map +1 -0
  39. package/dist/context/index.d.ts +119 -0
  40. package/dist/context/index.d.ts.map +1 -0
  41. package/dist/context/index.js +1289 -0
  42. package/dist/context/index.js.map +1 -0
  43. package/dist/context/markers.d.ts +19 -0
  44. package/dist/context/markers.d.ts.map +1 -0
  45. package/dist/context/markers.js +22 -0
  46. package/dist/context/markers.js.map +1 -0
  47. package/dist/db/index.d.ts +103 -0
  48. package/dist/db/index.d.ts.map +1 -0
  49. package/dist/db/index.js +279 -0
  50. package/dist/db/index.js.map +1 -0
  51. package/dist/db/migrations.d.ts +44 -0
  52. package/dist/db/migrations.d.ts.map +1 -0
  53. package/dist/db/migrations.js +503 -0
  54. package/dist/db/migrations.js.map +1 -0
  55. package/dist/db/queries.d.ts +357 -0
  56. package/dist/db/queries.d.ts.map +1 -0
  57. package/dist/db/queries.js +1504 -0
  58. package/dist/db/queries.js.map +1 -0
  59. package/dist/db/schema.sql +451 -0
  60. package/dist/db/spec-queries.d.ts +130 -0
  61. package/dist/db/spec-queries.d.ts.map +1 -0
  62. package/dist/db/spec-queries.js +738 -0
  63. package/dist/db/spec-queries.js.map +1 -0
  64. package/dist/db/sqlite-adapter.d.ts +65 -0
  65. package/dist/db/sqlite-adapter.d.ts.map +1 -0
  66. package/dist/db/sqlite-adapter.js +214 -0
  67. package/dist/db/sqlite-adapter.js.map +1 -0
  68. package/dist/designer/artifact-store.js +54 -0
  69. package/dist/designer/browser.js +141 -0
  70. package/dist/designer/cdp-ensure.js +60 -0
  71. package/dist/designer/cdp-env.js +18 -0
  72. package/dist/designer/cdp-trace.js +599 -0
  73. package/dist/designer/cross-platform.js +74 -0
  74. package/dist/designer/designer-controller.js +1413 -0
  75. package/dist/designer/file-panel.js +39 -0
  76. package/dist/designer/interstitials.js +97 -0
  77. package/dist/designer/oopif-reader.js +176 -0
  78. package/dist/designer/package-meta.js +18 -0
  79. package/dist/designer/preview-host.js +50 -0
  80. package/dist/designer/repo-root.js +31 -0
  81. package/dist/designer/run-state.js +353 -0
  82. package/dist/designer/session-store.js +59 -0
  83. package/dist/designer/ui-anchors.js +651 -0
  84. package/dist/directory.d.ts +67 -0
  85. package/dist/directory.d.ts.map +1 -0
  86. package/dist/directory.js +267 -0
  87. package/dist/directory.js.map +1 -0
  88. package/dist/enforce/enforce.d.ts +70 -0
  89. package/dist/enforce/enforce.d.ts.map +1 -0
  90. package/dist/enforce/enforce.js +125 -0
  91. package/dist/enforce/enforce.js.map +1 -0
  92. package/dist/errors.d.ts +136 -0
  93. package/dist/errors.d.ts.map +1 -0
  94. package/dist/errors.js +219 -0
  95. package/dist/errors.js.map +1 -0
  96. package/dist/extraction/dfm-extractor.d.ts +31 -0
  97. package/dist/extraction/dfm-extractor.d.ts.map +1 -0
  98. package/dist/extraction/dfm-extractor.js +151 -0
  99. package/dist/extraction/dfm-extractor.js.map +1 -0
  100. package/dist/extraction/generated-detection.d.ts +30 -0
  101. package/dist/extraction/generated-detection.d.ts.map +1 -0
  102. package/dist/extraction/generated-detection.js +80 -0
  103. package/dist/extraction/generated-detection.js.map +1 -0
  104. package/dist/extraction/grammars.d.ts +100 -0
  105. package/dist/extraction/grammars.d.ts.map +1 -0
  106. package/dist/extraction/grammars.js +426 -0
  107. package/dist/extraction/grammars.js.map +1 -0
  108. package/dist/extraction/index.d.ts +138 -0
  109. package/dist/extraction/index.d.ts.map +1 -0
  110. package/dist/extraction/index.js +1394 -0
  111. package/dist/extraction/index.js.map +1 -0
  112. package/dist/extraction/languages/c-cpp.d.ts +4 -0
  113. package/dist/extraction/languages/c-cpp.d.ts.map +1 -0
  114. package/dist/extraction/languages/c-cpp.js +171 -0
  115. package/dist/extraction/languages/c-cpp.js.map +1 -0
  116. package/dist/extraction/languages/csharp.d.ts +3 -0
  117. package/dist/extraction/languages/csharp.d.ts.map +1 -0
  118. package/dist/extraction/languages/csharp.js +73 -0
  119. package/dist/extraction/languages/csharp.js.map +1 -0
  120. package/dist/extraction/languages/dart.d.ts +3 -0
  121. package/dist/extraction/languages/dart.d.ts.map +1 -0
  122. package/dist/extraction/languages/dart.js +192 -0
  123. package/dist/extraction/languages/dart.js.map +1 -0
  124. package/dist/extraction/languages/go.d.ts +3 -0
  125. package/dist/extraction/languages/go.d.ts.map +1 -0
  126. package/dist/extraction/languages/go.js +74 -0
  127. package/dist/extraction/languages/go.js.map +1 -0
  128. package/dist/extraction/languages/index.d.ts +10 -0
  129. package/dist/extraction/languages/index.d.ts.map +1 -0
  130. package/dist/extraction/languages/index.js +51 -0
  131. package/dist/extraction/languages/index.js.map +1 -0
  132. package/dist/extraction/languages/java.d.ts +3 -0
  133. package/dist/extraction/languages/java.d.ts.map +1 -0
  134. package/dist/extraction/languages/java.js +70 -0
  135. package/dist/extraction/languages/java.js.map +1 -0
  136. package/dist/extraction/languages/javascript.d.ts +3 -0
  137. package/dist/extraction/languages/javascript.d.ts.map +1 -0
  138. package/dist/extraction/languages/javascript.js +90 -0
  139. package/dist/extraction/languages/javascript.js.map +1 -0
  140. package/dist/extraction/languages/kotlin.d.ts +3 -0
  141. package/dist/extraction/languages/kotlin.d.ts.map +1 -0
  142. package/dist/extraction/languages/kotlin.js +259 -0
  143. package/dist/extraction/languages/kotlin.js.map +1 -0
  144. package/dist/extraction/languages/lua.d.ts +3 -0
  145. package/dist/extraction/languages/lua.d.ts.map +1 -0
  146. package/dist/extraction/languages/lua.js +150 -0
  147. package/dist/extraction/languages/lua.js.map +1 -0
  148. package/dist/extraction/languages/luau.d.ts +3 -0
  149. package/dist/extraction/languages/luau.d.ts.map +1 -0
  150. package/dist/extraction/languages/luau.js +37 -0
  151. package/dist/extraction/languages/luau.js.map +1 -0
  152. package/dist/extraction/languages/objc.d.ts +3 -0
  153. package/dist/extraction/languages/objc.d.ts.map +1 -0
  154. package/dist/extraction/languages/objc.js +133 -0
  155. package/dist/extraction/languages/objc.js.map +1 -0
  156. package/dist/extraction/languages/pascal.d.ts +3 -0
  157. package/dist/extraction/languages/pascal.d.ts.map +1 -0
  158. package/dist/extraction/languages/pascal.js +66 -0
  159. package/dist/extraction/languages/pascal.js.map +1 -0
  160. package/dist/extraction/languages/php.d.ts +3 -0
  161. package/dist/extraction/languages/php.d.ts.map +1 -0
  162. package/dist/extraction/languages/php.js +107 -0
  163. package/dist/extraction/languages/php.js.map +1 -0
  164. package/dist/extraction/languages/python.d.ts +3 -0
  165. package/dist/extraction/languages/python.d.ts.map +1 -0
  166. package/dist/extraction/languages/python.js +56 -0
  167. package/dist/extraction/languages/python.js.map +1 -0
  168. package/dist/extraction/languages/ruby.d.ts +3 -0
  169. package/dist/extraction/languages/ruby.d.ts.map +1 -0
  170. package/dist/extraction/languages/ruby.js +114 -0
  171. package/dist/extraction/languages/ruby.js.map +1 -0
  172. package/dist/extraction/languages/rust.d.ts +3 -0
  173. package/dist/extraction/languages/rust.d.ts.map +1 -0
  174. package/dist/extraction/languages/rust.js +109 -0
  175. package/dist/extraction/languages/rust.js.map +1 -0
  176. package/dist/extraction/languages/scala.d.ts +3 -0
  177. package/dist/extraction/languages/scala.d.ts.map +1 -0
  178. package/dist/extraction/languages/scala.js +139 -0
  179. package/dist/extraction/languages/scala.js.map +1 -0
  180. package/dist/extraction/languages/swift.d.ts +3 -0
  181. package/dist/extraction/languages/swift.d.ts.map +1 -0
  182. package/dist/extraction/languages/swift.js +91 -0
  183. package/dist/extraction/languages/swift.js.map +1 -0
  184. package/dist/extraction/languages/typescript.d.ts +3 -0
  185. package/dist/extraction/languages/typescript.d.ts.map +1 -0
  186. package/dist/extraction/languages/typescript.js +129 -0
  187. package/dist/extraction/languages/typescript.js.map +1 -0
  188. package/dist/extraction/liquid-extractor.d.ts +52 -0
  189. package/dist/extraction/liquid-extractor.d.ts.map +1 -0
  190. package/dist/extraction/liquid-extractor.js +313 -0
  191. package/dist/extraction/liquid-extractor.js.map +1 -0
  192. package/dist/extraction/mybatis-extractor.d.ts +48 -0
  193. package/dist/extraction/mybatis-extractor.d.ts.map +1 -0
  194. package/dist/extraction/mybatis-extractor.js +198 -0
  195. package/dist/extraction/mybatis-extractor.js.map +1 -0
  196. package/dist/extraction/parse-worker.d.ts +8 -0
  197. package/dist/extraction/parse-worker.d.ts.map +1 -0
  198. package/dist/extraction/parse-worker.js +94 -0
  199. package/dist/extraction/parse-worker.js.map +1 -0
  200. package/dist/extraction/specs/markdown-spec-extractor.d.ts +114 -0
  201. package/dist/extraction/specs/markdown-spec-extractor.d.ts.map +1 -0
  202. package/dist/extraction/specs/markdown-spec-extractor.js +699 -0
  203. package/dist/extraction/specs/markdown-spec-extractor.js.map +1 -0
  204. package/dist/extraction/specs/types.d.ts +39 -0
  205. package/dist/extraction/specs/types.d.ts.map +1 -0
  206. package/dist/extraction/specs/types.js +8 -0
  207. package/dist/extraction/specs/types.js.map +1 -0
  208. package/dist/extraction/svelte-extractor.d.ts +56 -0
  209. package/dist/extraction/svelte-extractor.d.ts.map +1 -0
  210. package/dist/extraction/svelte-extractor.js +272 -0
  211. package/dist/extraction/svelte-extractor.js.map +1 -0
  212. package/dist/extraction/tree-sitter-helpers.d.ts +28 -0
  213. package/dist/extraction/tree-sitter-helpers.d.ts.map +1 -0
  214. package/dist/extraction/tree-sitter-helpers.js +103 -0
  215. package/dist/extraction/tree-sitter-helpers.js.map +1 -0
  216. package/dist/extraction/tree-sitter-types.d.ts +193 -0
  217. package/dist/extraction/tree-sitter-types.d.ts.map +1 -0
  218. package/dist/extraction/tree-sitter-types.js +10 -0
  219. package/dist/extraction/tree-sitter-types.js.map +1 -0
  220. package/dist/extraction/tree-sitter.d.ts +317 -0
  221. package/dist/extraction/tree-sitter.d.ts.map +1 -0
  222. package/dist/extraction/tree-sitter.js +3092 -0
  223. package/dist/extraction/tree-sitter.js.map +1 -0
  224. package/dist/extraction/vue-extractor.d.ts +51 -0
  225. package/dist/extraction/vue-extractor.d.ts.map +1 -0
  226. package/dist/extraction/vue-extractor.js +251 -0
  227. package/dist/extraction/vue-extractor.js.map +1 -0
  228. package/dist/extraction/wasm/tree-sitter-lua.wasm +0 -0
  229. package/dist/extraction/wasm/tree-sitter-luau.wasm +0 -0
  230. package/dist/extraction/wasm/tree-sitter-pascal.wasm +0 -0
  231. package/dist/extraction/wasm/tree-sitter-scala.wasm +0 -0
  232. package/dist/extraction/wasm-runtime-flags.d.ts +38 -0
  233. package/dist/extraction/wasm-runtime-flags.d.ts.map +1 -0
  234. package/dist/extraction/wasm-runtime-flags.js +106 -0
  235. package/dist/extraction/wasm-runtime-flags.js.map +1 -0
  236. package/dist/fitness/fitness.d.ts +75 -0
  237. package/dist/fitness/fitness.d.ts.map +1 -0
  238. package/dist/fitness/fitness.js +204 -0
  239. package/dist/fitness/fitness.js.map +1 -0
  240. package/dist/graph/index.d.ts +8 -0
  241. package/dist/graph/index.d.ts.map +1 -0
  242. package/dist/graph/index.js +13 -0
  243. package/dist/graph/index.js.map +1 -0
  244. package/dist/graph/maintainability.d.ts +115 -0
  245. package/dist/graph/maintainability.d.ts.map +1 -0
  246. package/dist/graph/maintainability.js +299 -0
  247. package/dist/graph/maintainability.js.map +1 -0
  248. package/dist/graph/queries.d.ts +106 -0
  249. package/dist/graph/queries.d.ts.map +1 -0
  250. package/dist/graph/queries.js +366 -0
  251. package/dist/graph/queries.js.map +1 -0
  252. package/dist/graph/traversal.d.ts +127 -0
  253. package/dist/graph/traversal.d.ts.map +1 -0
  254. package/dist/graph/traversal.js +531 -0
  255. package/dist/graph/traversal.js.map +1 -0
  256. package/dist/health/smoke-check.d.ts +85 -0
  257. package/dist/health/smoke-check.d.ts.map +1 -0
  258. package/dist/health/smoke-check.js +246 -0
  259. package/dist/health/smoke-check.js.map +1 -0
  260. package/dist/index.d.ts +674 -0
  261. package/dist/index.d.ts.map +1 -0
  262. package/dist/index.js +1473 -0
  263. package/dist/index.js.map +1 -0
  264. package/dist/installer/config-writer.d.ts +28 -0
  265. package/dist/installer/config-writer.d.ts.map +1 -0
  266. package/dist/installer/config-writer.js +91 -0
  267. package/dist/installer/config-writer.js.map +1 -0
  268. package/dist/installer/index.d.ts +100 -0
  269. package/dist/installer/index.d.ts.map +1 -0
  270. package/dist/installer/index.js +442 -0
  271. package/dist/installer/index.js.map +1 -0
  272. package/dist/installer/init-offer.d.ts +31 -0
  273. package/dist/installer/init-offer.d.ts.map +1 -0
  274. package/dist/installer/init-offer.js +30 -0
  275. package/dist/installer/init-offer.js.map +1 -0
  276. package/dist/installer/instructions-template.d.ts +36 -0
  277. package/dist/installer/instructions-template.d.ts.map +1 -0
  278. package/dist/installer/instructions-template.js +57 -0
  279. package/dist/installer/instructions-template.js.map +1 -0
  280. package/dist/installer/targets/claude.d.ts +146 -0
  281. package/dist/installer/targets/claude.d.ts.map +1 -0
  282. package/dist/installer/targets/claude.js +864 -0
  283. package/dist/installer/targets/claude.js.map +1 -0
  284. package/dist/installer/targets/registry.d.ts +19 -0
  285. package/dist/installer/targets/registry.d.ts.map +1 -0
  286. package/dist/installer/targets/registry.js +31 -0
  287. package/dist/installer/targets/registry.js.map +1 -0
  288. package/dist/installer/targets/shared.d.ts +76 -0
  289. package/dist/installer/targets/shared.d.ts.map +1 -0
  290. package/dist/installer/targets/shared.js +260 -0
  291. package/dist/installer/targets/shared.js.map +1 -0
  292. package/dist/installer/targets/types.d.ts +95 -0
  293. package/dist/installer/targets/types.d.ts.map +1 -0
  294. package/dist/installer/targets/types.js +12 -0
  295. package/dist/installer/targets/types.js.map +1 -0
  296. package/dist/isolation/worktree.d.ts +65 -0
  297. package/dist/isolation/worktree.d.ts.map +1 -0
  298. package/dist/isolation/worktree.js +231 -0
  299. package/dist/isolation/worktree.js.map +1 -0
  300. package/dist/mcp/daemon-paths.d.ts +46 -0
  301. package/dist/mcp/daemon-paths.d.ts.map +1 -0
  302. package/dist/mcp/daemon-paths.js +125 -0
  303. package/dist/mcp/daemon-paths.js.map +1 -0
  304. package/dist/mcp/daemon.d.ts +161 -0
  305. package/dist/mcp/daemon.d.ts.map +1 -0
  306. package/dist/mcp/daemon.js +403 -0
  307. package/dist/mcp/daemon.js.map +1 -0
  308. package/dist/mcp/designer-tools.d.ts +33 -0
  309. package/dist/mcp/designer-tools.d.ts.map +1 -0
  310. package/dist/mcp/designer-tools.js +313 -0
  311. package/dist/mcp/designer-tools.js.map +1 -0
  312. package/dist/mcp/engine.d.ts +105 -0
  313. package/dist/mcp/engine.d.ts.map +1 -0
  314. package/dist/mcp/engine.js +270 -0
  315. package/dist/mcp/engine.js.map +1 -0
  316. package/dist/mcp/fitness-tool.d.ts +12 -0
  317. package/dist/mcp/fitness-tool.d.ts.map +1 -0
  318. package/dist/mcp/fitness-tool.js +46 -0
  319. package/dist/mcp/fitness-tool.js.map +1 -0
  320. package/dist/mcp/index.d.ts +112 -0
  321. package/dist/mcp/index.d.ts.map +1 -0
  322. package/dist/mcp/index.js +477 -0
  323. package/dist/mcp/index.js.map +1 -0
  324. package/dist/mcp/maintainability-tool.d.ts +13 -0
  325. package/dist/mcp/maintainability-tool.d.ts.map +1 -0
  326. package/dist/mcp/maintainability-tool.js +64 -0
  327. package/dist/mcp/maintainability-tool.js.map +1 -0
  328. package/dist/mcp/proxy.d.ts +81 -0
  329. package/dist/mcp/proxy.d.ts.map +1 -0
  330. package/dist/mcp/proxy.js +510 -0
  331. package/dist/mcp/proxy.js.map +1 -0
  332. package/dist/mcp/server-instructions.d.ts +18 -0
  333. package/dist/mcp/server-instructions.d.ts.map +1 -0
  334. package/dist/mcp/server-instructions.js +79 -0
  335. package/dist/mcp/server-instructions.js.map +1 -0
  336. package/dist/mcp/session.d.ts +77 -0
  337. package/dist/mcp/session.d.ts.map +1 -0
  338. package/dist/mcp/session.js +294 -0
  339. package/dist/mcp/session.js.map +1 -0
  340. package/dist/mcp/spec-tools.d.ts +39 -0
  341. package/dist/mcp/spec-tools.d.ts.map +1 -0
  342. package/dist/mcp/spec-tools.js +534 -0
  343. package/dist/mcp/spec-tools.js.map +1 -0
  344. package/dist/mcp/tools.d.ts +417 -0
  345. package/dist/mcp/tools.d.ts.map +1 -0
  346. package/dist/mcp/tools.js +3179 -0
  347. package/dist/mcp/tools.js.map +1 -0
  348. package/dist/mcp/transport.d.ts +188 -0
  349. package/dist/mcp/transport.d.ts.map +1 -0
  350. package/dist/mcp/transport.js +343 -0
  351. package/dist/mcp/transport.js.map +1 -0
  352. package/dist/mcp/version.d.ts +19 -0
  353. package/dist/mcp/version.d.ts.map +1 -0
  354. package/dist/mcp/version.js +71 -0
  355. package/dist/mcp/version.js.map +1 -0
  356. package/dist/reflect/apply.d.ts +31 -0
  357. package/dist/reflect/apply.d.ts.map +1 -0
  358. package/dist/reflect/apply.js +286 -0
  359. package/dist/reflect/apply.js.map +1 -0
  360. package/dist/reflect/hash.d.ts +20 -0
  361. package/dist/reflect/hash.d.ts.map +1 -0
  362. package/dist/reflect/hash.js +36 -0
  363. package/dist/reflect/hash.js.map +1 -0
  364. package/dist/reflect/index.d.ts +16 -0
  365. package/dist/reflect/index.d.ts.map +1 -0
  366. package/dist/reflect/index.js +43 -0
  367. package/dist/reflect/index.js.map +1 -0
  368. package/dist/reflect/miner.d.ts +21 -0
  369. package/dist/reflect/miner.d.ts.map +1 -0
  370. package/dist/reflect/miner.js +463 -0
  371. package/dist/reflect/miner.js.map +1 -0
  372. package/dist/reflect/store.d.ts +31 -0
  373. package/dist/reflect/store.d.ts.map +1 -0
  374. package/dist/reflect/store.js +101 -0
  375. package/dist/reflect/store.js.map +1 -0
  376. package/dist/reflect/sweep.d.ts +26 -0
  377. package/dist/reflect/sweep.d.ts.map +1 -0
  378. package/dist/reflect/sweep.js +42 -0
  379. package/dist/reflect/sweep.js.map +1 -0
  380. package/dist/reflect/targets.d.ts +52 -0
  381. package/dist/reflect/targets.d.ts.map +1 -0
  382. package/dist/reflect/targets.js +192 -0
  383. package/dist/reflect/targets.js.map +1 -0
  384. package/dist/reflect/types.d.ts +96 -0
  385. package/dist/reflect/types.d.ts.map +1 -0
  386. package/dist/reflect/types.js +13 -0
  387. package/dist/reflect/types.js.map +1 -0
  388. package/dist/resolution/brief-link-resolver.d.ts +114 -0
  389. package/dist/resolution/brief-link-resolver.d.ts.map +1 -0
  390. package/dist/resolution/brief-link-resolver.js +261 -0
  391. package/dist/resolution/brief-link-resolver.js.map +1 -0
  392. package/dist/resolution/callback-synthesizer.d.ts +10 -0
  393. package/dist/resolution/callback-synthesizer.d.ts.map +1 -0
  394. package/dist/resolution/callback-synthesizer.js +1300 -0
  395. package/dist/resolution/callback-synthesizer.js.map +1 -0
  396. package/dist/resolution/domain-gap-seed.d.ts +60 -0
  397. package/dist/resolution/domain-gap-seed.d.ts.map +1 -0
  398. package/dist/resolution/domain-gap-seed.js +87 -0
  399. package/dist/resolution/domain-gap-seed.js.map +1 -0
  400. package/dist/resolution/frameworks/cargo-workspace.d.ts +18 -0
  401. package/dist/resolution/frameworks/cargo-workspace.d.ts.map +1 -0
  402. package/dist/resolution/frameworks/cargo-workspace.js +225 -0
  403. package/dist/resolution/frameworks/cargo-workspace.js.map +1 -0
  404. package/dist/resolution/frameworks/csharp.d.ts +8 -0
  405. package/dist/resolution/frameworks/csharp.d.ts.map +1 -0
  406. package/dist/resolution/frameworks/csharp.js +241 -0
  407. package/dist/resolution/frameworks/csharp.js.map +1 -0
  408. package/dist/resolution/frameworks/drupal.d.ts +51 -0
  409. package/dist/resolution/frameworks/drupal.d.ts.map +1 -0
  410. package/dist/resolution/frameworks/drupal.js +367 -0
  411. package/dist/resolution/frameworks/drupal.js.map +1 -0
  412. package/dist/resolution/frameworks/expo-modules.d.ts +3 -0
  413. package/dist/resolution/frameworks/expo-modules.d.ts.map +1 -0
  414. package/dist/resolution/frameworks/expo-modules.js +143 -0
  415. package/dist/resolution/frameworks/expo-modules.js.map +1 -0
  416. package/dist/resolution/frameworks/express.d.ts +8 -0
  417. package/dist/resolution/frameworks/express.d.ts.map +1 -0
  418. package/dist/resolution/frameworks/express.js +308 -0
  419. package/dist/resolution/frameworks/express.js.map +1 -0
  420. package/dist/resolution/frameworks/fabric.d.ts +3 -0
  421. package/dist/resolution/frameworks/fabric.d.ts.map +1 -0
  422. package/dist/resolution/frameworks/fabric.js +354 -0
  423. package/dist/resolution/frameworks/fabric.js.map +1 -0
  424. package/dist/resolution/frameworks/go.d.ts +8 -0
  425. package/dist/resolution/frameworks/go.d.ts.map +1 -0
  426. package/dist/resolution/frameworks/go.js +161 -0
  427. package/dist/resolution/frameworks/go.js.map +1 -0
  428. package/dist/resolution/frameworks/index.d.ts +48 -0
  429. package/dist/resolution/frameworks/index.d.ts.map +1 -0
  430. package/dist/resolution/frameworks/index.js +161 -0
  431. package/dist/resolution/frameworks/index.js.map +1 -0
  432. package/dist/resolution/frameworks/java.d.ts +8 -0
  433. package/dist/resolution/frameworks/java.d.ts.map +1 -0
  434. package/dist/resolution/frameworks/java.js +504 -0
  435. package/dist/resolution/frameworks/java.js.map +1 -0
  436. package/dist/resolution/frameworks/laravel.d.ts +13 -0
  437. package/dist/resolution/frameworks/laravel.d.ts.map +1 -0
  438. package/dist/resolution/frameworks/laravel.js +257 -0
  439. package/dist/resolution/frameworks/laravel.js.map +1 -0
  440. package/dist/resolution/frameworks/nestjs.d.ts +26 -0
  441. package/dist/resolution/frameworks/nestjs.d.ts.map +1 -0
  442. package/dist/resolution/frameworks/nestjs.js +698 -0
  443. package/dist/resolution/frameworks/nestjs.js.map +1 -0
  444. package/dist/resolution/frameworks/play.d.ts +19 -0
  445. package/dist/resolution/frameworks/play.d.ts.map +1 -0
  446. package/dist/resolution/frameworks/play.js +111 -0
  447. package/dist/resolution/frameworks/play.js.map +1 -0
  448. package/dist/resolution/frameworks/python.d.ts +10 -0
  449. package/dist/resolution/frameworks/python.d.ts.map +1 -0
  450. package/dist/resolution/frameworks/python.js +396 -0
  451. package/dist/resolution/frameworks/python.js.map +1 -0
  452. package/dist/resolution/frameworks/react-native.d.ts +3 -0
  453. package/dist/resolution/frameworks/react-native.d.ts.map +1 -0
  454. package/dist/resolution/frameworks/react-native.js +360 -0
  455. package/dist/resolution/frameworks/react-native.js.map +1 -0
  456. package/dist/resolution/frameworks/react.d.ts +8 -0
  457. package/dist/resolution/frameworks/react.d.ts.map +1 -0
  458. package/dist/resolution/frameworks/react.js +365 -0
  459. package/dist/resolution/frameworks/react.js.map +1 -0
  460. package/dist/resolution/frameworks/ruby.d.ts +8 -0
  461. package/dist/resolution/frameworks/ruby.d.ts.map +1 -0
  462. package/dist/resolution/frameworks/ruby.js +302 -0
  463. package/dist/resolution/frameworks/ruby.js.map +1 -0
  464. package/dist/resolution/frameworks/rust.d.ts +8 -0
  465. package/dist/resolution/frameworks/rust.d.ts.map +1 -0
  466. package/dist/resolution/frameworks/rust.js +304 -0
  467. package/dist/resolution/frameworks/rust.js.map +1 -0
  468. package/dist/resolution/frameworks/svelte.d.ts +9 -0
  469. package/dist/resolution/frameworks/svelte.d.ts.map +1 -0
  470. package/dist/resolution/frameworks/svelte.js +249 -0
  471. package/dist/resolution/frameworks/svelte.js.map +1 -0
  472. package/dist/resolution/frameworks/swift-objc.d.ts +37 -0
  473. package/dist/resolution/frameworks/swift-objc.d.ts.map +1 -0
  474. package/dist/resolution/frameworks/swift-objc.js +252 -0
  475. package/dist/resolution/frameworks/swift-objc.js.map +1 -0
  476. package/dist/resolution/frameworks/swift.d.ts +10 -0
  477. package/dist/resolution/frameworks/swift.d.ts.map +1 -0
  478. package/dist/resolution/frameworks/swift.js +400 -0
  479. package/dist/resolution/frameworks/swift.js.map +1 -0
  480. package/dist/resolution/frameworks/vue.d.ts +9 -0
  481. package/dist/resolution/frameworks/vue.d.ts.map +1 -0
  482. package/dist/resolution/frameworks/vue.js +306 -0
  483. package/dist/resolution/frameworks/vue.js.map +1 -0
  484. package/dist/resolution/go-module.d.ts +26 -0
  485. package/dist/resolution/go-module.d.ts.map +1 -0
  486. package/dist/resolution/go-module.js +78 -0
  487. package/dist/resolution/go-module.js.map +1 -0
  488. package/dist/resolution/import-resolver.d.ts +68 -0
  489. package/dist/resolution/import-resolver.d.ts.map +1 -0
  490. package/dist/resolution/import-resolver.js +1275 -0
  491. package/dist/resolution/import-resolver.js.map +1 -0
  492. package/dist/resolution/index.d.ts +117 -0
  493. package/dist/resolution/index.d.ts.map +1 -0
  494. package/dist/resolution/index.js +895 -0
  495. package/dist/resolution/index.js.map +1 -0
  496. package/dist/resolution/lru-cache.d.ts +24 -0
  497. package/dist/resolution/lru-cache.d.ts.map +1 -0
  498. package/dist/resolution/lru-cache.js +62 -0
  499. package/dist/resolution/lru-cache.js.map +1 -0
  500. package/dist/resolution/name-matcher.d.ts +32 -0
  501. package/dist/resolution/name-matcher.d.ts.map +1 -0
  502. package/dist/resolution/name-matcher.js +596 -0
  503. package/dist/resolution/name-matcher.js.map +1 -0
  504. package/dist/resolution/path-aliases.d.ts +68 -0
  505. package/dist/resolution/path-aliases.d.ts.map +1 -0
  506. package/dist/resolution/path-aliases.js +238 -0
  507. package/dist/resolution/path-aliases.js.map +1 -0
  508. package/dist/resolution/spec-link-resolver.d.ts +148 -0
  509. package/dist/resolution/spec-link-resolver.d.ts.map +1 -0
  510. package/dist/resolution/spec-link-resolver.js +337 -0
  511. package/dist/resolution/spec-link-resolver.js.map +1 -0
  512. package/dist/resolution/strip-comments.d.ts +27 -0
  513. package/dist/resolution/strip-comments.d.ts.map +1 -0
  514. package/dist/resolution/strip-comments.js +441 -0
  515. package/dist/resolution/strip-comments.js.map +1 -0
  516. package/dist/resolution/swift-objc-bridge.d.ts +134 -0
  517. package/dist/resolution/swift-objc-bridge.d.ts.map +1 -0
  518. package/dist/resolution/swift-objc-bridge.js +256 -0
  519. package/dist/resolution/swift-objc-bridge.js.map +1 -0
  520. package/dist/resolution/types.d.ts +216 -0
  521. package/dist/resolution/types.d.ts.map +1 -0
  522. package/dist/resolution/types.js +8 -0
  523. package/dist/resolution/types.js.map +1 -0
  524. package/dist/resolution/workspace-packages.d.ts +48 -0
  525. package/dist/resolution/workspace-packages.d.ts.map +1 -0
  526. package/dist/resolution/workspace-packages.js +208 -0
  527. package/dist/resolution/workspace-packages.js.map +1 -0
  528. package/dist/search/query-parser.d.ts +57 -0
  529. package/dist/search/query-parser.d.ts.map +1 -0
  530. package/dist/search/query-parser.js +177 -0
  531. package/dist/search/query-parser.js.map +1 -0
  532. package/dist/search/query-utils.d.ts +71 -0
  533. package/dist/search/query-utils.d.ts.map +1 -0
  534. package/dist/search/query-utils.js +380 -0
  535. package/dist/search/query-utils.js.map +1 -0
  536. package/dist/server/cli.js +152 -0
  537. package/dist/server/index.js +12 -0
  538. package/dist/server/ingest/impact-backfill.js +69 -0
  539. package/dist/server/ingest/impact-query.js +343 -0
  540. package/dist/server/ingest/index.js +19 -0
  541. package/dist/server/ingest/ingestor.js +541 -0
  542. package/dist/server/ingest/parser.js +104 -0
  543. package/dist/server/ingest/pricing.js +78 -0
  544. package/dist/server/ingest/specship-classify.js +153 -0
  545. package/dist/server/ingest/types.js +9 -0
  546. package/dist/server/ingest/watcher.js +77 -0
  547. package/dist/server/package.json +3 -0
  548. package/dist/server/project-registry.js +101 -0
  549. package/dist/server/routes/claude.js +907 -0
  550. package/dist/server/routes/domain.js +0 -0
  551. package/dist/server/routes/events.js +134 -0
  552. package/dist/server/routes/graph.js +248 -0
  553. package/dist/server/routes/maintainability.js +18 -0
  554. package/dist/server/routes/memory.js +272 -0
  555. package/dist/server/routes/projects.js +197 -0
  556. package/dist/server/routes/reflect.js +93 -0
  557. package/dist/server/routes/spec.js +373 -0
  558. package/dist/server/routes/status.js +112 -0
  559. package/dist/server/routes/workflow.js +253 -0
  560. package/dist/server/server.js +238 -0
  561. package/dist/server/static-handler.js +87 -0
  562. package/dist/statusline/active-run.d.ts +16 -0
  563. package/dist/statusline/active-run.d.ts.map +1 -0
  564. package/dist/statusline/active-run.js +73 -0
  565. package/dist/statusline/active-run.js.map +1 -0
  566. package/dist/statusline/cache.d.ts +21 -0
  567. package/dist/statusline/cache.d.ts.map +1 -0
  568. package/dist/statusline/cache.js +34 -0
  569. package/dist/statusline/cache.js.map +1 -0
  570. package/dist/statusline/index.d.ts +24 -0
  571. package/dist/statusline/index.d.ts.map +1 -0
  572. package/dist/statusline/index.js +128 -0
  573. package/dist/statusline/index.js.map +1 -0
  574. package/dist/statusline/paths.d.ts +27 -0
  575. package/dist/statusline/paths.d.ts.map +1 -0
  576. package/dist/statusline/paths.js +101 -0
  577. package/dist/statusline/paths.js.map +1 -0
  578. package/dist/statusline/render.d.ts +25 -0
  579. package/dist/statusline/render.d.ts.map +1 -0
  580. package/dist/statusline/render.js +72 -0
  581. package/dist/statusline/render.js.map +1 -0
  582. package/dist/statusline/session-marker.d.ts +30 -0
  583. package/dist/statusline/session-marker.d.ts.map +1 -0
  584. package/dist/statusline/session-marker.js +71 -0
  585. package/dist/statusline/session-marker.js.map +1 -0
  586. package/dist/statusline/types.d.ts +67 -0
  587. package/dist/statusline/types.d.ts.map +1 -0
  588. package/dist/statusline/types.js +16 -0
  589. package/dist/statusline/types.js.map +1 -0
  590. package/dist/sync/git-hooks.d.ts +45 -0
  591. package/dist/sync/git-hooks.d.ts.map +1 -0
  592. package/dist/sync/git-hooks.js +225 -0
  593. package/dist/sync/git-hooks.js.map +1 -0
  594. package/dist/sync/index.d.ts +19 -0
  595. package/dist/sync/index.d.ts.map +1 -0
  596. package/dist/sync/index.js +35 -0
  597. package/dist/sync/index.js.map +1 -0
  598. package/dist/sync/watch-policy.d.ts +48 -0
  599. package/dist/sync/watch-policy.d.ts.map +1 -0
  600. package/dist/sync/watch-policy.js +124 -0
  601. package/dist/sync/watch-policy.js.map +1 -0
  602. package/dist/sync/watcher.d.ts +283 -0
  603. package/dist/sync/watcher.d.ts.map +1 -0
  604. package/dist/sync/watcher.js +606 -0
  605. package/dist/sync/watcher.js.map +1 -0
  606. package/dist/sync/worktree.d.ts +54 -0
  607. package/dist/sync/worktree.d.ts.map +1 -0
  608. package/dist/sync/worktree.js +137 -0
  609. package/dist/sync/worktree.js.map +1 -0
  610. package/dist/types.d.ts +625 -0
  611. package/dist/types.d.ts.map +1 -0
  612. package/dist/types.js +118 -0
  613. package/dist/types.js.map +1 -0
  614. package/dist/ui/glyphs.d.ts +42 -0
  615. package/dist/ui/glyphs.d.ts.map +1 -0
  616. package/dist/ui/glyphs.js +78 -0
  617. package/dist/ui/glyphs.js.map +1 -0
  618. package/dist/ui/shimmer-progress.d.ts +11 -0
  619. package/dist/ui/shimmer-progress.d.ts.map +1 -0
  620. package/dist/ui/shimmer-progress.js +90 -0
  621. package/dist/ui/shimmer-progress.js.map +1 -0
  622. package/dist/ui/shimmer-worker.d.ts +2 -0
  623. package/dist/ui/shimmer-worker.d.ts.map +1 -0
  624. package/dist/ui/shimmer-worker.js +118 -0
  625. package/dist/ui/shimmer-worker.js.map +1 -0
  626. package/dist/ui/types.d.ts +17 -0
  627. package/dist/ui/types.d.ts.map +1 -0
  628. package/dist/ui/types.js +3 -0
  629. package/dist/ui/types.js.map +1 -0
  630. package/dist/utils.d.ts +205 -0
  631. package/dist/utils.d.ts.map +1 -0
  632. package/dist/utils.js +549 -0
  633. package/dist/utils.js.map +1 -0
  634. package/dist/web/chunk-2AJCHB7P.js +1 -0
  635. package/dist/web/chunk-2CPLUFCH.js +2 -0
  636. package/dist/web/chunk-2I7L37NS.js +1 -0
  637. package/dist/web/chunk-2NAWAJB5.js +1 -0
  638. package/dist/web/chunk-2OJBIPE4.js +1 -0
  639. package/dist/web/chunk-372AYXK6.js +17 -0
  640. package/dist/web/chunk-3E2WB6D5.js +1 -0
  641. package/dist/web/chunk-3EBFYSCH.js +2 -0
  642. package/dist/web/chunk-3QCQ4BXS.js +1 -0
  643. package/dist/web/chunk-42XVAQ6I.js +1 -0
  644. package/dist/web/chunk-4IMMPEYM.js +1 -0
  645. package/dist/web/chunk-4JYHAP7B.js +1 -0
  646. package/dist/web/chunk-4TJQJPCZ.js +1 -0
  647. package/dist/web/chunk-4WZIHTPC.js +1 -0
  648. package/dist/web/chunk-4YVSYOSD.js +1 -0
  649. package/dist/web/chunk-52PO6IMB.js +2 -0
  650. package/dist/web/chunk-54D6RFSW.js +1 -0
  651. package/dist/web/chunk-5BQIOYKW.js +1 -0
  652. package/dist/web/chunk-5HGWHUJA.js +1 -0
  653. package/dist/web/chunk-5XRUOPZE.js +1 -0
  654. package/dist/web/chunk-5Y244R4G.js +1 -0
  655. package/dist/web/chunk-6O7Z3P2M.js +1 -0
  656. package/dist/web/chunk-6QXULGLG.js +1 -0
  657. package/dist/web/chunk-6RRDPT5Z.js +1 -0
  658. package/dist/web/chunk-6VKB2ZWM.js +1 -0
  659. package/dist/web/chunk-7DMFVTU4.js +1 -0
  660. package/dist/web/chunk-7P5CVBJZ.js +1 -0
  661. package/dist/web/chunk-7SMPKVEP.js +1 -0
  662. package/dist/web/chunk-AHLX543M.js +1 -0
  663. package/dist/web/chunk-AMGJBO7D.js +3 -0
  664. package/dist/web/chunk-AZJVTPLU.js +1 -0
  665. package/dist/web/chunk-B3CWIVBW.js +1 -0
  666. package/dist/web/chunk-BLBRMCN2.js +1 -0
  667. package/dist/web/chunk-BMIAXD2V.js +2 -0
  668. package/dist/web/chunk-BPCJLNBS.js +47 -0
  669. package/dist/web/chunk-BRHEUDLY.js +6 -0
  670. package/dist/web/chunk-BUXWEHIY.js +1 -0
  671. package/dist/web/chunk-CD5IZM7Y.js +1 -0
  672. package/dist/web/chunk-DLQPZWSI.css +1 -0
  673. package/dist/web/chunk-DSGNOCKQ.js +1 -0
  674. package/dist/web/chunk-DT5LJYFX.js +1 -0
  675. package/dist/web/chunk-DYRFLPJA.js +1 -0
  676. package/dist/web/chunk-E3J3CXR5.js +1 -0
  677. package/dist/web/chunk-E73OX2P7.js +1 -0
  678. package/dist/web/chunk-EAXRKDLV.js +1 -0
  679. package/dist/web/chunk-EBKKDHYI.js +1 -0
  680. package/dist/web/chunk-EE7V7Q5P.js +1 -0
  681. package/dist/web/chunk-EKY2FUHU.js +1 -0
  682. package/dist/web/chunk-EP6XOPXH.js +1 -0
  683. package/dist/web/chunk-ESGDLJOJ.js +1 -0
  684. package/dist/web/chunk-ETJG7NCY.js +1 -0
  685. package/dist/web/chunk-EUUEFEDI.js +1 -0
  686. package/dist/web/chunk-EX4ZHR4F.js +1 -0
  687. package/dist/web/chunk-F5UNCSXP.js +1 -0
  688. package/dist/web/chunk-FFGJXUHI.js +1 -0
  689. package/dist/web/chunk-FGNZDHTL.js +11 -0
  690. package/dist/web/chunk-FIJW2UNJ.js +1 -0
  691. package/dist/web/chunk-FMV5PXRC.js +5 -0
  692. package/dist/web/chunk-G7VZT5KB.js +3 -0
  693. package/dist/web/chunk-GCOM4JPR.js +2 -0
  694. package/dist/web/chunk-GEIIDO6C.js +1 -0
  695. package/dist/web/chunk-GRZYXPSO.js +7 -0
  696. package/dist/web/chunk-GWBABPZ5.js +1 -0
  697. package/dist/web/chunk-GYGPS3AN.js +1 -0
  698. package/dist/web/chunk-H4GLRD3Q.js +1 -0
  699. package/dist/web/chunk-H5TWEFYX.js +1 -0
  700. package/dist/web/chunk-H7AF7YS4.js +1 -0
  701. package/dist/web/chunk-HCB2N2KH.js +1 -0
  702. package/dist/web/chunk-HDZDQILN.js +1 -0
  703. package/dist/web/chunk-HMK6UO6N.js +1 -0
  704. package/dist/web/chunk-HVVXPI4D.js +1 -0
  705. package/dist/web/chunk-IHEE5NYJ.js +1 -0
  706. package/dist/web/chunk-IPB746BT.js +1 -0
  707. package/dist/web/chunk-ISNEBICW.js +1 -0
  708. package/dist/web/chunk-J2GZVLHH.js +1 -0
  709. package/dist/web/chunk-JTFXTIPE.js +903 -0
  710. package/dist/web/chunk-KHU5M2AL.js +1 -0
  711. package/dist/web/chunk-KW3DHCFV.js +1 -0
  712. package/dist/web/chunk-LB6JPLX2.js +1 -0
  713. package/dist/web/chunk-LBXLFPVN.js +1 -0
  714. package/dist/web/chunk-LGNSHRCE.js +1 -0
  715. package/dist/web/chunk-LNSVDHCI.js +1 -0
  716. package/dist/web/chunk-LVGIY3SO.js +1 -0
  717. package/dist/web/chunk-LXLHIHEN.js +1 -0
  718. package/dist/web/chunk-MFHO2F2U.js +4 -0
  719. package/dist/web/chunk-N5OSSQFZ.js +1 -0
  720. package/dist/web/chunk-N6SS4G6S.js +1 -0
  721. package/dist/web/chunk-NAJYJNHS.js +1 -0
  722. package/dist/web/chunk-NHD66NOI.js +1 -0
  723. package/dist/web/chunk-NNLJ55MY.js +1 -0
  724. package/dist/web/chunk-NTBJG6SJ.js +1 -0
  725. package/dist/web/chunk-NUDB3Q2Y.js +3 -0
  726. package/dist/web/chunk-OM7JVWQQ.js +1 -0
  727. package/dist/web/chunk-OXEF5E3E.js +1 -0
  728. package/dist/web/chunk-PGGJPDJG.js +1 -0
  729. package/dist/web/chunk-PUYSJNJR.js +1 -0
  730. package/dist/web/chunk-Q2RVFS45.js +1 -0
  731. package/dist/web/chunk-Q7L6LLAK.js +1 -0
  732. package/dist/web/chunk-QCMKJIWY.js +1 -0
  733. package/dist/web/chunk-QEQRY4QQ.js +1 -0
  734. package/dist/web/chunk-QH6CF3M3.js +1 -0
  735. package/dist/web/chunk-QQ5LD7PI.js +1 -0
  736. package/dist/web/chunk-QR6L3KAC.js +1 -0
  737. package/dist/web/chunk-QXJS6F3U.js +1 -0
  738. package/dist/web/chunk-R2DLK4HO.js +1 -0
  739. package/dist/web/chunk-RD6TVPOT.js +1 -0
  740. package/dist/web/chunk-RKY4EJYJ.js +1 -0
  741. package/dist/web/chunk-RONYWVY7.js +1 -0
  742. package/dist/web/chunk-RSZZWGGC.js +1 -0
  743. package/dist/web/chunk-RXKXYF2C.js +1 -0
  744. package/dist/web/chunk-SCNDZRN2.js +1 -0
  745. package/dist/web/chunk-SH6UVHQC.js +1 -0
  746. package/dist/web/chunk-SWKJRNYY.js +1 -0
  747. package/dist/web/chunk-T7AZ65JP.js +1 -0
  748. package/dist/web/chunk-TCZDVOHD.js +1 -0
  749. package/dist/web/chunk-TF5TF6IP.js +1 -0
  750. package/dist/web/chunk-TPTITA3V.js +1 -0
  751. package/dist/web/chunk-TR335633.js +1 -0
  752. package/dist/web/chunk-UR5KDXPX.js +1 -0
  753. package/dist/web/chunk-UR6O2GEH.js +1 -0
  754. package/dist/web/chunk-UTNMGWTP.js +1 -0
  755. package/dist/web/chunk-VECWMHJP.js +1 -0
  756. package/dist/web/chunk-VUACT35R.js +3 -0
  757. package/dist/web/chunk-VZI7H4SZ.js +1 -0
  758. package/dist/web/chunk-W22AVG3N.js +1 -0
  759. package/dist/web/chunk-W6NGHRHX.js +1 -0
  760. package/dist/web/chunk-WB6YHOD4.js +1 -0
  761. package/dist/web/chunk-WBT64AWV.js +1 -0
  762. package/dist/web/chunk-WFXJIXZE.js +4 -0
  763. package/dist/web/chunk-WTGYRH3Z.js +298 -0
  764. package/dist/web/chunk-WXTCVDTP.js +1 -0
  765. package/dist/web/chunk-XCDHWLVH.js +1 -0
  766. package/dist/web/chunk-Y3H6FFUZ.js +1 -0
  767. package/dist/web/chunk-Y4F5ULGJ.js +1 -0
  768. package/dist/web/chunk-YEGKAAEE.js +1 -0
  769. package/dist/web/chunk-YM2KU57F.js +1 -0
  770. package/dist/web/chunk-YRERBP6T.js +1 -0
  771. package/dist/web/chunk-ZLV4VCDG.js +3 -0
  772. package/dist/web/chunk-ZQUJMA5K.js +4 -0
  773. package/dist/web/chunk-ZTVI5KFF.js +1 -0
  774. package/dist/web/favicon-16.png +0 -0
  775. package/dist/web/favicon-180.png +0 -0
  776. package/dist/web/favicon-32.png +0 -0
  777. package/dist/web/favicon-512.png +0 -0
  778. package/dist/web/favicon-small.svg +15 -0
  779. package/dist/web/favicon.ico +0 -0
  780. package/dist/web/favicon.svg +20 -0
  781. package/dist/web/icon-192.png +0 -0
  782. package/dist/web/icon-512.png +0 -0
  783. package/dist/web/index.html +146 -0
  784. package/dist/web/main-ESADRXN2.css +1 -0
  785. package/dist/web/main-SQFUMVQA.js +1 -0
  786. package/dist/web/manifest.webmanifest +15 -0
  787. package/dist/web/media/codicon-LN6W7LCM.ttf +0 -0
  788. package/dist/web/styles-KSOPUVDA.css +1 -0
  789. package/dist/web/sw.js +69 -0
  790. package/dist/workflows/condition-evaluator.d.ts +75 -0
  791. package/dist/workflows/condition-evaluator.d.ts.map +1 -0
  792. package/dist/workflows/condition-evaluator.js +282 -0
  793. package/dist/workflows/condition-evaluator.js.map +1 -0
  794. package/dist/workflows/defaults/claude-design-implement.yaml +336 -0
  795. package/dist/workflows/defaults/index.d.ts +26 -0
  796. package/dist/workflows/defaults/index.d.ts.map +1 -0
  797. package/dist/workflows/defaults/index.js +94 -0
  798. package/dist/workflows/defaults/index.js.map +1 -0
  799. package/dist/workflows/defaults/spec-author.yaml +214 -0
  800. package/dist/workflows/defaults/spec-fix.yaml +110 -0
  801. package/dist/workflows/defaults/spec-implement.yaml +150 -0
  802. package/dist/workflows/defaults/spec-relink.yaml +81 -0
  803. package/dist/workflows/defaults/spec-verify.yaml +51 -0
  804. package/dist/workflows/discovery.d.ts +46 -0
  805. package/dist/workflows/discovery.d.ts.map +1 -0
  806. package/dist/workflows/discovery.js +193 -0
  807. package/dist/workflows/discovery.js.map +1 -0
  808. package/dist/workflows/executor.d.ts +98 -0
  809. package/dist/workflows/executor.d.ts.map +1 -0
  810. package/dist/workflows/executor.js +664 -0
  811. package/dist/workflows/executor.js.map +1 -0
  812. package/dist/workflows/runners/approval.d.ts +18 -0
  813. package/dist/workflows/runners/approval.d.ts.map +1 -0
  814. package/dist/workflows/runners/approval.js +34 -0
  815. package/dist/workflows/runners/approval.js.map +1 -0
  816. package/dist/workflows/runners/bash.d.ts +13 -0
  817. package/dist/workflows/runners/bash.d.ts.map +1 -0
  818. package/dist/workflows/runners/bash.js +143 -0
  819. package/dist/workflows/runners/bash.js.map +1 -0
  820. package/dist/workflows/runners/cancel.d.ts +10 -0
  821. package/dist/workflows/runners/cancel.d.ts.map +1 -0
  822. package/dist/workflows/runners/cancel.js +19 -0
  823. package/dist/workflows/runners/cancel.js.map +1 -0
  824. package/dist/workflows/runners/prompt.d.ts +51 -0
  825. package/dist/workflows/runners/prompt.d.ts.map +1 -0
  826. package/dist/workflows/runners/prompt.js +306 -0
  827. package/dist/workflows/runners/prompt.js.map +1 -0
  828. package/dist/workflows/runners/script.d.ts +17 -0
  829. package/dist/workflows/runners/script.d.ts.map +1 -0
  830. package/dist/workflows/runners/script.js +155 -0
  831. package/dist/workflows/runners/script.js.map +1 -0
  832. package/dist/workflows/runners/types.d.ts +57 -0
  833. package/dist/workflows/runners/types.d.ts.map +1 -0
  834. package/dist/workflows/runners/types.js +13 -0
  835. package/dist/workflows/runners/types.js.map +1 -0
  836. package/dist/workflows/schemas/workflow.d.ts +166 -0
  837. package/dist/workflows/schemas/workflow.d.ts.map +1 -0
  838. package/dist/workflows/schemas/workflow.js +437 -0
  839. package/dist/workflows/schemas/workflow.js.map +1 -0
  840. package/hooks/hooks.json +38 -0
  841. package/package.json +78 -0
  842. package/scripts/add-lang/bench.sh +60 -0
  843. package/scripts/add-lang/check-grammar.mjs +75 -0
  844. package/scripts/add-lang/dump-ast.mjs +103 -0
  845. package/scripts/add-lang/verify-extraction.mjs +70 -0
  846. package/scripts/agent-eval/arms-F.sh +21 -0
  847. package/scripts/agent-eval/arms-matrix.sh +37 -0
  848. package/scripts/agent-eval/audit.sh +68 -0
  849. package/scripts/agent-eval/bench-readme.sh +28 -0
  850. package/scripts/agent-eval/bench-why-repo.sh +22 -0
  851. package/scripts/agent-eval/block-read-hook.sh +19 -0
  852. package/scripts/agent-eval/hook-settings.json +15 -0
  853. package/scripts/agent-eval/itrun.sh +120 -0
  854. package/scripts/agent-eval/parse-arms.mjs +116 -0
  855. package/scripts/agent-eval/parse-bench-readme.mjs +84 -0
  856. package/scripts/agent-eval/parse-run.mjs +45 -0
  857. package/scripts/agent-eval/parse-session.mjs +93 -0
  858. package/scripts/agent-eval/probe-context.mjs +21 -0
  859. package/scripts/agent-eval/probe-explore.mjs +40 -0
  860. package/scripts/agent-eval/probe-node.mjs +20 -0
  861. package/scripts/agent-eval/probe-sweep.mjs +119 -0
  862. package/scripts/agent-eval/probe-trace.mjs +20 -0
  863. package/scripts/agent-eval/run-agent.sh +34 -0
  864. package/scripts/agent-eval/run-all.sh +67 -0
  865. package/scripts/agent-eval/run-arms.sh +56 -0
  866. package/scripts/agent-eval/seq-matrix.mjs +137 -0
  867. package/scripts/build-bundle.sh +118 -0
  868. package/scripts/build-server-bundle.mjs +80 -0
  869. package/scripts/build-web-bundle.mjs +66 -0
  870. package/scripts/extract-release-notes.mjs +130 -0
  871. package/scripts/local-install.sh +41 -0
  872. package/scripts/npm-sdk.js +75 -0
  873. package/scripts/npm-shim.js +246 -0
  874. package/scripts/offline-install.ps1 +148 -0
  875. package/scripts/offline-install.sh +149 -0
  876. package/scripts/pack-npm.sh +119 -0
  877. package/scripts/prepare-release.mjs +270 -0
  878. package/scripts/sync-shim-version.mjs +64 -0
  879. package/selectors.json +41 -0
@@ -0,0 +1,541 @@
1
+ /**
2
+ * JSONL → SQLite ingestor for Claude Code transcripts.
3
+ *
4
+ * Each Claude Code session lives in `~/.claude/projects/<slug>/<sessionId>.jsonl`,
5
+ * where `<slug>` is the slash-escaped absolute path of the user's project.
6
+ * Files are append-only (Claude Code writes one JSON line per assistant/user
7
+ * turn), so we resume from the last byte offset on every pass — no re-parse
8
+ * of the whole file.
9
+ *
10
+ * Pipeline per file:
11
+ * 1. Read state from `claude_ingest_state` (offset, last_size). If file
12
+ * grew, open it and seek to offset; otherwise skip.
13
+ * 2. Parse each line with parseLine(). Group entries by promptId.
14
+ * 3. For each user entry: upsert claude_prompts row. For each assistant
15
+ * entry: aggregate usage, compute cost, accumulate tool_use blocks.
16
+ * 4. For each tool_use block: insert into claude_tool_calls with
17
+ * input_summary + result_length (matched from the next user entry's
18
+ * tool_result content).
19
+ * 5. Update claude_sessions aggregates (prompt_count, totals).
20
+ * 6. Persist new offset + file_size to claude_ingest_state.
21
+ *
22
+ * The ingestor is idempotent — re-running on the same offset is a no-op.
23
+ * Crash-safe — partial writes use a transaction per file.
24
+ */
25
+ import * as fs from 'fs';
26
+ import * as os from 'os';
27
+ import * as path from 'path';
28
+ import { computeCost, resolvePricing } from './pricing.js';
29
+ import { parseLine, toEpochMs, extractUserPrompt, summarizeToolInput, toolResultLength, } from './parser.js';
30
+ import { classifyToolCall } from './specship-classify.js';
31
+ /**
32
+ * Convert Claude's slash-escaped project dir name back into a real path.
33
+ * `~/.claude/projects/-Users-alice-projects-foo` → `/Users/alice/projects/foo`
34
+ */
35
+ export function decodeProjectSlug(slug) {
36
+ return slug.startsWith('-') ? '/' + slug.slice(1).replace(/-/g, '/') : slug;
37
+ }
38
+ /**
39
+ * Build a predicate that tells whether a stored `project_path` belongs to the
40
+ * primary project, given the primary's REAL filesystem path.
41
+ *
42
+ * Why this isn't a plain `===`: `decodeProjectSlug` lossily turns every '-' in
43
+ * the slug into '/', so a real path like `/Users/a/dev/claude-projects/x` gets
44
+ * STORED as `/Users/a/dev/claude/projects/x`. The savings graph resolver only
45
+ * has the real primary path, so it never matched the mangled stored form and
46
+ * every call resolved to a null graph (savedTokens stuck at 0). We match BOTH
47
+ * the real path and its mangled form (computed by round-tripping the real path
48
+ * through the same encode→decode the storage used). No stored data is changed,
49
+ * so the (consistently-mangled) project filter is unaffected.
50
+ */
51
+ export function primaryProjectMatcher(primaryRealPath) {
52
+ // encode: real path → slug form (every '/' → '-'); decode: slug → mangled path.
53
+ const mangled = decodeProjectSlug(primaryRealPath.replace(/\//g, '-'));
54
+ return (storedPath) => storedPath === primaryRealPath || storedPath === mangled;
55
+ }
56
+ /**
57
+ * List every JSONL file inside `<claudeRoot>/<slug>/<sessionId>.jsonl`.
58
+ * Returns the absolute file path + the decoded project path.
59
+ */
60
+ export function listTranscriptFiles(claudeRoot) {
61
+ const out = [];
62
+ let projects;
63
+ try {
64
+ projects = fs.readdirSync(claudeRoot, { withFileTypes: true });
65
+ }
66
+ catch {
67
+ return out;
68
+ }
69
+ for (const p of projects) {
70
+ if (!p.isDirectory())
71
+ continue;
72
+ const dir = path.join(claudeRoot, p.name);
73
+ let files;
74
+ try {
75
+ files = fs.readdirSync(dir, { withFileTypes: true });
76
+ }
77
+ catch {
78
+ continue;
79
+ }
80
+ for (const f of files) {
81
+ if (f.isFile() && f.name.toLowerCase().endsWith('.jsonl')) {
82
+ out.push({
83
+ filePath: path.join(dir, f.name),
84
+ projectPath: decodeProjectSlug(p.name),
85
+ projectSlug: p.name,
86
+ });
87
+ }
88
+ }
89
+ }
90
+ return out;
91
+ }
92
+ /**
93
+ * Default Anthropic pricing tiers (USD per 1M tokens) — used to seed the
94
+ * pricing table on first run if it's empty. Keeping these here (not just
95
+ * in the v6 migration) makes ingest self-sufficient: if a user upgrades
96
+ * specship but their migration ran in an older binary that didn't seed,
97
+ * the ingestor seeds on first pass instead of failing silently.
98
+ */
99
+ const DEFAULT_PRICING = [
100
+ ['claude-opus-4-7', 15.0, 75.0, 18.75, 1.5],
101
+ ['claude-opus-4', 15.0, 75.0, 18.75, 1.5],
102
+ ['claude-sonnet-4-6', 3.0, 15.0, 3.75, 0.3],
103
+ ['claude-sonnet-4-7', 3.0, 15.0, 3.75, 0.3],
104
+ ['claude-sonnet-4', 3.0, 15.0, 3.75, 0.3],
105
+ ['claude-haiku-4-5', 0.80, 4.0, 1.0, 0.08],
106
+ ['claude-haiku-4', 0.80, 4.0, 1.0, 0.08],
107
+ ];
108
+ /** Load the pricing table once per ingest pass. Seeds defaults if empty. */
109
+ function loadPricing(db) {
110
+ let rows = db
111
+ .prepare('SELECT model, input_per_mtok, output_per_mtok, cache_creation_per_mtok, cache_read_per_mtok FROM claude_pricing')
112
+ .all();
113
+ if (rows.length === 0) {
114
+ const now = Date.now();
115
+ const ins = db.prepare(`
116
+ INSERT OR IGNORE INTO claude_pricing
117
+ (model, input_per_mtok, output_per_mtok, cache_creation_per_mtok, cache_read_per_mtok, updated_at)
118
+ VALUES (?, ?, ?, ?, ?, ?)
119
+ `);
120
+ for (const r of DEFAULT_PRICING)
121
+ ins.run(r[0], r[1], r[2], r[3], r[4], now);
122
+ rows = db
123
+ .prepare('SELECT model, input_per_mtok, output_per_mtok, cache_creation_per_mtok, cache_read_per_mtok FROM claude_pricing')
124
+ .all();
125
+ }
126
+ return rows;
127
+ }
128
+ /**
129
+ * Read a file's tail from `fromOffset` to end. Returns the full text plus
130
+ * the new file size. We read the whole tail at once — JSONL transcripts are
131
+ * usually < 5MB even for long sessions, well within Node's sync read budget.
132
+ */
133
+ function readTail(filePath, fromOffset) {
134
+ const stat = fs.statSync(filePath);
135
+ if (stat.size <= fromOffset)
136
+ return { text: '', size: stat.size };
137
+ const fd = fs.openSync(filePath, 'r');
138
+ try {
139
+ const length = stat.size - fromOffset;
140
+ const buf = Buffer.allocUnsafe(length);
141
+ fs.readSync(fd, buf, 0, length, fromOffset);
142
+ return { text: buf.toString('utf-8'), size: stat.size };
143
+ }
144
+ finally {
145
+ fs.closeSync(fd);
146
+ }
147
+ }
148
+ /**
149
+ * Walk every transcript file under claudeRoot, ingest any new bytes, and
150
+ * return aggregate stats. Synchronous: the caller controls cadence.
151
+ */
152
+ export function ingestAll(db, options = {}) {
153
+ const start = Date.now();
154
+ const claudeRoot = options.claudeRoot ?? path.join(os.homedir(), '.claude', 'projects');
155
+ const verbose = options.verbose ?? false;
156
+ const stats = {
157
+ filesScanned: 0,
158
+ filesSkipped: 0,
159
+ bytesIngested: 0,
160
+ linesParsed: 0,
161
+ promptsInserted: 0,
162
+ toolCallsInserted: 0,
163
+ errors: 0,
164
+ durationMs: 0,
165
+ };
166
+ const pricing = loadPricing(db);
167
+ const files = listTranscriptFiles(claudeRoot);
168
+ for (const f of files) {
169
+ stats.filesScanned++;
170
+ try {
171
+ const wasIngested = ingestFile(db, f.filePath, f.projectPath, pricing, options);
172
+ if (!wasIngested.modified) {
173
+ stats.filesSkipped++;
174
+ }
175
+ else {
176
+ stats.bytesIngested += wasIngested.bytes;
177
+ stats.linesParsed += wasIngested.lines;
178
+ stats.promptsInserted += wasIngested.prompts;
179
+ stats.toolCallsInserted += wasIngested.toolCalls;
180
+ }
181
+ }
182
+ catch (err) {
183
+ stats.errors++;
184
+ if (verbose) {
185
+ // eslint-disable-next-line no-console
186
+ console.error('[ingest] failed:', f.filePath, err instanceof Error ? err.message : String(err));
187
+ }
188
+ }
189
+ }
190
+ stats.durationMs = Date.now() - start;
191
+ return stats;
192
+ }
193
+ function ingestFile(db, filePath, projectPath, pricing, options) {
194
+ // Load state.
195
+ const stateRow = db
196
+ .prepare('SELECT last_offset, file_size, session_id FROM claude_ingest_state WHERE file_path = ?')
197
+ .get(filePath);
198
+ const lastOffset = stateRow?.last_offset ?? 0;
199
+ const { text, size } = readTail(filePath, lastOffset);
200
+ if (text.length === 0) {
201
+ return { modified: false, bytes: 0, lines: 0, prompts: 0, toolCalls: 0 };
202
+ }
203
+ const lines = text.split('\n');
204
+ // The last fragment may be a partial line (the JSONL is append-only — Claude
205
+ // might be mid-write). Only consume complete lines; remember where the last
206
+ // complete newline ends so we resume from there.
207
+ let consumedLen = 0;
208
+ const completeLines = [];
209
+ for (let i = 0; i < lines.length; i++) {
210
+ const line = lines[i];
211
+ if (line === undefined)
212
+ continue;
213
+ // Last entry: if there's no trailing newline, treat as incomplete.
214
+ if (i === lines.length - 1) {
215
+ // If text ends with "\n", the last split element is "" — already complete.
216
+ if (line === '') {
217
+ consumedLen += 0; // already accounted for
218
+ }
219
+ else if (text.endsWith('\n')) {
220
+ completeLines.push(line);
221
+ consumedLen += line.length + 1;
222
+ }
223
+ else {
224
+ // partial — leave for next pass
225
+ }
226
+ continue;
227
+ }
228
+ completeLines.push(line);
229
+ consumedLen += line.length + 1; // +1 for the newline
230
+ }
231
+ const newOffset = lastOffset + consumedLen;
232
+ if (completeLines.length === 0) {
233
+ return { modified: false, bytes: 0, lines: 0, prompts: 0, toolCalls: 0 };
234
+ }
235
+ // Project lazy upsert — keep first_seen on insert, bump last_seen on update.
236
+ const projectSlug = path.basename(path.dirname(filePath));
237
+ const projectName = decodeProjectSlug(projectSlug);
238
+ const now = Date.now();
239
+ db.prepare(`
240
+ INSERT INTO claude_projects (path, name, first_seen, last_seen)
241
+ VALUES (?, ?, ?, ?)
242
+ ON CONFLICT(path) DO UPDATE SET last_seen = excluded.last_seen
243
+ `).run(projectPath, projectName, now, now);
244
+ // Resolve the graph once per file (per project path) — avoids reopening the DB
245
+ // on every tool call. Returns null when no resolver is configured. The
246
+ // resolver can throw on a locked/corrupt index; that estimate is best-effort
247
+ // decoration and must NEVER abort transcript ingest, so degrade to null.
248
+ let graph = null;
249
+ if (options.resolveGraph) {
250
+ try {
251
+ graph = options.resolveGraph(projectPath);
252
+ }
253
+ catch {
254
+ graph = null;
255
+ }
256
+ }
257
+ // Per-file ingest in a transaction.
258
+ const txn = db.transaction(() => {
259
+ return processLines(db, filePath, projectPath, completeLines, pricing, graph);
260
+ });
261
+ const result = txn();
262
+ // Persist new offset.
263
+ db.prepare(`
264
+ INSERT INTO claude_ingest_state (file_path, last_offset, last_ingested_at, file_size, session_id)
265
+ VALUES (?, ?, ?, ?, ?)
266
+ ON CONFLICT(file_path) DO UPDATE SET
267
+ last_offset = excluded.last_offset,
268
+ last_ingested_at = excluded.last_ingested_at,
269
+ file_size = excluded.file_size,
270
+ session_id = excluded.session_id
271
+ `).run(filePath, newOffset, now, size, result.lastSessionId);
272
+ if (options.verbose) {
273
+ // eslint-disable-next-line no-console
274
+ console.error(`[ingest] ${path.basename(filePath)}: +${result.prompts} prompts, +${result.toolCalls} tools, +${consumedLen}b`);
275
+ }
276
+ return {
277
+ modified: true,
278
+ bytes: consumedLen,
279
+ lines: completeLines.length,
280
+ prompts: result.prompts,
281
+ toolCalls: result.toolCalls,
282
+ };
283
+ }
284
+ /**
285
+ * Single-pass over the entries in this file batch. We need to relate
286
+ * tool_use blocks (in assistant entries) to their tool_result blocks (in
287
+ * the next user entry) so result_length is captured. Maintain a map of
288
+ * pending tool_use_id → { promptId, name, summary, ts } as we walk.
289
+ */
290
+ function processLines(db, filePath, projectPath, completeLines, pricing, graph) {
291
+ const insSession = db.prepare(`
292
+ INSERT INTO claude_sessions (id, project_path, source_file, started_at, ended_at, prompt_count, last_model)
293
+ VALUES (?, ?, ?, ?, ?, 0, ?)
294
+ ON CONFLICT(id) DO UPDATE SET
295
+ ended_at = excluded.ended_at,
296
+ last_model = COALESCE(excluded.last_model, claude_sessions.last_model)
297
+ `);
298
+ const incSessionAggregates = db.prepare(`
299
+ UPDATE claude_sessions SET
300
+ prompt_count = prompt_count + ?,
301
+ total_input_tokens = total_input_tokens + ?,
302
+ total_output_tokens = total_output_tokens + ?,
303
+ total_cache_creation_tokens = total_cache_creation_tokens + ?,
304
+ total_cache_read_tokens = total_cache_read_tokens + ?,
305
+ total_cost_usd = total_cost_usd + ?
306
+ WHERE id = ?
307
+ `);
308
+ const insPrompt = db.prepare(`
309
+ INSERT INTO claude_prompts (id, session_id, text, ts, leaf_uuid, model, input_tokens, output_tokens, cache_creation_tokens, cache_read_tokens, cost_usd, is_sidechain)
310
+ VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)
311
+ ON CONFLICT(id) DO UPDATE SET
312
+ text = COALESCE(excluded.text, claude_prompts.text),
313
+ model = COALESCE(excluded.model, claude_prompts.model),
314
+ input_tokens = excluded.input_tokens,
315
+ output_tokens = excluded.output_tokens,
316
+ cache_creation_tokens = excluded.cache_creation_tokens,
317
+ cache_read_tokens = excluded.cache_read_tokens,
318
+ cost_usd = excluded.cost_usd
319
+ `);
320
+ const insToolCall = db.prepare(`
321
+ INSERT INTO claude_tool_calls (prompt_id, session_id, assistant_uuid, tool_use_id, tool_name, input_summary, input_json, result_length, ts, is_specship, displaced_files, resolution)
322
+ VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)
323
+ `);
324
+ /**
325
+ * Append the assistant's text + thinking blocks from one assistant turn
326
+ * onto the prompt row. A single user prompt can span multiple assistant
327
+ * turns (model re-renders / continues after a tool round-trip), so we
328
+ * concatenate with `||` instead of overwriting. Empty contributions
329
+ * (e.g. an assistant turn that's all tool_use) leave the column NULL
330
+ * if nothing was previously accumulated — kept as NULL so the UI can
331
+ * cleanly hide the section.
332
+ */
333
+ const appendPromptText = db.prepare(`
334
+ UPDATE claude_prompts SET
335
+ assistant_text = CASE
336
+ WHEN ? = '' THEN assistant_text
337
+ WHEN assistant_text IS NULL THEN ?
338
+ ELSE assistant_text || ?
339
+ END,
340
+ thinking_text = CASE
341
+ WHEN ? = '' THEN thinking_text
342
+ WHEN thinking_text IS NULL THEN ?
343
+ ELSE thinking_text || ?
344
+ END
345
+ WHERE id = ?
346
+ `);
347
+ let lastSessionId = null;
348
+ let promptsInserted = 0;
349
+ let toolCallsInserted = 0;
350
+ // Dedupe state for "user entries that share a promptId with one we
351
+ // already inserted." `insertedPromptIds` covers the in-batch case
352
+ // (sequential tool_results inside the same JSONL chunk); the prepared
353
+ // `existsPromptStmt` covers the cross-batch case (tool_results that
354
+ // arrive after the original prompt landed in a previous batch).
355
+ const insertedPromptIds = new Set();
356
+ const existsPromptStmt = db.prepare(`SELECT 1 FROM claude_prompts WHERE id = ?`);
357
+ // Track active prompt context. Only user entries carry a `promptId` in the
358
+ // JSONL — assistant entries belong to whichever prompt the most-recent user
359
+ // entry started. When we resume from a saved offset, the first lines in the
360
+ // batch are typically assistant turns answering a prompt whose user entry
361
+ // landed in an earlier batch, so `activePromptId` starts null and we must
362
+ // recover it from the DB; otherwise tool_use blocks queue with a fabricated
363
+ // promptId and the eventual tool_result insert violates the prompt_id FK,
364
+ // rolling back the whole batch transaction and stalling the file forever.
365
+ let activePromptId = null;
366
+ const lookupLatestPrompt = db.prepare(`SELECT id FROM claude_prompts WHERE session_id = ? ORDER BY ts DESC LIMIT 1`);
367
+ const resolveActivePromptId = (sessionId) => {
368
+ if (activePromptId)
369
+ return activePromptId;
370
+ const row = lookupLatestPrompt.get(sessionId);
371
+ if (row?.id)
372
+ activePromptId = row.id;
373
+ return activePromptId;
374
+ };
375
+ const pendingTools = new Map();
376
+ for (const raw of completeLines) {
377
+ const entry = parseLine(raw);
378
+ if (!entry)
379
+ continue;
380
+ const sessionId = entry.sessionId ?? '';
381
+ if (!sessionId)
382
+ continue;
383
+ lastSessionId = sessionId;
384
+ const ts = toEpochMs(entry.timestamp);
385
+ if (entry.type === 'user') {
386
+ // Bookkeep session row first.
387
+ insSession.run(sessionId, projectPath, filePath, ts, ts, null);
388
+ const text = extractUserPrompt(entry);
389
+ const promptId = entry.promptId ?? entry.uuid ?? null;
390
+ const isSidechain = entry.isSidechain ? 1 : 0;
391
+ if (promptId) {
392
+ activePromptId = promptId;
393
+ // Claude Code emits MULTIPLE user-type entries per logical prompt:
394
+ // the initial user message + one entry per tool_result the assistant
395
+ // requested. All share the same `promptId`. The original ingestor
396
+ // ran insPrompt + bumped prompt_count for every one of them — so a
397
+ // 50-prompt session with ~15 tool calls each landed in the DB as
398
+ // 800+ "prompts" and the per-prompt token columns were repeatedly
399
+ // reset to 0 via the ON CONFLICT DO UPDATE clause. Detect follow-up
400
+ // tool_result entries by checking whether the prompt row already
401
+ // exists (in this batch or persisted from an earlier batch) and
402
+ // skip both the upsert and the aggregate bump for them.
403
+ const isFollowUp = insertedPromptIds.has(promptId) ||
404
+ !!existsPromptStmt.get(promptId);
405
+ if (!isFollowUp) {
406
+ // First time we've seen this promptId — INSERT, count it, mark seen.
407
+ insPrompt.run(promptId, sessionId, text || null, ts, entry.leafUuid ?? null, null, 0, 0, 0, 0, 0, isSidechain);
408
+ promptsInserted++;
409
+ insertedPromptIds.add(promptId);
410
+ incSessionAggregates.run(1, 0, 0, 0, 0, 0, sessionId);
411
+ }
412
+ }
413
+ // Handle tool_result blocks: scan content for tool_result entries and
414
+ // update the matching pending tool_call row's result_length.
415
+ const content = entry.message?.content;
416
+ if (Array.isArray(content)) {
417
+ for (const block of content) {
418
+ if (block && block.type === 'tool_result' && block.tool_use_id) {
419
+ const len = toolResultLength(block);
420
+ const pending = pendingTools.get(block.tool_use_id);
421
+ if (pending) {
422
+ const cls = classifyToolCall({ toolName: pending.toolName, inputJson: pending.inputJson, resultLength: len }, graph);
423
+ insToolCall.run(pending.promptId, pending.sessionId, pending.assistantUuid, block.tool_use_id, pending.toolName, pending.summary, pending.inputJson, len, pending.ts, cls.isSpecship, cls.displacedFiles, cls.resolution);
424
+ toolCallsInserted++;
425
+ pendingTools.delete(block.tool_use_id);
426
+ }
427
+ }
428
+ }
429
+ }
430
+ }
431
+ else if (entry.type === 'assistant') {
432
+ // Make sure session row exists.
433
+ insSession.run(sessionId, projectPath, filePath, ts, ts, entry.message?.model ?? null);
434
+ // Resolve the prompt this assistant turn belongs to. Never fall back to
435
+ // `entry.uuid` — that's the assistant's per-message id, not a row in
436
+ // claude_prompts, and using it would re-introduce the FK violation that
437
+ // caused this entire path to stall.
438
+ const promptId = resolveActivePromptId(sessionId);
439
+ if (!promptId)
440
+ continue;
441
+ const usage = entry.message?.usage;
442
+ const inputTok = usage?.input_tokens ?? 0;
443
+ const outputTok = usage?.output_tokens ?? 0;
444
+ const cacheCreate = usage?.cache_creation_input_tokens ?? 0;
445
+ const cacheRead = usage?.cache_read_input_tokens ?? 0;
446
+ const pricingRow = resolvePricing(entry.message?.model, pricing);
447
+ const cost = computeCost(usage, pricingRow);
448
+ // Update prompt's running usage. Re-uses ON CONFLICT to ADD to existing.
449
+ // Since INSERT...ON CONFLICT DO UPDATE replaces (not increments), do an
450
+ // explicit UPDATE here for the additive case.
451
+ db.prepare(`
452
+ UPDATE claude_prompts SET
453
+ input_tokens = input_tokens + ?,
454
+ output_tokens = output_tokens + ?,
455
+ cache_creation_tokens = cache_creation_tokens + ?,
456
+ cache_read_tokens = cache_read_tokens + ?,
457
+ cost_usd = cost_usd + ?,
458
+ model = COALESCE(?, model)
459
+ WHERE id = ?
460
+ `).run(inputTok, outputTok, cacheCreate, cacheRead, cost, entry.message?.model ?? null, promptId);
461
+ // Session aggregates: only token totals + cost. prompt_count was bumped
462
+ // when the user entry landed.
463
+ incSessionAggregates.run(0, inputTok, outputTok, cacheCreate, cacheRead, cost, sessionId);
464
+ // Scan content for tool_use, text, and thinking blocks. tool_use →
465
+ // queued for a later tool_result match; text + thinking → appended
466
+ // onto the prompt row so the dashboard can show the assistant's
467
+ // actual response, not just token counts. One pass over the array
468
+ // so we don't iterate twice on what can be a large list.
469
+ const content = entry.message?.content;
470
+ const assistantUuid = entry.uuid ?? '';
471
+ let assistantTextChunk = '';
472
+ let thinkingTextChunk = '';
473
+ if (Array.isArray(content)) {
474
+ for (const block of content) {
475
+ if (!block)
476
+ continue;
477
+ if (block.type === 'tool_use' && block.id && block.name && assistantUuid) {
478
+ // JSON-stringify the full input. Schema column is TEXT;
479
+ // large inputs (e.g. Bash with long heredocs) are fine as-is.
480
+ // Falsy / undefined / circular inputs degrade to a quiet null
481
+ // rather than throwing — the summary column still captures
482
+ // a display value.
483
+ let inputJson = null;
484
+ try {
485
+ inputJson = JSON.stringify(block.input ?? null);
486
+ }
487
+ catch {
488
+ inputJson = null;
489
+ }
490
+ pendingTools.set(block.id, {
491
+ promptId,
492
+ sessionId,
493
+ assistantUuid,
494
+ toolName: block.name,
495
+ summary: summarizeToolInput(block.name, block.input),
496
+ inputJson,
497
+ ts,
498
+ });
499
+ }
500
+ else if (block.type === 'text' && typeof block.text === 'string') {
501
+ // The assistant's prose response. Concatenated with the
502
+ // existing assistant_text via the appendPromptText UPDATE
503
+ // below — one prompt can span multiple assistant turns.
504
+ assistantTextChunk += block.text;
505
+ }
506
+ else if (block.type === 'thinking' && typeof block.text === 'string') {
507
+ // Extended thinking. Same accumulation pattern as text.
508
+ thinkingTextChunk += block.text;
509
+ }
510
+ }
511
+ }
512
+ if (assistantTextChunk || thinkingTextChunk) {
513
+ // Separate consecutive turn contributions with a blank line so
514
+ // multi-turn responses render with paragraph breaks instead of
515
+ // collapsing into a single run-on block.
516
+ const at = assistantTextChunk ? assistantTextChunk + '\n\n' : '';
517
+ const tt = thinkingTextChunk ? thinkingTextChunk + '\n\n' : '';
518
+ appendPromptText.run(at, at, at, tt, tt, tt, promptId);
519
+ }
520
+ }
521
+ // attachment / queue-operation / last-prompt entries are ignored for v1.
522
+ }
523
+ // Any remaining pendingTools didn't have a tool_result yet — they'll be
524
+ // matched on the next pass when the user reply arrives. We flush them with
525
+ // result_length=0 so the tool call still shows up in analytics (better to
526
+ // show "0 tokens returned" than to omit the call).
527
+ for (const [toolUseId, pending] of pendingTools) {
528
+ // result_length=0 for pending/unmatched tools → classifyToolCall returns 'n/a' for specship.
529
+ const cls = classifyToolCall({ toolName: pending.toolName, inputJson: pending.inputJson, resultLength: 0 }, graph);
530
+ insToolCall.run(pending.promptId, pending.sessionId, pending.assistantUuid, toolUseId, pending.toolName, pending.summary, pending.inputJson, 0, pending.ts, cls.isSpecship, cls.displacedFiles, cls.resolution);
531
+ toolCallsInserted++;
532
+ }
533
+ return {
534
+ modified: true,
535
+ bytes: 0,
536
+ lines: completeLines.length,
537
+ prompts: promptsInserted,
538
+ toolCalls: toolCallsInserted,
539
+ lastSessionId,
540
+ };
541
+ }
@@ -0,0 +1,104 @@
1
+ /**
2
+ * JSONL line parser — converts one line of a Claude Code transcript into a
3
+ * structured ClaudeRawEntry, or null for unparseable / unrecognised lines.
4
+ *
5
+ * Tolerant: a malformed line never throws; the worker logs and skips it.
6
+ */
7
+ export function parseLine(line) {
8
+ const trimmed = line.trim();
9
+ if (!trimmed)
10
+ return null;
11
+ try {
12
+ const obj = JSON.parse(trimmed);
13
+ if (!obj || typeof obj !== 'object' || typeof obj.type !== 'string') {
14
+ return null;
15
+ }
16
+ return obj;
17
+ }
18
+ catch {
19
+ return null;
20
+ }
21
+ }
22
+ /** Convert a timestamp field (ISO string or epoch number) to epoch ms. */
23
+ export function toEpochMs(ts) {
24
+ if (ts == null)
25
+ return Date.now();
26
+ if (typeof ts === 'number') {
27
+ // Heuristic: 10-digit values are seconds, 13-digit are ms.
28
+ return ts > 1e12 ? ts : ts * 1000;
29
+ }
30
+ const parsed = Date.parse(ts);
31
+ return Number.isFinite(parsed) ? parsed : Date.now();
32
+ }
33
+ /** Extract the user-visible prompt text from a user-entry message. */
34
+ export function extractUserPrompt(entry) {
35
+ // Some user entries store text at the top level; most use message.content.
36
+ if (typeof entry.text === 'string' && entry.text.length > 0)
37
+ return entry.text;
38
+ const content = entry.message?.content;
39
+ if (typeof content === 'string')
40
+ return content;
41
+ if (Array.isArray(content)) {
42
+ return content
43
+ .filter((b) => b && typeof b === 'object')
44
+ .map((b) => (b.type === 'text' && typeof b.text === 'string' ? b.text : ''))
45
+ .filter((t) => t.length > 0)
46
+ .join('\n')
47
+ .trim();
48
+ }
49
+ return '';
50
+ }
51
+ /**
52
+ * For a tool_use block, build a short, format-aware input summary:
53
+ * - Read/Edit/Write → file path
54
+ * - Bash → first 200 chars of command
55
+ * - others → JSON of input, truncated to 200 chars
56
+ *
57
+ * This is what shows up in the heatmap drill-down and the tips engine.
58
+ */
59
+ export function summarizeToolInput(name, input) {
60
+ if (!input || typeof input !== 'object')
61
+ return '';
62
+ const n = name.toLowerCase();
63
+ // File-targeted tools
64
+ if (n === 'read' || n === 'edit' || n === 'write' || n === 'notebookedit') {
65
+ const p = (input.file_path ?? input.path ?? input.notebook_path);
66
+ if (typeof p === 'string')
67
+ return p.slice(0, 400);
68
+ }
69
+ if (n === 'glob') {
70
+ const p = (input.pattern ?? input.glob);
71
+ if (typeof p === 'string')
72
+ return p.slice(0, 400);
73
+ }
74
+ if (n === 'grep') {
75
+ const p = (input.pattern ?? input.query);
76
+ if (typeof p === 'string')
77
+ return p.slice(0, 400);
78
+ }
79
+ if (n === 'bash' || n === 'shell') {
80
+ const c = (input.command ?? input.cmd);
81
+ if (typeof c === 'string')
82
+ return c.slice(0, 400);
83
+ }
84
+ // MCP tool — input.tool_name + JSON keys
85
+ try {
86
+ const j = JSON.stringify(input);
87
+ return j.length > 400 ? j.slice(0, 400) + '…' : j;
88
+ }
89
+ catch {
90
+ return '';
91
+ }
92
+ }
93
+ /** Sum the character length of a tool_result content block. */
94
+ export function toolResultLength(block) {
95
+ if (!block)
96
+ return 0;
97
+ const c = block.content;
98
+ if (typeof c === 'string')
99
+ return c.length;
100
+ if (Array.isArray(c)) {
101
+ return c.reduce((sum, item) => sum + (typeof item?.text === 'string' ? item.text.length : 0), 0);
102
+ }
103
+ return 0;
104
+ }