codebase-onboarder 0.6.0 → 0.7.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 (448) hide show
  1. package/README.md +174 -46
  2. package/bin/build-if-source.js +23 -0
  3. package/cli/commands.d.ts +26 -0
  4. package/cli/commands.js +836 -811
  5. package/cli/commands.js.map +1 -0
  6. package/cli/explorer/advanced.d.ts +14 -0
  7. package/cli/explorer/advanced.js +321 -329
  8. package/cli/explorer/advanced.js.map +1 -0
  9. package/cli/explorer/app.d.ts +1 -0
  10. package/cli/explorer/app.js +384 -313
  11. package/cli/explorer/app.js.map +1 -0
  12. package/cli/explorer/assistant.d.ts +9 -0
  13. package/cli/explorer/assistant.js +58 -0
  14. package/cli/explorer/assistant.js.map +1 -0
  15. package/cli/explorer/commands.d.ts +17 -0
  16. package/cli/explorer/commands.js +368 -302
  17. package/cli/explorer/commands.js.map +1 -0
  18. package/cli/explorer/featureViews.d.ts +124 -0
  19. package/cli/explorer/featureViews.js +179 -0
  20. package/cli/explorer/featureViews.js.map +1 -0
  21. package/cli/explorer/github.d.ts +21 -0
  22. package/cli/explorer/github.js +42 -44
  23. package/cli/explorer/github.js.map +1 -0
  24. package/cli/explorer/graphs.d.ts +7 -0
  25. package/cli/explorer/graphs.js +90 -95
  26. package/cli/explorer/graphs.js.map +1 -0
  27. package/cli/explorer/picker.d.ts +22 -0
  28. package/cli/explorer/picker.js +150 -0
  29. package/cli/explorer/picker.js.map +1 -0
  30. package/cli/explorer/report.d.ts +85 -0
  31. package/cli/explorer/report.js +60 -0
  32. package/cli/explorer/report.js.map +1 -0
  33. package/cli/explorer/session.d.ts +449 -0
  34. package/cli/explorer/session.js +143 -144
  35. package/cli/explorer/session.js.map +1 -0
  36. package/cli/explorer/views.d.ts +19 -0
  37. package/cli/explorer/views.js +465 -482
  38. package/cli/explorer/views.js.map +1 -0
  39. package/cli/explorer/wrap.d.ts +1 -0
  40. package/cli/explorer/wrap.js +28 -44
  41. package/cli/explorer/wrap.js.map +1 -0
  42. package/cli/main.d.ts +1 -0
  43. package/cli/main.js +214 -161
  44. package/cli/main.js.map +1 -0
  45. package/cli/prompt.d.ts +5 -0
  46. package/cli/prompt.js +84 -80
  47. package/cli/prompt.js.map +1 -0
  48. package/cli/scanOptions.d.ts +2 -0
  49. package/cli/scanOptions.js +11 -0
  50. package/cli/scanOptions.js.map +1 -0
  51. package/cli/ui.d.ts +33 -0
  52. package/cli/ui.js +35 -44
  53. package/cli/ui.js.map +1 -0
  54. package/cli/wizard.d.ts +187 -0
  55. package/cli/wizard.js +304 -284
  56. package/cli/wizard.js.map +1 -0
  57. package/package.json +15 -4
  58. package/public/app.d.ts +1 -0
  59. package/public/app.js +1057 -1009
  60. package/public/app.js.map +1 -0
  61. package/public/browser.d.ts +68 -0
  62. package/public/browser.js +2 -0
  63. package/public/browser.js.map +1 -0
  64. package/public/index.html +30 -13
  65. package/public/js/about.d.ts +6 -0
  66. package/public/js/about.js +152 -172
  67. package/public/js/about.js.map +1 -0
  68. package/public/js/aiDraft.d.ts +3 -0
  69. package/public/js/aiDraft.js +116 -124
  70. package/public/js/aiDraft.js.map +1 -0
  71. package/public/js/analysisPanel.d.ts +7 -0
  72. package/public/js/analysisPanel.js +166 -166
  73. package/public/js/analysisPanel.js.map +1 -0
  74. package/public/js/analysisReport.d.ts +38 -0
  75. package/public/js/analysisReport.js +105 -110
  76. package/public/js/analysisReport.js.map +1 -0
  77. package/public/js/api.d.ts +26 -0
  78. package/public/js/api.js +176 -167
  79. package/public/js/api.js.map +1 -0
  80. package/public/js/atlas.d.ts +6 -0
  81. package/public/js/atlas.js +50 -58
  82. package/public/js/atlas.js.map +1 -0
  83. package/public/js/blameView.d.ts +2 -0
  84. package/public/js/blameView.js +36 -37
  85. package/public/js/blameView.js.map +1 -0
  86. package/public/js/codeTab.d.ts +3 -0
  87. package/public/js/codeTab.js +175 -180
  88. package/public/js/codeTab.js.map +1 -0
  89. package/public/js/codeViewer.d.ts +5 -0
  90. package/public/js/codeViewer.js +162 -150
  91. package/public/js/codeViewer.js.map +1 -0
  92. package/public/js/components/FileChip.d.ts +9 -0
  93. package/public/js/components/FileChip.js +45 -49
  94. package/public/js/components/FileChip.js.map +1 -0
  95. package/public/js/components/MetricSparkline.d.ts +7 -0
  96. package/public/js/components/MetricSparkline.js +35 -44
  97. package/public/js/components/MetricSparkline.js.map +1 -0
  98. package/public/js/components/RiskBadge.d.ts +9 -0
  99. package/public/js/components/RiskBadge.js +55 -63
  100. package/public/js/components/RiskBadge.js.map +1 -0
  101. package/public/js/deepAnalysisView.d.ts +99 -0
  102. package/public/js/deepAnalysisView.js +282 -302
  103. package/public/js/deepAnalysisView.js.map +1 -0
  104. package/public/js/diagramPane.d.ts +8 -0
  105. package/public/js/diagramPane.js +133 -135
  106. package/public/js/diagramPane.js.map +1 -0
  107. package/public/js/diffView.d.ts +6 -0
  108. package/public/js/diffView.js +222 -209
  109. package/public/js/diffView.js.map +1 -0
  110. package/public/js/docsView.d.ts +2 -0
  111. package/public/js/docsView.js +441 -442
  112. package/public/js/docsView.js.map +1 -0
  113. package/public/js/dom.d.ts +189 -0
  114. package/public/js/dom.js +5 -0
  115. package/public/js/dom.js.map +1 -0
  116. package/public/js/fileSourceBrowser.d.ts +5 -0
  117. package/public/js/fileSourceBrowser.js +33 -41
  118. package/public/js/fileSourceBrowser.js.map +1 -0
  119. package/public/js/flameGraph.d.ts +5 -0
  120. package/public/js/flameGraph.js +62 -72
  121. package/public/js/flameGraph.js.map +1 -0
  122. package/public/js/forceGraph.d.ts +10 -0
  123. package/public/js/forceGraph.js +581 -556
  124. package/public/js/forceGraph.js.map +1 -0
  125. package/public/js/heatmap.d.ts +4 -0
  126. package/public/js/heatmap.js +142 -164
  127. package/public/js/heatmap.js.map +1 -0
  128. package/public/js/highlight.d.ts +2 -0
  129. package/public/js/highlight.js +116 -107
  130. package/public/js/highlight.js.map +1 -0
  131. package/public/js/html.d.ts +2 -0
  132. package/public/js/html.js +14 -44
  133. package/public/js/html.js.map +1 -0
  134. package/public/js/insightsView.d.ts +5 -0
  135. package/public/js/insightsView.js +93 -111
  136. package/public/js/insightsView.js.map +1 -0
  137. package/public/js/inspector.d.ts +37 -0
  138. package/public/js/inspector.js +416 -445
  139. package/public/js/inspector.js.map +1 -0
  140. package/public/js/llm.d.ts +113 -0
  141. package/public/js/llm.js +233 -272
  142. package/public/js/llm.js.map +1 -0
  143. package/public/js/mapView.d.ts +3 -0
  144. package/public/js/mapView.js +121 -120
  145. package/public/js/mapView.js.map +1 -0
  146. package/public/js/markdown.d.ts +3 -0
  147. package/public/js/markdown.js +84 -91
  148. package/public/js/markdown.js.map +1 -0
  149. package/public/js/mindmap.d.ts +32 -0
  150. package/public/js/mindmap.js +244 -259
  151. package/public/js/mindmap.js.map +1 -0
  152. package/public/js/mobilePanels.d.ts +5 -0
  153. package/public/js/mobilePanels.js +50 -0
  154. package/public/js/mobilePanels.js.map +1 -0
  155. package/public/js/repoFiles.d.ts +12 -0
  156. package/public/js/repoFiles.js +28 -27
  157. package/public/js/repoFiles.js.map +1 -0
  158. package/public/js/reviewView.d.ts +28 -0
  159. package/public/js/reviewView.js +256 -0
  160. package/public/js/reviewView.js.map +1 -0
  161. package/public/js/sbomView.d.ts +3 -0
  162. package/public/js/sbomView.js +59 -67
  163. package/public/js/sbomView.js.map +1 -0
  164. package/public/js/scanCache.d.ts +16 -0
  165. package/public/js/scanCache.js +67 -65
  166. package/public/js/scanCache.js.map +1 -0
  167. package/public/js/search.d.ts +7 -0
  168. package/public/js/search.js +868 -800
  169. package/public/js/search.js.map +1 -0
  170. package/public/js/searchLocal.d.ts +42 -0
  171. package/public/js/searchLocal.js +87 -0
  172. package/public/js/searchLocal.js.map +1 -0
  173. package/public/js/serverSettings.d.ts +5 -0
  174. package/public/js/serverSettings.js +153 -164
  175. package/public/js/serverSettings.js.map +1 -0
  176. package/public/js/state.d.ts +798 -0
  177. package/public/js/state.js +114 -122
  178. package/public/js/state.js.map +1 -0
  179. package/public/js/tour.d.ts +6 -0
  180. package/public/js/tour.js +5 -7
  181. package/public/js/tour.js.map +1 -0
  182. package/public/js/transitions.d.ts +2 -0
  183. package/public/js/transitions.js +9 -10
  184. package/public/js/transitions.js.map +1 -0
  185. package/public/js/tree.d.ts +12 -0
  186. package/public/js/tree.js +157 -154
  187. package/public/js/tree.js.map +1 -0
  188. package/public/js/workflowsView.d.ts +3 -0
  189. package/public/js/workflowsView.js +15 -22
  190. package/public/js/workflowsView.js.map +1 -0
  191. package/public/search.css +495 -0
  192. package/public/styles.css +163 -346
  193. package/public/workbench.css +166 -0
  194. package/server/apiAuth.d.ts +3 -0
  195. package/server/apiAuth.js +18 -20
  196. package/server/apiAuth.js.map +1 -0
  197. package/server/apiDiff.d.ts +2 -0
  198. package/server/apiDiff.js +20 -18
  199. package/server/apiDiff.js.map +1 -0
  200. package/server/apiDocs.d.ts +2 -0
  201. package/server/apiDocs.js +38 -40
  202. package/server/apiDocs.js.map +1 -0
  203. package/server/apiFile.d.ts +1 -0
  204. package/server/apiFile.js +14 -17
  205. package/server/apiFile.js.map +1 -0
  206. package/server/apiGitBlame.d.ts +2 -0
  207. package/server/apiGitBlame.js +50 -51
  208. package/server/apiGitBlame.js.map +1 -0
  209. package/server/apiMcp.d.ts +4 -0
  210. package/server/apiMcp.js +64 -66
  211. package/server/apiMcp.js.map +1 -0
  212. package/server/apiReview.d.ts +2 -0
  213. package/server/apiReview.js +45 -0
  214. package/server/apiReview.js.map +1 -0
  215. package/server/apiScan.d.ts +5 -0
  216. package/server/apiScan.js +90 -71
  217. package/server/apiScan.js.map +1 -0
  218. package/server/apiSearch.d.ts +33 -0
  219. package/server/apiSearch.js +184 -200
  220. package/server/apiSearch.js.map +1 -0
  221. package/server/apiSettings.d.ts +4 -0
  222. package/server/apiSettings.js +84 -85
  223. package/server/apiSettings.js.map +1 -0
  224. package/server/apiTools.d.ts +3 -0
  225. package/server/apiTools.js +55 -56
  226. package/server/apiTools.js.map +1 -0
  227. package/server/auth.d.ts +5 -0
  228. package/server/auth.js +54 -51
  229. package/server/auth.js.map +1 -0
  230. package/server/config.d.ts +42 -0
  231. package/server/config.js +189 -194
  232. package/server/config.js.map +1 -0
  233. package/server/daemon.d.ts +12 -0
  234. package/server/daemon.js +124 -114
  235. package/server/daemon.js.map +1 -0
  236. package/server/fileSourceNode.d.ts +2 -0
  237. package/server/fileSourceNode.js +34 -36
  238. package/server/fileSourceNode.js.map +1 -0
  239. package/server/gitClone.d.ts +9 -0
  240. package/server/gitClone.js +59 -61
  241. package/server/gitClone.js.map +1 -0
  242. package/server/gitDiff.d.ts +36 -0
  243. package/server/gitDiff.js +271 -169
  244. package/server/gitDiff.js.map +1 -0
  245. package/server/gitHistory.d.ts +12 -0
  246. package/server/gitHistory.js +80 -80
  247. package/server/gitHistory.js.map +1 -0
  248. package/server/gitRemote.d.ts +12 -0
  249. package/server/gitRemote.js +37 -38
  250. package/server/gitRemote.js.map +1 -0
  251. package/server/htmlText.d.ts +4 -0
  252. package/server/htmlText.js +16 -23
  253. package/server/htmlText.js.map +1 -0
  254. package/server/http.d.ts +5 -0
  255. package/server/http.js +27 -30
  256. package/server/http.js.map +1 -0
  257. package/server/httpGuards.d.ts +2 -0
  258. package/server/httpGuards.js +47 -43
  259. package/server/httpGuards.js.map +1 -0
  260. package/server/https.d.ts +34 -0
  261. package/server/https.js +121 -111
  262. package/server/https.js.map +1 -0
  263. package/server/index.d.ts +40 -0
  264. package/server/index.js +139 -147
  265. package/server/index.js.map +1 -0
  266. package/server/layout.d.ts +26 -0
  267. package/server/layout.js +59 -64
  268. package/server/layout.js.map +1 -0
  269. package/server/llmProxy.d.ts +3 -0
  270. package/server/llmProxy.js +137 -135
  271. package/server/llmProxy.js.map +1 -0
  272. package/server/logger.d.ts +38 -0
  273. package/server/logger.js +198 -211
  274. package/server/logger.js.map +1 -0
  275. package/server/mcp/analysis.d.ts +29 -0
  276. package/server/mcp/analysis.js +99 -120
  277. package/server/mcp/analysis.js.map +1 -0
  278. package/server/mcp/http.d.ts +9 -0
  279. package/server/mcp/http.js +128 -137
  280. package/server/mcp/http.js.map +1 -0
  281. package/server/mcp/runner.d.ts +68 -0
  282. package/server/mcp/runner.js +208 -218
  283. package/server/mcp/runner.js.map +1 -0
  284. package/server/mcp/server.d.ts +29 -0
  285. package/server/mcp/server.js +166 -179
  286. package/server/mcp/server.js.map +1 -0
  287. package/server/mcp/standalone.d.ts +1 -0
  288. package/server/mcp/standalone.js +8 -10
  289. package/server/mcp/standalone.js.map +1 -0
  290. package/server/mcp/tools.d.ts +2020 -0
  291. package/server/mcp/tools.js +523 -574
  292. package/server/mcp/tools.js.map +1 -0
  293. package/server/paths.d.ts +3 -0
  294. package/server/paths.js +17 -15
  295. package/server/paths.js.map +1 -0
  296. package/server/pidfile.d.ts +9 -0
  297. package/server/pidfile.js +43 -45
  298. package/server/pidfile.js.map +1 -0
  299. package/server/review.d.ts +5 -0
  300. package/server/review.js +35 -0
  301. package/server/review.js.map +1 -0
  302. package/server/router.d.ts +33 -0
  303. package/server/router.js +191 -197
  304. package/server/router.js.map +1 -0
  305. package/server/scanRequest.d.ts +3 -0
  306. package/server/scanRequest.js +36 -0
  307. package/server/scanRequest.js.map +1 -0
  308. package/server/searchIndex.d.ts +17 -0
  309. package/server/searchIndex.js +83 -80
  310. package/server/searchIndex.js.map +1 -0
  311. package/server/sessions.d.ts +14 -0
  312. package/server/sessions.js +62 -70
  313. package/server/sessions.js.map +1 -0
  314. package/server/startup.d.ts +118 -0
  315. package/server/startup.js +143 -148
  316. package/server/startup.js.map +1 -0
  317. package/server/static.d.ts +6 -0
  318. package/server/static.js +28 -31
  319. package/server/static.js.map +1 -0
  320. package/server/tools/install.d.ts +4 -0
  321. package/server/tools/install.js +176 -185
  322. package/server/tools/install.js.map +1 -0
  323. package/server/tools/parse.d.ts +8 -0
  324. package/server/tools/parse.js +112 -114
  325. package/server/tools/parse.js.map +1 -0
  326. package/server/tools/platform.d.ts +9 -0
  327. package/server/tools/platform.js +49 -47
  328. package/server/tools/platform.js.map +1 -0
  329. package/server/tools/registry.d.ts +137 -0
  330. package/server/tools/registry.js +173 -172
  331. package/server/tools/registry.js.map +1 -0
  332. package/server/tools/scan.d.ts +34 -0
  333. package/server/tools/scan.js +89 -98
  334. package/server/tools/scan.js.map +1 -0
  335. package/server/tools.d.ts +34 -0
  336. package/server/tools.js +94 -107
  337. package/server/tools.js.map +1 -0
  338. package/server/tunnel.d.ts +29 -0
  339. package/server/tunnel.js +61 -66
  340. package/server/tunnel.js.map +1 -0
  341. package/shared/analyzer/docs.d.ts +16 -0
  342. package/shared/analyzer/docs.js +99 -93
  343. package/shared/analyzer/docs.js.map +1 -0
  344. package/shared/analyzer/explainLocal.d.ts +4 -0
  345. package/shared/analyzer/explainLocal.js +122 -142
  346. package/shared/analyzer/explainLocal.js.map +1 -0
  347. package/shared/analyzer/github.d.ts +37 -0
  348. package/shared/analyzer/github.js +41 -43
  349. package/shared/analyzer/github.js.map +1 -0
  350. package/shared/analyzer/graph.d.ts +41 -0
  351. package/shared/analyzer/graph.js +393 -400
  352. package/shared/analyzer/graph.js.map +1 -0
  353. package/shared/analyzer/health.d.ts +33 -0
  354. package/shared/analyzer/health.js +197 -193
  355. package/shared/analyzer/health.js.map +1 -0
  356. package/shared/analyzer/history.d.ts +29 -0
  357. package/shared/analyzer/history.js +110 -111
  358. package/shared/analyzer/history.js.map +1 -0
  359. package/shared/analyzer/jsonConfig.d.ts +2 -0
  360. package/shared/analyzer/jsonConfig.js +61 -0
  361. package/shared/analyzer/jsonConfig.js.map +1 -0
  362. package/shared/analyzer/languages/csharp.d.ts +26 -0
  363. package/shared/analyzer/languages/csharp.js +83 -88
  364. package/shared/analyzer/languages/csharp.js.map +1 -0
  365. package/shared/analyzer/languages/generic.d.ts +23 -0
  366. package/shared/analyzer/languages/generic.js +94 -105
  367. package/shared/analyzer/languages/generic.js.map +1 -0
  368. package/shared/analyzer/languages/go.d.ts +24 -0
  369. package/shared/analyzer/languages/go.js +45 -54
  370. package/shared/analyzer/languages/go.js.map +1 -0
  371. package/shared/analyzer/languages/index.d.ts +6 -0
  372. package/shared/analyzer/languages/index.js +19 -20
  373. package/shared/analyzer/languages/index.js.map +1 -0
  374. package/shared/analyzer/languages/java.d.ts +20 -0
  375. package/shared/analyzer/languages/java.js +73 -78
  376. package/shared/analyzer/languages/java.js.map +1 -0
  377. package/shared/analyzer/languages/javascript.d.ts +12 -0
  378. package/shared/analyzer/languages/javascript.js +258 -209
  379. package/shared/analyzer/languages/javascript.js.map +1 -0
  380. package/shared/analyzer/languages/python.d.ts +23 -0
  381. package/shared/analyzer/languages/python.js +92 -100
  382. package/shared/analyzer/languages/python.js.map +1 -0
  383. package/shared/analyzer/languages/rust.d.ts +17 -0
  384. package/shared/analyzer/languages/rust.js +96 -98
  385. package/shared/analyzer/languages/rust.js.map +1 -0
  386. package/shared/analyzer/languages/typescript.d.ts +11 -0
  387. package/shared/analyzer/languages/typescript.js +117 -116
  388. package/shared/analyzer/languages/typescript.js.map +1 -0
  389. package/shared/analyzer/licenses.d.ts +18 -0
  390. package/shared/analyzer/licenses.js +130 -133
  391. package/shared/analyzer/licenses.js.map +1 -0
  392. package/shared/analyzer/metrics.d.ts +20 -0
  393. package/shared/analyzer/metrics.js +112 -104
  394. package/shared/analyzer/metrics.js.map +1 -0
  395. package/shared/analyzer/pathUtil.d.ts +10 -0
  396. package/shared/analyzer/pathUtil.js +29 -35
  397. package/shared/analyzer/pathUtil.js.map +1 -0
  398. package/shared/analyzer/patterns.d.ts +11 -0
  399. package/shared/analyzer/patterns.js +231 -253
  400. package/shared/analyzer/patterns.js.map +1 -0
  401. package/shared/analyzer/scan.d.ts +62 -0
  402. package/shared/analyzer/scan.js +451 -442
  403. package/shared/analyzer/scan.js.map +1 -0
  404. package/shared/analyzer/scanControl.d.ts +11 -0
  405. package/shared/analyzer/scanControl.js +62 -0
  406. package/shared/analyzer/scanControl.js.map +1 -0
  407. package/shared/analyzer/security.d.ts +18 -0
  408. package/shared/analyzer/security.js +159 -159
  409. package/shared/analyzer/security.js.map +1 -0
  410. package/shared/analyzer/services.d.ts +5 -0
  411. package/shared/analyzer/services.js +141 -138
  412. package/shared/analyzer/services.js.map +1 -0
  413. package/shared/analyzer/stack.d.ts +6 -0
  414. package/shared/analyzer/stack.js +134 -141
  415. package/shared/analyzer/stack.js.map +1 -0
  416. package/shared/analyzer/tour.d.ts +2 -0
  417. package/shared/analyzer/tour.js +45 -53
  418. package/shared/analyzer/tour.js.map +1 -0
  419. package/shared/analyzer/util.d.ts +8 -0
  420. package/shared/analyzer/util.js +130 -76
  421. package/shared/analyzer/util.js.map +1 -0
  422. package/shared/analyzer/workflows.d.ts +8 -0
  423. package/shared/analyzer/workflows.js +139 -134
  424. package/shared/analyzer/workflows.js.map +1 -0
  425. package/shared/contracts.d.ts +250 -0
  426. package/shared/contracts.js +2 -0
  427. package/shared/contracts.js.map +1 -0
  428. package/shared/diagram/aiFacts.d.ts +35 -0
  429. package/shared/diagram/aiFacts.js +102 -105
  430. package/shared/diagram/aiFacts.js.map +1 -0
  431. package/shared/diagram/aiMermaid.d.ts +5 -0
  432. package/shared/diagram/aiMermaid.js +46 -45
  433. package/shared/diagram/aiMermaid.js.map +1 -0
  434. package/shared/diagram/atlas.d.ts +16 -0
  435. package/shared/diagram/atlas.js +51 -60
  436. package/shared/diagram/atlas.js.map +1 -0
  437. package/shared/diagram/mermaid.d.ts +43 -0
  438. package/shared/diagram/mermaid.js +348 -370
  439. package/shared/diagram/mermaid.js.map +1 -0
  440. package/shared/review/contracts.d.ts +95 -0
  441. package/shared/review/contracts.js +2 -0
  442. package/shared/review/contracts.js.map +1 -0
  443. package/shared/review/review.d.ts +10 -0
  444. package/shared/review/review.js +184 -0
  445. package/shared/review/review.js.map +1 -0
  446. package/shared/search/query.d.ts +32 -0
  447. package/shared/search/query.js +395 -388
  448. package/shared/search/query.js.map +1 -0
@@ -2,100 +2,96 @@
2
2
  // language counts, name the frameworks, libraries and languages a repo leans
3
3
  // on — each tagged with a category and the official docs URL. The docs URLs
4
4
  // feed the server-side /api/doc fetch (allowlisted) for informed summaries.
5
-
6
5
  // name -> [category, docs url]
7
6
  const KNOWN = {
8
- react: ['Frontend framework', 'https://react.dev'],
9
- 'react-dom': ['Frontend framework', 'https://react.dev'],
10
- '@angular/core': ['Frontend framework', 'https://angular.dev'],
11
- vue: ['Frontend framework', 'https://vuejs.org'],
12
- svelte: ['Frontend framework', 'https://svelte.dev'],
13
- next: ['Web framework', 'https://nextjs.org/docs'],
14
- nuxt: ['Web framework', 'https://nuxt.com/docs'],
15
- remix: ['Web framework', 'https://remix.run/docs'],
16
- gatsby: ['Web framework', 'https://www.gatsbyjs.com/docs'],
17
- express: ['Web framework', 'https://expressjs.com'],
18
- fastify: ['Web framework', 'https://fastify.dev'],
19
- koa: ['Web framework', 'https://koajs.com'],
20
- '@nestjs/core': ['Web framework', 'https://docs.nestjs.com'],
21
- hapi: ['Web framework', 'https://hapi.dev'],
22
- flask: ['Web framework', 'https://flask.palletsprojects.com'],
23
- django: ['Web framework', 'https://docs.djangoproject.com'],
24
- fastapi: ['Web framework', 'https://fastapi.tiangolo.com'],
25
- 'spring-boot': ['Web framework', 'https://docs.spring.io/spring-boot'],
26
- laravel: ['Web framework', 'https://laravel.com/docs'],
27
- rails: ['Web framework', 'https://guides.rubyonrails.org'],
28
- gin: ['Web framework', 'https://gin-gonic.com'],
29
- echo: ['Web framework', 'https://echo.labstack.com'],
30
- fiber: ['Web framework', 'https://gofiber.io'],
31
- 'actix-web': ['Web framework', 'https://actix.rs'],
32
- axum: ['Web framework', 'https://docs.rs/axum'],
33
- rocket: ['Web framework', 'https://rocket.rs'],
34
- prisma: ['Database / ORM', 'https://www.prisma.io/docs'],
35
- sequelize: ['Database / ORM', 'https://sequelize.org'],
36
- typeorm: ['Database / ORM', 'https://typeorm.io'],
37
- sqlalchemy: ['Database / ORM', 'https://docs.sqlalchemy.org'],
38
- 'drizzle-orm': ['Database / ORM', 'https://orm.drizzle.team'],
39
- mongoose: ['Database / ORM', 'https://mongoosejs.com'],
40
- knex: ['Database / ORM', 'https://knexjs.org'],
41
- pg: ['Database / ORM', 'https://node-postgres.com'],
42
- pymongo: ['Database / ORM', 'https://pymongo.readthedocs.io'],
43
- gorm: ['Database / ORM', 'https://gorm.io'],
44
- sqlx: ['Database / ORM', 'https://docs.rs/sqlx'],
45
- diesel: ['Database / ORM', 'https://diesel.rs'],
46
- redis: ['Database / ORM', 'https://redis.io/docs/'],
47
- jest: ['Testing', 'https://jestjs.io'],
48
- vitest: ['Testing', 'https://vitest.dev'],
49
- mocha: ['Testing', 'https://mochajs.org'],
50
- '@testing-library/react': ['Testing', 'https://testing-library.com'],
51
- pytest: ['Testing', 'https://docs.pytest.org'],
52
- playwright: ['Testing', 'https://playwright.dev'],
53
- cypress: ['Testing', 'https://docs.cypress.io'],
54
- rspec: ['Testing', 'https://rspec.info'],
55
- typescript: ['Tooling / build', 'https://www.typescriptlang.org/docs'],
56
- vite: ['Tooling / build', 'https://vitejs.dev/guide/'],
57
- webpack: ['Tooling / build', 'https://webpack.js.org'],
58
- esbuild: ['Tooling / build', 'https://esbuild.github.io'],
59
- babel: ['Tooling / build', 'https://babeljs.io/docs'],
60
- rollup: ['Tooling / build', 'https://rollupjs.org'],
61
- tailwindcss: ['UI / styling', 'https://tailwindcss.com/docs'],
62
- bootstrap: ['UI / styling', 'https://getbootstrap.com/docs'],
63
- sass: ['UI / styling', 'https://sass-lang.com/documentation'],
64
- 'styled-components': ['UI / styling', 'https://styled-components.com'],
65
- axios: ['Networking', 'https://axios-http.com'],
66
- requests: ['Networking', 'https://requests.readthedocs.io'],
67
- urllib3: ['Networking', 'https://urllib3.readthedocs.io'],
68
- httpx: ['Networking', 'https://www.python-httpx.org'],
69
- passport: ['Auth', 'https://www.passportjs.org'],
70
- 'next-auth': ['Auth', 'https://next-auth.js.org'],
71
- jsonwebtoken: ['Auth', 'https://github.com/auth0/node-jsonwebtoken'],
72
- pydantic: ['Data validation', 'https://docs.pydantic.dev'],
73
- numpy: ['Data / science', 'https://numpy.org/doc/'],
74
- pandas: ['Data / science', 'https://pandas.pydata.org/docs/'],
75
- 'scikit-learn': ['Data / science', 'https://scikit-learn.org/stable/'],
76
- torch: ['Data / science', 'https://pytorch.org/docs/'],
77
- tensorflow: ['Data / science', 'https://www.tensorflow.org/api_docs'],
78
- 'opencv-python': ['Data / science', 'https://docs.opencv.org'],
79
- keras: ['Data / science', 'https://keras.io'],
80
- 'python-dotenv': ['Tooling / config', 'https://github.com/theskumar/python-dotenv'],
7
+ react: ['Frontend framework', 'https://react.dev'],
8
+ 'react-dom': ['Frontend framework', 'https://react.dev'],
9
+ '@angular/core': ['Frontend framework', 'https://angular.dev'],
10
+ vue: ['Frontend framework', 'https://vuejs.org'],
11
+ svelte: ['Frontend framework', 'https://svelte.dev'],
12
+ next: ['Web framework', 'https://nextjs.org/docs'],
13
+ nuxt: ['Web framework', 'https://nuxt.com/docs'],
14
+ remix: ['Web framework', 'https://remix.run/docs'],
15
+ gatsby: ['Web framework', 'https://www.gatsbyjs.com/docs'],
16
+ express: ['Web framework', 'https://expressjs.com'],
17
+ fastify: ['Web framework', 'https://fastify.dev'],
18
+ koa: ['Web framework', 'https://koajs.com'],
19
+ '@nestjs/core': ['Web framework', 'https://docs.nestjs.com'],
20
+ hapi: ['Web framework', 'https://hapi.dev'],
21
+ flask: ['Web framework', 'https://flask.palletsprojects.com'],
22
+ django: ['Web framework', 'https://docs.djangoproject.com'],
23
+ fastapi: ['Web framework', 'https://fastapi.tiangolo.com'],
24
+ 'spring-boot': ['Web framework', 'https://docs.spring.io/spring-boot'],
25
+ laravel: ['Web framework', 'https://laravel.com/docs'],
26
+ rails: ['Web framework', 'https://guides.rubyonrails.org'],
27
+ gin: ['Web framework', 'https://gin-gonic.com'],
28
+ echo: ['Web framework', 'https://echo.labstack.com'],
29
+ fiber: ['Web framework', 'https://gofiber.io'],
30
+ 'actix-web': ['Web framework', 'https://actix.rs'],
31
+ axum: ['Web framework', 'https://docs.rs/axum'],
32
+ rocket: ['Web framework', 'https://rocket.rs'],
33
+ prisma: ['Database / ORM', 'https://www.prisma.io/docs'],
34
+ sequelize: ['Database / ORM', 'https://sequelize.org'],
35
+ typeorm: ['Database / ORM', 'https://typeorm.io'],
36
+ sqlalchemy: ['Database / ORM', 'https://docs.sqlalchemy.org'],
37
+ 'drizzle-orm': ['Database / ORM', 'https://orm.drizzle.team'],
38
+ mongoose: ['Database / ORM', 'https://mongoosejs.com'],
39
+ knex: ['Database / ORM', 'https://knexjs.org'],
40
+ pg: ['Database / ORM', 'https://node-postgres.com'],
41
+ pymongo: ['Database / ORM', 'https://pymongo.readthedocs.io'],
42
+ gorm: ['Database / ORM', 'https://gorm.io'],
43
+ sqlx: ['Database / ORM', 'https://docs.rs/sqlx'],
44
+ diesel: ['Database / ORM', 'https://diesel.rs'],
45
+ redis: ['Database / ORM', 'https://redis.io/docs/'],
46
+ jest: ['Testing', 'https://jestjs.io'],
47
+ vitest: ['Testing', 'https://vitest.dev'],
48
+ mocha: ['Testing', 'https://mochajs.org'],
49
+ '@testing-library/react': ['Testing', 'https://testing-library.com'],
50
+ pytest: ['Testing', 'https://docs.pytest.org'],
51
+ playwright: ['Testing', 'https://playwright.dev'],
52
+ cypress: ['Testing', 'https://docs.cypress.io'],
53
+ rspec: ['Testing', 'https://rspec.info'],
54
+ typescript: ['Tooling / build', 'https://www.typescriptlang.org/docs'],
55
+ vite: ['Tooling / build', 'https://vitejs.dev/guide/'],
56
+ webpack: ['Tooling / build', 'https://webpack.js.org'],
57
+ esbuild: ['Tooling / build', 'https://esbuild.github.io'],
58
+ babel: ['Tooling / build', 'https://babeljs.io/docs'],
59
+ rollup: ['Tooling / build', 'https://rollupjs.org'],
60
+ tailwindcss: ['UI / styling', 'https://tailwindcss.com/docs'],
61
+ bootstrap: ['UI / styling', 'https://getbootstrap.com/docs'],
62
+ sass: ['UI / styling', 'https://sass-lang.com/documentation'],
63
+ 'styled-components': ['UI / styling', 'https://styled-components.com'],
64
+ axios: ['Networking', 'https://axios-http.com'],
65
+ requests: ['Networking', 'https://requests.readthedocs.io'],
66
+ urllib3: ['Networking', 'https://urllib3.readthedocs.io'],
67
+ httpx: ['Networking', 'https://www.python-httpx.org'],
68
+ passport: ['Auth', 'https://www.passportjs.org'],
69
+ 'next-auth': ['Auth', 'https://next-auth.js.org'],
70
+ jsonwebtoken: ['Auth', 'https://github.com/auth0/node-jsonwebtoken'],
71
+ pydantic: ['Data validation', 'https://docs.pydantic.dev'],
72
+ numpy: ['Data / science', 'https://numpy.org/doc/'],
73
+ pandas: ['Data / science', 'https://pandas.pydata.org/docs/'],
74
+ 'scikit-learn': ['Data / science', 'https://scikit-learn.org/stable/'],
75
+ torch: ['Data / science', 'https://pytorch.org/docs/'],
76
+ tensorflow: ['Data / science', 'https://www.tensorflow.org/api_docs'],
77
+ 'opencv-python': ['Data / science', 'https://docs.opencv.org'],
78
+ keras: ['Data / science', 'https://keras.io'],
79
+ 'python-dotenv': ['Tooling / config', 'https://github.com/theskumar/python-dotenv'],
81
80
  };
82
-
83
81
  const ORDER = [
84
- 'Web framework', 'Frontend framework', 'Database / ORM', 'Auth',
85
- 'Networking', 'Data / science', 'Data validation', 'UI / styling',
86
- 'Testing', 'Tooling / build', 'Tooling / config', 'Library',
82
+ 'Web framework', 'Frontend framework', 'Database / ORM', 'Auth',
83
+ 'Networking', 'Data / science', 'Data validation', 'UI / styling',
84
+ 'Testing', 'Tooling / build', 'Tooling / config', 'Library',
87
85
  ];
88
-
89
86
  // Where a dependency that is not in KNOWN sends you: its registry page. Named
90
87
  // here rather than inlined below because two things need them — the URL
91
88
  // builders, and the host allowlist under them.
92
89
  const REGISTRY = {
93
- npm: (name) => `https://www.npmjs.com/package/${name}`,
94
- pip: (name) => `https://pypi.org/project/${name}/`,
95
- go: (name) => `https://pkg.go.dev/${name}`,
96
- cargo: (name) => `https://docs.rs/${name}`,
90
+ npm: (name) => `https://www.npmjs.com/package/${name}`,
91
+ pip: (name) => `https://pypi.org/project/${name}/`,
92
+ go: (name) => `https://pkg.go.dev/${name}`,
93
+ cargo: (name) => `https://docs.rs/${name}`,
97
94
  };
98
-
99
95
  // Every host `analyzeStack` can hand out a docs URL for. The server allowlists
100
96
  // exactly this set for `/api/doc`, and that is the SSRF guard: a host no
101
97
  // dependency name can produce is a host the server will not fetch.
@@ -110,64 +106,61 @@ const REGISTRY = {
110
106
  // `www.` comes off because the caller strips it from the incoming host too;
111
107
  // leaving it on would mean `www.npmjs.com` never matched a request for
112
108
  // `npmjs.com`.
113
- export const DOC_HOSTS = Object.freeze([...new Set(
114
- [
115
- ...Object.values(KNOWN).map(([, url]) => url),
116
- ...Object.values(REGISTRY).map((toUrl) => toUrl('any')),
117
- ].map((url) => new URL(url).hostname.replace(/^www\./, ''))
118
- )].sort());
119
-
109
+ export const DOC_HOSTS = Object.freeze([...new Set([
110
+ ...Object.values(KNOWN).map(([, url]) => url),
111
+ ...Object.values(REGISTRY).map((toUrl) => toUrl('any')),
112
+ ].map((url) => new URL(url).hostname.replace(/^www\./, '')))].sort());
120
113
  function cleanVersion(v) {
121
- return String(v || '').replace(/^[\^~>=< ]+/, '').split(' ')[0].trim();
114
+ return String(v || '').replace(/^[\^~>=< ]+/, '').split(' ')[0].trim();
122
115
  }
123
-
124
116
  export function analyzeStack(manifest = {}, languages = {}) {
125
- const deps = manifest.deps || { npm: {}, dev: {}, pip: [], go: [], cargo: [] };
126
- const items = [];
127
- const seen = new Set();
128
-
129
- const add = (name, version, category, lang, docs, dev = false) => {
130
- if (!name || seen.has(name)) return;
131
- seen.add(name);
132
- items.push({ name, version: cleanVersion(version), category, lang, docs, dev });
133
- };
134
-
135
- const npmDocs = (name) => {
136
- const k = KNOWN[name];
137
- return k ? k[1] : REGISTRY.npm(name);
138
- };
139
- const catOf = (name) => {
140
- const k = KNOWN[name];
141
- return k ? k[0] : 'Library';
142
- };
143
-
144
- for (const [name, ver] of Object.entries(deps.npm || {})) {
145
- if (name !== 'react-dom') add(name, ver, catOf(name), 'JavaScript', npmDocs(name), false);
146
- }
147
- for (const [name, ver] of Object.entries(deps.dev || {})) {
148
- if (name !== 'react-dom') add(name, ver, catOf(name), 'JavaScript', npmDocs(name), true);
149
- }
150
- for (const name of deps.pip || []) {
151
- const k = KNOWN[name];
152
- add(name, '', k ? k[0] : 'Library', 'Python', k ? k[1] : REGISTRY.pip(name), false);
153
- }
154
- for (const name of deps.go || []) {
155
- const k = KNOWN[name.split('/').pop()];
156
- add(name, '', k ? k[0] : 'Library', 'Go', REGISTRY.go(name), false);
157
- }
158
- for (const name of deps.cargo || []) {
159
- const k = KNOWN[name] || KNOWN[name.replace(/_/g, '-')];
160
- add(name, '', k ? k[0] : 'Library', 'Rust', k ? k[1] : REGISTRY.cargo(name), false);
161
- }
162
-
163
- items.sort((a, b) => (ORDER.indexOf(a.category) - ORDER.indexOf(b.category)) || a.name.localeCompare(b.name));
164
-
165
- const pm = [];
166
- if (deps.npm && Object.keys(deps.npm).length) pm.push('npm');
167
- if (deps.pip && deps.pip.length) pm.push('pip');
168
- if (deps.go && deps.go.length) pm.push('go modules');
169
- if (deps.cargo && deps.cargo.length) pm.push('cargo');
170
-
171
- return { languages, pm, items: items.slice(0, 48) };
117
+ const deps = manifest.deps || { npm: {}, dev: {}, pip: [], go: [], cargo: [] };
118
+ const items = [];
119
+ const seen = new Set();
120
+ const add = (name, version, category, lang, docs, dev = false) => {
121
+ if (!name || seen.has(name))
122
+ return;
123
+ seen.add(name);
124
+ items.push({ name, version: cleanVersion(version), category, lang, docs, dev });
125
+ };
126
+ const npmDocs = (name) => {
127
+ const k = KNOWN[name];
128
+ return k ? k[1] : REGISTRY.npm(name);
129
+ };
130
+ const catOf = (name) => {
131
+ const k = KNOWN[name];
132
+ return k ? k[0] : 'Library';
133
+ };
134
+ for (const [name, ver] of Object.entries(deps.npm || {})) {
135
+ if (name !== 'react-dom')
136
+ add(name, ver, catOf(name), 'JavaScript', npmDocs(name), false);
137
+ }
138
+ for (const [name, ver] of Object.entries(deps.dev || {})) {
139
+ if (name !== 'react-dom')
140
+ add(name, ver, catOf(name), 'JavaScript', npmDocs(name), true);
141
+ }
142
+ for (const name of deps.pip || []) {
143
+ const k = KNOWN[name];
144
+ add(name, '', k ? k[0] : 'Library', 'Python', k ? k[1] : REGISTRY.pip(name), false);
145
+ }
146
+ for (const name of deps.go || []) {
147
+ const k = KNOWN[name.split('/').pop()];
148
+ add(name, '', k ? k[0] : 'Library', 'Go', REGISTRY.go(name), false);
149
+ }
150
+ for (const name of deps.cargo || []) {
151
+ const k = KNOWN[name] || KNOWN[name.replace(/_/g, '-')];
152
+ add(name, '', k ? k[0] : 'Library', 'Rust', k ? k[1] : REGISTRY.cargo(name), false);
153
+ }
154
+ items.sort((a, b) => (ORDER.indexOf(a.category) - ORDER.indexOf(b.category)) || a.name.localeCompare(b.name));
155
+ const pm = [];
156
+ if (deps.npm && Object.keys(deps.npm).length)
157
+ pm.push('npm');
158
+ if (deps.pip && deps.pip.length)
159
+ pm.push('pip');
160
+ if (deps.go && deps.go.length)
161
+ pm.push('go modules');
162
+ if (deps.cargo && deps.cargo.length)
163
+ pm.push('cargo');
164
+ return { languages, pm, items: items.slice(0, 48) };
172
165
  }
173
-
166
+ //# sourceMappingURL=stack.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"stack.js","sourceRoot":"","sources":["../../src/shared/analyzer/stack.ts"],"names":[],"mappings":"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","sourcesContent":["// Stack analytics: from the manifest's declared dependencies plus the scan\n// language counts, name the frameworks, libraries and languages a repo leans\n// on — each tagged with a category and the official docs URL. The docs URLs\n// feed the server-side /api/doc fetch (allowlisted) for informed summaries.\n\n// name -> [category, docs url]\nconst KNOWN = {\n react: ['Frontend framework', 'https://react.dev'],\n 'react-dom': ['Frontend framework', 'https://react.dev'],\n '@angular/core': ['Frontend framework', 'https://angular.dev'],\n vue: ['Frontend framework', 'https://vuejs.org'],\n svelte: ['Frontend framework', 'https://svelte.dev'],\n next: ['Web framework', 'https://nextjs.org/docs'],\n nuxt: ['Web framework', 'https://nuxt.com/docs'],\n remix: ['Web framework', 'https://remix.run/docs'],\n gatsby: ['Web framework', 'https://www.gatsbyjs.com/docs'],\n express: ['Web framework', 'https://expressjs.com'],\n fastify: ['Web framework', 'https://fastify.dev'],\n koa: ['Web framework', 'https://koajs.com'],\n '@nestjs/core': ['Web framework', 'https://docs.nestjs.com'],\n hapi: ['Web framework', 'https://hapi.dev'],\n flask: ['Web framework', 'https://flask.palletsprojects.com'],\n django: ['Web framework', 'https://docs.djangoproject.com'],\n fastapi: ['Web framework', 'https://fastapi.tiangolo.com'],\n 'spring-boot': ['Web framework', 'https://docs.spring.io/spring-boot'],\n laravel: ['Web framework', 'https://laravel.com/docs'],\n rails: ['Web framework', 'https://guides.rubyonrails.org'],\n gin: ['Web framework', 'https://gin-gonic.com'],\n echo: ['Web framework', 'https://echo.labstack.com'],\n fiber: ['Web framework', 'https://gofiber.io'],\n 'actix-web': ['Web framework', 'https://actix.rs'],\n axum: ['Web framework', 'https://docs.rs/axum'],\n rocket: ['Web framework', 'https://rocket.rs'],\n prisma: ['Database / ORM', 'https://www.prisma.io/docs'],\n sequelize: ['Database / ORM', 'https://sequelize.org'],\n typeorm: ['Database / ORM', 'https://typeorm.io'],\n sqlalchemy: ['Database / ORM', 'https://docs.sqlalchemy.org'],\n 'drizzle-orm': ['Database / ORM', 'https://orm.drizzle.team'],\n mongoose: ['Database / ORM', 'https://mongoosejs.com'],\n knex: ['Database / ORM', 'https://knexjs.org'],\n pg: ['Database / ORM', 'https://node-postgres.com'],\n pymongo: ['Database / ORM', 'https://pymongo.readthedocs.io'],\n gorm: ['Database / ORM', 'https://gorm.io'],\n sqlx: ['Database / ORM', 'https://docs.rs/sqlx'],\n diesel: ['Database / ORM', 'https://diesel.rs'],\n redis: ['Database / ORM', 'https://redis.io/docs/'],\n jest: ['Testing', 'https://jestjs.io'],\n vitest: ['Testing', 'https://vitest.dev'],\n mocha: ['Testing', 'https://mochajs.org'],\n '@testing-library/react': ['Testing', 'https://testing-library.com'],\n pytest: ['Testing', 'https://docs.pytest.org'],\n playwright: ['Testing', 'https://playwright.dev'],\n cypress: ['Testing', 'https://docs.cypress.io'],\n rspec: ['Testing', 'https://rspec.info'],\n typescript: ['Tooling / build', 'https://www.typescriptlang.org/docs'],\n vite: ['Tooling / build', 'https://vitejs.dev/guide/'],\n webpack: ['Tooling / build', 'https://webpack.js.org'],\n esbuild: ['Tooling / build', 'https://esbuild.github.io'],\n babel: ['Tooling / build', 'https://babeljs.io/docs'],\n rollup: ['Tooling / build', 'https://rollupjs.org'],\n tailwindcss: ['UI / styling', 'https://tailwindcss.com/docs'],\n bootstrap: ['UI / styling', 'https://getbootstrap.com/docs'],\n sass: ['UI / styling', 'https://sass-lang.com/documentation'],\n 'styled-components': ['UI / styling', 'https://styled-components.com'],\n axios: ['Networking', 'https://axios-http.com'],\n requests: ['Networking', 'https://requests.readthedocs.io'],\n urllib3: ['Networking', 'https://urllib3.readthedocs.io'],\n httpx: ['Networking', 'https://www.python-httpx.org'],\n passport: ['Auth', 'https://www.passportjs.org'],\n 'next-auth': ['Auth', 'https://next-auth.js.org'],\n jsonwebtoken: ['Auth', 'https://github.com/auth0/node-jsonwebtoken'],\n pydantic: ['Data validation', 'https://docs.pydantic.dev'],\n numpy: ['Data / science', 'https://numpy.org/doc/'],\n pandas: ['Data / science', 'https://pandas.pydata.org/docs/'],\n 'scikit-learn': ['Data / science', 'https://scikit-learn.org/stable/'],\n torch: ['Data / science', 'https://pytorch.org/docs/'],\n tensorflow: ['Data / science', 'https://www.tensorflow.org/api_docs'],\n 'opencv-python': ['Data / science', 'https://docs.opencv.org'],\n keras: ['Data / science', 'https://keras.io'],\n 'python-dotenv': ['Tooling / config', 'https://github.com/theskumar/python-dotenv'],\n};\n\nconst ORDER = [\n 'Web framework', 'Frontend framework', 'Database / ORM', 'Auth',\n 'Networking', 'Data / science', 'Data validation', 'UI / styling',\n 'Testing', 'Tooling / build', 'Tooling / config', 'Library',\n];\n\n// Where a dependency that is not in KNOWN sends you: its registry page. Named\n// here rather than inlined below because two things need them — the URL\n// builders, and the host allowlist under them.\nconst REGISTRY = {\n npm: (name) => `https://www.npmjs.com/package/${name}`,\n pip: (name) => `https://pypi.org/project/${name}/`,\n go: (name) => `https://pkg.go.dev/${name}`,\n cargo: (name) => `https://docs.rs/${name}`,\n};\n\n// Every host `analyzeStack` can hand out a docs URL for. The server allowlists\n// exactly this set for `/api/doc`, and that is the SSRF guard: a host no\n// dependency name can produce is a host the server will not fetch.\n//\n// Derived, not restated. The server used to carry its own hand-written copy of\n// this list, and the two had drifted: `diesel.rs` was reachable from a Cargo\n// dependency but missing from the allowlist, so those docs always came back 403,\n// while `docusaurus.io`, `auth0.com` and a bare `readthedocs.io` were allowed\n// and nothing here could ever ask for them — the last one opening every project\n// on the site rather than the three we name.\n//\n// `www.` comes off because the caller strips it from the incoming host too;\n// leaving it on would mean `www.npmjs.com` never matched a request for\n// `npmjs.com`.\nexport const DOC_HOSTS = Object.freeze([...new Set(\n [\n ...Object.values(KNOWN).map(([, url]) => url),\n ...Object.values(REGISTRY).map((toUrl) => toUrl('any')),\n ].map((url) => new URL(url).hostname.replace(/^www\\./, ''))\n)].sort());\n\nfunction cleanVersion(v) {\n return String(v || '').replace(/^[\\^~>=< ]+/, '').split(' ')[0].trim();\n}\n\nexport function analyzeStack(manifest: Record<string, any> = {}, languages: Record<string, any> = {}) {\n const deps = manifest.deps || { npm: {}, dev: {}, pip: [], go: [], cargo: [] };\n const items = [];\n const seen = new Set();\n\n const add = (name, version, category, lang, docs, dev = false) => {\n if (!name || seen.has(name)) return;\n seen.add(name);\n items.push({ name, version: cleanVersion(version), category, lang, docs, dev });\n };\n\n const npmDocs = (name) => {\n const k = KNOWN[name];\n return k ? k[1] : REGISTRY.npm(name);\n };\n const catOf = (name) => {\n const k = KNOWN[name];\n return k ? k[0] : 'Library';\n };\n\n for (const [name, ver] of Object.entries(deps.npm || {})) {\n if (name !== 'react-dom') add(name, ver, catOf(name), 'JavaScript', npmDocs(name), false);\n }\n for (const [name, ver] of Object.entries(deps.dev || {})) {\n if (name !== 'react-dom') add(name, ver, catOf(name), 'JavaScript', npmDocs(name), true);\n }\n for (const name of deps.pip || []) {\n const k = KNOWN[name];\n add(name, '', k ? k[0] : 'Library', 'Python', k ? k[1] : REGISTRY.pip(name), false);\n }\n for (const name of deps.go || []) {\n const k = KNOWN[name.split('/').pop()];\n add(name, '', k ? k[0] : 'Library', 'Go', REGISTRY.go(name), false);\n }\n for (const name of deps.cargo || []) {\n const k = KNOWN[name] || KNOWN[name.replace(/_/g, '-')];\n add(name, '', k ? k[0] : 'Library', 'Rust', k ? k[1] : REGISTRY.cargo(name), false);\n }\n\n items.sort((a, b) => (ORDER.indexOf(a.category) - ORDER.indexOf(b.category)) || a.name.localeCompare(b.name));\n\n const pm = [];\n if (deps.npm && Object.keys(deps.npm).length) pm.push('npm');\n if (deps.pip && deps.pip.length) pm.push('pip');\n if (deps.go && deps.go.length) pm.push('go modules');\n if (deps.cargo && deps.cargo.length) pm.push('cargo');\n\n return { languages, pm, items: items.slice(0, 48) };\n}\n\n"]}
@@ -0,0 +1,2 @@
1
+ export declare function buildTourStops(scan: any, facts: any): any[];
2
+ export declare function tourStopTitle(stop: any): any;
@@ -7,63 +7,55 @@
7
7
  // and a drifted tour would tell a person and an agent different things about the
8
8
  // same repository. `describeStop` is presentation for the browser's own chrome
9
9
  // and has no business here.
10
-
11
10
  import { baseName } from './pathUtil.js';
12
-
13
11
  export function buildTourStops(scan, facts) {
14
- const stops = [];
15
- const used = new Set();
16
-
17
- const push = (path, why) => {
18
- if (!path || used.has(path)) return;
19
- if (!scan.files.some((f) => f.path === path)) return;
20
- used.add(path);
21
- stops.push({ path, why });
22
- };
23
-
24
- // 1. The front door: the entry point with the most reach.
25
- const entriesByReach = facts.entries
26
- .map((p) => ({ path: p, out: facts.fanOut[p] || 0 }))
27
- .sort((a, b) => b.out - a.out);
28
- if (entriesByReach.length) {
29
- push(entriesByReach[0].path, 'Start here. This is a way in — code that runs first and calls everything else.');
30
- }
31
-
32
- // 2–4. The load-bearing files.
33
- for (const hub of facts.hubs.slice(0, 3)) {
34
- push(hub.path, `${hub.fanIn} files depend on this. Understand it before you change anything around it.`);
35
- }
36
-
37
- // 5. A second entry if there is one (servers often have a CLI beside them).
38
- if (entriesByReach.length > 1) {
39
- push(entriesByReach[1].path, 'Another door into the codebase — same building, different handle.');
40
- }
41
-
42
- // 6. A well-used leaf: end of a chain, usually where the real work happens.
43
- const leaf = scan.files
44
- .filter((f) => (facts.fanOut[f.path] || 0) === 0 && (facts.fanIn[f.path] || 0) >= 2)
45
- .sort((a, b) => (facts.fanIn[b.path] || 0) - (facts.fanIn[a.path] || 0))[0];
46
- if (leaf) {
47
- push(leaf.path, 'The end of a chain. Nothing below it but the work itself.');
48
- }
49
-
50
- // 7. A cycle member, if the repo has them — worth the warning early.
51
- if (facts.cycles.length) {
52
- const member = facts.cycles[0][0];
53
- push(member, `Careful with this one: it sits in a loop of ${facts.cycles[0].length} files importing each other.`);
54
- }
55
-
56
- // 8. An orphan, if any survive the earlier stops.
57
- const orphan = facts.orphans.find((p) => !used.has(p));
58
- if (orphan && stops.length < 8) {
59
- push(orphan, 'Nothing imports this. Dead code, or a door we did not recognize — you decide.');
60
- }
61
-
62
- return stops.slice(0, 8);
12
+ const stops = [];
13
+ const used = new Set();
14
+ const push = (path, why) => {
15
+ if (!path || used.has(path))
16
+ return;
17
+ if (!scan.files.some((f) => f.path === path))
18
+ return;
19
+ used.add(path);
20
+ stops.push({ path, why });
21
+ };
22
+ // 1. The front door: the entry point with the most reach.
23
+ const entriesByReach = facts.entries
24
+ .map((p) => ({ path: p, out: facts.fanOut[p] || 0 }))
25
+ .sort((a, b) => b.out - a.out);
26
+ if (entriesByReach.length) {
27
+ push(entriesByReach[0].path, 'Start here. This is a way in — code that runs first and calls everything else.');
28
+ }
29
+ // 2–4. The load-bearing files.
30
+ for (const hub of facts.hubs.slice(0, 3)) {
31
+ push(hub.path, `${hub.fanIn} files depend on this. Understand it before you change anything around it.`);
32
+ }
33
+ // 5. A second entry if there is one (servers often have a CLI beside them).
34
+ if (entriesByReach.length > 1) {
35
+ push(entriesByReach[1].path, 'Another door into the codebase — same building, different handle.');
36
+ }
37
+ // 6. A well-used leaf: end of a chain, usually where the real work happens.
38
+ const leaf = scan.files
39
+ .filter((f) => (facts.fanOut[f.path] || 0) === 0 && (facts.fanIn[f.path] || 0) >= 2)
40
+ .sort((a, b) => (facts.fanIn[b.path] || 0) - (facts.fanIn[a.path] || 0))[0];
41
+ if (leaf) {
42
+ push(leaf.path, 'The end of a chain. Nothing below it but the work itself.');
43
+ }
44
+ // 7. A cycle member, if the repo has them — worth the warning early.
45
+ if (facts.cycles.length) {
46
+ const member = facts.cycles[0][0];
47
+ push(member, `Careful with this one: it sits in a loop of ${facts.cycles[0].length} files importing each other.`);
48
+ }
49
+ // 8. An orphan, if any survive the earlier stops.
50
+ const orphan = facts.orphans.find((p) => !used.has(p));
51
+ if (orphan && stops.length < 8) {
52
+ push(orphan, 'Nothing imports this. Dead code, or a door we did not recognize — you decide.');
53
+ }
54
+ return stops.slice(0, 8);
63
55
  }
64
-
65
56
  // The name a stop shows in the browser's tour bar. Exported from here anyway so
66
57
  // neither caller has to import `baseName` just to label a stop.
67
58
  export function tourStopTitle(stop) {
68
- return baseName(stop.path);
59
+ return baseName(stop.path);
69
60
  }
61
+ //# sourceMappingURL=tour.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"tour.js","sourceRoot":"","sources":["../../src/shared/analyzer/tour.ts"],"names":[],"mappings":"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","sourcesContent":["// The guided walk: pick the handful of files a new teammate should see\n// first, in the order they should see them, each with a one-line reason why.\n//\n// This lives in `shared/` because two very different callers want the same\n// ordering: the browser draws it as a tour, and the MCP server hands it to an\n// agent as \"read these eight files first\". A second implementation would drift,\n// and a drifted tour would tell a person and an agent different things about the\n// same repository. `describeStop` is presentation for the browser's own chrome\n// and has no business here.\n\nimport { baseName } from './pathUtil.js';\n\nexport function buildTourStops(scan, facts) {\n const stops = [];\n const used = new Set();\n\n const push = (path, why) => {\n if (!path || used.has(path)) return;\n if (!scan.files.some((f) => f.path === path)) return;\n used.add(path);\n stops.push({ path, why });\n };\n\n // 1. The front door: the entry point with the most reach.\n const entriesByReach = facts.entries\n .map((p) => ({ path: p, out: facts.fanOut[p] || 0 }))\n .sort((a, b) => b.out - a.out);\n if (entriesByReach.length) {\n push(entriesByReach[0].path, 'Start here. This is a way in — code that runs first and calls everything else.');\n }\n\n // 2–4. The load-bearing files.\n for (const hub of facts.hubs.slice(0, 3)) {\n push(hub.path, `${hub.fanIn} files depend on this. Understand it before you change anything around it.`);\n }\n\n // 5. A second entry if there is one (servers often have a CLI beside them).\n if (entriesByReach.length > 1) {\n push(entriesByReach[1].path, 'Another door into the codebase — same building, different handle.');\n }\n\n // 6. A well-used leaf: end of a chain, usually where the real work happens.\n const leaf = scan.files\n .filter((f) => (facts.fanOut[f.path] || 0) === 0 && (facts.fanIn[f.path] || 0) >= 2)\n .sort((a, b) => (facts.fanIn[b.path] || 0) - (facts.fanIn[a.path] || 0))[0];\n if (leaf) {\n push(leaf.path, 'The end of a chain. Nothing below it but the work itself.');\n }\n\n // 7. A cycle member, if the repo has them — worth the warning early.\n if (facts.cycles.length) {\n const member = facts.cycles[0][0];\n push(member, `Careful with this one: it sits in a loop of ${facts.cycles[0].length} files importing each other.`);\n }\n\n // 8. An orphan, if any survive the earlier stops.\n const orphan = facts.orphans.find((p) => !used.has(p));\n if (orphan && stops.length < 8) {\n push(orphan, 'Nothing imports this. Dead code, or a door we did not recognize — you decide.');\n }\n\n return stops.slice(0, 8);\n}\n\n// The name a stop shows in the browser's tour bar. Exported from here anyway so\n// neither caller has to import `baseName` just to label a stop.\nexport function tourStopTitle(stop) {\n return baseName(stop.path);\n}\n"]}
@@ -0,0 +1,8 @@
1
+ export declare function blankComments(source: any, { block, line, lineChar }?: Record<string, any>): any;
2
+ export declare function jsCodeMask(source: any): string;
3
+ export declare function lineOf(source: any, index: any): number;
4
+ export declare function lineCounter(source: any): (index: any) => number;
5
+ export declare function braceBodyEnd(source: any, openIndex: any): any;
6
+ export declare function uniqueBy(items: any, key: any): any[];
7
+ export declare function callsWithin(body: any, names: any): any[];
8
+ export declare function declarationOrder(fns: any): Map<any, any>;