gitnexus 1.6.6-rc.98 → 1.6.6

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 (541) hide show
  1. package/README.md +122 -68
  2. package/dist/_shared/graph/types.d.ts +17 -1
  3. package/dist/_shared/graph/types.d.ts.map +1 -1
  4. package/dist/_shared/index.d.ts +3 -5
  5. package/dist/_shared/index.d.ts.map +1 -1
  6. package/dist/_shared/index.js +2 -4
  7. package/dist/_shared/index.js.map +1 -1
  8. package/dist/_shared/scope-resolution/module-scope-index.d.ts +1 -2
  9. package/dist/_shared/scope-resolution/module-scope-index.d.ts.map +1 -1
  10. package/dist/_shared/scope-resolution/module-scope-index.js +1 -2
  11. package/dist/_shared/scope-resolution/module-scope-index.js.map +1 -1
  12. package/dist/_shared/scope-resolution/parsed-file.d.ts +24 -0
  13. package/dist/_shared/scope-resolution/parsed-file.d.ts.map +1 -1
  14. package/dist/_shared/scope-resolution/reference-site.d.ts +13 -1
  15. package/dist/_shared/scope-resolution/reference-site.d.ts.map +1 -1
  16. package/dist/_shared/scope-resolution/registries/context.d.ts +1 -0
  17. package/dist/_shared/scope-resolution/registries/context.d.ts.map +1 -1
  18. package/dist/_shared/scope-resolution/registries/context.js +6 -0
  19. package/dist/_shared/scope-resolution/registries/context.js.map +1 -1
  20. package/dist/_shared/scope-resolution/registries/evidence.d.ts +2 -3
  21. package/dist/_shared/scope-resolution/registries/evidence.d.ts.map +1 -1
  22. package/dist/_shared/scope-resolution/registries/evidence.js +2 -3
  23. package/dist/_shared/scope-resolution/registries/evidence.js.map +1 -1
  24. package/dist/_shared/scope-resolution/registries/macro-registry.d.ts +29 -0
  25. package/dist/_shared/scope-resolution/registries/macro-registry.d.ts.map +1 -0
  26. package/dist/_shared/scope-resolution/registries/macro-registry.js +32 -0
  27. package/dist/_shared/scope-resolution/registries/macro-registry.js.map +1 -0
  28. package/dist/_shared/scope-resolution/symbol-definition.d.ts +9 -0
  29. package/dist/_shared/scope-resolution/symbol-definition.d.ts.map +1 -1
  30. package/dist/_shared/scope-resolution/types.d.ts +1 -1
  31. package/dist/_shared/scope-resolution/types.d.ts.map +1 -1
  32. package/dist/cli/ai-context.d.ts +35 -1
  33. package/dist/cli/ai-context.js +111 -12
  34. package/dist/cli/analyze-config.d.ts +92 -0
  35. package/dist/cli/analyze-config.js +364 -0
  36. package/dist/cli/analyze.d.ts +17 -1
  37. package/dist/cli/analyze.js +224 -71
  38. package/dist/cli/cli-message.d.ts +1 -1
  39. package/dist/cli/doctor.d.ts +18 -0
  40. package/dist/cli/doctor.js +32 -0
  41. package/dist/cli/i18n/en.d.ts +2 -2
  42. package/dist/cli/i18n/en.js +2 -2
  43. package/dist/cli/i18n/resources.d.ts +2 -2
  44. package/dist/cli/i18n/zh-CN.js +2 -2
  45. package/dist/cli/index.js +4 -2
  46. package/dist/cli/resolve-invocation.d.ts +21 -0
  47. package/dist/cli/resolve-invocation.js +68 -0
  48. package/dist/cli/setup.d.ts +33 -0
  49. package/dist/cli/setup.js +96 -35
  50. package/dist/cli/skill-gen.js +2 -2
  51. package/dist/cli/wiki.js +20 -4
  52. package/dist/core/embeddings/embedder.d.ts +1 -1
  53. package/dist/core/embeddings/embedder.js +14 -1
  54. package/dist/core/embeddings/runtime-support.d.ts +41 -0
  55. package/dist/core/embeddings/runtime-support.js +65 -0
  56. package/dist/core/group/extractors/grpc-patterns/proto.js +2 -1
  57. package/dist/core/group/extractors/http-patterns/java.js +15 -1
  58. package/dist/core/ingestion/call-processor.d.ts +57 -227
  59. package/dist/core/ingestion/call-processor.js +172 -2595
  60. package/dist/core/ingestion/call-routing.d.ts +6 -5
  61. package/dist/core/ingestion/call-routing.js +6 -6
  62. package/dist/core/ingestion/call-types.d.ts +0 -75
  63. package/dist/core/ingestion/class-extractors/configs/c-cpp.js +26 -1
  64. package/dist/core/ingestion/class-extractors/configs/ruby.js +3 -0
  65. package/dist/core/ingestion/class-extractors/generic.js +9 -11
  66. package/dist/core/ingestion/class-types.d.ts +23 -0
  67. package/dist/core/ingestion/cobol/cobol-preprocessor.d.ts +11 -0
  68. package/dist/core/ingestion/cobol/cobol-preprocessor.js +227 -73
  69. package/dist/core/ingestion/cobol-processor.d.ts +1 -0
  70. package/dist/core/ingestion/cobol-processor.js +51 -2
  71. package/dist/core/ingestion/emit-references.js +8 -2
  72. package/dist/core/ingestion/export-detection.d.ts +2 -1
  73. package/dist/core/ingestion/export-detection.js +2 -6
  74. package/dist/core/ingestion/field-extractors/configs/dart.d.ts +0 -6
  75. package/dist/core/ingestion/field-extractors/configs/dart.js +62 -44
  76. package/dist/core/ingestion/field-extractors/configs/go.d.ts +0 -9
  77. package/dist/core/ingestion/field-extractors/configs/go.js +40 -1
  78. package/dist/core/ingestion/field-extractors/configs/jvm.js +43 -4
  79. package/dist/core/ingestion/field-extractors/configs/php.js +1 -2
  80. package/dist/core/ingestion/field-extractors/configs/swift.d.ts +12 -1
  81. package/dist/core/ingestion/field-extractors/configs/swift.js +31 -6
  82. package/dist/core/ingestion/field-extractors/generic.d.ts +6 -0
  83. package/dist/core/ingestion/field-extractors/generic.js +5 -4
  84. package/dist/core/ingestion/field-extractors/typescript.js +0 -29
  85. package/dist/core/ingestion/filesystem-walker.d.ts +0 -9
  86. package/dist/core/ingestion/filesystem-walker.js +0 -11
  87. package/dist/core/ingestion/finalize-orchestrator.js +14 -2
  88. package/dist/core/ingestion/import-resolvers/configs/swift.d.ts +21 -0
  89. package/dist/core/ingestion/import-resolvers/configs/swift.js +72 -11
  90. package/dist/core/ingestion/import-resolvers/python.d.ts +1 -1
  91. package/dist/core/ingestion/import-resolvers/standard.d.ts +2 -2
  92. package/dist/core/ingestion/import-resolvers/standard.js +6 -5
  93. package/dist/core/ingestion/import-resolvers/utils.d.ts +2 -5
  94. package/dist/core/ingestion/import-resolvers/utils.js +1 -9
  95. package/dist/core/ingestion/language-provider.d.ts +39 -119
  96. package/dist/core/ingestion/language-provider.js +0 -2
  97. package/dist/core/ingestion/languages/c/capture-side-channel.d.ts +62 -0
  98. package/dist/core/ingestion/languages/c/capture-side-channel.js +65 -0
  99. package/dist/core/ingestion/languages/c/captures.js +41 -23
  100. package/dist/core/ingestion/languages/c/import-decomposer.d.ts +9 -0
  101. package/dist/core/ingestion/languages/c/import-decomposer.js +15 -0
  102. package/dist/core/ingestion/languages/c/import-target.js +52 -9
  103. package/dist/core/ingestion/languages/c/index.d.ts +2 -1
  104. package/dist/core/ingestion/languages/c/index.js +2 -1
  105. package/dist/core/ingestion/languages/c/query.js +15 -0
  106. package/dist/core/ingestion/languages/c/scope-resolver.js +47 -4
  107. package/dist/core/ingestion/languages/c/static-linkage.d.ts +8 -0
  108. package/dist/core/ingestion/languages/c/static-linkage.js +46 -1
  109. package/dist/core/ingestion/languages/c-cpp.js +16 -7
  110. package/dist/core/ingestion/languages/cobol/captures.js +25 -2
  111. package/dist/core/ingestion/languages/cpp/adl.d.ts +88 -4
  112. package/dist/core/ingestion/languages/cpp/adl.js +380 -160
  113. package/dist/core/ingestion/languages/cpp/arity-metadata.js +2 -8
  114. package/dist/core/ingestion/languages/cpp/capture-side-channel.d.ts +65 -0
  115. package/dist/core/ingestion/languages/cpp/capture-side-channel.js +78 -0
  116. package/dist/core/ingestion/languages/cpp/captures.js +162 -54
  117. package/dist/core/ingestion/languages/cpp/file-local-linkage.d.ts +18 -52
  118. package/dist/core/ingestion/languages/cpp/file-local-linkage.js +49 -1
  119. package/dist/core/ingestion/languages/cpp/import-decomposer.d.ts +7 -0
  120. package/dist/core/ingestion/languages/cpp/import-decomposer.js +12 -0
  121. package/dist/core/ingestion/languages/cpp/index.d.ts +1 -0
  122. package/dist/core/ingestion/languages/cpp/index.js +1 -0
  123. package/dist/core/ingestion/languages/cpp/inline-namespaces.d.ts +8 -0
  124. package/dist/core/ingestion/languages/cpp/inline-namespaces.js +21 -0
  125. package/dist/core/ingestion/languages/cpp/query.js +21 -0
  126. package/dist/core/ingestion/languages/cpp/range-bindings.js +20 -5
  127. package/dist/core/ingestion/languages/cpp/scope-resolver.js +52 -5
  128. package/dist/core/ingestion/languages/cpp/two-phase-lookup.d.ts +20 -0
  129. package/dist/core/ingestion/languages/cpp/two-phase-lookup.js +83 -3
  130. package/dist/core/ingestion/languages/csharp/captures.js +205 -41
  131. package/dist/core/ingestion/languages/csharp/index.d.ts +3 -4
  132. package/dist/core/ingestion/languages/csharp/index.js +3 -4
  133. package/dist/core/ingestion/languages/csharp/interpret.js +17 -3
  134. package/dist/core/ingestion/languages/csharp/namespace-siblings.d.ts +17 -7
  135. package/dist/core/ingestion/languages/csharp/namespace-siblings.js +129 -124
  136. package/dist/core/ingestion/languages/csharp/qualified-type-names.d.ts +14 -0
  137. package/dist/core/ingestion/languages/csharp/qualified-type-names.js +59 -0
  138. package/dist/core/ingestion/languages/csharp/query.js +13 -0
  139. package/dist/core/ingestion/languages/csharp/receiver-binding.js +10 -6
  140. package/dist/core/ingestion/languages/csharp/scope-resolver.js +8 -1
  141. package/dist/core/ingestion/languages/csharp.js +0 -5
  142. package/dist/core/ingestion/languages/dart/arity-metadata.d.ts +25 -0
  143. package/dist/core/ingestion/languages/dart/arity-metadata.js +35 -0
  144. package/dist/core/ingestion/languages/dart/arity.d.ts +19 -0
  145. package/dist/core/ingestion/languages/dart/arity.js +31 -0
  146. package/dist/core/ingestion/languages/dart/built-ins.d.ts +11 -0
  147. package/dist/core/ingestion/languages/dart/built-ins.js +34 -0
  148. package/dist/core/ingestion/languages/dart/cache-stats.d.ts +13 -0
  149. package/dist/core/ingestion/languages/dart/cache-stats.js +24 -0
  150. package/dist/core/ingestion/languages/dart/captures.d.ts +29 -0
  151. package/dist/core/ingestion/languages/dart/captures.js +445 -0
  152. package/dist/core/ingestion/languages/dart/expand-wildcards.d.ts +13 -0
  153. package/dist/core/ingestion/languages/dart/expand-wildcards.js +31 -0
  154. package/dist/core/ingestion/languages/dart/import-target.d.ts +15 -0
  155. package/dist/core/ingestion/languages/dart/import-target.js +65 -0
  156. package/dist/core/ingestion/languages/dart/index.d.ts +28 -0
  157. package/dist/core/ingestion/languages/dart/index.js +28 -0
  158. package/dist/core/ingestion/languages/dart/interpret.d.ts +24 -0
  159. package/dist/core/ingestion/languages/dart/interpret.js +95 -0
  160. package/dist/core/ingestion/languages/dart/merge-bindings.d.ts +10 -0
  161. package/dist/core/ingestion/languages/dart/merge-bindings.js +39 -0
  162. package/dist/core/ingestion/languages/dart/query.d.ts +26 -0
  163. package/dist/core/ingestion/languages/dart/query.js +142 -0
  164. package/dist/core/ingestion/languages/dart/receiver-binding.d.ts +24 -0
  165. package/dist/core/ingestion/languages/dart/receiver-binding.js +87 -0
  166. package/dist/core/ingestion/languages/dart/scope-resolver.d.ts +29 -0
  167. package/dist/core/ingestion/languages/dart/scope-resolver.js +194 -0
  168. package/dist/core/ingestion/languages/dart/signature-bindings.d.ts +23 -0
  169. package/dist/core/ingestion/languages/dart/signature-bindings.js +51 -0
  170. package/dist/core/ingestion/languages/dart/simple-hooks.d.ts +20 -0
  171. package/dist/core/ingestion/languages/dart/simple-hooks.js +47 -0
  172. package/dist/core/ingestion/languages/dart.d.ts +0 -1
  173. package/dist/core/ingestion/languages/dart.js +15 -29
  174. package/dist/core/ingestion/languages/go/arity-metadata.d.ts +1 -0
  175. package/dist/core/ingestion/languages/go/arity-metadata.js +31 -1
  176. package/dist/core/ingestion/languages/go/captures.js +247 -26
  177. package/dist/core/ingestion/languages/go/interface-impls.js +476 -50
  178. package/dist/core/ingestion/languages/go/interpret.js +21 -11
  179. package/dist/core/ingestion/languages/go/method-owners.js +20 -8
  180. package/dist/core/ingestion/languages/go/query.js +15 -7
  181. package/dist/core/ingestion/languages/go/range-binding.js +24 -9
  182. package/dist/core/ingestion/languages/go/receiver-binding.js +1 -1
  183. package/dist/core/ingestion/languages/go/scope-resolver.js +2 -2
  184. package/dist/core/ingestion/languages/go/simple-hooks.js +10 -5
  185. package/dist/core/ingestion/languages/go/type-binding.d.ts +1 -0
  186. package/dist/core/ingestion/languages/go/type-binding.js +40 -2
  187. package/dist/core/ingestion/languages/go.d.ts +0 -1
  188. package/dist/core/ingestion/languages/go.js +0 -5
  189. package/dist/core/ingestion/languages/index.d.ts +0 -5
  190. package/dist/core/ingestion/languages/index.js +0 -3
  191. package/dist/core/ingestion/languages/java/captures.js +252 -23
  192. package/dist/core/ingestion/languages/java/interpret.js +12 -6
  193. package/dist/core/ingestion/languages/java/package-siblings.js +18 -5
  194. package/dist/core/ingestion/languages/java/query.js +16 -1
  195. package/dist/core/ingestion/languages/java/scope-resolver.d.ts +2 -8
  196. package/dist/core/ingestion/languages/java/scope-resolver.js +2 -8
  197. package/dist/core/ingestion/languages/java.js +0 -5
  198. package/dist/core/ingestion/languages/javascript/captures.js +185 -11
  199. package/dist/core/ingestion/languages/javascript/query.js +107 -1
  200. package/dist/core/ingestion/languages/kotlin/capture-side-channel.d.ts +57 -0
  201. package/dist/core/ingestion/languages/kotlin/capture-side-channel.js +60 -0
  202. package/dist/core/ingestion/languages/kotlin/captures.js +213 -22
  203. package/dist/core/ingestion/languages/kotlin/companion-scopes.d.ts +7 -0
  204. package/dist/core/ingestion/languages/kotlin/companion-scopes.js +10 -0
  205. package/dist/core/ingestion/languages/kotlin/index.d.ts +1 -0
  206. package/dist/core/ingestion/languages/kotlin/index.js +1 -0
  207. package/dist/core/ingestion/languages/kotlin/query.js +30 -0
  208. package/dist/core/ingestion/languages/kotlin/scope-resolver.d.ts +5 -7
  209. package/dist/core/ingestion/languages/kotlin/scope-resolver.js +22 -7
  210. package/dist/core/ingestion/languages/kotlin.js +8 -5
  211. package/dist/core/ingestion/languages/php/captures.js +135 -19
  212. package/dist/core/ingestion/languages/php/import-decomposer.js +21 -63
  213. package/dist/core/ingestion/languages/php/index.d.ts +3 -4
  214. package/dist/core/ingestion/languages/php/index.js +3 -4
  215. package/dist/core/ingestion/languages/php/query.js +5 -0
  216. package/dist/core/ingestion/languages/php/receiver-binding.js +8 -4
  217. package/dist/core/ingestion/languages/php.js +0 -4
  218. package/dist/core/ingestion/languages/python/captures.js +128 -13
  219. package/dist/core/ingestion/languages/python/depends-references.js +1 -1
  220. package/dist/core/ingestion/languages/python/import-target.d.ts +4 -5
  221. package/dist/core/ingestion/languages/python/import-target.js +108 -16
  222. package/dist/core/ingestion/languages/python/index-stats.d.ts +18 -0
  223. package/dist/core/ingestion/languages/python/index-stats.js +25 -0
  224. package/dist/core/ingestion/languages/python/index.d.ts +3 -4
  225. package/dist/core/ingestion/languages/python/index.js +3 -4
  226. package/dist/core/ingestion/languages/python/query.js +17 -0
  227. package/dist/core/ingestion/languages/python/scope-resolver.js +7 -6
  228. package/dist/core/ingestion/languages/python.d.ts +0 -2
  229. package/dist/core/ingestion/languages/python.js +0 -7
  230. package/dist/core/ingestion/languages/ruby/captures.js +174 -31
  231. package/dist/core/ingestion/languages/ruby/import-target.js +2 -1
  232. package/dist/core/ingestion/languages/ruby/interpret.js +2 -1
  233. package/dist/core/ingestion/languages/ruby/query.js +10 -0
  234. package/dist/core/ingestion/languages/ruby/scope-resolver.js +61 -11
  235. package/dist/core/ingestion/languages/ruby.js +4 -53
  236. package/dist/core/ingestion/languages/rust/captures.js +95 -13
  237. package/dist/core/ingestion/languages/rust/query.js +64 -1
  238. package/dist/core/ingestion/languages/rust/range-binding.js +40 -12
  239. package/dist/core/ingestion/languages/rust/receiver-binding.js +9 -0
  240. package/dist/core/ingestion/languages/rust/scope-resolver.js +75 -1
  241. package/dist/core/ingestion/languages/rust.d.ts +0 -2
  242. package/dist/core/ingestion/languages/rust.js +0 -6
  243. package/dist/core/ingestion/languages/swift/arity-metadata.d.ts +24 -0
  244. package/dist/core/ingestion/languages/swift/arity-metadata.js +41 -0
  245. package/dist/core/ingestion/languages/swift/arity.d.ts +29 -0
  246. package/dist/core/ingestion/languages/swift/arity.js +42 -0
  247. package/dist/core/ingestion/languages/swift/base-type.d.ts +20 -0
  248. package/dist/core/ingestion/languages/swift/base-type.js +27 -0
  249. package/dist/core/ingestion/languages/swift/cache-stats.d.ts +15 -0
  250. package/dist/core/ingestion/languages/swift/cache-stats.js +26 -0
  251. package/dist/core/ingestion/languages/swift/captures.d.ts +35 -0
  252. package/dist/core/ingestion/languages/swift/captures.js +495 -0
  253. package/dist/core/ingestion/languages/swift/implicit-imports.d.ts +34 -0
  254. package/dist/core/ingestion/languages/swift/implicit-imports.js +57 -0
  255. package/dist/core/ingestion/languages/swift/import-decomposer.d.ts +24 -0
  256. package/dist/core/ingestion/languages/swift/import-decomposer.js +84 -0
  257. package/dist/core/ingestion/languages/swift/import-target.d.ts +33 -0
  258. package/dist/core/ingestion/languages/swift/import-target.js +81 -0
  259. package/dist/core/ingestion/languages/swift/index.d.ts +37 -0
  260. package/dist/core/ingestion/languages/swift/index.js +37 -0
  261. package/dist/core/ingestion/languages/swift/interpret.d.ts +15 -0
  262. package/dist/core/ingestion/languages/swift/interpret.js +89 -0
  263. package/dist/core/ingestion/languages/swift/merge-bindings.d.ts +20 -0
  264. package/dist/core/ingestion/languages/swift/merge-bindings.js +48 -0
  265. package/dist/core/ingestion/languages/swift/query.d.ts +46 -0
  266. package/dist/core/ingestion/languages/swift/query.js +194 -0
  267. package/dist/core/ingestion/languages/swift/receiver-binding.d.ts +40 -0
  268. package/dist/core/ingestion/languages/swift/receiver-binding.js +161 -0
  269. package/dist/core/ingestion/languages/swift/scope-resolver.d.ts +50 -0
  270. package/dist/core/ingestion/languages/swift/scope-resolver.js +189 -0
  271. package/dist/core/ingestion/languages/swift/sibling-type-bindings.d.ts +34 -0
  272. package/dist/core/ingestion/languages/swift/sibling-type-bindings.js +65 -0
  273. package/dist/core/ingestion/languages/swift/signature-bindings.d.ts +25 -0
  274. package/dist/core/ingestion/languages/swift/signature-bindings.js +66 -0
  275. package/dist/core/ingestion/languages/swift/simple-hooks.d.ts +37 -0
  276. package/dist/core/ingestion/languages/swift/simple-hooks.js +60 -0
  277. package/dist/core/ingestion/languages/swift/target-grouping.d.ts +51 -0
  278. package/dist/core/ingestion/languages/swift/target-grouping.js +93 -0
  279. package/dist/core/ingestion/languages/swift/target-siblings.d.ts +30 -0
  280. package/dist/core/ingestion/languages/swift/target-siblings.js +71 -0
  281. package/dist/core/ingestion/languages/swift.d.ts +0 -5
  282. package/dist/core/ingestion/languages/swift.js +11 -87
  283. package/dist/core/ingestion/languages/typescript/array-callback.d.ts +3 -29
  284. package/dist/core/ingestion/languages/typescript/array-callback.js +4 -43
  285. package/dist/core/ingestion/languages/typescript/captures.js +147 -17
  286. package/dist/core/ingestion/languages/typescript/index.d.ts +3 -4
  287. package/dist/core/ingestion/languages/typescript/index.js +3 -4
  288. package/dist/core/ingestion/languages/typescript/query.d.ts +2 -3
  289. package/dist/core/ingestion/languages/typescript/query.js +125 -4
  290. package/dist/core/ingestion/languages/typescript/receiver-binding.js +0 -1
  291. package/dist/core/ingestion/languages/typescript.d.ts +2 -3
  292. package/dist/core/ingestion/languages/typescript.js +46 -23
  293. package/dist/core/ingestion/languages/vue/captures.d.ts +46 -0
  294. package/dist/core/ingestion/languages/vue/captures.js +67 -0
  295. package/dist/core/ingestion/languages/vue/import-target.d.ts +27 -0
  296. package/dist/core/ingestion/languages/vue/import-target.js +58 -0
  297. package/dist/core/ingestion/languages/vue/index.d.ts +49 -0
  298. package/dist/core/ingestion/languages/vue/index.js +49 -0
  299. package/dist/core/ingestion/languages/vue/scope-resolver.d.ts +55 -0
  300. package/dist/core/ingestion/languages/vue/scope-resolver.js +292 -0
  301. package/dist/core/ingestion/languages/vue.js +12 -4
  302. package/dist/core/ingestion/local-symbol-pruner.d.ts +11 -0
  303. package/dist/core/ingestion/local-symbol-pruner.js +63 -0
  304. package/dist/core/ingestion/method-extractors/configs/dart.js +14 -1
  305. package/dist/core/ingestion/method-extractors/configs/jvm.js +37 -20
  306. package/dist/core/ingestion/method-extractors/configs/php.js +0 -1
  307. package/dist/core/ingestion/method-extractors/configs/swift.js +11 -4
  308. package/dist/core/ingestion/method-types.d.ts +2 -2
  309. package/dist/core/ingestion/model/index.d.ts +0 -3
  310. package/dist/core/ingestion/model/index.js +0 -8
  311. package/dist/core/ingestion/model/resolve.d.ts +7 -43
  312. package/dist/core/ingestion/model/resolve.js +7 -226
  313. package/dist/core/ingestion/model/scope-resolution-indexes.d.ts +46 -1
  314. package/dist/core/ingestion/model/semantic-model.d.ts +4 -6
  315. package/dist/core/ingestion/model/semantic-model.js +1 -1
  316. package/dist/core/ingestion/model/symbol-table.d.ts +3 -4
  317. package/dist/core/ingestion/model/symbol-table.js +3 -4
  318. package/dist/core/ingestion/parsing-processor.d.ts +30 -24
  319. package/dist/core/ingestion/parsing-processor.js +76 -640
  320. package/dist/core/ingestion/pipeline-phases/communities.d.ts +1 -1
  321. package/dist/core/ingestion/pipeline-phases/communities.js +5 -2
  322. package/dist/core/ingestion/pipeline-phases/cross-file.d.ts +9 -8
  323. package/dist/core/ingestion/pipeline-phases/cross-file.js +16 -12
  324. package/dist/core/ingestion/pipeline-phases/index.d.ts +1 -0
  325. package/dist/core/ingestion/pipeline-phases/index.js +1 -0
  326. package/dist/core/ingestion/pipeline-phases/mro.d.ts +1 -1
  327. package/dist/core/ingestion/pipeline-phases/mro.js +2 -2
  328. package/dist/core/ingestion/pipeline-phases/parse-impl.d.ts +44 -22
  329. package/dist/core/ingestion/pipeline-phases/parse-impl.js +426 -565
  330. package/dist/core/ingestion/pipeline-phases/parse.d.ts +13 -33
  331. package/dist/core/ingestion/pipeline-phases/parse.js +2 -2
  332. package/dist/core/ingestion/pipeline-phases/processes.d.ts +1 -1
  333. package/dist/core/ingestion/pipeline-phases/processes.js +5 -3
  334. package/dist/core/ingestion/pipeline-phases/prune-local-symbols.d.ts +14 -0
  335. package/dist/core/ingestion/pipeline-phases/prune-local-symbols.js +26 -0
  336. package/dist/core/ingestion/pipeline.d.ts +27 -19
  337. package/dist/core/ingestion/pipeline.js +4 -2
  338. package/dist/core/ingestion/resolve-references.js +15 -3
  339. package/dist/core/ingestion/route-extractors/laravel.d.ts +10 -0
  340. package/dist/core/ingestion/route-extractors/laravel.js +88 -9
  341. package/dist/core/ingestion/scope-extractor-bridge.d.ts +2 -1
  342. package/dist/core/ingestion/scope-extractor-bridge.js +2 -2
  343. package/dist/core/ingestion/scope-extractor.js +13 -0
  344. package/dist/core/ingestion/scope-resolution/contract/scope-resolver.d.ts +181 -15
  345. package/dist/core/ingestion/scope-resolution/contract/scope-resolver.js +21 -10
  346. package/dist/core/ingestion/scope-resolution/graph-bridge/edges.js +10 -2
  347. package/dist/core/ingestion/scope-resolution/graph-bridge/ids.d.ts +7 -1
  348. package/dist/core/ingestion/scope-resolution/graph-bridge/ids.js +58 -6
  349. package/dist/core/ingestion/scope-resolution/graph-bridge/node-lookup.js +24 -5
  350. package/dist/core/ingestion/scope-resolution/passes/free-call-fallback.d.ts +68 -1
  351. package/dist/core/ingestion/scope-resolution/passes/free-call-fallback.js +189 -29
  352. package/dist/core/ingestion/scope-resolution/passes/imported-return-types.js +21 -1
  353. package/dist/core/ingestion/scope-resolution/passes/receiver-bound-calls.js +1 -1
  354. package/dist/core/ingestion/scope-resolution/pipeline/phase.d.ts +8 -11
  355. package/dist/core/ingestion/scope-resolution/pipeline/phase.js +171 -50
  356. package/dist/core/ingestion/scope-resolution/pipeline/registry.d.ts +3 -4
  357. package/dist/core/ingestion/scope-resolution/pipeline/registry.js +9 -4
  358. package/dist/core/ingestion/scope-resolution/pipeline/run.d.ts +28 -5
  359. package/dist/core/ingestion/scope-resolution/pipeline/run.js +191 -24
  360. package/dist/core/ingestion/scope-resolution/pipeline/validate-bindings-immutability.js +31 -0
  361. package/dist/core/ingestion/scope-resolution/scope/walkers.d.ts +72 -0
  362. package/dist/core/ingestion/scope-resolution/scope/walkers.js +440 -39
  363. package/dist/core/ingestion/scope-resolution/workspace-index.d.ts +18 -2
  364. package/dist/core/ingestion/scope-resolution/workspace-index.js +94 -7
  365. package/dist/core/ingestion/tree-sitter-queries.d.ts +14 -14
  366. package/dist/core/ingestion/tree-sitter-queries.js +380 -158
  367. package/dist/core/ingestion/ts-js-hoc-utils.d.ts +12 -0
  368. package/dist/core/ingestion/ts-js-hoc-utils.js +105 -0
  369. package/dist/core/ingestion/type-env.d.ts +2 -1
  370. package/dist/core/ingestion/type-env.js +6 -8
  371. package/dist/core/ingestion/type-extractors/c-cpp.js +8 -10
  372. package/dist/core/ingestion/type-extractors/csharp.js +18 -34
  373. package/dist/core/ingestion/type-extractors/go.js +2 -10
  374. package/dist/core/ingestion/type-extractors/jvm.js +6 -5
  375. package/dist/core/ingestion/type-extractors/php.js +1 -1
  376. package/dist/core/ingestion/type-extractors/python.js +1 -1
  377. package/dist/core/ingestion/type-extractors/ruby.js +2 -2
  378. package/dist/core/ingestion/type-extractors/rust.js +0 -16
  379. package/dist/core/ingestion/type-extractors/shared.d.ts +2 -2
  380. package/dist/core/ingestion/type-extractors/shared.js +25 -11
  381. package/dist/core/ingestion/type-extractors/swift.js +5 -5
  382. package/dist/core/ingestion/type-extractors/types.d.ts +1 -1
  383. package/dist/core/ingestion/type-extractors/typescript.js +1 -1
  384. package/dist/core/ingestion/utils/ast-helpers.d.ts +119 -1
  385. package/dist/core/ingestion/utils/ast-helpers.js +260 -13
  386. package/dist/core/ingestion/utils/callable-labels.d.ts +13 -0
  387. package/dist/core/ingestion/utils/callable-labels.js +14 -0
  388. package/dist/core/ingestion/utils/deferred-resolution-profile.d.ts +10 -0
  389. package/dist/core/ingestion/utils/deferred-resolution-profile.js +30 -0
  390. package/dist/core/ingestion/utils/heap-probe.d.ts +20 -0
  391. package/dist/core/ingestion/utils/heap-probe.js +39 -0
  392. package/dist/core/ingestion/utils/heritage-marker.d.ts +33 -0
  393. package/dist/core/ingestion/utils/heritage-marker.js +41 -0
  394. package/dist/core/ingestion/utils/qualified-name.d.ts +37 -0
  395. package/dist/core/ingestion/utils/qualified-name.js +67 -0
  396. package/dist/core/ingestion/variable-extractors/configs/c-cpp.js +49 -0
  397. package/dist/core/ingestion/variable-extractors/configs/dart.js +76 -62
  398. package/dist/core/ingestion/variable-extractors/configs/go.js +74 -7
  399. package/dist/core/ingestion/variable-extractors/configs/jvm.js +35 -8
  400. package/dist/core/ingestion/variable-extractors/generic.js +40 -12
  401. package/dist/core/ingestion/variable-types.d.ts +9 -0
  402. package/dist/core/ingestion/vue-sfc-extractor.d.ts +97 -7
  403. package/dist/core/ingestion/vue-sfc-extractor.js +433 -11
  404. package/dist/core/ingestion/workers/parse-worker.d.ts +0 -11
  405. package/dist/core/ingestion/workers/parse-worker.js +358 -187
  406. package/dist/core/ingestion/workers/worker-pool.d.ts +78 -9
  407. package/dist/core/ingestion/workers/worker-pool.js +346 -49
  408. package/dist/core/lbug/csv-generator.js +20 -2
  409. package/dist/core/lbug/lbug-adapter.js +29 -10
  410. package/dist/core/lbug/native-check.js +17 -5
  411. package/dist/core/lbug/pool-adapter.d.ts +0 -19
  412. package/dist/core/lbug/pool-adapter.js +40 -77
  413. package/dist/core/lbug/query-result-utils.d.ts +19 -0
  414. package/dist/core/lbug/query-result-utils.js +28 -0
  415. package/dist/core/run-analyze.d.ts +9 -2
  416. package/dist/core/run-analyze.js +24 -3
  417. package/dist/core/tree-sitter/parser-loader.d.ts +13 -0
  418. package/dist/core/tree-sitter/parser-loader.js +4 -0
  419. package/dist/core/tree-sitter/safe-parse.d.ts +70 -3
  420. package/dist/core/tree-sitter/safe-parse.js +214 -11
  421. package/dist/core/wiki/generator.js +13 -5
  422. package/dist/core/wiki/graph-queries.d.ts +3 -0
  423. package/dist/core/wiki/graph-queries.js +9 -1
  424. package/dist/core/wiki/llm-client.d.ts +1 -1
  425. package/dist/core/wiki/llm-client.js +7 -2
  426. package/dist/core/wiki/local-cli-client.d.ts +2 -1
  427. package/dist/core/wiki/local-cli-client.js +62 -4
  428. package/dist/mcp/compatible-stdio-transport.d.ts +3 -0
  429. package/dist/mcp/compatible-stdio-transport.js +22 -0
  430. package/dist/mcp/core/embedder.d.ts +1 -1
  431. package/dist/mcp/core/embedder.js +13 -1
  432. package/dist/mcp/local/local-backend.d.ts +37 -5
  433. package/dist/mcp/local/local-backend.js +227 -129
  434. package/dist/mcp/resources.js +3 -3
  435. package/dist/mcp/server.js +9 -1
  436. package/dist/storage/git.d.ts +11 -0
  437. package/dist/storage/git.js +30 -0
  438. package/dist/storage/parse-cache.d.ts +23 -1
  439. package/dist/storage/parse-cache.js +138 -32
  440. package/dist/storage/parsedfile-store.d.ts +142 -0
  441. package/dist/storage/parsedfile-store.js +367 -0
  442. package/dist/storage/repo-manager.d.ts +2 -1
  443. package/dist/storage/scope-index-store.d.ts +114 -0
  444. package/dist/storage/scope-index-store.js +236 -0
  445. package/dist/types/pipeline.d.ts +6 -3
  446. package/hooks/antigravity/gitnexus-antigravity-hook.cjs +2 -1
  447. package/hooks/claude/gitnexus-hook.cjs +2 -1
  448. package/hooks/claude/resolve-analyze-cmd.cjs +323 -0
  449. package/package.json +4 -5
  450. package/scripts/bench-scope-resolution.ts +1 -3
  451. package/scripts/cross-platform-tests.ts +4 -1
  452. package/skills/gitnexus-cli.md +8 -6
  453. package/skills/gitnexus-debugging.md +15 -15
  454. package/skills/gitnexus-exploring.md +11 -11
  455. package/skills/gitnexus-guide.md +1 -1
  456. package/skills/gitnexus-impact-analysis.md +10 -10
  457. package/skills/gitnexus-pr-review.md +19 -19
  458. package/skills/gitnexus-refactoring.md +25 -25
  459. package/web/assets/{agent-BRX-afm3.js → agent-EkX7webX.js} +156 -131
  460. package/web/assets/{architectureDiagram-UL44E2DR-B1oYB8-c.js → architectureDiagram-UL44E2DR-BoczH8cv.js} +1 -1
  461. package/web/assets/{chunk-LCXTWHL2-SPC6pgWI.js → chunk-LCXTWHL2-By5HB3b-.js} +1 -1
  462. package/web/assets/{chunk-RG4AUYOV-DZXr4Yv3.js → chunk-RG4AUYOV-BQE_DkpL.js} +1 -1
  463. package/web/assets/{classDiagram-KGZ6W3CR-BqpOj8L9.js → classDiagram-KGZ6W3CR-Dj_02GUH.js} +1 -1
  464. package/web/assets/{classDiagram-v2-72OJOZXJ-FmElywK2.js → classDiagram-v2-72OJOZXJ-D-NArMpf.js} +1 -1
  465. package/web/assets/{diagram-3NCE3AQN-BWtJXMDq.js → diagram-3NCE3AQN-VXtXDO95.js} +1 -1
  466. package/web/assets/{diagram-GF46GFSD-Hh-fChxU.js → diagram-GF46GFSD-B1qab2Ah.js} +1 -1
  467. package/web/assets/{diagram-QXG6HAR7-DYeQHxGU.js → diagram-QXG6HAR7-BSCHGzzT.js} +1 -1
  468. package/web/assets/{diagram-WEQXMOUZ-DYGU4T0y.js → diagram-WEQXMOUZ-DHtknmNT.js} +1 -1
  469. package/web/assets/{erDiagram-L5TCEMPS-bN3wlP2A.js → erDiagram-L5TCEMPS-Db-IYTmm.js} +1 -1
  470. package/web/assets/{flowDiagram-H6V6AXG4-YACVtF3-.js → flowDiagram-H6V6AXG4-BHDoyVoW.js} +1 -1
  471. package/web/assets/{index-BhnAdWTt.js → index-BR0IhgbR.js} +10 -10
  472. package/web/assets/{infoDiagram-3YFTVSEB-BWBzD28-.js → infoDiagram-3YFTVSEB-6h8wbWEe.js} +1 -1
  473. package/web/assets/{ishikawaDiagram-BNXS4ZKH-B8qYT-j9.js → ishikawaDiagram-BNXS4ZKH-Dx2OkPk1.js} +1 -1
  474. package/web/assets/{kanban-definition-75IXJCU3-BeoPr5Tl.js → kanban-definition-75IXJCU3-CIIEZfqV.js} +1 -1
  475. package/web/assets/{mindmap-definition-2TDM6QVE-CdLLN_so.js → mindmap-definition-2TDM6QVE-DUAqydRq.js} +1 -1
  476. package/web/assets/{pieDiagram-CU6KROY3-DEd2a_k_.js → pieDiagram-CU6KROY3-BntYuYZa.js} +1 -1
  477. package/web/assets/{requirementDiagram-JXO7QTGE-QNeTo5C_.js → requirementDiagram-JXO7QTGE-QCD6I29n.js} +1 -1
  478. package/web/assets/{sequenceDiagram-VS2MUI6T-BHC7q7yJ.js → sequenceDiagram-VS2MUI6T-DScFwLz2.js} +1 -1
  479. package/web/assets/{stateDiagram-7D4R322I-KONnc2Px.js → stateDiagram-7D4R322I-AkRAm6Hl.js} +1 -1
  480. package/web/assets/{stateDiagram-v2-36443NZ5-C2QfuMlu.js → stateDiagram-v2-36443NZ5-BCK1vigR.js} +1 -1
  481. package/web/assets/{timeline-definition-O6YCAMPW-D4t4NJx1.js → timeline-definition-O6YCAMPW-BvpIVXjX.js} +1 -1
  482. package/web/assets/{vennDiagram-MWXL3ELB-6bctC9Yg.js → vennDiagram-MWXL3ELB-BYGWk6dK.js} +1 -1
  483. package/web/assets/{wardleyDiagram-CUQ6CDDI-BPZYNTvC.js → wardleyDiagram-CUQ6CDDI-Dk1z7H2T.js} +1 -1
  484. package/web/assets/{xychartDiagram-N2JHSOCM-lBI9O6DW.js → xychartDiagram-N2JHSOCM-2N6NCSWN.js} +1 -1
  485. package/web/index.html +1 -1
  486. package/dist/_shared/scope-resolution/shadow/aggregate.d.ts +0 -63
  487. package/dist/_shared/scope-resolution/shadow/aggregate.d.ts.map +0 -1
  488. package/dist/_shared/scope-resolution/shadow/aggregate.js +0 -122
  489. package/dist/_shared/scope-resolution/shadow/aggregate.js.map +0 -1
  490. package/dist/_shared/scope-resolution/shadow/diff.d.ts +0 -59
  491. package/dist/_shared/scope-resolution/shadow/diff.d.ts.map +0 -1
  492. package/dist/_shared/scope-resolution/shadow/diff.js +0 -79
  493. package/dist/_shared/scope-resolution/shadow/diff.js.map +0 -1
  494. package/dist/core/ingestion/ast-cache.d.ts +0 -26
  495. package/dist/core/ingestion/ast-cache.js +0 -48
  496. package/dist/core/ingestion/heritage-extractors/configs/go.d.ts +0 -13
  497. package/dist/core/ingestion/heritage-extractors/configs/go.js +0 -20
  498. package/dist/core/ingestion/heritage-extractors/configs/ruby.d.ts +0 -18
  499. package/dist/core/ingestion/heritage-extractors/configs/ruby.js +0 -65
  500. package/dist/core/ingestion/heritage-extractors/generic.d.ts +0 -23
  501. package/dist/core/ingestion/heritage-extractors/generic.js +0 -47
  502. package/dist/core/ingestion/heritage-processor.d.ts +0 -54
  503. package/dist/core/ingestion/heritage-processor.js +0 -367
  504. package/dist/core/ingestion/heritage-types.d.ts +0 -73
  505. package/dist/core/ingestion/heritage-types.js +0 -2
  506. package/dist/core/ingestion/import-processor.d.ts +0 -23
  507. package/dist/core/ingestion/import-processor.js +0 -377
  508. package/dist/core/ingestion/model/heritage-map.d.ts +0 -105
  509. package/dist/core/ingestion/model/heritage-map.js +0 -294
  510. package/dist/core/ingestion/model/resolution-context.d.ts +0 -93
  511. package/dist/core/ingestion/model/resolution-context.js +0 -337
  512. package/dist/core/ingestion/named-bindings/csharp.d.ts +0 -3
  513. package/dist/core/ingestion/named-bindings/csharp.js +0 -37
  514. package/dist/core/ingestion/named-bindings/java.d.ts +0 -3
  515. package/dist/core/ingestion/named-bindings/java.js +0 -29
  516. package/dist/core/ingestion/named-bindings/kotlin.d.ts +0 -3
  517. package/dist/core/ingestion/named-bindings/kotlin.js +0 -36
  518. package/dist/core/ingestion/named-bindings/php.d.ts +0 -3
  519. package/dist/core/ingestion/named-bindings/php.js +0 -61
  520. package/dist/core/ingestion/named-bindings/python.d.ts +0 -3
  521. package/dist/core/ingestion/named-bindings/python.js +0 -49
  522. package/dist/core/ingestion/named-bindings/rust.d.ts +0 -3
  523. package/dist/core/ingestion/named-bindings/rust.js +0 -66
  524. package/dist/core/ingestion/named-bindings/types.d.ts +0 -16
  525. package/dist/core/ingestion/named-bindings/types.js +0 -6
  526. package/dist/core/ingestion/named-bindings/typescript.d.ts +0 -3
  527. package/dist/core/ingestion/named-bindings/typescript.js +0 -58
  528. package/dist/core/ingestion/pipeline-phases/cross-file-impl.d.ts +0 -17
  529. package/dist/core/ingestion/pipeline-phases/cross-file-impl.js +0 -209
  530. package/dist/core/ingestion/pipeline-phases/orm-extraction.d.ts +0 -22
  531. package/dist/core/ingestion/pipeline-phases/orm-extraction.js +0 -92
  532. package/dist/core/ingestion/pipeline-phases/wildcard-synthesis.d.ts +0 -70
  533. package/dist/core/ingestion/pipeline-phases/wildcard-synthesis.js +0 -312
  534. package/dist/core/ingestion/registry-primary-flag.d.ts +0 -89
  535. package/dist/core/ingestion/registry-primary-flag.js +0 -122
  536. package/dist/core/ingestion/shadow-harness.d.ts +0 -113
  537. package/dist/core/ingestion/shadow-harness.js +0 -148
  538. package/dist/core/ingestion/utils/ruby-self-call.d.ts +0 -52
  539. package/dist/core/ingestion/utils/ruby-self-call.js +0 -59
  540. package/scripts/ci-list-migrated-languages.ts +0 -24
  541. package/scripts/run-parity.ts +0 -128
@@ -0,0 +1,236 @@
1
+ /**
2
+ * Disk-backed scope store + lazy `ScopeTree` (out-of-core scope index — kernel scope-resolution
3
+ * out-of-core index).
4
+ *
5
+ * ## Why this exists
6
+ *
7
+ * The scope-resolution resident floor is dominated by the per-`Scope` binding
8
+ * payload (`Scope.bindings` / `typeBindings` / `ownedDefs`) — ~17-20 GB for one
9
+ * language on the Linux kernel — held in `preExtractedByPath` AND aliased by the
10
+ * finalize `scopeTree` through the whole emit phase. The emit passes never read
11
+ * `parsed.scopes` directly; they reach scopes EXCLUSIVELY through
12
+ * `scopeTree.getScope(id)` (a point lookup) and `getChildren(id)`. So the heavy
13
+ * scope payload can move to disk behind that point lookup without changing what
14
+ * any consumer observes: every consumer reads a `Scope` BY VALUE (its `bindings`
15
+ * / `ownedDefs` contents, `parent`, `range`), never by object identity.
16
+ *
17
+ * {@link persistScopeShards} writes the scopes to per-file JSON shards (one file
18
+ * = one shard, so a file's whole parent-chain — which never crosses filePath —
19
+ * stays within one shard) using the same `mapReplacer` + def-interning reviver
20
+ * the ParsedFile store proved byte-identical (#1983 / def-object interning). {@link DiskBackedScopeTree}
21
+ * serves `getScope` from a bounded LRU of decoded shards plus a small resident
22
+ * skeleton (`scopeId -> {shard, childIds, parent}`), so only the working set of
23
+ * scopes is resident, not all of them.
24
+ *
25
+ * Default-off: only constructed when `GITNEXUS_DISK_SCOPE_INDEX` is set. The
26
+ * resident `buildScopeTree` path is untouched otherwise.
27
+ */
28
+ import { mkdirSync, writeFileSync, readFileSync, rmSync } from 'node:fs';
29
+ import path from 'node:path';
30
+ import { buildScopeTree } from '../_shared/index.js';
31
+ import { mapReplacer } from './parse-cache.js';
32
+ import { makeInterningReviver } from './parsedfile-store.js';
33
+ const STORE_DIRNAME = 'scope-index-store';
34
+ export const getScopeIndexStoreDir = (storagePath) => path.join(storagePath, STORE_DIRNAME);
35
+ /**
36
+ * Remove any prior seal's scope shards so a fresh seal starts clean. The shard
37
+ * names are sequential (`s<n>.json`) and the index resets per `persistScopeShards`
38
+ * call, so without this a seal that writes FEWER shards than a previous one (a
39
+ * later language with fewer files, or a later run of a shrunken repo) would leave
40
+ * stale tail shards on disk indefinitely — pure garbage the disk-backed tree
41
+ * never reads, but multi-GB on kernel-scale repos. Idempotent; synchronous to
42
+ * fit the main-thread seal path. Safe to call before each seal: the previously
43
+ * sealed language has finished emit and been released before the next seal runs,
44
+ * so its `DiskBackedScopeTree` never reads these shards again.
45
+ */
46
+ export const clearScopeIndexStore = (storagePath) => {
47
+ rmSync(getScopeIndexStoreDir(storagePath), { recursive: true, force: true });
48
+ };
49
+ const EMPTY = Object.freeze([]);
50
+ /**
51
+ * Persist `scopes` to per-file shards under `<storagePath>/scope-index-store/`
52
+ * and return the resident skeleton the {@link DiskBackedScopeTree} needs. Sharded
53
+ * by `filePath` (sequential `s<n>.json` names — no filePath→filename encoding),
54
+ * so one file's full scope subtree round-trips together. Synchronous: pass-A runs
55
+ * on the main thread and this replaces an in-heap `buildScopeTree`.
56
+ */
57
+ export const persistScopeShards = (storagePath, scopes) => {
58
+ const dir = getScopeIndexStoreDir(storagePath);
59
+ // Clear first so a seal that writes fewer shards than the previous one (a
60
+ // later language with fewer files, or a shrunken repo on re-run) leaves no
61
+ // stale `s<n>.json` tail behind. See {@link clearScopeIndexStore}.
62
+ clearScopeIndexStore(storagePath);
63
+ mkdirSync(dir, { recursive: true });
64
+ // Group scope objects by filePath, preserving input order within a file.
65
+ const byFile = new Map();
66
+ for (const s of scopes) {
67
+ const bucket = byFile.get(s.filePath);
68
+ if (bucket)
69
+ bucket.push(s);
70
+ else
71
+ byFile.set(s.filePath, [s]);
72
+ }
73
+ // childIds in input order (mirrors buildScopeTree's children buckets).
74
+ const childIds = new Map();
75
+ for (const s of scopes) {
76
+ if (s.parent !== null) {
77
+ const b = childIds.get(s.parent);
78
+ if (b)
79
+ b.push(s.id);
80
+ else
81
+ childIds.set(s.parent, [s.id]);
82
+ }
83
+ }
84
+ const skeleton = new Map();
85
+ let shardIndex = 0;
86
+ for (const [, fileScopes] of byFile) {
87
+ const shard = `s${shardIndex++}.json`;
88
+ writeFileSync(path.join(dir, shard), JSON.stringify(fileScopes, mapReplacer), 'utf-8');
89
+ for (const s of fileScopes) {
90
+ skeleton.set(s.id, {
91
+ shard,
92
+ parent: s.parent,
93
+ childIds: childIds.get(s.id) ?? [],
94
+ });
95
+ }
96
+ }
97
+ return skeleton;
98
+ };
99
+ /**
100
+ * A `ScopeTree` that serves `getScope` from disk shards via a bounded LRU,
101
+ * holding only `maxResidentShards` decoded shards + the resident skeleton. Drop-in
102
+ * for the in-heap `buildScopeTree` result for the methods scope-resolution
103
+ * actually calls — `getScope` (the hot one), `getChildren`, `getParent`,
104
+ * `getAncestors`, `has`, `size`. `byId` (a full materialization) is only used by
105
+ * the `INGESTION_EMIT_SCOPES=1` debug path and is unsupported here — the two flags
106
+ * are mutually exclusive.
107
+ */
108
+ export class DiskBackedScopeTree {
109
+ dir;
110
+ skeleton;
111
+ maxResidentShards;
112
+ /** Decoded shards, most-recently-used last (Map preserves insertion order). */
113
+ lru = new Map();
114
+ constructor(storagePath, skeleton, maxResidentShards = 64) {
115
+ this.dir = getScopeIndexStoreDir(storagePath);
116
+ this.skeleton = skeleton;
117
+ this.maxResidentShards = Math.max(1, maxResidentShards);
118
+ }
119
+ get size() {
120
+ return this.skeleton.size;
121
+ }
122
+ get byId() {
123
+ throw new Error('DiskBackedScopeTree.byId is unsupported (INGESTION_EMIT_SCOPES is incompatible with GITNEXUS_DISK_SCOPE_INDEX).');
124
+ }
125
+ has(id) {
126
+ return this.skeleton.has(id);
127
+ }
128
+ getChildren(id) {
129
+ return this.skeleton.get(id)?.childIds ?? EMPTY;
130
+ }
131
+ getScope(id) {
132
+ const meta = this.skeleton.get(id);
133
+ if (meta === undefined)
134
+ return undefined;
135
+ return this.loadShard(meta.shard).get(id);
136
+ }
137
+ getParent(id) {
138
+ const parent = this.skeleton.get(id)?.parent;
139
+ return parent === null || parent === undefined ? undefined : this.getScope(parent);
140
+ }
141
+ getAncestors(id) {
142
+ const out = [];
143
+ let cur = this.skeleton.get(id)?.parent ?? null;
144
+ const seen = new Set();
145
+ while (cur !== null && !seen.has(cur)) {
146
+ seen.add(cur);
147
+ out.push(cur);
148
+ cur = this.skeleton.get(cur)?.parent ?? null;
149
+ }
150
+ return out;
151
+ }
152
+ /** Load + decode a shard, touch it as MRU, evict the LRU tail past the cap. */
153
+ loadShard(shard) {
154
+ const cached = this.lru.get(shard);
155
+ if (cached !== undefined) {
156
+ // Touch: move to MRU end.
157
+ this.lru.delete(shard);
158
+ this.lru.set(shard, cached);
159
+ return cached;
160
+ }
161
+ const pool = new Map();
162
+ const defPool = new Map();
163
+ const raw = readFileSync(path.join(this.dir, shard), 'utf-8');
164
+ const fileScopes = JSON.parse(raw, makeInterningReviver(pool, defPool));
165
+ const decoded = new Map();
166
+ for (const s of fileScopes)
167
+ decoded.set(s.id, s);
168
+ this.lru.set(shard, decoded);
169
+ if (this.lru.size > this.maxResidentShards) {
170
+ const oldest = this.lru.keys().next().value;
171
+ if (oldest !== undefined)
172
+ this.lru.delete(oldest);
173
+ }
174
+ return decoded;
175
+ }
176
+ }
177
+ /**
178
+ * A `ScopeTree` that starts fully resident (validated by `buildScopeTree`, used
179
+ * by finalize / propagate / resolve, which may mutate `Scope.typeBindings` in
180
+ * place) and then {@link seal}s to a {@link DiskBackedScopeTree} just before emit.
181
+ *
182
+ * Sealing is what actually frees the ~17-20 GB of `Scope.bindings`: the resident
183
+ * tree is held BY THE MODEL'S frozen index bundle, so it cannot be swapped out
184
+ * from the outside. This wrapper IS that held object — `seal()` mutates its own
185
+ * (non-frozen) internal field to null the resident tree from the inside, after
186
+ * persisting it, so the model's reference now points at the disk-backed serving
187
+ * path and the heavy scopes become collectible (once the emit-side ParsedFiles
188
+ * also drop their `scopes`). Idempotent; a no-op before `seal()` keeps today's
189
+ * fully-resident behavior byte-identical.
190
+ */
191
+ export class TransitionalScopeTree {
192
+ resident;
193
+ disk = null;
194
+ constructor(scopes) {
195
+ this.resident = buildScopeTree(scopes); // validates invariants + serves the resident phase
196
+ }
197
+ /** Persist the resident scopes, switch to disk-backed serving, and drop the
198
+ * resident tree so its scope/binding payload can be reclaimed. Idempotent. */
199
+ seal(storagePath, maxResidentShards) {
200
+ if (this.disk !== null || this.resident === null)
201
+ return;
202
+ const skeleton = persistScopeShards(storagePath, [...this.resident.byId.values()]);
203
+ this.disk = new DiskBackedScopeTree(storagePath, skeleton, maxResidentShards);
204
+ this.resident = null;
205
+ }
206
+ get sealed() {
207
+ return this.disk !== null;
208
+ }
209
+ get active() {
210
+ const t = this.disk ?? this.resident;
211
+ if (t === null)
212
+ throw new Error('TransitionalScopeTree has no active backing (resident dropped without seal).');
213
+ return t;
214
+ }
215
+ get size() {
216
+ return this.active.size;
217
+ }
218
+ get byId() {
219
+ return this.active.byId; // throws in disk mode (DiskBackedScopeTree.byId)
220
+ }
221
+ has(id) {
222
+ return this.active.has(id);
223
+ }
224
+ getScope(id) {
225
+ return this.active.getScope(id);
226
+ }
227
+ getParent(id) {
228
+ return this.active.getParent(id);
229
+ }
230
+ getChildren(id) {
231
+ return this.active.getChildren(id);
232
+ }
233
+ getAncestors(id) {
234
+ return this.active.getAncestors(id);
235
+ }
236
+ }
@@ -17,9 +17,12 @@ export interface PipelineResult {
17
17
  */
18
18
  resolutionOutcomes: readonly ResolutionOutcome[];
19
19
  /**
20
- * True if the parse phase spawned a worker pool for this run. False means
21
- * the sequential fallback handled every chunk. Primarily a test affordance
22
- * so regression suites can prove which path executed.
20
+ * True if a worker pool was actually constructed for this run. The worker
21
+ * pool is the sole parse path (sequential parsing was removed). False means
22
+ * no pool was needed: either there were no parseable files, or every chunk
23
+ * was a parse-cache hit and the cached worker output was replayed without
24
+ * spawning workers (a warm all-cache-hit run, #2038). Primarily a test
25
+ * affordance so regression suites can prove the pool engaged.
23
26
  */
24
27
  usedWorkerPool: boolean;
25
28
  }
@@ -25,6 +25,7 @@ const path = require('path');
25
25
  const { spawnSync } = require('child_process');
26
26
  const { acquireHookSlot } = require('./hook-lock.cjs');
27
27
  const { hasGitNexusDbLockedByGitNexusServer } = require('./hook-db-lock-probe.cjs');
28
+ const { formatAnalyzeCommand } = require('./resolve-analyze-cmd.cjs');
28
29
 
29
30
  function readInput() {
30
31
  try {
@@ -315,7 +316,7 @@ function buildStaleIndexHint(gitNexusDir, cwd) {
315
316
 
316
317
  if (currentHead === lastCommit) return '';
317
318
 
318
- const analyzeCmd = `npx gitnexus analyze${hadEmbeddings ? ' --embeddings' : ''}`;
319
+ const analyzeCmd = formatAnalyzeCommand({ embeddings: hadEmbeddings });
319
320
  return (
320
321
  `[GitNexus] index is stale (last indexed: ${lastCommit ? lastCommit.slice(0, 7) : 'never'}). ` +
321
322
  `Run \`${analyzeCmd}\` to refresh the knowledge graph.`
@@ -16,6 +16,7 @@ const path = require('path');
16
16
  const { spawnSync } = require('child_process');
17
17
  const { acquireHookSlot } = require('./hook-lock.cjs');
18
18
  const { hasGitNexusDbLockedByGitNexusServer } = require('./hook-db-lock-probe.cjs');
19
+ const { formatAnalyzeCommand } = require('./resolve-analyze-cmd.cjs');
19
20
 
20
21
  /**
21
22
  * Read JSON input from stdin synchronously.
@@ -340,7 +341,7 @@ function handlePostToolUse(input) {
340
341
  // If HEAD matches last indexed commit, no reindex needed
341
342
  if (currentHead && currentHead === lastCommit) return;
342
343
 
343
- const analyzeCmd = `npx gitnexus analyze${hadEmbeddings ? ' --embeddings' : ''}`;
344
+ const analyzeCmd = formatAnalyzeCommand({ embeddings: hadEmbeddings });
344
345
  sendHookResponse(
345
346
  'PostToolUse',
346
347
  `GitNexus index is stale (last indexed: ${lastCommit ? lastCommit.slice(0, 7) : 'never'}). ` +
@@ -0,0 +1,323 @@
1
+ /**
2
+ * Single source of truth for how docs, hooks, and warnings invoke gitnexus.
3
+ *
4
+ * Automatically selects a working invocation path:
5
+ * 1. Global `gitnexus` on PATH (best — no install step)
6
+ * 2. npm 11+ with pnpm on PATH → `pnpm --allow-build=… dlx` (avoids the npx
7
+ * arborist crash *and* pnpm 10+ ignored-build-script failures, #1939)
8
+ * 3. npm < 11 with npm on PATH → `npx` (works; simpler than pnpm dlx)
9
+ * 4. pnpm-only → `pnpm --allow-build=… dlx`
10
+ * 5. Last resort → `npx` (warned on npm 11+ from analyze.ts)
11
+ *
12
+ * The `--allow-build` flags MUST precede the `dlx` token. pnpm < 10.14 keeps
13
+ * `dlx` in its argv escape list, so flags placed *after* `dlx` are parsed as
14
+ * package specs (ERR_PNPM_SPEC_NOT_SUPPORTED). The pre-`dlx` position parses
15
+ * into dlx's allow-build option and has been honored since pnpm 10.2.0 (#1939).
16
+ *
17
+ * This stays self-contained CJS because the Claude/Antigravity hooks run as
18
+ * standalone files copied into the user's hook dir, where no package import is
19
+ * available. The CLI reuses this module from src/cli/resolve-invocation.ts via
20
+ * createRequire rather than re-implementing it. Two committed copies must stay
21
+ * byte-identical (enforced by resolve-invocation.test.ts) — edit both together:
22
+ * gitnexus/hooks/claude/ (the canonical copy the CLI and `gitnexus setup` read)
23
+ * and gitnexus-claude-plugin/hooks/. A THIRD copy is written at runtime to
24
+ * `<repo>/.gitnexus/run.cjs` by `gitnexus analyze` (ai-context.ts) so docs can
25
+ * reference it directly via the `require.main === module` exec tail below; that
26
+ * copy is gitignored and refreshed on every analyze, so it cannot drift for long.
27
+ */
28
+
29
+ const { execFileSync } = require('child_process');
30
+ const fs = require('fs');
31
+ const path = require('path');
32
+
33
+ const NPX_REF = 'gitnexus@latest';
34
+
35
+ // Native packages whose postinstall must run under pnpm 10+ (blocked by default).
36
+ const PNPM_ALLOW_BUILD_BASE = ['@ladybugdb/core', 'gitnexus', 'tree-sitter'];
37
+ const PNPM_ALLOW_BUILD_EMBEDDINGS = ['onnxruntime-node'];
38
+
39
+ // Version-probe timeout, kept under Claude Code's 10s hook budget. PATH presence
40
+ // detection is now spawn-free (resolveOnPath scans PATH directly), so the only
41
+ // subprocesses left are the version probes: in a linked worktree the stale-index
42
+ // hook first runs `git rev-parse --git-common-dir` (~2s) and `git rev-parse HEAD`
43
+ // (~3s); the pnpm path then adds up to two 1s `--version` probes (npm, pnpm), so
44
+ // the worst case is ~7s — within budget. A healthy `--version` returns in well
45
+ // under a second, so the realistic cost is far lower.
46
+ const PROBE_TIMEOUT_MS = 1000;
47
+
48
+ /**
49
+ * Absolute path to `command` on PATH, or null — a pure-Node, spawn-free lookup
50
+ * that mirrors how a shell resolves a bare command name: each PATH dir × the
51
+ * platform's executable extensions (PATHEXT on Windows; the bare name + X_OK on
52
+ * POSIX). This replaces the former `where`/`which` subprocess (#1938 "Option A"):
53
+ * it is byte-for-byte identical on every OS, with no dependency on the probe
54
+ * binary being reachable (a sanitized PATH that drops System32 / `/usr/bin` no
55
+ * longer defeats detection), no shell-spawn surface (CVE-2024-27980), and no
56
+ * spawn timeout to tune. On Windows it matches PATHEXT extensions ONLY — exactly
57
+ * what `where`/cmd.exe resolve — so neither an un-spawnable `.ps1`-only shim (not
58
+ * in default PATHEXT) nor a bare extensionless file (which the shell cannot launch
59
+ * as `command`) is a false positive. `preferExecExt` returns a recognized
60
+ * `.cmd`/`.bat`/`.exe` shim ahead of an exotic PATHEXT hit (e.g. `.COM`) when both
61
+ * match, matching what a user would actually launch. Pure (platform/env injectable)
62
+ * so it is unit-testable without touching the host PATH.
63
+ */
64
+ function resolveOnPath(
65
+ command,
66
+ preferExecExt = false,
67
+ { platform = process.platform, env = process.env } = {},
68
+ ) {
69
+ const pathValue = env.PATH || env.Path || env.path || '';
70
+ if (!pathValue) return null;
71
+ const isWin = platform === 'win32';
72
+ const exts = isWin
73
+ ? (env.PATHEXT || '.COM;.EXE;.BAT;.CMD')
74
+ .split(';')
75
+ .map((e) => e.trim())
76
+ .filter(Boolean)
77
+ .map((e) => (e.startsWith('.') ? e : `.${e}`))
78
+ : [''];
79
+ let weakHit = null;
80
+ // Split on the host's PATH delimiter. `platform` is injected only to choose the
81
+ // extension/exec-bit rules; the PATH string is always host-format, so it must
82
+ // split on the host delimiter (`path.delimiter`) — in production `platform` IS
83
+ // the host, so they coincide. (Deriving the delimiter from an injected platform
84
+ // would split a Windows drive-letter path `C:\…` at its colon under a POSIX
85
+ // injection.)
86
+ for (const dir of pathValue.split(path.delimiter).filter(Boolean)) {
87
+ for (const ext of exts) {
88
+ const candidate = path.join(dir, `${command}${ext}`);
89
+ try {
90
+ if (!fs.statSync(candidate).isFile()) continue;
91
+ if (!isWin) fs.accessSync(candidate, fs.constants.X_OK);
92
+ // Prefer a runnable .cmd/.bat/.exe shim; remember an exotic PATHEXT hit
93
+ // (e.g. .COM) only as a last resort if nothing better turns up.
94
+ if (isWin && preferExecExt && !/\.(cmd|bat|exe)$/i.test(ext)) {
95
+ weakHit = weakHit || candidate;
96
+ continue;
97
+ }
98
+ return candidate;
99
+ } catch {
100
+ /* not a runnable file here — try the next candidate */
101
+ }
102
+ }
103
+ }
104
+ return weakHit;
105
+ }
106
+
107
+ // One spawn of `<command> --version` → { major, minor } (each null when
108
+ // unreadable). Version injection happens at the resolver seam (getNpmMajorVersion
109
+ // / formatPnpmAllowBuildArgs), so this stays a pure real-process probe.
110
+ function probeVersion(command) {
111
+ try {
112
+ const output = execFileSync(command, ['--version'], {
113
+ encoding: 'utf-8',
114
+ timeout: PROBE_TIMEOUT_MS,
115
+ stdio: ['ignore', 'pipe', 'ignore'],
116
+ windowsHide: true,
117
+ // On Windows, npm/pnpm resolve to `.cmd` shims; execFileSync does no
118
+ // PATHEXT resolution and Node refuses to spawn `.cmd`/`.bat` without a
119
+ // shell (CVE-2024-27980), so a bare `<command> --version` ENOENTs and the
120
+ // probe would wrongly report a present tool as absent. A shell lets the OS
121
+ // resolve the shim. POSIX needs no shell (direct PATH lookup works).
122
+ shell: process.platform === 'win32',
123
+ });
124
+ // Find the first line that starts with a version token (`MAJOR.MINOR`,
125
+ // optional `v` prefix) rather than splitting the whole output — pnpm/npm
126
+ // under Corepack or with an update notice can print a banner line on stdout
127
+ // before the version (stderr is already dropped via the stdio config).
128
+ const versionLine = output
129
+ .split('\n')
130
+ .map((l) => l.trim())
131
+ .find((l) => /^v?\d+\.\d+/.test(l));
132
+ const match = versionLine ? versionLine.match(/^v?(\d+)\.(\d+)/) : null;
133
+ return {
134
+ major: match ? Number(match[1]) : null,
135
+ minor: match ? Number(match[2]) : null,
136
+ };
137
+ } catch {
138
+ return { major: null, minor: null };
139
+ }
140
+ }
141
+
142
+ // `deps` is the single injection seam: an explicitly provided key — including a
143
+ // `null` value, detected via `in` — is honored as-is so tests can simulate an
144
+ // absent tool without spawning; an absent key falls through to the real probe.
145
+ function getNpmMajorVersion(deps = {}) {
146
+ return 'npmMajor' in deps ? deps.npmMajor : probeVersion('npm').major;
147
+ }
148
+
149
+ /**
150
+ * `--allow-build` flags for the pre-`dlx` position. Emitted for pnpm >= 10.2
151
+ * (where the flag exists, and pnpm 10+ blocks build scripts by default). Omitted
152
+ * below 10.2: pnpm < 10 runs build scripts anyway, and pnpm 10.0/10.1 lack the
153
+ * flag (it would be rejected as an unknown option). `alwaysAllowBuild` forces the
154
+ * flags for committed documentation, which cannot probe the reader's pnpm.
155
+ */
156
+ function formatPnpmAllowBuildArgs(options = {}, deps = {}) {
157
+ if (!options.alwaysAllowBuild) {
158
+ const { major, minor } =
159
+ 'pnpmMajor' in deps
160
+ ? { major: deps.pnpmMajor, minor: 'pnpmMinor' in deps ? deps.pnpmMinor : null }
161
+ : probeVersion('pnpm');
162
+ const lacksAllowBuild =
163
+ major !== null && (major < 10 || (major === 10 && minor !== null && minor < 2));
164
+ if (lacksAllowBuild) return [];
165
+ }
166
+ const pkgs = [...PNPM_ALLOW_BUILD_BASE];
167
+ if (options.embeddings) pkgs.push(...PNPM_ALLOW_BUILD_EMBEDDINGS);
168
+ return pkgs.map((p) => `--allow-build=${p}`);
169
+ }
170
+
171
+ /** Fixed install-free command for committed AGENTS.md / SKILL.md (pnpm >= 10.2). */
172
+ function formatDocumentationDlxCommand(gitnexusArgs, options = {}) {
173
+ const flags = formatPnpmAllowBuildArgs({ ...options, alwaysAllowBuild: true }).join(' ');
174
+ const prefix = flags ? `${flags} ` : '';
175
+ return `pnpm ${prefix}dlx ${NPX_REF} ${gitnexusArgs}`;
176
+ }
177
+
178
+ /**
179
+ * Resolve `gitnexus` | `pnpm` | `npx`. `GITNEXUS_INVOCATION` forces a mode
180
+ * (test/escape hatch). `probe` is injectable so the preference order can be
181
+ * unit-tested without spawning; it defaults to the real PATH probe. `deps` can
182
+ * inject `{ npmMajor, pnpmMajor }` for tests.
183
+ */
184
+ function resolveInvocationMode(probe = resolveOnPath, deps = {}) {
185
+ const forced = process.env.GITNEXUS_INVOCATION?.trim().toLowerCase();
186
+ if (forced === 'gitnexus' || forced === 'pnpm' || forced === 'npx') {
187
+ return forced;
188
+ }
189
+ if (probe('gitnexus', true)) return 'gitnexus';
190
+
191
+ const npmMajor = getNpmMajorVersion(deps);
192
+ // pnpm presence: prefer an explicit `pnpmPresent` flag (set by
193
+ // formatAnalyzeCommand, which falls back to a PATH probe when the version is
194
+ // unreadable) so a present-but-unparseable pnpm — slow probe, Corepack
195
+ // banner — still selects pnpm instead of the npx crash path. Otherwise an
196
+ // injected version (a successful `pnpm --version` proves presence)
197
+ // short-circuits the `which pnpm` probe; failing both, fall back to PATH.
198
+ const hasPnpm =
199
+ 'pnpmPresent' in deps
200
+ ? deps.pnpmPresent
201
+ : 'pnpmMajor' in deps
202
+ ? deps.pnpmMajor !== null
203
+ : Boolean(probe('pnpm'));
204
+
205
+ // npm 11+ npx install crash (#1939) — prefer pnpm dlx when available.
206
+ if (hasPnpm && npmMajor !== null && npmMajor >= 11) return 'pnpm';
207
+ // npm 10 and earlier: npx works; prefer it over pnpm dlx when npm is present.
208
+ if (npmMajor !== null && npmMajor < 11) return 'npx';
209
+ // npm absent or unreadable — use pnpm if present (with allow-build flags).
210
+ if (hasPnpm) return 'pnpm';
211
+
212
+ return 'npx';
213
+ }
214
+
215
+ function formatPnpmDlxCommand(gitnexusArgs, options = {}, deps = {}) {
216
+ const flags = formatPnpmAllowBuildArgs(options, deps).join(' ');
217
+ const prefix = flags ? `${flags} ` : '';
218
+ return `pnpm ${prefix}dlx ${NPX_REF} ${gitnexusArgs}`;
219
+ }
220
+
221
+ function formatAnalyzeCommand(options = {}, deps = {}) {
222
+ const suffix = options.embeddings ? ' --embeddings' : '';
223
+ // Keep the stale-index hook budget tight by querying each tool at most once.
224
+ // The memoized `probe` is a spawn-free PATH scan (resolveOnPath) shared with
225
+ // resolveInvocationMode, so `gitnexus` is scanned only once and no subprocess
226
+ // is spawned for presence. pnpm's *version* is still captured by a single
227
+ // `pnpm --version` (the allow-build gate needs the number), which also proves
228
+ // presence; the memoized scan only re-checks pnpm when that version is
229
+ // unreadable. Injected deps (tests) and forced/global modes skip the pnpm probe.
230
+ const cache = new Map();
231
+ const probe = (command, gitnexusWrapper) => {
232
+ const key = `${command}:${gitnexusWrapper ? 1 : 0}`;
233
+ if (!cache.has(key)) cache.set(key, resolveOnPath(command, gitnexusWrapper));
234
+ return cache.get(key);
235
+ };
236
+ let resolved = deps;
237
+ if (!('pnpmMajor' in deps)) {
238
+ const forced = process.env.GITNEXUS_INVOCATION?.trim().toLowerCase();
239
+ // pnpm is only consulted when no non-pnpm mode is already certain: forced
240
+ // gitnexus/npx never use pnpm, and a present global gitnexus wins outright.
241
+ const mightUsePnpm = forced === 'pnpm' || (forced !== 'gitnexus' && forced !== 'npx');
242
+ if (mightUsePnpm && (forced === 'pnpm' || !probe('gitnexus', true))) {
243
+ const { major, minor } = probeVersion('pnpm');
244
+ // Carry presence separately from version: when the version probe fails
245
+ // (timeout, Corepack banner) but pnpm is on PATH, still treat it as
246
+ // present so mode resolution picks pnpm over the npx crash path. The
247
+ // PATH probe is memoized and only runs when the version is unreadable.
248
+ const pnpmPresent = major !== null || Boolean(probe('pnpm'));
249
+ resolved = { ...deps, pnpmMajor: major, pnpmMinor: minor, pnpmPresent };
250
+ }
251
+ }
252
+ const mode = resolveInvocationMode(probe, resolved);
253
+ if (mode === 'gitnexus') return `gitnexus analyze${suffix}`;
254
+ if (mode === 'pnpm') return `${formatPnpmDlxCommand(`analyze${suffix}`, options, resolved)}`;
255
+ return `npx ${NPX_REF} analyze${suffix}`;
256
+ }
257
+
258
+ /**
259
+ * Resolve `mode` into a concrete { program, args } pair for a set of gitnexus
260
+ * subcommand arguments. Shared by the direct-exec entrypoint below; pure (no
261
+ * spawn) so it is unit-testable. `--embeddings` widens the pnpm allow-build set.
262
+ */
263
+ function buildRunnerArgv(mode, gitnexusArgs, deps = {}) {
264
+ // Match both the space form (`--embeddings`) and the equals form
265
+ // (`--embeddings=5000`) Commander accepts, so the pnpm allow-build set still
266
+ // widens to onnxruntime-node when a user hand-types the equals form.
267
+ const embeddings = gitnexusArgs.some(
268
+ (a) => a === '--embeddings' || a.startsWith('--embeddings='),
269
+ );
270
+ if (mode === 'gitnexus') return { program: 'gitnexus', args: [...gitnexusArgs] };
271
+ if (mode === 'pnpm') {
272
+ return {
273
+ program: 'pnpm',
274
+ args: [...formatPnpmAllowBuildArgs({ embeddings }, deps), 'dlx', NPX_REF, ...gitnexusArgs],
275
+ };
276
+ }
277
+ return { program: 'npx', args: [NPX_REF, ...gitnexusArgs] };
278
+ }
279
+
280
+ module.exports = {
281
+ formatAnalyzeCommand,
282
+ formatDocumentationDlxCommand,
283
+ formatPnpmAllowBuildArgs,
284
+ formatPnpmDlxCommand,
285
+ resolveInvocationMode,
286
+ buildRunnerArgv,
287
+ resolveOnPath,
288
+ getNpmMajorVersion,
289
+ NPX_REF,
290
+ PNPM_ALLOW_BUILD_BASE,
291
+ };
292
+
293
+ // Direct-exec entrypoint (#1945): `node run.cjs <gitnexus args…>` resolves the
294
+ // best available runner (global `gitnexus` → `pnpm dlx` → `npx`) at call time and
295
+ // runs it, inheriting stdio and propagating the child's exit code. This lets the
296
+ // committed skills and generated AGENTS.md/CLAUDE.md reference ONE stable,
297
+ // CLI-neutral command without baking in a package-manager assumption. `gitnexus
298
+ // analyze` drops a copy of this file at `.gitnexus/run.cjs`. Skipped on require()
299
+ // (the CLI and tests reuse the exports above), so it runs only when invoked as a
300
+ // script.
301
+ if (require.main === module) {
302
+ const gitnexusArgs = process.argv.slice(2);
303
+ const { program, args } = buildRunnerArgv(resolveInvocationMode(), gitnexusArgs);
304
+ try {
305
+ execFileSync(program, args, {
306
+ stdio: 'inherit',
307
+ windowsHide: true,
308
+ // On Windows, `npx`/`pnpm`/`gitnexus` resolve to `.cmd`/`.ps1`/`.exe`
309
+ // shims (npm, Volta, Corepack, scoop). execFileSync does not do PATHEXT
310
+ // resolution and Node refuses to spawn `.cmd`/`.bat` without a shell
311
+ // (CVE-2024-27980), so a bare program name ENOENTs. A shell lets the OS
312
+ // resolve the shim; POSIX needs no shell (direct PATH lookup works).
313
+ shell: process.platform === 'win32',
314
+ });
315
+ } catch (err) {
316
+ // Make spawn failures (resolved program absent from PATH) self-explanatory
317
+ // instead of a silent exit 1, then propagate the runner's own exit code.
318
+ if (typeof err.status !== 'number') {
319
+ process.stderr.write(`gitnexus runner: could not launch \`${program}\` — ${err.message}\n`);
320
+ }
321
+ process.exit(typeof err.status === 'number' ? err.status : 1);
322
+ }
323
+ }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "gitnexus",
3
- "version": "1.6.6-rc.98",
3
+ "version": "1.6.6",
4
4
  "description": "Graph-powered code intelligence for AI agents. Index any codebase, query via MCP or CLI.",
5
5
  "author": "Abhigyan Patwari",
6
6
  "license": "PolyForm-Noncommercial-1.0.0",
@@ -48,7 +48,6 @@
48
48
  "test:integration": "vitest run test/integration",
49
49
  "test:watch": "vitest",
50
50
  "test:coverage": "vitest run --coverage",
51
- "test:parity": "tsx scripts/run-parity.ts",
52
51
  "test:cross-platform": "tsx scripts/run-cross-platform.ts",
53
52
  "postinstall": "node scripts/materialize-vendor-grammars.cjs && node scripts/build-tree-sitter-dart.cjs && node scripts/build-tree-sitter-proto.cjs && node scripts/build-tree-sitter-swift.cjs",
54
53
  "prepare": "node scripts/build.js",
@@ -56,7 +55,7 @@
56
55
  },
57
56
  "dependencies": {
58
57
  "@huggingface/transformers": "^4.1.0",
59
- "@ladybugdb/core": "^0.16.1",
58
+ "@ladybugdb/core": "^0.17.0",
60
59
  "@modelcontextprotocol/sdk": "^1.0.0",
61
60
  "@scarf/scarf": "^1.4.0",
62
61
  "cli-progress": "^3.12.0",
@@ -71,13 +70,13 @@
71
70
  "ignore": "^7.0.5",
72
71
  "js-yaml": "^4.1.1",
73
72
  "jsonc-parser": "^3.3.1",
74
- "lru-cache": "^11.0.0",
75
73
  "mnemonist": "^0.40.3",
74
+ "onnxruntime-common": "^1.26.0",
76
75
  "onnxruntime-node": "^1.24.0",
77
76
  "pandemonium": "^2.4.0",
78
77
  "pino": "^10.3.1",
79
78
  "pino-pretty": "^13.1.3",
80
- "tree-sitter": "^0.21.1",
79
+ "tree-sitter": "0.21.1",
81
80
  "tree-sitter-c": "0.21.4",
82
81
  "tree-sitter-c-sharp": "0.23.1",
83
82
  "tree-sitter-cpp": "0.23.2",
@@ -4,10 +4,8 @@
4
4
  * isolating the resolution cost from parse / heritage / pipeline
5
5
  * overhead.
6
6
  *
7
- * Usage: REGISTRY_PRIMARY_PYTHON=1 npx tsx scripts/bench-scope-resolution.ts
7
+ * Usage: npx tsx scripts/bench-scope-resolution.ts
8
8
  */
9
- process.env.REGISTRY_PRIMARY_PYTHON = '1';
10
-
11
9
  import { generateId } from '../src/lib/utils.js';
12
10
  import { createKnowledgeGraph } from '../src/core/graph/graph.js';
13
11
  import { runScopeResolution } from '../src/core/ingestion/scope-resolution/index.js';