@superblocksteam/vite-plugin-file-sync 2.0.162 → 2.0.163-next.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 (420) hide show
  1. package/dist/ai-service/agent/middleware.d.ts.map +1 -1
  2. package/dist/ai-service/agent/middleware.js +18 -7
  3. package/dist/ai-service/agent/middleware.js.map +1 -1
  4. package/dist/ai-service/agent/prompts/build-base-system-prompt.d.ts.map +1 -1
  5. package/dist/ai-service/agent/prompts/build-base-system-prompt.js +43 -29
  6. package/dist/ai-service/agent/prompts/build-base-system-prompt.js.map +1 -1
  7. package/dist/ai-service/agent/prompts/build-security-scan-prompt.d.ts.map +1 -1
  8. package/dist/ai-service/agent/prompts/build-security-scan-prompt.js +25 -0
  9. package/dist/ai-service/agent/prompts/build-security-scan-prompt.js.map +1 -1
  10. package/dist/ai-service/agent/subagents/coding/run-coding-subagent.d.ts.map +1 -1
  11. package/dist/ai-service/agent/subagents/coding/run-coding-subagent.js +15 -0
  12. package/dist/ai-service/agent/subagents/coding/run-coding-subagent.js.map +1 -1
  13. package/dist/ai-service/agent/tools/apis/test-api.d.ts.map +1 -1
  14. package/dist/ai-service/agent/tools/apis/test-api.js +4 -2
  15. package/dist/ai-service/agent/tools/apis/test-api.js.map +1 -1
  16. package/dist/ai-service/agent/tools/app-environment/switch-selected-environment.d.ts +18 -0
  17. package/dist/ai-service/agent/tools/app-environment/switch-selected-environment.d.ts.map +1 -0
  18. package/dist/ai-service/agent/tools/app-environment/switch-selected-environment.js +61 -0
  19. package/dist/ai-service/agent/tools/app-environment/switch-selected-environment.js.map +1 -0
  20. package/dist/ai-service/agent/tools/build-capture-screenshot.js +1 -1
  21. package/dist/ai-service/agent/tools/build-install-packages.d.ts.map +1 -1
  22. package/dist/ai-service/agent/tools/build-install-packages.js +21 -8
  23. package/dist/ai-service/agent/tools/build-install-packages.js.map +1 -1
  24. package/dist/ai-service/agent/tools/build-read-file.d.ts +87 -1
  25. package/dist/ai-service/agent/tools/build-read-file.d.ts.map +1 -1
  26. package/dist/ai-service/agent/tools/build-read-file.js +453 -82
  27. package/dist/ai-service/agent/tools/build-read-file.js.map +1 -1
  28. package/dist/ai-service/agent/tools/build-write-file.d.ts +1 -0
  29. package/dist/ai-service/agent/tools/build-write-file.d.ts.map +1 -1
  30. package/dist/ai-service/agent/tools/build-write-file.js +18 -2
  31. package/dist/ai-service/agent/tools/build-write-file.js.map +1 -1
  32. package/dist/ai-service/agent/tools/debug-cache.d.ts +11 -0
  33. package/dist/ai-service/agent/tools/debug-cache.d.ts.map +1 -1
  34. package/dist/ai-service/agent/tools/debug-cache.js +62 -14
  35. package/dist/ai-service/agent/tools/debug-cache.js.map +1 -1
  36. package/dist/ai-service/agent/tools/index.d.ts +2 -1
  37. package/dist/ai-service/agent/tools/index.d.ts.map +1 -1
  38. package/dist/ai-service/agent/tools/index.js +2 -1
  39. package/dist/ai-service/agent/tools/index.js.map +1 -1
  40. package/dist/ai-service/agent/tools/integrations/metadata.d.ts +1 -0
  41. package/dist/ai-service/agent/tools/integrations/metadata.d.ts.map +1 -1
  42. package/dist/ai-service/agent/tools/integrations/metadata.js +7 -2
  43. package/dist/ai-service/agent/tools/integrations/metadata.js.map +1 -1
  44. package/dist/ai-service/agent/tools/read-file-metrics.d.ts +30 -0
  45. package/dist/ai-service/agent/tools/read-file-metrics.d.ts.map +1 -0
  46. package/dist/ai-service/agent/tools/read-file-metrics.js +158 -0
  47. package/dist/ai-service/agent/tools/read-file-metrics.js.map +1 -0
  48. package/dist/ai-service/agent/tools/subagent-isolation.d.ts +27 -0
  49. package/dist/ai-service/agent/tools/subagent-isolation.d.ts.map +1 -0
  50. package/dist/ai-service/agent/tools/subagent-isolation.js +57 -0
  51. package/dist/ai-service/agent/tools/subagent-isolation.js.map +1 -0
  52. package/dist/ai-service/agent/tools.d.ts +4 -1
  53. package/dist/ai-service/agent/tools.d.ts.map +1 -1
  54. package/dist/ai-service/agent/tools.js +51 -5
  55. package/dist/ai-service/agent/tools.js.map +1 -1
  56. package/dist/ai-service/agent/tools2/tools/download-attachments.d.ts.map +1 -1
  57. package/dist/ai-service/agent/tools2/tools/download-attachments.js +1 -0
  58. package/dist/ai-service/agent/tools2/tools/download-attachments.js.map +1 -1
  59. package/dist/ai-service/agent/tools2/tools/start-test-run.d.ts.map +1 -1
  60. package/dist/ai-service/agent/tools2/tools/start-test-run.js +14 -0
  61. package/dist/ai-service/agent/tools2/tools/start-test-run.js.map +1 -1
  62. package/dist/ai-service/agent/utils.d.ts.map +1 -1
  63. package/dist/ai-service/agent/utils.js +2 -2
  64. package/dist/ai-service/agent/utils.js.map +1 -1
  65. package/dist/ai-service/app-interface/filesystem/draft-manager.d.ts +2 -1
  66. package/dist/ai-service/app-interface/filesystem/draft-manager.d.ts.map +1 -1
  67. package/dist/ai-service/app-interface/filesystem/draft-manager.js +3 -0
  68. package/dist/ai-service/app-interface/filesystem/draft-manager.js.map +1 -1
  69. package/dist/ai-service/app-interface/filesystem/handlers/skill-handler.d.ts +2 -1
  70. package/dist/ai-service/app-interface/filesystem/handlers/skill-handler.d.ts.map +1 -1
  71. package/dist/ai-service/app-interface/filesystem/handlers/skill-handler.js +13 -11
  72. package/dist/ai-service/app-interface/filesystem/handlers/skill-handler.js.map +1 -1
  73. package/dist/ai-service/app-interface/filesystem/virtual-file-system.d.ts.map +1 -1
  74. package/dist/ai-service/app-interface/filesystem/virtual-file-system.js +1 -1
  75. package/dist/ai-service/app-interface/filesystem/virtual-file-system.js.map +1 -1
  76. package/dist/ai-service/app-interface/shell.d.ts +18 -9
  77. package/dist/ai-service/app-interface/shell.d.ts.map +1 -1
  78. package/dist/ai-service/app-interface/shell.js +92 -112
  79. package/dist/ai-service/app-interface/shell.js.map +1 -1
  80. package/dist/ai-service/app-interface/typecheck-output-parser.d.ts +9 -0
  81. package/dist/ai-service/app-interface/typecheck-output-parser.d.ts.map +1 -0
  82. package/dist/ai-service/app-interface/typecheck-output-parser.js +21 -0
  83. package/dist/ai-service/app-interface/typecheck-output-parser.js.map +1 -0
  84. package/dist/ai-service/app-interface/vulnerability-gate.d.ts +5 -0
  85. package/dist/ai-service/app-interface/vulnerability-gate.d.ts.map +1 -1
  86. package/dist/ai-service/app-interface/vulnerability-gate.js +9 -2
  87. package/dist/ai-service/app-interface/vulnerability-gate.js.map +1 -1
  88. package/dist/ai-service/app-layout.d.ts +13 -0
  89. package/dist/ai-service/app-layout.d.ts.map +1 -0
  90. package/dist/ai-service/app-layout.js +25 -0
  91. package/dist/ai-service/app-layout.js.map +1 -0
  92. package/dist/ai-service/app-skills/manager.d.ts +2 -0
  93. package/dist/ai-service/app-skills/manager.d.ts.map +1 -1
  94. package/dist/ai-service/app-skills/manager.js +13 -6
  95. package/dist/ai-service/app-skills/manager.js.map +1 -1
  96. package/dist/ai-service/attachment-label-metrics.d.ts +5 -0
  97. package/dist/ai-service/attachment-label-metrics.d.ts.map +1 -0
  98. package/dist/ai-service/attachment-label-metrics.js +26 -0
  99. package/dist/ai-service/attachment-label-metrics.js.map +1 -0
  100. package/dist/ai-service/attachment-upload.d.ts.map +1 -1
  101. package/dist/ai-service/attachment-upload.js +6 -1
  102. package/dist/ai-service/attachment-upload.js.map +1 -1
  103. package/dist/ai-service/attachments/validate-prompt-attachments.d.ts +7 -0
  104. package/dist/ai-service/attachments/validate-prompt-attachments.d.ts.map +1 -0
  105. package/dist/ai-service/attachments/validate-prompt-attachments.js +96 -0
  106. package/dist/ai-service/attachments/validate-prompt-attachments.js.map +1 -0
  107. package/dist/ai-service/chat/chat-push-metrics.d.ts +17 -0
  108. package/dist/ai-service/chat/chat-push-metrics.d.ts.map +1 -1
  109. package/dist/ai-service/chat/chat-push-metrics.js +45 -0
  110. package/dist/ai-service/chat/chat-push-metrics.js.map +1 -1
  111. package/dist/ai-service/chat/chat-session-store.d.ts +51 -0
  112. package/dist/ai-service/chat/chat-session-store.d.ts.map +1 -1
  113. package/dist/ai-service/chat/chat-session-store.js +181 -4
  114. package/dist/ai-service/chat/chat-session-store.js.map +1 -1
  115. package/dist/ai-service/features.d.ts +32 -0
  116. package/dist/ai-service/features.d.ts.map +1 -1
  117. package/dist/ai-service/features.js +32 -0
  118. package/dist/ai-service/features.js.map +1 -1
  119. package/dist/ai-service/helper-system-ai-attributes.d.ts +1 -1
  120. package/dist/ai-service/helper-system-ai-attributes.d.ts.map +1 -1
  121. package/dist/ai-service/helper-system-ai-attributes.js.map +1 -1
  122. package/dist/ai-service/index.d.ts +19 -4
  123. package/dist/ai-service/index.d.ts.map +1 -1
  124. package/dist/ai-service/index.js +176 -23
  125. package/dist/ai-service/index.js.map +1 -1
  126. package/dist/ai-service/llm/client.d.ts +9 -0
  127. package/dist/ai-service/llm/client.d.ts.map +1 -1
  128. package/dist/ai-service/llm/client.js +13 -43
  129. package/dist/ai-service/llm/client.js.map +1 -1
  130. package/dist/ai-service/llm/context-v2/adapter.d.ts +2 -0
  131. package/dist/ai-service/llm/context-v2/adapter.d.ts.map +1 -1
  132. package/dist/ai-service/llm/context-v2/adapter.js +6 -0
  133. package/dist/ai-service/llm/context-v2/adapter.js.map +1 -1
  134. package/dist/ai-service/llm/context-v2/compaction/server-side.d.ts +8 -0
  135. package/dist/ai-service/llm/context-v2/compaction/server-side.d.ts.map +1 -1
  136. package/dist/ai-service/llm/context-v2/compaction/server-side.js +8 -0
  137. package/dist/ai-service/llm/context-v2/compaction/server-side.js.map +1 -1
  138. package/dist/ai-service/llm/context-v2/context-component-partition.d.ts +24 -0
  139. package/dist/ai-service/llm/context-v2/context-component-partition.d.ts.map +1 -0
  140. package/dist/ai-service/llm/context-v2/context-component-partition.js +222 -0
  141. package/dist/ai-service/llm/context-v2/context-component-partition.js.map +1 -0
  142. package/dist/ai-service/llm/context-v2/context-metrics.d.ts +9 -0
  143. package/dist/ai-service/llm/context-v2/context-metrics.d.ts.map +1 -1
  144. package/dist/ai-service/llm/context-v2/context-metrics.js +40 -2
  145. package/dist/ai-service/llm/context-v2/context-metrics.js.map +1 -1
  146. package/dist/ai-service/llm/context-v2/context.d.ts +116 -4
  147. package/dist/ai-service/llm/context-v2/context.d.ts.map +1 -1
  148. package/dist/ai-service/llm/context-v2/context.js +276 -64
  149. package/dist/ai-service/llm/context-v2/context.js.map +1 -1
  150. package/dist/ai-service/llm/context-v2/conversation-context.d.ts +18 -0
  151. package/dist/ai-service/llm/context-v2/conversation-context.d.ts.map +1 -1
  152. package/dist/ai-service/llm/context-v2/file-read-ledger.d.ts +218 -0
  153. package/dist/ai-service/llm/context-v2/file-read-ledger.d.ts.map +1 -0
  154. package/dist/ai-service/llm/context-v2/file-read-ledger.js +275 -0
  155. package/dist/ai-service/llm/context-v2/file-read-ledger.js.map +1 -0
  156. package/dist/ai-service/llm/context-v2/phase1-tool-summarizer.d.ts.map +1 -1
  157. package/dist/ai-service/llm/context-v2/phase1-tool-summarizer.js +5 -2
  158. package/dist/ai-service/llm/context-v2/phase1-tool-summarizer.js.map +1 -1
  159. package/dist/ai-service/llm/context-v2/token-tracker.d.ts +2 -0
  160. package/dist/ai-service/llm/context-v2/token-tracker.d.ts.map +1 -1
  161. package/dist/ai-service/llm/context-v2/token-tracker.js +4 -0
  162. package/dist/ai-service/llm/context-v2/token-tracker.js.map +1 -1
  163. package/dist/ai-service/llm/context-v2/tool-schema-tokens.d.ts +22 -0
  164. package/dist/ai-service/llm/context-v2/tool-schema-tokens.d.ts.map +1 -0
  165. package/dist/ai-service/llm/context-v2/tool-schema-tokens.js +36 -0
  166. package/dist/ai-service/llm/context-v2/tool-schema-tokens.js.map +1 -0
  167. package/dist/ai-service/llm/context-v2/types.d.ts +8 -0
  168. package/dist/ai-service/llm/context-v2/types.d.ts.map +1 -1
  169. package/dist/ai-service/llm/context-v2/types.js +48 -0
  170. package/dist/ai-service/llm/context-v2/types.js.map +1 -1
  171. package/dist/ai-service/llm/error.d.ts +2 -0
  172. package/dist/ai-service/llm/error.d.ts.map +1 -1
  173. package/dist/ai-service/llm/error.js +1 -0
  174. package/dist/ai-service/llm/error.js.map +1 -1
  175. package/dist/ai-service/llm/retry-exhaustion-reason.d.ts +2 -0
  176. package/dist/ai-service/llm/retry-exhaustion-reason.d.ts.map +1 -0
  177. package/dist/ai-service/llm/retry-exhaustion-reason.js +2 -0
  178. package/dist/ai-service/llm/retry-exhaustion-reason.js.map +1 -0
  179. package/dist/ai-service/llm/stream/errors.d.ts +6 -7
  180. package/dist/ai-service/llm/stream/errors.d.ts.map +1 -1
  181. package/dist/ai-service/llm/stream/errors.js +7 -1
  182. package/dist/ai-service/llm/stream/errors.js.map +1 -1
  183. package/dist/ai-service/llm/stream/event-bus.d.ts +9 -1
  184. package/dist/ai-service/llm/stream/event-bus.d.ts.map +1 -1
  185. package/dist/ai-service/llm/stream/event-bus.js.map +1 -1
  186. package/dist/ai-service/llm/stream/idle-monitor.d.ts.map +1 -1
  187. package/dist/ai-service/llm/stream/idle-monitor.js.map +1 -1
  188. package/dist/ai-service/llm/stream/observers/context.d.ts.map +1 -1
  189. package/dist/ai-service/llm/stream/observers/context.js +13 -0
  190. package/dist/ai-service/llm/stream/observers/context.js.map +1 -1
  191. package/dist/ai-service/llm/stream/observers/llmobs.d.ts +14 -1
  192. package/dist/ai-service/llm/stream/observers/llmobs.d.ts.map +1 -1
  193. package/dist/ai-service/llm/stream/observers/llmobs.js +91 -7
  194. package/dist/ai-service/llm/stream/observers/llmobs.js.map +1 -1
  195. package/dist/ai-service/llm/stream/observers/logging.d.ts +3 -1
  196. package/dist/ai-service/llm/stream/observers/logging.d.ts.map +1 -1
  197. package/dist/ai-service/llm/stream/observers/logging.js +73 -52
  198. package/dist/ai-service/llm/stream/observers/logging.js.map +1 -1
  199. package/dist/ai-service/llm/stream/observers/retry-notification.d.ts.map +1 -1
  200. package/dist/ai-service/llm/stream/observers/retry-notification.js +16 -9
  201. package/dist/ai-service/llm/stream/observers/retry-notification.js.map +1 -1
  202. package/dist/ai-service/llm/stream/orchestrator.d.ts +5 -1
  203. package/dist/ai-service/llm/stream/orchestrator.d.ts.map +1 -1
  204. package/dist/ai-service/llm/stream/orchestrator.js +103 -12
  205. package/dist/ai-service/llm/stream/orchestrator.js.map +1 -1
  206. package/dist/ai-service/llm/stream/retry-engine.d.ts +3 -1
  207. package/dist/ai-service/llm/stream/retry-engine.d.ts.map +1 -1
  208. package/dist/ai-service/llm/stream/retry-engine.js +9 -0
  209. package/dist/ai-service/llm/stream/retry-engine.js.map +1 -1
  210. package/dist/ai-service/llm/stream/session.d.ts +8 -1
  211. package/dist/ai-service/llm/stream/session.d.ts.map +1 -1
  212. package/dist/ai-service/llm/stream/session.js +19 -0
  213. package/dist/ai-service/llm/stream/session.js.map +1 -1
  214. package/dist/ai-service/llm/stream/types.d.ts +13 -0
  215. package/dist/ai-service/llm/stream/types.d.ts.map +1 -1
  216. package/dist/ai-service/llm/stream/wait-state-tracker.d.ts +5 -14
  217. package/dist/ai-service/llm/stream/wait-state-tracker.d.ts.map +1 -1
  218. package/dist/ai-service/llm/stream/wait-state-tracker.js +25 -0
  219. package/dist/ai-service/llm/stream/wait-state-tracker.js.map +1 -1
  220. package/dist/ai-service/mcp/embedded-playwright-mcp-server.js +8 -8
  221. package/dist/ai-service/mcp/embedded-playwright-mcp-server.js.map +1 -1
  222. package/dist/ai-service/policy-gate-remediation-usage.d.ts +2 -0
  223. package/dist/ai-service/policy-gate-remediation-usage.d.ts.map +1 -0
  224. package/dist/ai-service/policy-gate-remediation-usage.js +56 -0
  225. package/dist/ai-service/policy-gate-remediation-usage.js.map +1 -0
  226. package/dist/ai-service/prompts/summarize-destructive-migration.d.ts +12 -0
  227. package/dist/ai-service/prompts/summarize-destructive-migration.d.ts.map +1 -0
  228. package/dist/ai-service/prompts/summarize-destructive-migration.js +37 -0
  229. package/dist/ai-service/prompts/summarize-destructive-migration.js.map +1 -0
  230. package/dist/ai-service/recording/storage/session-recording-storage.js +2 -2
  231. package/dist/ai-service/recording/storage/session-recording-storage.js.map +1 -1
  232. package/dist/ai-service/security/secret-scanner-service.d.ts.map +1 -1
  233. package/dist/ai-service/security/secret-scanner-service.js +88 -23
  234. package/dist/ai-service/security/secret-scanner-service.js.map +1 -1
  235. package/dist/ai-service/skills/index.d.ts +0 -7
  236. package/dist/ai-service/skills/index.d.ts.map +1 -1
  237. package/dist/ai-service/skills/index.js +0 -9
  238. package/dist/ai-service/skills/index.js.map +1 -1
  239. package/dist/ai-service/skills/system/_registry.generated.d.ts.map +1 -1
  240. package/dist/ai-service/skills/system/_registry.generated.js +4 -0
  241. package/dist/ai-service/skills/system/_registry.generated.js.map +1 -1
  242. package/dist/ai-service/skills/system/resolve.d.ts +2 -0
  243. package/dist/ai-service/skills/system/resolve.d.ts.map +1 -0
  244. package/dist/ai-service/skills/system/resolve.js +32 -0
  245. package/dist/ai-service/skills/system/resolve.js.map +1 -0
  246. package/dist/ai-service/skills/system/superblocks-frontend/_variants/api-imports-legacy.generated.d.ts +2 -0
  247. package/dist/ai-service/skills/system/superblocks-frontend/_variants/api-imports-legacy.generated.d.ts.map +1 -0
  248. package/dist/ai-service/skills/system/superblocks-frontend/_variants/api-imports-legacy.generated.js +9 -0
  249. package/dist/ai-service/skills/system/superblocks-frontend/_variants/api-imports-legacy.generated.js.map +1 -0
  250. package/dist/ai-service/skills/system/superblocks-frontend/_variants/api-imports-sdk.generated.d.ts +2 -0
  251. package/dist/ai-service/skills/system/superblocks-frontend/_variants/api-imports-sdk.generated.d.ts.map +1 -0
  252. package/dist/ai-service/skills/system/superblocks-frontend/_variants/api-imports-sdk.generated.js +11 -0
  253. package/dist/ai-service/skills/system/superblocks-frontend/_variants/api-imports-sdk.generated.js.map +1 -0
  254. package/dist/ai-service/skills/system/superblocks-frontend/skill.generated.d.ts +1 -1
  255. package/dist/ai-service/skills/system/superblocks-frontend/skill.generated.d.ts.map +1 -1
  256. package/dist/ai-service/skills/system/superblocks-frontend/skill.generated.js +16 -24
  257. package/dist/ai-service/skills/system/superblocks-frontend/skill.generated.js.map +1 -1
  258. package/dist/ai-service/skills/system/third-party-migration/skill.generated.d.ts +1 -1
  259. package/dist/ai-service/skills/system/third-party-migration/skill.generated.d.ts.map +1 -1
  260. package/dist/ai-service/skills/system/third-party-migration/skill.generated.js +1 -1
  261. package/dist/ai-service/state-machine/clark-fsm.d.ts +11 -0
  262. package/dist/ai-service/state-machine/clark-fsm.d.ts.map +1 -1
  263. package/dist/ai-service/state-machine/clark-fsm.js +7 -1
  264. package/dist/ai-service/state-machine/clark-fsm.js.map +1 -1
  265. package/dist/ai-service/state-machine/handlers/agent-planning.d.ts.map +1 -1
  266. package/dist/ai-service/state-machine/handlers/agent-planning.js +21 -0
  267. package/dist/ai-service/state-machine/handlers/agent-planning.js.map +1 -1
  268. package/dist/ai-service/state-machine/handlers/llm-generating.d.ts.map +1 -1
  269. package/dist/ai-service/state-machine/handlers/llm-generating.js +32 -9
  270. package/dist/ai-service/state-machine/handlers/llm-generating.js.map +1 -1
  271. package/dist/ai-service/state-machine/handlers/runtime-reviewing.d.ts.map +1 -1
  272. package/dist/ai-service/state-machine/handlers/runtime-reviewing.js +21 -2
  273. package/dist/ai-service/state-machine/handlers/runtime-reviewing.js.map +1 -1
  274. package/dist/ai-service/state-machine/helpers/stable-peer.d.ts +11 -2
  275. package/dist/ai-service/state-machine/helpers/stable-peer.d.ts.map +1 -1
  276. package/dist/ai-service/state-machine/helpers/stable-peer.js +105 -18
  277. package/dist/ai-service/state-machine/helpers/stable-peer.js.map +1 -1
  278. package/dist/ai-service/state-machine/mocks.d.ts +3 -1
  279. package/dist/ai-service/state-machine/mocks.d.ts.map +1 -1
  280. package/dist/ai-service/state-machine/mocks.js +52 -13
  281. package/dist/ai-service/state-machine/mocks.js.map +1 -1
  282. package/dist/ai-service/tasks/peer-push.d.ts +3 -0
  283. package/dist/ai-service/tasks/peer-push.d.ts.map +1 -1
  284. package/dist/ai-service/tasks/peer-push.js +33 -0
  285. package/dist/ai-service/tasks/peer-push.js.map +1 -1
  286. package/dist/ai-service/util/call-peer.d.ts +2 -0
  287. package/dist/ai-service/util/call-peer.d.ts.map +1 -1
  288. package/dist/ai-service/util/call-peer.js +17 -4
  289. package/dist/ai-service/util/call-peer.js.map +1 -1
  290. package/dist/ai-service/util/line-ranges.d.ts +21 -0
  291. package/dist/ai-service/util/line-ranges.d.ts.map +1 -0
  292. package/dist/ai-service/util/line-ranges.js +36 -0
  293. package/dist/ai-service/util/line-ranges.js.map +1 -0
  294. package/dist/ai-service/util/peer-liveness.d.ts +1 -0
  295. package/dist/ai-service/util/peer-liveness.d.ts.map +1 -1
  296. package/dist/ai-service/util/peer-liveness.js +2 -0
  297. package/dist/ai-service/util/peer-liveness.js.map +1 -1
  298. package/dist/dev-server-ws-smoke-client.d.ts.map +1 -1
  299. package/dist/dev-server-ws-smoke-client.js +7 -0
  300. package/dist/dev-server-ws-smoke-client.js.map +1 -1
  301. package/dist/draft-interface.d.ts +8 -0
  302. package/dist/draft-interface.d.ts.map +1 -1
  303. package/dist/early-error-relay.d.ts +2 -0
  304. package/dist/early-error-relay.d.ts.map +1 -1
  305. package/dist/early-error-relay.js +7 -3
  306. package/dist/early-error-relay.js.map +1 -1
  307. package/dist/file-sync-vite-plugin.d.ts.map +1 -1
  308. package/dist/file-sync-vite-plugin.js +43 -15
  309. package/dist/file-sync-vite-plugin.js.map +1 -1
  310. package/dist/file-system-helpers.d.ts +2 -2
  311. package/dist/file-system-helpers.d.ts.map +1 -1
  312. package/dist/file-system-helpers.js +3 -3
  313. package/dist/file-system-helpers.js.map +1 -1
  314. package/dist/git-service/errors.d.ts +9 -0
  315. package/dist/git-service/errors.d.ts.map +1 -1
  316. package/dist/git-service/errors.js +15 -0
  317. package/dist/git-service/errors.js.map +1 -1
  318. package/dist/git-service/index.d.ts +2 -2
  319. package/dist/git-service/index.d.ts.map +1 -1
  320. package/dist/git-service/index.js +2 -2
  321. package/dist/git-service/index.js.map +1 -1
  322. package/dist/index.d.ts +1 -0
  323. package/dist/index.d.ts.map +1 -1
  324. package/dist/index.js +1 -0
  325. package/dist/index.js.map +1 -1
  326. package/dist/lock-service/activity-tracker.d.ts +5 -0
  327. package/dist/lock-service/activity-tracker.d.ts.map +1 -1
  328. package/dist/lock-service/activity-tracker.js +10 -0
  329. package/dist/lock-service/activity-tracker.js.map +1 -1
  330. package/dist/lock-service/index.d.ts +69 -4
  331. package/dist/lock-service/index.d.ts.map +1 -1
  332. package/dist/lock-service/index.js +139 -29
  333. package/dist/lock-service/index.js.map +1 -1
  334. package/dist/migration-templates/app-fullstack/client/components/ui/accordion.tsx +9 -65
  335. package/dist/migration-templates/app-fullstack/client/components/ui/area-chart.tsx +36 -156
  336. package/dist/migration-templates/app-fullstack/client/components/ui/aspect-ratio.tsx +1 -5
  337. package/dist/migration-templates/app-fullstack/client/components/ui/avatar.tsx +4 -18
  338. package/dist/migration-templates/app-fullstack/client/components/ui/badge.tsx +6 -29
  339. package/dist/migration-templates/app-fullstack/client/components/ui/bar-chart.tsx +41 -167
  340. package/dist/migration-templates/app-fullstack/client/components/ui/breadcrumb.tsx +1 -4
  341. package/dist/migration-templates/app-fullstack/client/components/ui/button.tsx +5 -64
  342. package/dist/migration-templates/app-fullstack/client/components/ui/calendar.tsx +6 -42
  343. package/dist/migration-templates/app-fullstack/client/components/ui/card.tsx +1 -4
  344. package/dist/migration-templates/app-fullstack/client/components/ui/checkbox.tsx +4 -29
  345. package/dist/migration-templates/app-fullstack/client/components/ui/date-range-picker.tsx +13 -154
  346. package/dist/migration-templates/app-fullstack/client/components/ui/dialog.tsx +7 -34
  347. package/dist/migration-templates/app-fullstack/client/components/ui/file-dropzone.tsx +12 -95
  348. package/dist/migration-templates/app-fullstack/client/components/ui/file-input.tsx +12 -73
  349. package/dist/migration-templates/app-fullstack/client/components/ui/hover-card.tsx +10 -66
  350. package/dist/migration-templates/app-fullstack/client/components/ui/icon.tsx +3 -16
  351. package/dist/migration-templates/app-fullstack/client/components/ui/image.tsx +4 -16
  352. package/dist/migration-templates/app-fullstack/client/components/ui/input.tsx +18 -159
  353. package/dist/migration-templates/app-fullstack/client/components/ui/label.tsx +1 -4
  354. package/dist/migration-templates/app-fullstack/client/components/ui/line-chart.tsx +32 -148
  355. package/dist/migration-templates/app-fullstack/client/components/ui/link.tsx +4 -24
  356. package/dist/migration-templates/app-fullstack/client/components/ui/navigation-menu.tsx +3 -24
  357. package/dist/migration-templates/app-fullstack/client/components/ui/pagination.tsx +4 -24
  358. package/dist/migration-templates/app-fullstack/client/components/ui/pie-chart.tsx +28 -142
  359. package/dist/migration-templates/app-fullstack/client/components/ui/popover.tsx +9 -61
  360. package/dist/migration-templates/app-fullstack/client/components/ui/progress.tsx +2 -11
  361. package/dist/migration-templates/app-fullstack/client/components/ui/radar-chart.tsx +37 -171
  362. package/dist/migration-templates/app-fullstack/client/components/ui/radial-chart.tsx +50 -202
  363. package/dist/migration-templates/app-fullstack/client/components/ui/select.tsx +5 -35
  364. package/dist/migration-templates/app-fullstack/client/components/ui/separator.tsx +1 -8
  365. package/dist/migration-templates/app-fullstack/client/components/ui/sheet.tsx +7 -40
  366. package/dist/migration-templates/app-fullstack/client/components/ui/sidebar.tsx +3 -35
  367. package/dist/migration-templates/app-fullstack/client/components/ui/slider.tsx +11 -95
  368. package/dist/migration-templates/app-fullstack/client/components/ui/switch.tsx +5 -32
  369. package/dist/migration-templates/app-fullstack/client/components/ui/textarea.tsx +13 -90
  370. package/dist/migration-templates/app-fullstack/client/components/ui/toggle-group.tsx +11 -75
  371. package/dist/migration-templates/app-fullstack/client/components/ui/toggle.tsx +8 -70
  372. package/dist/migration-templates/app-fullstack/client/components/ui/tooltip.tsx +9 -62
  373. package/dist/parsing/imports.d.ts +22 -0
  374. package/dist/parsing/imports.d.ts.map +1 -1
  375. package/dist/parsing/imports.js +71 -0
  376. package/dist/parsing/imports.js.map +1 -1
  377. package/dist/reconnect-guard-plugin.d.ts +53 -0
  378. package/dist/reconnect-guard-plugin.d.ts.map +1 -0
  379. package/dist/reconnect-guard-plugin.js +203 -0
  380. package/dist/reconnect-guard-plugin.js.map +1 -0
  381. package/dist/resolver.d.ts +2 -1
  382. package/dist/resolver.d.ts.map +1 -1
  383. package/dist/resolver.js +4 -6
  384. package/dist/resolver.js.map +1 -1
  385. package/dist/router-parser-metrics.d.ts +2 -1
  386. package/dist/router-parser-metrics.d.ts.map +1 -1
  387. package/dist/router-parser-metrics.js.map +1 -1
  388. package/dist/router-parser.d.ts +10 -1
  389. package/dist/router-parser.d.ts.map +1 -1
  390. package/dist/router-parser.js +306 -69
  391. package/dist/router-parser.js.map +1 -1
  392. package/dist/scan-scope-merge-metrics.d.ts +2 -0
  393. package/dist/scan-scope-merge-metrics.d.ts.map +1 -0
  394. package/dist/scan-scope-merge-metrics.js +18 -0
  395. package/dist/scan-scope-merge-metrics.js.map +1 -0
  396. package/dist/scan-scope-merge.d.ts +2 -2
  397. package/dist/scan-scope-merge.d.ts.map +1 -1
  398. package/dist/scan-scope-merge.js +64 -14
  399. package/dist/scan-scope-merge.js.map +1 -1
  400. package/dist/server-rpc/index.d.ts.map +1 -1
  401. package/dist/server-rpc/index.js +12 -2
  402. package/dist/server-rpc/index.js.map +1 -1
  403. package/dist/socket-manager.d.ts +1 -1
  404. package/dist/socket-manager.d.ts.map +1 -1
  405. package/dist/socket-manager.js +276 -15
  406. package/dist/socket-manager.js.map +1 -1
  407. package/dist/sync-service/download.js +2 -2
  408. package/dist/sync-service/download.js.map +1 -1
  409. package/dist/sync-service/index.d.ts +95 -22
  410. package/dist/sync-service/index.d.ts.map +1 -1
  411. package/dist/sync-service/index.js +402 -56
  412. package/dist/sync-service/index.js.map +1 -1
  413. package/dist/sync-service/page-reference-guard.d.ts +17 -0
  414. package/dist/sync-service/page-reference-guard.d.ts.map +1 -0
  415. package/dist/sync-service/page-reference-guard.js +170 -0
  416. package/dist/sync-service/page-reference-guard.js.map +1 -0
  417. package/dist/util.d.ts.map +1 -1
  418. package/dist/util.js +16 -2
  419. package/dist/util.js.map +1 -1
  420. package/package.json +15 -14
@@ -3,9 +3,18 @@ import { join, resolve, dirname, relative } from "node:path";
3
3
  import { parse } from "@babel/parser";
4
4
  import { findStaticImports, parseStaticImport } from "mlly";
5
5
  import { joinURL } from "ufo";
6
+ import { isLocalModuleSpecifier } from "./parsing/imports.js";
6
7
  import { getFullImportPath } from "./resolver.js";
7
8
  import { traverse } from "./traverse.js";
8
9
  import { getLogger } from "./util/logger.js";
10
+ export class MissingCreateBrowserRouterError extends Error {
11
+ routerFilePath;
12
+ constructor(routerFilePath) {
13
+ super("Could not find router file with createBrowserRouter in project");
14
+ this.routerFilePath = routerFilePath;
15
+ this.name = "MissingCreateBrowserRouterError";
16
+ }
17
+ }
9
18
  function countRouteObjects(routes) {
10
19
  let count = 0;
11
20
  for (const element of routes.elements) {
@@ -23,11 +32,13 @@ function countRouteObjects(routes) {
23
32
  }
24
33
  return count;
25
34
  }
26
- const CONVENTIONAL_ROUTER_PATHS = [
35
+ export const CONVENTIONAL_ROUTER_PATHS = [
27
36
  "router.tsx",
28
37
  "router.ts",
29
38
  "src/router.tsx",
30
39
  "src/router.ts",
40
+ "client/router.tsx",
41
+ "client/router.ts",
31
42
  ];
32
43
  let cachedRouterFileLocation = null;
33
44
  /**
@@ -132,7 +143,7 @@ function extractReactRouterImports(content) {
132
143
  /**
133
144
  * Check if content contains createBrowserRouter call, accounting for import aliases
134
145
  */
135
- function hasCreateBrowserRouter(content) {
146
+ export function hasCreateBrowserRouter(content) {
136
147
  const { createBrowserRouterAliases, namespaceImports } = extractReactRouterImports(content);
137
148
  // Quick substring check first for performance
138
149
  if (!content.includes("createBrowserRouter") &&
@@ -249,7 +260,7 @@ export async function findRouterFile(rootDir) {
249
260
  cachedRouterFileLocation = null;
250
261
  }
251
262
  }
252
- // Try conventional locations first
263
+ let routerWithoutCreateBrowserRouter;
253
264
  for (const conventionalPath of CONVENTIONAL_ROUTER_PATHS) {
254
265
  const fullPath = join(rootDir, conventionalPath);
255
266
  try {
@@ -261,13 +272,14 @@ export async function findRouterFile(rootDir) {
261
272
  getLogger().info(`Found router file at: ${conventionalPath}`);
262
273
  return fullPath;
263
274
  }
275
+ routerWithoutCreateBrowserRouter ??= fullPath;
264
276
  }
265
277
  catch {
266
278
  continue;
267
279
  }
268
280
  }
269
281
  // Fall back to scanning all TypeScript files in rootDir
270
- getLogger().info("Router not found in conventional locations, scanning TypeScript files…");
282
+ getLogger().info("Router not found in conventional locations, scanning TypeScript files...");
271
283
  const allTsFiles = await findAllTsFiles(rootDir);
272
284
  for (const file of allTsFiles) {
273
285
  try {
@@ -283,17 +295,11 @@ export async function findRouterFile(rootDir) {
283
295
  continue;
284
296
  }
285
297
  }
298
+ if (routerWithoutCreateBrowserRouter) {
299
+ throw new MissingCreateBrowserRouterError(routerWithoutCreateBrowserRouter);
300
+ }
286
301
  throw new Error("Could not find router file with createBrowserRouter in project");
287
302
  }
288
- /**
289
- * True for project-relative or alias imports (./, ../, /, @/) — i.e. paths
290
- * we can resolve to a file in this repo. Filters out npm packages.
291
- */
292
- function isRelativeOrAliasImport(specifier) {
293
- return (specifier.startsWith(".") ||
294
- specifier.startsWith("/") ||
295
- specifier.startsWith("@/"));
296
- }
297
303
  /**
298
304
  * Debug log emitted when `Component:` / `element:` references a value the
299
305
  * parser couldn't resolve to an import, usually because the user wrote a
@@ -418,7 +424,10 @@ function extractImportPathFromFunction(node, callableImportMap) {
418
424
  return extractImportSpecifierFromExpression(expr, callableImportMap);
419
425
  }
420
426
  /**
421
- * Extract the page import specifier from a `lazy:` route property value.
427
+ * Extract the page import specifier from a route loader expression: a `lazy:`
428
+ * property value, a top-level const initializer bound as a loader, or a
429
+ * spread argument (page-classified factory calls and unclassified spreads
430
+ * alike).
422
431
  *
423
432
  * Handles the direct arrow form the template ships with
424
433
  * (`lazy: () => import("...")`, `lazy: () => import("...").then(...)`), a plain
@@ -443,17 +452,11 @@ function extractImportPathFromFunction(node, callableImportMap) {
443
452
  * found wins. Every real/tested loader shape carries exactly one importer.
444
453
  */
445
454
  function extractImportPathFromLazyValue(node, callableImportMap, lazyLoaderBindings) {
455
+ node = unwrapTsWrappers(node);
446
456
  // `lazy: overview` — a const bound to a loader elsewhere in the file.
447
457
  if (node.type === "Identifier") {
448
458
  return lazyLoaderBindings?.get(node.name) ?? null;
449
459
  }
450
- // See through TS type wrappers (`... as any`, `... satisfies T`, `...!`).
451
- // They are transparent at runtime, so the importer lives on `.expression`.
452
- if (node.type === "TSAsExpression" ||
453
- node.type === "TSSatisfiesExpression" ||
454
- node.type === "TSNonNullExpression") {
455
- return extractImportPathFromLazyValue(node.expression, callableImportMap, lazyLoaderBindings);
456
- }
457
460
  if (node.type === "ArrowFunctionExpression" ||
458
461
  node.type === "FunctionExpression") {
459
462
  return extractImportPathFromFunction(node, callableImportMap);
@@ -484,6 +487,200 @@ function extractImportPathFromLazyValue(node, callableImportMap, lazyLoaderBindi
484
487
  }
485
488
  return null;
486
489
  }
490
+ /**
491
+ * The route-object keys that make a property (or spread contribution) the
492
+ * page source for a route, as opposed to loaders, handles, and other
493
+ * metadata.
494
+ */
495
+ const ROUTE_PAGE_KEYS = new Set(["lazy", "Component", "element"]);
496
+ /** Unwrap runtime-transparent TS wrappers (`as`, `satisfies`, `!`). */
497
+ function unwrapTsWrappers(node) {
498
+ while (node.type === "TSAsExpression" ||
499
+ node.type === "TSSatisfiesExpression" ||
500
+ node.type === "TSNonNullExpression") {
501
+ node = node.expression;
502
+ }
503
+ return node;
504
+ }
505
+ /**
506
+ * Static key of an object member: identifier (`lazy:`) or string literal
507
+ * (`"lazy":`). Computed keys are not statically knowable and return null.
508
+ */
509
+ function getStaticPropertyKey(prop) {
510
+ if (prop.key.type === "Identifier" && !prop.computed)
511
+ return prop.key.name;
512
+ if (prop.key.type === "StringLiteral")
513
+ return prop.key.value;
514
+ return null;
515
+ }
516
+ /** True when `p` is the Program, or an export declaration directly under it. */
517
+ function isProgramLevel(p) {
518
+ if (!p)
519
+ return false;
520
+ return (p.isProgram() ||
521
+ (p.isExportNamedDeclaration() && (p.parentPath?.isProgram() ?? false)));
522
+ }
523
+ /**
524
+ * Classify what an object literal contributes when spread into a route:
525
+ * "page" when it carries a page key, "non-page" when its full key set is
526
+ * visible and carries none, "unknown" when an inner spread hides keys.
527
+ */
528
+ function classifyRouteFragment(obj) {
529
+ let sawUnknowableKey = false;
530
+ for (const prop of obj.properties) {
531
+ if (prop.type === "SpreadElement") {
532
+ sawUnknowableKey = true;
533
+ continue;
534
+ }
535
+ const name = getStaticPropertyKey(prop);
536
+ if (name && ROUTE_PAGE_KEYS.has(name))
537
+ return "page";
538
+ // A computed dynamic key could be anything at runtime, so its absence
539
+ // from the static keys proves nothing.
540
+ if (!name && prop.computed)
541
+ sawUnknowableKey = true;
542
+ }
543
+ return sawUnknowableKey ? "unknown" : "non-page";
544
+ }
545
+ /**
546
+ * Classify a local factory by the object literal it returns. Only bodies
547
+ * made of straight-line statements are inspected; anything that could hide
548
+ * a return (conditionals, loops, try blocks) classifies as "unknown" so the
549
+ * caller falls back to the import heuristic instead of wrongly ruling the
550
+ * factory out. In a straight-line body only the first return is reachable,
551
+ * so it alone decides.
552
+ */
553
+ function classifyLocalFactory(fn) {
554
+ if (fn.body.type !== "BlockStatement") {
555
+ const expr = unwrapTsWrappers(fn.body);
556
+ return expr.type === "ObjectExpression"
557
+ ? { shape: classifyRouteFragment(expr), fragment: expr }
558
+ : { shape: "unknown", fragment: null };
559
+ }
560
+ for (const statement of fn.body.body) {
561
+ if (statement.type === "ReturnStatement") {
562
+ const arg = statement.argument
563
+ ? unwrapTsWrappers(statement.argument)
564
+ : null;
565
+ return arg?.type === "ObjectExpression"
566
+ ? { shape: classifyRouteFragment(arg), fragment: arg }
567
+ : { shape: "unknown", fragment: null };
568
+ }
569
+ if (statement.type !== "VariableDeclaration" &&
570
+ statement.type !== "ExpressionStatement") {
571
+ return { shape: "unknown", fragment: null };
572
+ }
573
+ }
574
+ return { shape: "unknown", fragment: null };
575
+ }
576
+ /**
577
+ * Extract the page import from an object literal spread into a route
578
+ * (`...{ lazy: () => import("...") }` or a const bound to one). Later page
579
+ * keys override earlier ones, matching runtime object semantics. Broader
580
+ * than the explicit-property loop by design: classifyRouteFragment counts
581
+ * method shorthand and string-literal keys as page-bearing, so extraction
582
+ * must recognize the same shapes or a "page" fragment would silently
583
+ * extract nothing.
584
+ */
585
+ function extractPageImportFromFragment(fragment, allImports, callableImportMap, lazyLoaderBindings) {
586
+ let importPath = null;
587
+ for (const prop of fragment.properties) {
588
+ if (prop.type === "SpreadElement")
589
+ continue;
590
+ const key = getStaticPropertyKey(prop);
591
+ if (!key || !ROUTE_PAGE_KEYS.has(key))
592
+ continue;
593
+ if (prop.type === "ObjectMethod") {
594
+ if (key === "lazy") {
595
+ const path = extractImportPathFromFunction(prop, callableImportMap);
596
+ if (path)
597
+ importPath = path;
598
+ }
599
+ continue;
600
+ }
601
+ if (key === "lazy") {
602
+ const path = extractImportPathFromLazyValue(prop.value, callableImportMap, lazyLoaderBindings);
603
+ if (path)
604
+ importPath = path;
605
+ }
606
+ else if (key === "Component" && prop.value.type === "Identifier") {
607
+ importPath = allImports.get(prop.value.name) ?? importPath;
608
+ }
609
+ else if (key === "element") {
610
+ const path = resolveElementImportPath(prop.value, allImports);
611
+ if (path)
612
+ importPath = path;
613
+ }
614
+ }
615
+ return importPath;
616
+ }
617
+ /**
618
+ * Resolve what a route-object spread contributes to the route's page.
619
+ *
620
+ * "page": the spread verifiably carries a page key (an object literal, a
621
+ * const bound to one, or a local factory call, direct or through a const,
622
+ * whose return shape is inspectable); its import participates like an
623
+ * explicit property.
624
+ * "none": the spread verifiably carries no page key and must be ignored, so
625
+ * a loader-only helper's import is never mistaken for the page.
626
+ * "heuristic": the parser cannot classify the contribution (an imported
627
+ * factory, or an indirection it does not chase); the first import found in
628
+ * the expression is offered as a fallback for the caller to use only when
629
+ * nothing verified resolves.
630
+ */
631
+ function resolveSpreadContribution(argument, allImports, callableImportMap, lazyLoaderBindings, spreadBindings) {
632
+ const unwrapped = unwrapTsWrappers(argument);
633
+ let fragment = null;
634
+ let factoryCallee = null;
635
+ if (unwrapped.type === "ObjectExpression") {
636
+ fragment = unwrapped;
637
+ }
638
+ else if (unwrapped.type === "Identifier") {
639
+ fragment = spreadBindings?.objectLiterals.get(unwrapped.name) ?? null;
640
+ if (!fragment) {
641
+ factoryCallee =
642
+ spreadBindings?.constFactoryCalls.get(unwrapped.name) ?? null;
643
+ }
644
+ }
645
+ else if (unwrapped.type === "CallExpression" &&
646
+ unwrapped.callee.type === "Identifier") {
647
+ factoryCallee = unwrapped.callee.name;
648
+ }
649
+ // An inferred page import must be a local module, matching the gate every
650
+ // other inference site in this file applies; a bare specifier inside a
651
+ // spread (analytics/i18n wrappers) is never the page.
652
+ const localOnly = (path) => path && isLocalModuleSpecifier(path) ? path : null;
653
+ if (fragment) {
654
+ const shape = classifyRouteFragment(fragment);
655
+ if (shape === "page") {
656
+ return {
657
+ kind: "page",
658
+ importPath: localOnly(extractPageImportFromFragment(fragment, allImports, callableImportMap, lazyLoaderBindings)),
659
+ };
660
+ }
661
+ if (shape === "non-page")
662
+ return { kind: "none" };
663
+ // "unknown": an inner spread hides keys; fall through to the heuristic.
664
+ }
665
+ else if (factoryCallee) {
666
+ const factory = spreadBindings?.factoryShapes.get(factoryCallee);
667
+ if (factory?.shape === "page") {
668
+ // The importer is usually passed in through the call's arguments; a
669
+ // zero-argument factory instead hardcodes it in the returned fragment.
670
+ const fromArguments = localOnly(extractImportPathFromLazyValue(argument, callableImportMap, lazyLoaderBindings));
671
+ const fromFragment = factory.fragment
672
+ ? localOnly(extractPageImportFromFragment(factory.fragment, allImports, callableImportMap, lazyLoaderBindings))
673
+ : null;
674
+ return { kind: "page", importPath: fromArguments ?? fromFragment };
675
+ }
676
+ if (factory?.shape === "non-page")
677
+ return { kind: "none" };
678
+ }
679
+ return {
680
+ kind: "heuristic",
681
+ importPath: localOnly(extractImportPathFromLazyValue(argument, callableImportMap, lazyLoaderBindings)),
682
+ };
683
+ }
487
684
  /**
488
685
  * Recognize `lazy(() => import("..."))` / `React.lazy(() => import("..."))`
489
686
  * (arrow or plain `function () { return import("..."); }` importer) and return
@@ -527,7 +724,7 @@ function extractAllImports(content) {
527
724
  for (const staticImport of staticImports) {
528
725
  const parsed = parseStaticImport(staticImport);
529
726
  // Skip imports from node_modules and react-router
530
- if (!isRelativeOrAliasImport(parsed.specifier)) {
727
+ if (!isLocalModuleSpecifier(parsed.specifier)) {
531
728
  continue;
532
729
  }
533
730
  // Handle default imports: import Page1 from "./components/Page1.tsx"
@@ -587,47 +784,41 @@ export async function parseRouterFile(routerFilePath, rootDir, onDiagnostic) {
587
784
  // (Identifier) resolves. e.g. const overview = lazyPage(() => import("..."))
588
785
  // Maps loaderName → importPath.
589
786
  const lazyLoaderBindings = new Map();
787
+ // Bindings that let route-object spreads be classified statically:
788
+ // object-literal consts (`...homeRoute`) and local factories whose return
789
+ // shape says whether the spread contributes a page key (`...gatedLazy(...)`).
790
+ const spreadBindings = {
791
+ objectLiterals: new Map(),
792
+ factoryShapes: new Map(),
793
+ constFactoryCalls: new Map(),
794
+ };
590
795
  traverse(ast, {
796
+ FunctionDeclaration(astPath) {
797
+ const node = astPath.node;
798
+ if (!node.id)
799
+ return;
800
+ if (isProgramLevel(astPath.parentPath) &&
801
+ !spreadBindings.factoryShapes.has(node.id.name)) {
802
+ spreadBindings.factoryShapes.set(node.id.name, classifyLocalFactory(node));
803
+ }
804
+ },
591
805
  VariableDeclarator(astPath) {
592
806
  const node = astPath.node;
593
807
  if (node.id.type !== "Identifier" || !node.init)
594
808
  return;
595
- if (node.init.type === "ArrayExpression") {
596
- variableDeclarations.set(node.id.name, node.init);
597
- }
598
- else if (node.init.type === "TSAsExpression" &&
599
- node.init.expression.type === "ArrayExpression") {
600
- variableDeclarations.set(node.id.name, node.init.expression);
601
- }
602
- else if (node.init.type === "TSSatisfiesExpression" &&
603
- node.init.expression.type === "ArrayExpression") {
604
- variableDeclarations.set(node.id.name, node.init.expression);
809
+ // TS wrappers (`as const`, `satisfies T`, `!`) are runtime-transparent.
810
+ const initExpr = unwrapTsWrappers(node.init);
811
+ if (initExpr.type === "ArrayExpression") {
812
+ variableDeclarations.set(node.id.name, initExpr);
605
813
  }
606
814
  // Only register top-level lazy bindings (Program > VarDecl or
607
815
  // Program > ExportNamedDecl > VarDecl) and never overwrite a
608
816
  // static import — prevents nested/helper-scoped rebindings.
609
- const declarationParent = astPath.parentPath?.parentPath;
610
- const isTopLevel = declarationParent
611
- ? declarationParent.isProgram() ||
612
- (declarationParent.isExportNamedDeclaration() &&
613
- (declarationParent.parentPath?.isProgram() ?? false))
614
- : false;
817
+ const isTopLevel = isProgramLevel(astPath.parentPath?.parentPath);
615
818
  // Collect top-level object expressions with arrow-function properties
616
819
  // that contain import() calls (e.g. preload/chunk maps).
617
- // Unwrap `as const` / `satisfies T` wrappers the same way we do for arrays.
618
820
  if (isTopLevel) {
619
- let objectExpr = null;
620
- if (node.init.type === "ObjectExpression") {
621
- objectExpr = node.init;
622
- }
623
- else if (node.init.type === "TSAsExpression" &&
624
- node.init.expression.type === "ObjectExpression") {
625
- objectExpr = node.init.expression;
626
- }
627
- else if (node.init.type === "TSSatisfiesExpression" &&
628
- node.init.expression.type === "ObjectExpression") {
629
- objectExpr = node.init.expression;
630
- }
821
+ const objectExpr = initExpr.type === "ObjectExpression" ? initExpr : null;
631
822
  if (objectExpr) {
632
823
  const propMap = new Map();
633
824
  for (const prop of objectExpr.properties) {
@@ -646,30 +837,35 @@ export async function parseRouterFile(routerFilePath, rootDir, onDiagnostic) {
646
837
  else {
647
838
  continue;
648
839
  }
649
- // Accept both identifier keys (`Welcome:`) and string-literal
650
- // keys (`"my-page":`); both look up the same way at call sites.
651
- let propName = null;
652
- if (prop.key.type === "Identifier" && !prop.computed) {
653
- propName = prop.key.name;
654
- }
655
- else if (prop.key.type === "StringLiteral") {
656
- propName = prop.key.value;
657
- }
840
+ const propName = getStaticPropertyKey(prop);
658
841
  if (!propName)
659
842
  continue;
660
843
  const importPath = extractImportPathFromFunction(fn);
661
- if (importPath && isRelativeOrAliasImport(importPath)) {
844
+ if (importPath && isLocalModuleSpecifier(importPath)) {
662
845
  propMap.set(propName, importPath);
663
846
  }
664
847
  }
665
848
  if (propMap.size > 0) {
666
849
  callableImportMap.set(node.id.name, propMap);
667
850
  }
851
+ if (!spreadBindings.objectLiterals.has(node.id.name)) {
852
+ spreadBindings.objectLiterals.set(node.id.name, objectExpr);
853
+ }
854
+ }
855
+ if ((initExpr.type === "ArrowFunctionExpression" ||
856
+ initExpr.type === "FunctionExpression") &&
857
+ !spreadBindings.factoryShapes.has(node.id.name)) {
858
+ spreadBindings.factoryShapes.set(node.id.name, classifyLocalFactory(initExpr));
859
+ }
860
+ if (initExpr.type === "CallExpression" &&
861
+ initExpr.callee.type === "Identifier" &&
862
+ !spreadBindings.constFactoryCalls.has(node.id.name)) {
863
+ spreadBindings.constFactoryCalls.set(node.id.name, initExpr.callee.name);
668
864
  }
669
865
  }
670
866
  if (isTopLevel && !allImports.has(node.id.name)) {
671
- const lazyImportPath = extractLazyImportPath(node.init);
672
- if (lazyImportPath && isRelativeOrAliasImport(lazyImportPath)) {
867
+ const lazyImportPath = extractLazyImportPath(initExpr);
868
+ if (lazyImportPath && isLocalModuleSpecifier(lazyImportPath)) {
673
869
  allImports.set(node.id.name, lazyImportPath);
674
870
  }
675
871
  }
@@ -679,7 +875,7 @@ export async function parseRouterFile(routerFilePath, rootDir, onDiagnostic) {
679
875
  // limited to actual component bindings.
680
876
  if (isTopLevel && !lazyLoaderBindings.has(node.id.name)) {
681
877
  const loaderImportPath = extractImportPathFromLazyValue(node.init, callableImportMap, lazyLoaderBindings);
682
- if (loaderImportPath && isRelativeOrAliasImport(loaderImportPath)) {
878
+ if (loaderImportPath && isLocalModuleSpecifier(loaderImportPath)) {
683
879
  lazyLoaderBindings.set(node.id.name, loaderImportPath);
684
880
  }
685
881
  }
@@ -722,7 +918,7 @@ export async function parseRouterFile(routerFilePath, rootDir, onDiagnostic) {
722
918
  });
723
919
  // Process routes asynchronously after traverse
724
920
  if (routesArray) {
725
- await extractRoutesFromArray(routesArray, routes, routerFilePath, rootDir, "", allImports, callableImportMap, lazyLoaderBindings);
921
+ await extractRoutesFromArray(routesArray, routes, routerFilePath, rootDir, "", allImports, callableImportMap, lazyLoaderBindings, spreadBindings);
726
922
  if (routeObjectCount > 0 && routes.length === 0) {
727
923
  onDiagnostic?.({
728
924
  kind: "unsupported_route_shape",
@@ -746,19 +942,52 @@ export async function parseRouterFile(routerFilePath, rootDir, onDiagnostic) {
746
942
  return [];
747
943
  }
748
944
  }
749
- async function extractRoutesFromArray(node, routes, routerFilePath, rootDir, parentPath, allImports, callableImportMap, lazyLoaderBindings) {
945
+ async function extractRoutesFromArray(node, routes, routerFilePath, rootDir, parentPath, allImports, callableImportMap, lazyLoaderBindings, spreadBindings) {
750
946
  for (const element of node.elements) {
751
947
  if (element && element.type === "ObjectExpression") {
752
- await extractRouteFromObject(element, routes, routerFilePath, rootDir, parentPath, allImports, callableImportMap, lazyLoaderBindings);
948
+ await extractRouteFromObject(element, routes, routerFilePath, rootDir, parentPath, allImports, callableImportMap, lazyLoaderBindings, spreadBindings);
753
949
  }
754
950
  }
755
951
  }
756
- async function extractRouteFromObject(node, routes, routerFilePath, rootDir, parentPath, allImports, callableImportMap, lazyLoaderBindings) {
952
+ async function extractRouteFromObject(node, routes, routerFilePath, rootDir, parentPath, allImports, callableImportMap, lazyLoaderBindings, spreadBindings) {
757
953
  let routePath = null;
758
954
  let pageImportPath = null;
759
955
  let children = null;
760
956
  let hasIndex = false;
957
+ let heuristicSpreadImportPath = null;
958
+ let sawUnresolvedPageSpread = false;
761
959
  for (const prop of node.properties) {
960
+ // A route may receive its page property through a spread instead of a
961
+ // literal key: `{ path: "/home", ...gatedLazy(() => import("...")) }`.
962
+ // A classified page contribution participates like an explicit property
963
+ // in source order, so a later contributor overrides an earlier one,
964
+ // matching runtime spread order when the import is extractable; a
965
+ // heuristic one is only a fallback for when nothing verified resolves.
966
+ if (prop.type === "SpreadElement") {
967
+ const contribution = resolveSpreadContribution(prop.argument, allImports, callableImportMap, lazyLoaderBindings, spreadBindings);
968
+ if (contribution.kind === "page") {
969
+ if (contribution.importPath) {
970
+ pageImportPath = contribution.importPath;
971
+ }
972
+ else {
973
+ // The spread verifiably carries the route's page and it could not
974
+ // be resolved. At runtime it overrides whatever came before it, so
975
+ // an earlier contributor's import is discarded and the heuristic
976
+ // fallback suppressed; mapping either would point the route at a
977
+ // file the router no longer renders. The route drops unless a
978
+ // later contributor resolves.
979
+ pageImportPath = null;
980
+ sawUnresolvedPageSpread = true;
981
+ getLogger().debug(`Router parser: a spread on route "${routePath ?? "(index)"}" in ${routerFilePath} ` +
982
+ `carries a page key (lazy/Component/element) the parser could not resolve to an import; ` +
983
+ `the route will be dropped unless a later page property resolves.`);
984
+ }
985
+ }
986
+ else if (contribution.kind === "heuristic" && contribution.importPath) {
987
+ heuristicSpreadImportPath = contribution.importPath;
988
+ }
989
+ continue;
990
+ }
762
991
  if (prop.type !== "ObjectProperty")
763
992
  continue;
764
993
  const key = prop.key.type === "Identifier" ? prop.key.name : null;
@@ -806,6 +1035,14 @@ async function extractRouteFromObject(node, routes, routerFilePath, rootDir, par
806
1035
  children = prop.value;
807
1036
  }
808
1037
  }
1038
+ if (!pageImportPath &&
1039
+ heuristicSpreadImportPath &&
1040
+ !sawUnresolvedPageSpread) {
1041
+ pageImportPath = heuristicSpreadImportPath;
1042
+ getLogger().debug(`Router parser: route "${routePath ?? "(index)"}" in ${routerFilePath} has no verified page property; ` +
1043
+ `treating import "${heuristicSpreadImportPath}" from a spread the parser could not classify as the page. ` +
1044
+ `If that spread contributes a loader rather than a page, the mapping will be wrong.`);
1045
+ }
809
1046
  // Check if any children have index: true
810
1047
  let hasIndexChild = false;
811
1048
  if (children) {
@@ -888,7 +1125,7 @@ async function extractRouteFromObject(node, routes, routerFilePath, rootDir, par
888
1125
  const currentPath = routePath ? joinURL(parentPath, routePath) : parentPath;
889
1126
  // Normalize empty path to "/" before passing to children
890
1127
  const normalizedCurrentPath = currentPath || "/";
891
- await extractRoutesFromArray(children, routes, routerFilePath, rootDir, normalizedCurrentPath, allImports, callableImportMap, lazyLoaderBindings);
1128
+ await extractRoutesFromArray(children, routes, routerFilePath, rootDir, normalizedCurrentPath, allImports, callableImportMap, lazyLoaderBindings, spreadBindings);
892
1129
  }
893
1130
  }
894
1131
  //# sourceMappingURL=router-parser.js.map