testeranto 0.202.0 → 0.203.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 (773) hide show
  1. package/README.md +23 -0
  2. package/UX/chache/index.md +11 -0
  3. package/dist/prebuild/App.css +78 -0
  4. package/dist/prebuild/App.js +4828 -2814
  5. package/dist/prebuild/testeranto.mjs +2650 -1037
  6. package/example/Calculator.go +63 -0
  7. package/example/Calculator.golingvu.adapter.go +81 -0
  8. package/example/Calculator.golingvu.go +67 -0
  9. package/example/Calculator.golingvu.implementation.go +95 -0
  10. package/example/Calculator.golingvu.specification.go +68 -0
  11. package/example/Calculator.pitono.adapter.py +68 -0
  12. package/example/Calculator.pitono.implementation.py +30 -0
  13. package/example/Calculator.pitono.specification.py +154 -0
  14. package/example/Calculator.pitono.test.py +47 -0
  15. package/example/Calculator.py +93 -0
  16. package/example/Calculator.test.adapter.ts +86 -0
  17. package/example/Calculator.test.implementation.ts +82 -0
  18. package/example/Calculator.test.specification.ts +213 -0
  19. package/example/Calculator.test.ts +13 -0
  20. package/example/Calculator.test.types.ts +50 -0
  21. package/example/Calculator.ts +130 -0
  22. package/example/README.md +1 -0
  23. package/example/base_suite_test.go +51 -0
  24. package/example/cmd/main.go +16 -0
  25. package/example/go.mod +9 -0
  26. package/example/main +0 -0
  27. package/example/test_example.py +143 -74
  28. package/{testeranto → example/testeranto}/bundles/golang/core/Calculator.golingvu.go +1 -1
  29. package/example/testeranto/metafiles/golang/core.json +198 -0
  30. package/go.mod +3 -1
  31. package/golingvu.tmp.txt +68 -0
  32. package/log.txt +85 -0
  33. package/package.json +50 -41
  34. package/scripts/build-example.ts +245 -0
  35. package/src/App.tsx +94 -44
  36. package/src/Helpo.tsx +89 -0
  37. package/src/PM/PM_WithBuild.ts +32 -20
  38. package/src/PM/PM_WithGit.ts +60 -13
  39. package/src/PM/PM_WithHelpo.ts +341 -0
  40. package/src/PM/PM_WithProcesses.ts +484 -223
  41. package/src/PM/PM_WithWebSocket.ts +210 -2
  42. package/src/PM/golingvuBuild.ts +56 -0
  43. package/src/PM/main.ts +570 -438
  44. package/src/PM/pitonoBuild.ts +56 -0
  45. package/src/PM/utils.ts +7 -1
  46. package/src/app.scss +102 -0
  47. package/src/components/pure/AppFrame.tsx +259 -149
  48. package/src/components/pure/GitIntegrationView.tsx +527 -238
  49. package/src/components/pure/HelpoChatDrawer.tsx +222 -0
  50. package/src/components/pure/MagicRobotModal.tsx +136 -0
  51. package/src/components/pure/ProcessDetails.tsx +99 -0
  52. package/src/components/pure/ProcessInput.tsx +67 -0
  53. package/src/components/pure/ProcessList.tsx +89 -0
  54. package/src/components/pure/ProcessLogs.tsx +54 -0
  55. package/src/components/pure/ProcessManager.tsx +37 -46
  56. package/src/components/pure/ProcessManagerView.tsx +42 -367
  57. package/src/components/pure/ProcessManagerViewTypes.ts +10 -0
  58. package/src/components/pure/ProcessSidebar.tsx +88 -0
  59. package/src/components/pure/ProcessTerminal.tsx +51 -0
  60. package/src/components/pure/SingleProcessView.tsx +140 -231
  61. package/src/components/pure/TerminalInput.tsx +73 -0
  62. package/src/components/pure/TerminalLogs.tsx +80 -0
  63. package/src/components/pure/TestPageView.tsx +21 -116
  64. package/src/components/pure/TestPageView_utils.tsx +2 -0
  65. package/src/components/stateful/DratoPage.tsx +457 -0
  66. package/src/components/stateful/GenericXMLEditor/AttributeEditor.tsx +87 -0
  67. package/src/components/stateful/GenericXMLEditor/Drawer.tsx +174 -0
  68. package/src/components/stateful/GenericXMLEditor/GenericPreview.tsx +160 -0
  69. package/src/components/stateful/GenericXMLEditor/GenericTextEditor.tsx +104 -0
  70. package/src/components/stateful/GenericXMLEditor/GenericTree.tsx +104 -0
  71. package/src/components/stateful/GenericXMLEditorPage.tsx +346 -0
  72. package/src/components/stateful/GitIntegrationPage.tsx +258 -3
  73. package/src/components/stateful/GrafeoPage.tsx +563 -0
  74. package/src/components/stateful/SVGEditor/SVGAttributesEditor.tsx +26 -8
  75. package/src/components/stateful/SVGEditor/SVGPreview.tsx +4 -2
  76. package/src/components/stateful/SVGEditorPage.tsx +195 -181
  77. package/src/components/stateful/SingleProcessPage.tsx +133 -131
  78. package/src/components/stateful/SkriboPage.tsx +765 -0
  79. package/src/components/stateful/TestPage.tsx +3 -2
  80. package/src/esbuildConfigs/node.ts +1 -1
  81. package/src/example/go.mod +9 -0
  82. package/src/example/main.go +61 -0
  83. package/src/golingvu/PM/golang_test.go +103 -0
  84. package/src/golingvu/README.md +186 -2
  85. package/src/golingvu/base_given.go +89 -2
  86. package/src/golingvu/base_suite.go +48 -2
  87. package/src/golingvu/go.mod +6 -0
  88. package/src/golingvu/golingvu.go +703 -29
  89. package/src/golingvu/types.go +0 -14
  90. package/src/helpo/directives.md +5 -0
  91. package/src/helpo/prompt.txt +38 -0
  92. package/src/hooks/useTerminalWebSocket.ts +49 -0
  93. package/src/lib/BaseGiven.ts +126 -28
  94. package/src/lib/BaseSuite.test/test.ts +97 -180
  95. package/src/lib/BaseSuite.ts +52 -10
  96. package/src/lib/BaseThen.ts +34 -38
  97. package/src/lib/BaseWhen.ts +9 -2
  98. package/src/lib/Tiposkripto.test/Tiposkripto.specification.ts +9 -8
  99. package/src/lib/Tiposkripto.ts +41 -11
  100. package/src/lib/pmProxy.ts +55 -18
  101. package/src/pitono/PM/python.py +165 -0
  102. package/src/pitono/Pitono.py +298 -0
  103. package/src/pitono/PitonoTest.py +25 -0
  104. package/src/pitono/README.md +21 -0
  105. package/src/pitono/__init__.py +6 -0
  106. package/{pitono → src/pitono}/base_given.py +42 -20
  107. package/{pitono → src/pitono}/base_suite.py +55 -2
  108. package/{pitono → src/pitono}/base_then.py +15 -1
  109. package/{pitono → src/pitono}/base_when.py +15 -1
  110. package/{pitono → src/pitono}/pitono.egg-info/PKG-INFO +25 -0
  111. package/{pitono → src/pitono}/pitono.egg-info/SOURCES.txt +1 -0
  112. package/src/pitono/types.py +87 -0
  113. package/src/services/FileService.ts +146 -11
  114. package/src/testeranto.ts +115 -149
  115. package/src/utils/golingvuMetafile.ts +822 -118
  116. package/src/utils/golingvuWatcher.ts +285 -0
  117. package/src/utils/logFiles.ts +10 -2
  118. package/src/utils/makePrompt.ts +12 -1
  119. package/src/utils/pitonoMetafile.ts +326 -54
  120. package/src/utils/pitonoWatcher.ts +157 -0
  121. package/testeranto/App.css +78 -0
  122. package/testeranto/App.js +4828 -2814
  123. package/testeranto/bundles/node/core/{chunk-RIM6RECA.mjs → chunk-MJTSYIAQ.mjs} +179 -250
  124. package/testeranto/bundles/node/core/src/lib/BaseSuite.test/node.test.mjs +110 -62
  125. package/testeranto/bundles/node/core/src/lib/TipoSkripto.test/TipoSkripto.mjs +135 -137
  126. package/testeranto/bundles/node/core/src/lib/pmProxy.test/index.mjs +4317 -4
  127. package/testeranto/bundles/pure/core/{chunk-XYOCRDEQ.mjs → chunk-6HR24P27.mjs} +96 -173
  128. package/testeranto/bundles/pure/core/src/Pure.test.mjs +1 -1
  129. package/testeranto/bundles/pure/core/src/lib/BaseSuite.test/pure.test.mjs +110 -62
  130. package/testeranto/bundles/web/core/{chunk-JMDLMADH.mjs → chunk-AZZHJNSU.mjs} +2473 -191
  131. package/testeranto/bundles/web/core/{chunk-LQMU5NCG.mjs → chunk-ME6I6FJZ.mjs} +96 -173
  132. package/testeranto/bundles/web/core/src/components/pure/FeaturesReporterView.test/index.html +15 -0
  133. package/testeranto/bundles/web/core/src/components/pure/FeaturesReporterView.test/index.mjs +3 -5
  134. package/testeranto/bundles/web/core/src/components/pure/ProjectPageView.test/index.css +0 -78
  135. package/testeranto/bundles/web/core/src/components/pure/ProjectPageView.test/index.html +15 -0
  136. package/testeranto/bundles/web/core/src/components/pure/ProjectPageView.test/index.mjs +6476 -69
  137. package/testeranto/bundles/web/core/src/lib/BaseSuite.test/web.test.html +15 -0
  138. package/testeranto/bundles/web/core/src/lib/BaseSuite.test/web.test.mjs +110 -62
  139. package/testeranto/helpo_chat_history.json +1 -0
  140. package/testeranto/metafiles/golang/core.json +42 -47
  141. package/testeranto/metafiles/node/core.json +263 -247
  142. package/testeranto/metafiles/pure/core.json +23 -38
  143. package/testeranto/metafiles/python/core.json +85 -9
  144. package/testeranto/metafiles/web/core.json +966 -460
  145. package/testeranto/reports/core/config.json +30 -6
  146. package/testeranto/reports/core/example/Calculator.golingvu/golang/exit.log +1 -0
  147. package/testeranto/reports/core/example/Calculator.golingvu/golang/stderr.log +2 -0
  148. package/testeranto/reports/core/example/Calculator.golingvu/golang/stdout.log +1 -0
  149. package/testeranto/reports/core/example/Calculator.pitono.test/python/exit.log +1 -0
  150. package/testeranto/reports/core/example/Calculator.pitono.test/python/stderr.log +11 -0
  151. package/testeranto/reports/core/example/Calculator.pitono.test/python/stdout.log +1 -0
  152. package/testeranto/reports/core/example/Calculator.test/node/exit.log +1 -0
  153. package/testeranto/reports/core/example/Calculator.test/node/lint_errors.txt +2 -0
  154. package/testeranto/reports/core/example/Calculator.test/node/message.txt +16 -0
  155. package/testeranto/reports/core/example/Calculator.test/node/prompt.txt +13 -0
  156. package/testeranto/reports/core/example/Calculator.test/node/stderr.log +33 -0
  157. package/testeranto/reports/core/example/Calculator.test/node/stdout.log +1076 -0
  158. package/testeranto/reports/core/example/Calculator.test/node/tests.json +1109 -0
  159. package/testeranto/reports/core/example/Calculator.test/node/type_errors.txt +34 -0
  160. package/testeranto/reports/core/example/test_example/python/exit.log +1 -0
  161. package/testeranto/reports/core/example/test_example/python/stderr.log +24 -0
  162. package/testeranto/reports/core/src/Pure.test/pure/message.txt +1 -2
  163. package/testeranto/reports/core/src/Pure.test/pure/prompt.txt +4 -5
  164. package/testeranto/reports/core/src/Pure.test/pure/type_errors.txt +16 -3
  165. package/testeranto/reports/core/src/components/pure/FeaturesReporterView.test/index/web/error.log +0 -91
  166. package/testeranto/reports/core/src/components/pure/FeaturesReporterView.test/index/web/exit.log +0 -1
  167. package/testeranto/reports/core/src/components/pure/FeaturesReporterView.test/index/web/info.log +0 -2
  168. package/testeranto/reports/core/src/components/pure/FeaturesReporterView.test/index/web/message.txt +17 -0
  169. package/testeranto/reports/core/src/components/pure/FeaturesReporterView.test/index/web/prompt.txt +26 -0
  170. package/testeranto/reports/core/src/components/pure/FeaturesReporterView.test/index/web/type_errors.txt +69 -0
  171. package/testeranto/reports/core/src/components/pure/ModalContent.test/index/web/lint_errors.txt +16 -0
  172. package/testeranto/reports/core/src/components/pure/ModalContent.test/index/web/message.txt +17 -0
  173. package/testeranto/reports/core/src/components/pure/ModalContent.test/index/web/prompt.txt +27 -0
  174. package/testeranto/reports/core/src/components/pure/ModalContent.test/index/web/type_errors.txt +42 -0
  175. package/testeranto/reports/core/src/components/pure/ProjectPageView.test/index/web/error.log +0 -30
  176. package/testeranto/reports/core/src/components/pure/ProjectPageView.test/index/web/exit.log +0 -1
  177. package/testeranto/reports/core/src/components/pure/ProjectPageView.test/index/web/info.log +0 -2
  178. package/testeranto/reports/core/src/components/pure/ProjectPageView.test/index/web/lint_errors.txt +30 -0
  179. package/testeranto/reports/core/src/components/pure/ProjectPageView.test/index/web/message.txt +17 -0
  180. package/testeranto/reports/core/src/components/pure/ProjectPageView.test/index/web/prompt.txt +30 -0
  181. package/testeranto/reports/core/src/components/pure/ProjectPageView.test/index/web/type_errors.txt +58 -0
  182. package/testeranto/reports/core/src/lib/BaseSuite.test/node.test/node/exit.log +1 -1
  183. package/testeranto/reports/core/src/lib/BaseSuite.test/node.test/node/prompt.txt +9 -1
  184. package/testeranto/reports/core/src/lib/BaseSuite.test/node.test/node/stderr.log +1 -0
  185. package/testeranto/reports/core/src/lib/BaseSuite.test/node.test/node/stdout.log +4 -1
  186. package/testeranto/reports/core/src/lib/BaseSuite.test/node.test/node/tests.json +98 -7
  187. package/testeranto/reports/core/src/lib/BaseSuite.test/node.test/node/type_errors.txt +44 -28
  188. package/testeranto/reports/core/src/lib/BaseSuite.test/pure.test/pure/message.txt +1 -2
  189. package/testeranto/reports/core/src/lib/BaseSuite.test/pure.test/pure/prompt.txt +4 -6
  190. package/testeranto/reports/core/src/lib/BaseSuite.test/pure.test/pure/type_errors.txt +44 -28
  191. package/testeranto/reports/core/src/lib/BaseSuite.test/web.test/web/error.log +0 -1
  192. package/testeranto/reports/core/src/lib/BaseSuite.test/web.test/web/exit.log +0 -1
  193. package/testeranto/reports/core/src/lib/BaseSuite.test/web.test/web/message.txt +17 -0
  194. package/testeranto/reports/core/src/lib/BaseSuite.test/web.test/web/prompt.txt +25 -0
  195. package/testeranto/reports/core/src/lib/BaseSuite.test/web.test/web/type_errors.txt +69 -0
  196. package/testeranto/reports/core/src/lib/TipoSkripto.test/TipoSkripto/node/exit.log +1 -1
  197. package/testeranto/reports/core/src/lib/TipoSkripto.test/TipoSkripto/node/message.txt +1 -2
  198. package/testeranto/reports/core/src/lib/TipoSkripto.test/TipoSkripto/node/prompt.txt +4 -8
  199. package/testeranto/reports/core/src/lib/TipoSkripto.test/TipoSkripto/node/stderr.log +68 -35
  200. package/testeranto/reports/core/src/lib/TipoSkripto.test/TipoSkripto/node/stdout.log +336 -6
  201. package/testeranto/reports/core/src/lib/TipoSkripto.test/TipoSkripto/node/tests.json +166 -0
  202. package/testeranto/reports/core/src/lib/TipoSkripto.test/TipoSkripto/node/type_errors.txt +20 -13
  203. package/testeranto/reports/core/src/lib/pmProxy.test/index/node/exit.log +1 -1
  204. package/testeranto/reports/core/src/lib/pmProxy.test/index/node/prompt.txt +9 -1
  205. package/testeranto/reports/core/src/lib/pmProxy.test/index/node/stderr.log +0 -20
  206. package/testeranto/reports/core/src/lib/pmProxy.test/index/node/stdout.log +1 -3
  207. package/testeranto/reports/core/src/lib/pmProxy.test/index/node/tests.json +31 -0
  208. package/testeranto/reports/core/src/lib/pmProxy.test/index/node/type_errors.txt +16 -3
  209. package/testeranto/reports/core/summary.json +46 -19
  210. package/testeranto.config.ts +18 -30
  211. package/dist/cjs-shim.js +0 -12
  212. package/dist/common/design-editor/DesignEditor.js +0 -77
  213. package/dist/common/design-editor/index.js +0 -18
  214. package/dist/common/design-editor/server.js +0 -98
  215. package/dist/common/design-editor/types.js +0 -2
  216. package/dist/common/package.json +0 -3
  217. package/dist/common/src/App.js +0 -219
  218. package/dist/common/src/CoreTypes.js +0 -2
  219. package/dist/common/src/Init.js +0 -48
  220. package/dist/common/src/Node.js +0 -40
  221. package/dist/common/src/NodeSidecar.js +0 -15
  222. package/dist/common/src/PM/PM_WithBuild.js +0 -135
  223. package/dist/common/src/PM/PM_WithEslintAndTsc.js +0 -204
  224. package/dist/common/src/PM/PM_WithGit.js +0 -517
  225. package/dist/common/src/PM/PM_WithProcesses.js +0 -519
  226. package/dist/common/src/PM/PM_WithWebSocket.js +0 -535
  227. package/dist/common/src/PM/__tests__/nodeSidecar.testeranto.js +0 -108
  228. package/dist/common/src/PM/__tests__/pureSidecar.testeranto.js +0 -93
  229. package/dist/common/src/PM/__tests__/webSidecar.testeranto.js +0 -93
  230. package/dist/common/src/PM/base.js +0 -319
  231. package/dist/common/src/PM/index.js +0 -6
  232. package/dist/common/src/PM/main.js +0 -672
  233. package/dist/common/src/PM/metafileOutputs.js +0 -78
  234. package/dist/common/src/PM/node.js +0 -179
  235. package/dist/common/src/PM/nodeSidecar.js +0 -65
  236. package/dist/common/src/PM/pitonoRunner.js +0 -54
  237. package/dist/common/src/PM/pure.js +0 -103
  238. package/dist/common/src/PM/pureSidecar.js +0 -48
  239. package/dist/common/src/PM/sidecar.js +0 -11
  240. package/dist/common/src/PM/types.js +0 -2
  241. package/dist/common/src/PM/utils.js +0 -210
  242. package/dist/common/src/PM/web.js +0 -106
  243. package/dist/common/src/PM/webSidecar.js +0 -47
  244. package/dist/common/src/Pure.js +0 -52
  245. package/dist/common/src/Pure.test.js +0 -180
  246. package/dist/common/src/PureSidecar.js +0 -13
  247. package/dist/common/src/ReportServer.js +0 -1
  248. package/dist/common/src/ReportServer.test.ts/index.js +0 -78
  249. package/dist/common/src/ReportServerLib.js +0 -1
  250. package/dist/common/src/Types.js +0 -2
  251. package/dist/common/src/Web.js +0 -61
  252. package/dist/common/src/WebSidecar.js +0 -14
  253. package/dist/common/src/components/DesignEditorPage.js +0 -205
  254. package/dist/common/src/components/SunriseAnimation.js +0 -291
  255. package/dist/common/src/components/SunriseAnimation.test/implementation.js +0 -1
  256. package/dist/common/src/components/SunriseAnimation.test/index.js +0 -1
  257. package/dist/common/src/components/SunriseAnimation.test/interface.js +0 -68
  258. package/dist/common/src/components/SunriseAnimation.test/specification.js +0 -1
  259. package/dist/common/src/components/SunriseAnimation.test/types.js +0 -2
  260. package/dist/common/src/components/TestStatusBadge.js +0 -35
  261. package/dist/common/src/components/pure/AppFrame.js +0 -81
  262. package/dist/common/src/components/pure/AppFrame.test/implementation.js +0 -63
  263. package/dist/common/src/components/pure/AppFrame.test/index.js +0 -14
  264. package/dist/common/src/components/pure/AppFrame.test/specification.js +0 -25
  265. package/dist/common/src/components/pure/AppFrame.test/types.js +0 -3
  266. package/dist/common/src/components/pure/ArtifactTree.js +0 -80
  267. package/dist/common/src/components/pure/BuildLogViewer.js +0 -106
  268. package/dist/common/src/components/pure/DebugEnv.js +0 -30
  269. package/dist/common/src/components/pure/FeaturesReporterView.js +0 -23
  270. package/dist/common/src/components/pure/FeaturesReporterView.test/implementation.js +0 -84
  271. package/dist/common/src/components/pure/FeaturesReporterView.test/index.js +0 -14
  272. package/dist/common/src/components/pure/FeaturesReporterView.test/specification.js +0 -27
  273. package/dist/common/src/components/pure/FeaturesReporterView.test/types.js +0 -2
  274. package/dist/common/src/components/pure/FileTree.js +0 -34
  275. package/dist/common/src/components/pure/FileTreeItem.js +0 -29
  276. package/dist/common/src/components/pure/GitHubLoginButton.js +0 -18
  277. package/dist/common/src/components/pure/GitIntegrationView.js +0 -342
  278. package/dist/common/src/components/pure/ModalContent.js +0 -86
  279. package/dist/common/src/components/pure/ModalContent.test/implementation.js +0 -35
  280. package/dist/common/src/components/pure/ModalContent.test/index.js +0 -58
  281. package/dist/common/src/components/pure/ModalContent.test/specification.js +0 -19
  282. package/dist/common/src/components/pure/ModalContent.test/types.js +0 -4
  283. package/dist/common/src/components/pure/NavBar.js +0 -44
  284. package/dist/common/src/components/pure/ProcessManager.js +0 -113
  285. package/dist/common/src/components/pure/ProcessManagerView.js +0 -236
  286. package/dist/common/src/components/pure/ProjectPageView.js +0 -68
  287. package/dist/common/src/components/pure/ProjectPageView.test/implementation.js +0 -184
  288. package/dist/common/src/components/pure/ProjectPageView.test/index.js +0 -14
  289. package/dist/common/src/components/pure/ProjectPageView.test/specification.js +0 -32
  290. package/dist/common/src/components/pure/ProjectPageView.test/types.js +0 -4
  291. package/dist/common/src/components/pure/ProjectsPageView.js +0 -72
  292. package/dist/common/src/components/pure/Settings.js +0 -121
  293. package/dist/common/src/components/pure/Settings.test.js +0 -34
  294. package/dist/common/src/components/pure/SettingsButton.js +0 -13
  295. package/dist/common/src/components/pure/SignIn.js +0 -22
  296. package/dist/common/src/components/pure/SingleProcessView.js +0 -167
  297. package/dist/common/src/components/pure/TestPageView.js +0 -373
  298. package/dist/common/src/components/pure/TestPageView.test/implementation.js +0 -157
  299. package/dist/common/src/components/pure/TestPageView.test/index.js +0 -15
  300. package/dist/common/src/components/pure/TestPageView.test/specification.js +0 -26
  301. package/dist/common/src/components/pure/TestPageView.test/types.js +0 -4
  302. package/dist/common/src/components/pure/TestPageView_utils.js +0 -117
  303. package/dist/common/src/components/pure/TestTable.js +0 -33
  304. package/dist/common/src/components/pure/ThemeCard.js +0 -15
  305. package/dist/common/src/components/pure/ToastNotification.js +0 -14
  306. package/dist/common/src/components/pure/UserProfile.js +0 -27
  307. package/dist/common/src/components/stateful/AuthCallbackPage.js +0 -51
  308. package/dist/common/src/components/stateful/FeaturesReporter.js +0 -60
  309. package/dist/common/src/components/stateful/FileTree.js +0 -59
  310. package/dist/common/src/components/stateful/GitIntegrationPage.js +0 -12
  311. package/dist/common/src/components/stateful/ProcessManagerPage.js +0 -110
  312. package/dist/common/src/components/stateful/ProjectPage.js +0 -102
  313. package/dist/common/src/components/stateful/ProjectsPage.js +0 -116
  314. package/dist/common/src/components/stateful/SettingsPage.js +0 -72
  315. package/dist/common/src/components/stateful/SingleProcessPage.js +0 -137
  316. package/dist/common/src/components/stateful/TestPage.js +0 -270
  317. package/dist/common/src/components/stateful/TextEditorPage.js +0 -154
  318. package/dist/common/src/defaultConfig.js +0 -19
  319. package/dist/common/src/esbuildConfigs/consoleDetectorPlugin.js +0 -38
  320. package/dist/common/src/esbuildConfigs/eslint-formatter-testeranto.js +0 -21
  321. package/dist/common/src/esbuildConfigs/featuresPlugin.js +0 -39
  322. package/dist/common/src/esbuildConfigs/index.js +0 -21
  323. package/dist/common/src/esbuildConfigs/inputFilesPlugin.js +0 -30
  324. package/dist/common/src/esbuildConfigs/nativeImportDetectorPlugin.js +0 -24
  325. package/dist/common/src/esbuildConfigs/node.js +0 -24
  326. package/dist/common/src/esbuildConfigs/pure.js +0 -42
  327. package/dist/common/src/esbuildConfigs/rebuildPlugin.js +0 -19
  328. package/dist/common/src/esbuildConfigs/web.js +0 -48
  329. package/dist/common/src/hooks/useGitMode.js +0 -21
  330. package/dist/common/src/init-docs.js +0 -9
  331. package/dist/common/src/lib/BaseGiven.js +0 -99
  332. package/dist/common/src/lib/BaseSuite.js +0 -91
  333. package/dist/common/src/lib/BaseSuite.test/mock.js +0 -68
  334. package/dist/common/src/lib/BaseSuite.test/node.test.js +0 -10
  335. package/dist/common/src/lib/BaseSuite.test/pure.test.js +0 -10
  336. package/dist/common/src/lib/BaseSuite.test/test.js +0 -229
  337. package/dist/common/src/lib/BaseSuite.test/web.test.js +0 -10
  338. package/dist/common/src/lib/BaseThen.js +0 -64
  339. package/dist/common/src/lib/BaseWhen.js +0 -45
  340. package/dist/common/src/lib/Sidecar.js +0 -7
  341. package/dist/common/src/lib/Tiposkripto.js +0 -173
  342. package/dist/common/src/lib/Tiposkripto.test/MockTiposkripto.js +0 -180
  343. package/dist/common/src/lib/Tiposkripto.test/Tiposkripto.adapter.js +0 -29
  344. package/dist/common/src/lib/Tiposkripto.test/Tiposkripto.implementation.js +0 -213
  345. package/dist/common/src/lib/Tiposkripto.test/Tiposkripto.js +0 -11
  346. package/dist/common/src/lib/Tiposkripto.test/Tiposkripto.specification.js +0 -50
  347. package/dist/common/src/lib/Tiposkripto.test/Tiposkripto.types.js +0 -2
  348. package/dist/common/src/lib/abstractBase.test/MockGiven.js +0 -24
  349. package/dist/common/src/lib/abstractBase.test/MockThen.js +0 -16
  350. package/dist/common/src/lib/abstractBase.test/MockWhen.js +0 -20
  351. package/dist/common/src/lib/abstractBase.test/adapter.js +0 -24
  352. package/dist/common/src/lib/abstractBase.test/implementation.js +0 -38
  353. package/dist/common/src/lib/abstractBase.test/index.js +0 -18
  354. package/dist/common/src/lib/abstractBase.test/specification.js +0 -19
  355. package/dist/common/src/lib/abstractBase.test/types.js +0 -2
  356. package/dist/common/src/lib/index.js +0 -31
  357. package/dist/common/src/lib/pmProxy.js +0 -293
  358. package/dist/common/src/lib/pmProxy.test/adapter.js +0 -54
  359. package/dist/common/src/lib/pmProxy.test/implementation.js +0 -137
  360. package/dist/common/src/lib/pmProxy.test/index.js +0 -15
  361. package/dist/common/src/lib/pmProxy.test/mockPM.js +0 -34
  362. package/dist/common/src/lib/pmProxy.test/mockPMBase.js +0 -131
  363. package/dist/common/src/lib/pmProxy.test/specification.js +0 -179
  364. package/dist/common/src/lib/pmProxy.test/types.js +0 -2
  365. package/dist/common/src/lib/types.js +0 -3
  366. package/dist/common/src/mothership/index.js +0 -21
  367. package/dist/common/src/mothership/test.js +0 -83
  368. package/dist/common/src/run.js +0 -49
  369. package/dist/common/src/services/FileService.js +0 -505
  370. package/dist/common/src/services/GitHubAuthService.js +0 -184
  371. package/dist/common/src/testeranto.js +0 -224
  372. package/dist/common/src/types/features.js +0 -34
  373. package/dist/common/src/utils/api.js +0 -93
  374. package/dist/common/src/utils/buildTemplates.js +0 -37
  375. package/dist/common/src/utils/featureUtils.js +0 -29
  376. package/dist/common/src/utils/gitTest.js +0 -27
  377. package/dist/common/src/utils/golingvuMetafile.js +0 -116
  378. package/dist/common/src/utils/logFiles.js +0 -52
  379. package/dist/common/src/utils/makePrompt.js +0 -116
  380. package/dist/common/src/utils/pitonoMetafile.js +0 -67
  381. package/dist/common/src/utils/queue.js +0 -36
  382. package/dist/common/src/utils.js +0 -143
  383. package/dist/common/src/web.html.js +0 -18
  384. package/dist/common/testeranto.config.js +0 -102
  385. package/dist/common/tsconfig.common.tsbuildinfo +0 -1
  386. package/dist/module/design-editor/DesignEditor.js +0 -40
  387. package/dist/module/design-editor/index.js +0 -2
  388. package/dist/module/design-editor/server.js +0 -92
  389. package/dist/module/design-editor/types.js +0 -1
  390. package/dist/module/package.json +0 -3
  391. package/dist/module/src/App.js +0 -176
  392. package/dist/module/src/CoreTypes.js +0 -1
  393. package/dist/module/src/Init.js +0 -43
  394. package/dist/module/src/Node.js +0 -33
  395. package/dist/module/src/NodeSidecar.js +0 -11
  396. package/dist/module/src/PM/PM_WithBuild.js +0 -128
  397. package/dist/module/src/PM/PM_WithEslintAndTsc.js +0 -197
  398. package/dist/module/src/PM/PM_WithGit.js +0 -477
  399. package/dist/module/src/PM/PM_WithProcesses.js +0 -479
  400. package/dist/module/src/PM/PM_WithWebSocket.js +0 -528
  401. package/dist/module/src/PM/__tests__/nodeSidecar.testeranto.js +0 -103
  402. package/dist/module/src/PM/__tests__/pureSidecar.testeranto.js +0 -88
  403. package/dist/module/src/PM/__tests__/webSidecar.testeranto.js +0 -88
  404. package/dist/module/src/PM/base.js +0 -312
  405. package/dist/module/src/PM/index.js +0 -2
  406. package/dist/module/src/PM/main.js +0 -632
  407. package/dist/module/src/PM/metafileOutputs.js +0 -78
  408. package/dist/module/src/PM/node.js +0 -172
  409. package/dist/module/src/PM/nodeSidecar.js +0 -58
  410. package/dist/module/src/PM/pitonoRunner.js +0 -47
  411. package/dist/module/src/PM/pure.js +0 -99
  412. package/dist/module/src/PM/pureSidecar.js +0 -41
  413. package/dist/module/src/PM/sidecar.js +0 -7
  414. package/dist/module/src/PM/types.js +0 -1
  415. package/dist/module/src/PM/utils.js +0 -196
  416. package/dist/module/src/PM/web.js +0 -102
  417. package/dist/module/src/PM/webSidecar.js +0 -40
  418. package/dist/module/src/Pure.js +0 -45
  419. package/dist/module/src/Pure.test.js +0 -175
  420. package/dist/module/src/PureSidecar.js +0 -9
  421. package/dist/module/src/ReportServer.js +0 -1
  422. package/dist/module/src/ReportServer.test.ts/index.js +0 -73
  423. package/dist/module/src/ReportServerLib.js +0 -1
  424. package/dist/module/src/Types.js +0 -1
  425. package/dist/module/src/Web.js +0 -54
  426. package/dist/module/src/WebSidecar.js +0 -10
  427. package/dist/module/src/components/DesignEditorPage.js +0 -168
  428. package/dist/module/src/components/SunriseAnimation.js +0 -256
  429. package/dist/module/src/components/SunriseAnimation.test/implementation.js +0 -1
  430. package/dist/module/src/components/SunriseAnimation.test/index.js +0 -1
  431. package/dist/module/src/components/SunriseAnimation.test/interface.js +0 -32
  432. package/dist/module/src/components/SunriseAnimation.test/specification.js +0 -1
  433. package/dist/module/src/components/SunriseAnimation.test/types.js +0 -1
  434. package/dist/module/src/components/TestStatusBadge.js +0 -28
  435. package/dist/module/src/components/pure/AppFrame.js +0 -74
  436. package/dist/module/src/components/pure/AppFrame.test/implementation.js +0 -57
  437. package/dist/module/src/components/pure/AppFrame.test/index.js +0 -9
  438. package/dist/module/src/components/pure/AppFrame.test/specification.js +0 -21
  439. package/dist/module/src/components/pure/AppFrame.test/types.js +0 -2
  440. package/dist/module/src/components/pure/ArtifactTree.js +0 -80
  441. package/dist/module/src/components/pure/BuildLogViewer.js +0 -99
  442. package/dist/module/src/components/pure/DebugEnv.js +0 -23
  443. package/dist/module/src/components/pure/FeaturesReporterView.js +0 -16
  444. package/dist/module/src/components/pure/FeaturesReporterView.test/implementation.js +0 -81
  445. package/dist/module/src/components/pure/FeaturesReporterView.test/index.js +0 -9
  446. package/dist/module/src/components/pure/FeaturesReporterView.test/specification.js +0 -23
  447. package/dist/module/src/components/pure/FeaturesReporterView.test/types.js +0 -1
  448. package/dist/module/src/components/pure/FileTree.js +0 -27
  449. package/dist/module/src/components/pure/FileTreeItem.js +0 -22
  450. package/dist/module/src/components/pure/GitHubLoginButton.js +0 -11
  451. package/dist/module/src/components/pure/GitIntegrationView.js +0 -305
  452. package/dist/module/src/components/pure/ModalContent.js +0 -79
  453. package/dist/module/src/components/pure/ModalContent.test/implementation.js +0 -32
  454. package/dist/module/src/components/pure/ModalContent.test/index.js +0 -53
  455. package/dist/module/src/components/pure/ModalContent.test/specification.js +0 -15
  456. package/dist/module/src/components/pure/ModalContent.test/types.js +0 -3
  457. package/dist/module/src/components/pure/NavBar.js +0 -37
  458. package/dist/module/src/components/pure/ProcessManager.js +0 -76
  459. package/dist/module/src/components/pure/ProcessManagerView.js +0 -199
  460. package/dist/module/src/components/pure/ProjectPageView.js +0 -61
  461. package/dist/module/src/components/pure/ProjectPageView.test/implementation.js +0 -181
  462. package/dist/module/src/components/pure/ProjectPageView.test/index.js +0 -9
  463. package/dist/module/src/components/pure/ProjectPageView.test/specification.js +0 -28
  464. package/dist/module/src/components/pure/ProjectPageView.test/types.js +0 -3
  465. package/dist/module/src/components/pure/ProjectsPageView.js +0 -65
  466. package/dist/module/src/components/pure/Settings.js +0 -84
  467. package/dist/module/src/components/pure/Settings.test.js +0 -29
  468. package/dist/module/src/components/pure/SettingsButton.js +0 -6
  469. package/dist/module/src/components/pure/SignIn.js +0 -15
  470. package/dist/module/src/components/pure/SingleProcessView.js +0 -130
  471. package/dist/module/src/components/pure/TestPageView.js +0 -336
  472. package/dist/module/src/components/pure/TestPageView.test/implementation.js +0 -121
  473. package/dist/module/src/components/pure/TestPageView.test/index.js +0 -10
  474. package/dist/module/src/components/pure/TestPageView.test/specification.js +0 -22
  475. package/dist/module/src/components/pure/TestPageView.test/types.js +0 -3
  476. package/dist/module/src/components/pure/TestPageView_utils.js +0 -109
  477. package/dist/module/src/components/pure/TestTable.js +0 -26
  478. package/dist/module/src/components/pure/ThemeCard.js +0 -8
  479. package/dist/module/src/components/pure/ToastNotification.js +0 -7
  480. package/dist/module/src/components/pure/UserProfile.js +0 -20
  481. package/dist/module/src/components/stateful/AuthCallbackPage.js +0 -14
  482. package/dist/module/src/components/stateful/FeaturesReporter.js +0 -23
  483. package/dist/module/src/components/stateful/FileTree.js +0 -59
  484. package/dist/module/src/components/stateful/GitIntegrationPage.js +0 -5
  485. package/dist/module/src/components/stateful/ProcessManagerPage.js +0 -73
  486. package/dist/module/src/components/stateful/ProjectPage.js +0 -65
  487. package/dist/module/src/components/stateful/ProjectsPage.js +0 -79
  488. package/dist/module/src/components/stateful/SettingsPage.js +0 -35
  489. package/dist/module/src/components/stateful/SingleProcessPage.js +0 -100
  490. package/dist/module/src/components/stateful/TestPage.js +0 -233
  491. package/dist/module/src/components/stateful/TextEditorPage.js +0 -117
  492. package/dist/module/src/defaultConfig.js +0 -17
  493. package/dist/module/src/esbuildConfigs/consoleDetectorPlugin.js +0 -32
  494. package/dist/module/src/esbuildConfigs/eslint-formatter-testeranto.js +0 -18
  495. package/dist/module/src/esbuildConfigs/featuresPlugin.js +0 -34
  496. package/dist/module/src/esbuildConfigs/index.js +0 -19
  497. package/dist/module/src/esbuildConfigs/inputFilesPlugin.js +0 -25
  498. package/dist/module/src/esbuildConfigs/nativeImportDetectorPlugin.js +0 -21
  499. package/dist/module/src/esbuildConfigs/node.js +0 -19
  500. package/dist/module/src/esbuildConfigs/pure.js +0 -37
  501. package/dist/module/src/esbuildConfigs/rebuildPlugin.js +0 -14
  502. package/dist/module/src/esbuildConfigs/web.js +0 -43
  503. package/dist/module/src/hooks/useGitMode.js +0 -17
  504. package/dist/module/src/init-docs.js +0 -4
  505. package/dist/module/src/lib/BaseGiven.js +0 -95
  506. package/dist/module/src/lib/BaseSuite.js +0 -87
  507. package/dist/module/src/lib/BaseSuite.test/mock.js +0 -61
  508. package/dist/module/src/lib/BaseSuite.test/node.test.js +0 -5
  509. package/dist/module/src/lib/BaseSuite.test/pure.test.js +0 -5
  510. package/dist/module/src/lib/BaseSuite.test/test.js +0 -225
  511. package/dist/module/src/lib/BaseSuite.test/web.test.js +0 -5
  512. package/dist/module/src/lib/BaseThen.js +0 -60
  513. package/dist/module/src/lib/BaseWhen.js +0 -41
  514. package/dist/module/src/lib/Sidecar.js +0 -3
  515. package/dist/module/src/lib/Tiposkripto.js +0 -170
  516. package/dist/module/src/lib/Tiposkripto.test/MockTiposkripto.js +0 -173
  517. package/dist/module/src/lib/Tiposkripto.test/Tiposkripto.adapter.js +0 -26
  518. package/dist/module/src/lib/Tiposkripto.test/Tiposkripto.implementation.js +0 -210
  519. package/dist/module/src/lib/Tiposkripto.test/Tiposkripto.js +0 -6
  520. package/dist/module/src/lib/Tiposkripto.test/Tiposkripto.specification.js +0 -46
  521. package/dist/module/src/lib/Tiposkripto.test/Tiposkripto.types.js +0 -1
  522. package/dist/module/src/lib/abstractBase.test/MockGiven.js +0 -20
  523. package/dist/module/src/lib/abstractBase.test/MockThen.js +0 -12
  524. package/dist/module/src/lib/abstractBase.test/MockWhen.js +0 -16
  525. package/dist/module/src/lib/abstractBase.test/adapter.js +0 -21
  526. package/dist/module/src/lib/abstractBase.test/implementation.js +0 -35
  527. package/dist/module/src/lib/abstractBase.test/index.js +0 -13
  528. package/dist/module/src/lib/abstractBase.test/specification.js +0 -15
  529. package/dist/module/src/lib/abstractBase.test/types.js +0 -1
  530. package/dist/module/src/lib/index.js +0 -26
  531. package/dist/module/src/lib/pmProxy.js +0 -284
  532. package/dist/module/src/lib/pmProxy.test/adapter.js +0 -51
  533. package/dist/module/src/lib/pmProxy.test/implementation.js +0 -134
  534. package/dist/module/src/lib/pmProxy.test/index.js +0 -10
  535. package/dist/module/src/lib/pmProxy.test/mockPM.js +0 -30
  536. package/dist/module/src/lib/pmProxy.test/mockPMBase.js +0 -127
  537. package/dist/module/src/lib/pmProxy.test/specification.js +0 -175
  538. package/dist/module/src/lib/pmProxy.test/types.js +0 -1
  539. package/dist/module/src/lib/types.js +0 -2
  540. package/dist/module/src/mothership/index.js +0 -16
  541. package/dist/module/src/mothership/test.js +0 -78
  542. package/dist/module/src/run.js +0 -49
  543. package/dist/module/src/services/FileService.js +0 -468
  544. package/dist/module/src/services/GitHubAuthService.js +0 -180
  545. package/dist/module/src/testeranto.js +0 -186
  546. package/dist/module/src/types/features.js +0 -31
  547. package/dist/module/src/utils/api.js +0 -87
  548. package/dist/module/src/utils/buildTemplates.js +0 -33
  549. package/dist/module/src/utils/featureUtils.js +0 -24
  550. package/dist/module/src/utils/gitTest.js +0 -23
  551. package/dist/module/src/utils/golingvuMetafile.js +0 -109
  552. package/dist/module/src/utils/logFiles.js +0 -47
  553. package/dist/module/src/utils/makePrompt.js +0 -109
  554. package/dist/module/src/utils/pitonoMetafile.js +0 -60
  555. package/dist/module/src/utils/queue.js +0 -32
  556. package/dist/module/src/utils.js +0 -130
  557. package/dist/module/src/web.html.js +0 -16
  558. package/dist/module/testeranto.config.js +0 -100
  559. package/dist/module/tsconfig.module.tsbuildinfo +0 -1
  560. package/dist/types/design-editor/DesignEditor.d.ts +0 -1
  561. package/dist/types/src/App.d.ts +0 -19
  562. package/dist/types/src/CoreTypes.d.ts +0 -52
  563. package/dist/types/src/Init.d.ts +0 -2
  564. package/dist/types/src/Node.d.ts +0 -9
  565. package/dist/types/src/NodeSidecar.d.ts +0 -6
  566. package/dist/types/src/PM/PM_WithBuild.d.ts +0 -13
  567. package/dist/types/src/PM/PM_WithEslintAndTsc.d.ts +0 -22
  568. package/dist/types/src/PM/PM_WithGit.d.ts +0 -27
  569. package/dist/types/src/PM/PM_WithProcesses.d.ts +0 -29
  570. package/dist/types/src/PM/PM_WithWebSocket.d.ts +0 -108
  571. package/dist/types/src/PM/__tests__/nodeSidecar.testeranto.d.ts +0 -2
  572. package/dist/types/src/PM/__tests__/pureSidecar.testeranto.d.ts +0 -2
  573. package/dist/types/src/PM/__tests__/webSidecar.testeranto.d.ts +0 -2
  574. package/dist/types/src/PM/base.d.ts +0 -35
  575. package/dist/types/src/PM/index.d.ts +0 -35
  576. package/dist/types/src/PM/main.d.ts +0 -8
  577. package/dist/types/src/PM/node.d.ts +0 -38
  578. package/dist/types/src/PM/nodeSidecar.d.ts +0 -13
  579. package/dist/types/src/PM/pitonoRunner.d.ts +0 -7
  580. package/dist/types/src/PM/pure.d.ts +0 -41
  581. package/dist/types/src/PM/pureSidecar.d.ts +0 -11
  582. package/dist/types/src/PM/sidecar.d.ts +0 -8
  583. package/dist/types/src/PM/types.d.ts +0 -118
  584. package/dist/types/src/PM/utils.d.ts +0 -35
  585. package/dist/types/src/PM/web.d.ts +0 -41
  586. package/dist/types/src/PM/webSidecar.d.ts +0 -11
  587. package/dist/types/src/Pure.d.ts +0 -14
  588. package/dist/types/src/Pure.test.d.ts +0 -2
  589. package/dist/types/src/PureSidecar.d.ts +0 -8
  590. package/dist/types/src/ReportServer.test.ts/index.d.ts +0 -2
  591. package/dist/types/src/Types.d.ts +0 -119
  592. package/dist/types/src/Web.d.ts +0 -9
  593. package/dist/types/src/WebSidecar.d.ts +0 -8
  594. package/dist/types/src/components/DesignEditorPage.d.ts +0 -1
  595. package/dist/types/src/components/SunriseAnimation.d.ts +0 -5
  596. package/dist/types/src/components/SunriseAnimation.test/interface.d.ts +0 -11
  597. package/dist/types/src/components/SunriseAnimation.test/types.d.ts +0 -39
  598. package/dist/types/src/components/TestStatusBadge.d.ts +0 -15
  599. package/dist/types/src/components/pure/AppFrame.d.ts +0 -11
  600. package/dist/types/src/components/pure/AppFrame.test/implementation.d.ts +0 -3
  601. package/dist/types/src/components/pure/AppFrame.test/index.d.ts +0 -3
  602. package/dist/types/src/components/pure/AppFrame.test/specification.d.ts +0 -3
  603. package/dist/types/src/components/pure/AppFrame.test/types.d.ts +0 -33
  604. package/dist/types/src/components/pure/BuildLogViewer.d.ts +0 -7
  605. package/dist/types/src/components/pure/DebugEnv.d.ts +0 -2
  606. package/dist/types/src/components/pure/FeaturesReporterView.d.ts +0 -7
  607. package/dist/types/src/components/pure/FeaturesReporterView.test/implementation.d.ts +0 -3
  608. package/dist/types/src/components/pure/FeaturesReporterView.test/index.d.ts +0 -2
  609. package/dist/types/src/components/pure/FeaturesReporterView.test/specification.d.ts +0 -3
  610. package/dist/types/src/components/pure/FeaturesReporterView.test/types.d.ts +0 -54
  611. package/dist/types/src/components/pure/FileTree.d.ts +0 -6
  612. package/dist/types/src/components/pure/FileTreeItem.d.ts +0 -8
  613. package/dist/types/src/components/pure/GitHubLoginButton.d.ts +0 -8
  614. package/dist/types/src/components/pure/GitIntegrationView.d.ts +0 -1
  615. package/dist/types/src/components/pure/ModalContent.d.ts +0 -7
  616. package/dist/types/src/components/pure/ModalContent.test/implementation.d.ts +0 -3
  617. package/dist/types/src/components/pure/ModalContent.test/index.d.ts +0 -2
  618. package/dist/types/src/components/pure/ModalContent.test/specification.d.ts +0 -3
  619. package/dist/types/src/components/pure/ModalContent.test/types.d.ts +0 -45
  620. package/dist/types/src/components/pure/NavBar.d.ts +0 -23
  621. package/dist/types/src/components/pure/ProcessManager.d.ts +0 -8
  622. package/dist/types/src/components/pure/ProcessManagerView.d.ts +0 -20
  623. package/dist/types/src/components/pure/ProjectPageView.d.ts +0 -14
  624. package/dist/types/src/components/pure/ProjectPageView.test/implementation.d.ts +0 -3
  625. package/dist/types/src/components/pure/ProjectPageView.test/index.d.ts +0 -2
  626. package/dist/types/src/components/pure/ProjectPageView.test/specification.d.ts +0 -3
  627. package/dist/types/src/components/pure/ProjectPageView.test/types.d.ts +0 -57
  628. package/dist/types/src/components/pure/ProjectsPageView.d.ts +0 -29
  629. package/dist/types/src/components/pure/Settings.d.ts +0 -1
  630. package/dist/types/src/components/pure/Settings.test.d.ts +0 -1
  631. package/dist/types/src/components/pure/SettingsButton.d.ts +0 -2
  632. package/dist/types/src/components/pure/SignIn.d.ts +0 -1
  633. package/dist/types/src/components/pure/SingleProcessView.d.ts +0 -10
  634. package/dist/types/src/components/pure/TestPageView.d.ts +0 -16
  635. package/dist/types/src/components/pure/TestPageView.test/implementation.d.ts +0 -12
  636. package/dist/types/src/components/pure/TestPageView.test/index.d.ts +0 -3
  637. package/dist/types/src/components/pure/TestPageView.test/specification.d.ts +0 -11
  638. package/dist/types/src/components/pure/TestPageView.test/types.d.ts +0 -65
  639. package/dist/types/src/components/pure/TestPageView_utils.d.ts +0 -23
  640. package/dist/types/src/components/pure/TestTable.d.ts +0 -16
  641. package/dist/types/src/components/pure/ThemeCard.d.ts +0 -9
  642. package/dist/types/src/components/pure/ToastNotification.d.ts +0 -6
  643. package/dist/types/src/components/pure/UserProfile.d.ts +0 -2
  644. package/dist/types/src/components/stateful/AuthCallbackPage.d.ts +0 -2
  645. package/dist/types/src/components/stateful/FeaturesReporter.d.ts +0 -2
  646. package/dist/types/src/components/stateful/GitIntegrationPage.d.ts +0 -1
  647. package/dist/types/src/components/stateful/ProcessManagerPage.d.ts +0 -2
  648. package/dist/types/src/components/stateful/ProjectPage.d.ts +0 -1
  649. package/dist/types/src/components/stateful/ProjectsPage.d.ts +0 -1
  650. package/dist/types/src/components/stateful/SettingsPage.d.ts +0 -2
  651. package/dist/types/src/components/stateful/SingleProcessPage.d.ts +0 -2
  652. package/dist/types/src/components/stateful/TestPage.d.ts +0 -1
  653. package/dist/types/src/components/stateful/TextEditorPage.d.ts +0 -1
  654. package/dist/types/src/defaultConfig.d.ts +0 -3
  655. package/dist/types/src/esbuildConfigs/consoleDetectorPlugin.d.ts +0 -2
  656. package/dist/types/src/esbuildConfigs/eslint-formatter-testeranto.d.ts +0 -2
  657. package/dist/types/src/esbuildConfigs/featuresPlugin.d.ts +0 -5
  658. package/dist/types/src/esbuildConfigs/index.d.ts +0 -4
  659. package/dist/types/src/esbuildConfigs/inputFilesPlugin.d.ts +0 -7
  660. package/dist/types/src/esbuildConfigs/nativeImportDetectorPlugin.d.ts +0 -2
  661. package/dist/types/src/esbuildConfigs/node.d.ts +0 -4
  662. package/dist/types/src/esbuildConfigs/pure.d.ts +0 -4
  663. package/dist/types/src/esbuildConfigs/rebuildPlugin.d.ts +0 -6
  664. package/dist/types/src/esbuildConfigs/web.d.ts +0 -4
  665. package/dist/types/src/hooks/useGitMode.d.ts +0 -7
  666. package/dist/types/src/init-docs.d.ts +0 -1
  667. package/dist/types/src/lib/BaseGiven.d.ts +0 -44
  668. package/dist/types/src/lib/BaseSuite.d.ts +0 -46
  669. package/dist/types/src/lib/BaseSuite.test/mock.d.ts +0 -21
  670. package/dist/types/src/lib/BaseSuite.test/node.test.d.ts +0 -2
  671. package/dist/types/src/lib/BaseSuite.test/pure.test.d.ts +0 -2
  672. package/dist/types/src/lib/BaseSuite.test/test.d.ts +0 -37
  673. package/dist/types/src/lib/BaseSuite.test/web.test.d.ts +0 -2
  674. package/dist/types/src/lib/BaseThen.d.ts +0 -27
  675. package/dist/types/src/lib/BaseWhen.d.ts +0 -27
  676. package/dist/types/src/lib/Sidecar.d.ts +0 -5
  677. package/dist/types/src/lib/Tiposkripto.d.ts +0 -37
  678. package/dist/types/src/lib/Tiposkripto.test/MockTiposkripto.d.ts +0 -18
  679. package/dist/types/src/lib/Tiposkripto.test/Tiposkripto.adapter.d.ts +0 -3
  680. package/dist/types/src/lib/Tiposkripto.test/Tiposkripto.d.ts +0 -2
  681. package/dist/types/src/lib/Tiposkripto.test/Tiposkripto.implementation.d.ts +0 -3
  682. package/dist/types/src/lib/Tiposkripto.test/Tiposkripto.specification.d.ts +0 -3
  683. package/dist/types/src/lib/Tiposkripto.test/Tiposkripto.types.d.ts +0 -58
  684. package/dist/types/src/lib/abstractBase.test/MockGiven.d.ts +0 -9
  685. package/dist/types/src/lib/abstractBase.test/MockThen.d.ts +0 -6
  686. package/dist/types/src/lib/abstractBase.test/MockWhen.d.ts +0 -6
  687. package/dist/types/src/lib/abstractBase.test/adapter.d.ts +0 -3
  688. package/dist/types/src/lib/abstractBase.test/implementation.d.ts +0 -3
  689. package/dist/types/src/lib/abstractBase.test/index.d.ts +0 -2
  690. package/dist/types/src/lib/abstractBase.test/specification.d.ts +0 -3
  691. package/dist/types/src/lib/abstractBase.test/types.d.ts +0 -39
  692. package/dist/types/src/lib/index.d.ts +0 -73
  693. package/dist/types/src/lib/pmProxy.d.ts +0 -12
  694. package/dist/types/src/lib/pmProxy.test/adapter.d.ts +0 -3
  695. package/dist/types/src/lib/pmProxy.test/implementation.d.ts +0 -3
  696. package/dist/types/src/lib/pmProxy.test/index.d.ts +0 -6
  697. package/dist/types/src/lib/pmProxy.test/mockPM.d.ts +0 -10
  698. package/dist/types/src/lib/pmProxy.test/mockPMBase.d.ts +0 -40
  699. package/dist/types/src/lib/pmProxy.test/specification.d.ts +0 -3
  700. package/dist/types/src/lib/pmProxy.test/types.d.ts +0 -42
  701. package/dist/types/src/lib/types.d.ts +0 -24
  702. package/dist/types/src/mothership/index.d.ts +0 -2
  703. package/dist/types/src/mothership/test.d.ts +0 -2
  704. package/dist/types/src/services/FileService.d.ts +0 -34
  705. package/dist/types/src/services/GitHubAuthService.d.ts +0 -32
  706. package/dist/types/src/testeranto.d.ts +0 -1
  707. package/dist/types/src/types/features.d.ts +0 -7
  708. package/dist/types/src/utils/api.d.ts +0 -10
  709. package/dist/types/src/utils/buildTemplates.d.ts +0 -1
  710. package/dist/types/src/utils/featureUtils.d.ts +0 -6
  711. package/dist/types/src/utils/gitTest.d.ts +0 -11
  712. package/dist/types/src/utils/golingvuMetafile.d.ts +0 -19
  713. package/dist/types/src/utils/logFiles.d.ts +0 -75
  714. package/dist/types/src/utils/makePrompt.d.ts +0 -2
  715. package/dist/types/src/utils/pitonoMetafile.d.ts +0 -7
  716. package/dist/types/src/utils/queue.d.ts +0 -11
  717. package/dist/types/src/utils.d.ts +0 -20
  718. package/dist/types/src/web.html.d.ts +0 -2
  719. package/dist/types/tsconfig.types.tsbuildinfo +0 -1
  720. package/example/__pycache__/Calculator.cpython-313.pyc +0 -0
  721. package/example/vendor/github.com/adamwong246/testeranto/src/golingvu/README.md +0 -187
  722. package/example/vendor/github.com/adamwong246/testeranto/src/golingvu/base_given.go +0 -163
  723. package/example/vendor/github.com/adamwong246/testeranto/src/golingvu/base_suite.go +0 -85
  724. package/example/vendor/github.com/adamwong246/testeranto/src/golingvu/base_then.go +0 -21
  725. package/example/vendor/github.com/adamwong246/testeranto/src/golingvu/base_when.go +0 -21
  726. package/example/vendor/github.com/adamwong246/testeranto/src/golingvu/golingvu.go +0 -554
  727. package/example/vendor/github.com/adamwong246/testeranto/src/golingvu/test_adapter.go +0 -33
  728. package/example/vendor/github.com/adamwong246/testeranto/src/golingvu/types.go +0 -72
  729. package/example/vendor/modules.txt +0 -5
  730. package/pitono/__init__.py +0 -54
  731. package/pitono/types.py +0 -78
  732. package/src/PM/metafileOutputs.ts +0 -90
  733. package/src/golingvu/base_suite_test.go +0 -197
  734. package/src/pitono/PM/__pycache__/python.cpython-313.pyc +0 -0
  735. package/src/pitono/__pycache__/Pitono.cpython-313.pyc +0 -0
  736. package/src/pitono/__pycache__/__init__.cpython-313.pyc +0 -0
  737. package/src/pitono/__pycache__/base_given.cpython-313.pyc +0 -0
  738. package/src/pitono/__pycache__/base_suite.cpython-313.pyc +0 -0
  739. package/src/pitono/__pycache__/base_then.cpython-313.pyc +0 -0
  740. package/src/pitono/__pycache__/base_when.cpython-313.pyc +0 -0
  741. package/src/pitono/__pycache__/core_generator.cpython-313.pyc +0 -0
  742. package/src/pitono/__pycache__/simple_adapter.cpython-313.pyc +0 -0
  743. package/src/pitono/__pycache__/types.cpython-313.pyc +0 -0
  744. package/src/templates/frontpage.html +0 -340
  745. package/src/templates/frontpage.md +0 -79
  746. package/testeranto/bundles/golang/core/Calculator.golingvu.golingvu.go +0 -53
  747. package/testeranto/bundles/node/core/chunk-VXVF7WFO.mjs +0 -4321
  748. package/testeranto/bundles/node/core/example/Calculator.test.mjs +0 -503
  749. package/testeranto/bundles/python/core/Calculator.pitono.test.py +0 -24
  750. package/testeranto/bundles/python/core/test_example.py +0 -24
  751. package/testeranto/bundles/web/core/chunk-DFRN4SYZ.mjs +0 -2297
  752. package/testeranto/bundles/web/core/chunk-Q5TONB2Z.mjs +0 -6874
  753. package/testeranto/bundles/web/core/src/components/pure/ModalContent.test/index.css +0 -11697
  754. package/testeranto/bundles/web/core/src/components/pure/ModalContent.test/index.mjs +0 -336
  755. package/testeranto/reports/core/src/components/pure/FeaturesReporterView.test/index/web/tests.json +0 -68
  756. package/testeranto/reports/core/src/components/pure/ProjectPageView.test/index/web/tests.json +0 -88
  757. package/testeranto/reports/core/src/lib/BaseSuite.test/web.test/web/tests.json +0 -29
  758. /package/{pitono → src/pitono}/core_generator.py +0 -0
  759. /package/{pitono → src/pitono}/pitono.egg-info/dependency_links.txt +0 -0
  760. /package/{pitono → src/pitono}/pitono.egg-info/entry_points.txt +0 -0
  761. /package/{pitono → src/pitono}/pitono.egg-info/top_level.txt +0 -0
  762. /package/{pitono → src/pitono}/pyproject.toml +0 -0
  763. /package/{pitono → src/pitono}/setup.py +0 -0
  764. /package/{pitono → src/pitono}/simple_adapter.py +0 -0
  765. /package/{dist/types/src/PM/metafileOutputs.d.ts → testeranto/helpo_chat_message.txt} +0 -0
  766. /package/{dist/types/src/ReportServer.d.ts → testeranto/reports/core/example/test_example/python/stdout.log} +0 -0
  767. /package/{dist/types/src/ReportServerLib.d.ts → testeranto/reports/core/src/components/pure/FeaturesReporterView.test/index/web/lint_errors.txt} +0 -0
  768. /package/{dist/types/src/components/SunriseAnimation.test/implementation.d.ts → testeranto/reports/core/src/components/pure/ModalContent.test/index/web/debug.log} +0 -0
  769. /package/{dist/types/src/components/SunriseAnimation.test/index.d.ts → testeranto/reports/core/src/components/pure/ModalContent.test/index/web/error.log} +0 -0
  770. /package/{dist/types/src/components/SunriseAnimation.test/specification.d.ts → testeranto/reports/core/src/components/pure/ModalContent.test/index/web/exit.log} +0 -0
  771. /package/{dist/types/src/components/pure/ArtifactTree.d.ts → testeranto/reports/core/src/components/pure/ModalContent.test/index/web/info.log} +0 -0
  772. /package/{dist/types/src/components/stateful/FileTree.d.ts → testeranto/reports/core/src/components/pure/ModalContent.test/index/web/warn.log} +0 -0
  773. /package/{dist/types/src/run.d.ts → testeranto/reports/core/src/lib/BaseSuite.test/web.test/web/lint_errors.txt} +0 -0
@@ -10,7 +10,7 @@ var __export = (target, all) => {
10
10
  };
11
11
 
12
12
  // src/utils.ts
13
- import path2 from "path";
13
+ import path from "path";
14
14
  var webEvaluator, tscPather, lintPather, promptPather, getRunnables;
15
15
  var init_utils = __esm({
16
16
  "src/utils.ts"() {
@@ -27,7 +27,7 @@ import('${d}').then(async (x) => {
27
27
  `;
28
28
  };
29
29
  tscPather = (entryPoint, platform, projectName) => {
30
- return path2.join(
30
+ return path.join(
31
31
  "testeranto",
32
32
  "reports",
33
33
  projectName,
@@ -37,7 +37,7 @@ import('${d}').then(async (x) => {
37
37
  );
38
38
  };
39
39
  lintPather = (entryPoint, platform, projectName) => {
40
- return path2.join(
40
+ return path.join(
41
41
  "testeranto",
42
42
  "reports",
43
43
  projectName,
@@ -47,7 +47,7 @@ import('${d}').then(async (x) => {
47
47
  );
48
48
  };
49
49
  promptPather = (entryPoint, platform, projectName) => {
50
- return path2.join(
50
+ return path.join(
51
51
  "testeranto",
52
52
  "reports",
53
53
  projectName,
@@ -82,42 +82,42 @@ import('${d}').then(async (x) => {
82
82
  };
83
83
  return tests.reduce((pt, cv, cndx, cry) => {
84
84
  if (cv[1] === "node") {
85
- pt.nodeEntryPoints[cv[0]] = path2.resolve(
85
+ pt.nodeEntryPoints[cv[0]] = path.resolve(
86
86
  `./testeranto/bundles/node/${projectName}/${cv[0].split(".").slice(0, -1).concat("mjs").join(".")}`
87
87
  );
88
88
  } else if (cv[1] === "web") {
89
- pt.webEntryPoints[cv[0]] = path2.resolve(
89
+ pt.webEntryPoints[cv[0]] = path.resolve(
90
90
  `./testeranto/bundles/web/${projectName}/${cv[0].split(".").slice(0, -1).concat("mjs").join(".")}`
91
91
  );
92
92
  } else if (cv[1] === "pure") {
93
- pt.pureEntryPoints[cv[0]] = path2.resolve(
93
+ pt.pureEntryPoints[cv[0]] = path.resolve(
94
94
  `./testeranto/bundles/pure/${projectName}/${cv[0].split(".").slice(0, -1).concat("mjs").join(".")}`
95
95
  );
96
96
  } else if (cv[1] === "golang") {
97
- pt.golangEntryPoints[cv[0]] = path2.resolve(cv[0]);
97
+ pt.golangEntryPoints[cv[0]] = path.resolve(cv[0]);
98
98
  } else if (cv[1] === "python") {
99
- pt.pythonEntryPoints[cv[0]] = path2.resolve(cv[0]);
99
+ pt.pythonEntryPoints[cv[0]] = path.resolve(cv[0]);
100
100
  }
101
101
  cv[3].filter((t) => t[1] === "node").forEach((t) => {
102
- pt.nodeEntryPointSidecars[`${t[0]}`] = path2.resolve(
102
+ pt.nodeEntryPointSidecars[`${t[0]}`] = path.resolve(
103
103
  `./testeranto/bundles/node/${projectName}/${cv[0].split(".").slice(0, -1).concat("mjs").join(".")}`
104
104
  );
105
105
  });
106
106
  cv[3].filter((t) => t[1] === "web").forEach((t) => {
107
- pt.webEntryPointSidecars[`${t[0]}`] = path2.resolve(
107
+ pt.webEntryPointSidecars[`${t[0]}`] = path.resolve(
108
108
  `./testeranto/bundles/web/${projectName}/${cv[0].split(".").slice(0, -1).concat("mjs").join(".")}`
109
109
  );
110
110
  });
111
111
  cv[3].filter((t) => t[1] === "pure").forEach((t) => {
112
- pt.pureEntryPointSidecars[`${t[0]}`] = path2.resolve(
112
+ pt.pureEntryPointSidecars[`${t[0]}`] = path.resolve(
113
113
  `./testeranto/bundles/pure/${projectName}/${cv[0].split(".").slice(0, -1).concat("mjs").join(".")}`
114
114
  );
115
115
  });
116
116
  cv[3].filter((t) => t[1] === "golang").forEach((t) => {
117
- pt.golangEntryPointSidecars[`${t[0]}`] = path2.resolve(t[0]);
117
+ pt.golangEntryPointSidecars[`${t[0]}`] = path.resolve(t[0]);
118
118
  });
119
119
  cv[3].filter((t) => t[1] === "python").forEach((t) => {
120
- pt.pythonEntryPointSidecars[`${t[0]}`] = path2.resolve(t[0]);
120
+ pt.pythonEntryPointSidecars[`${t[0]}`] = path.resolve(t[0]);
121
121
  });
122
122
  return pt;
123
123
  }, initializedPayload);
@@ -125,6 +125,872 @@ import('${d}').then(async (x) => {
125
125
  }
126
126
  });
127
127
 
128
+ // src/utils/golingvuMetafile.ts
129
+ import fs3 from "fs";
130
+ import path4 from "path";
131
+ import { execSync } from "child_process";
132
+ function runGoList(pattern) {
133
+ try {
134
+ let processedPattern = pattern;
135
+ if (fs3.existsSync(pattern) && pattern.endsWith(".go")) {
136
+ const dir = path4.dirname(pattern);
137
+ processedPattern = dir;
138
+ }
139
+ const output = execSync(`go list -mod=readonly -json ${processedPattern}`, {
140
+ encoding: "utf-8",
141
+ cwd: process.cwd(),
142
+ stdio: ["pipe", "pipe", "pipe"]
143
+ });
144
+ const objects = [];
145
+ let buffer = "";
146
+ let depth = 0;
147
+ let inString = false;
148
+ let escapeNext = false;
149
+ for (const char of output) {
150
+ if (escapeNext) {
151
+ buffer += char;
152
+ escapeNext = false;
153
+ continue;
154
+ }
155
+ if (char === "\\") {
156
+ escapeNext = true;
157
+ buffer += char;
158
+ continue;
159
+ }
160
+ if (char === '"') {
161
+ inString = !inString;
162
+ }
163
+ if (!inString) {
164
+ if (char === "{") {
165
+ depth++;
166
+ } else if (char === "}") {
167
+ depth--;
168
+ if (depth === 0) {
169
+ try {
170
+ objects.push(JSON.parse(buffer + char));
171
+ buffer = "";
172
+ continue;
173
+ } catch (e) {
174
+ console.warn("Failed to parse JSON object:", buffer + char);
175
+ buffer = "";
176
+ }
177
+ }
178
+ }
179
+ }
180
+ if (depth > 0 || buffer.length > 0) {
181
+ buffer += char;
182
+ }
183
+ }
184
+ return objects;
185
+ } catch (error) {
186
+ console.warn(`Error running 'go list -json ${pattern}':`, error);
187
+ try {
188
+ const output = execSync(`go list -mod=readonly -json .`, {
189
+ encoding: "utf-8",
190
+ cwd: process.cwd(),
191
+ stdio: ["pipe", "pipe", "pipe"]
192
+ });
193
+ const objects = [];
194
+ let buffer = "";
195
+ let depth = 0;
196
+ let inString = false;
197
+ let escapeNext = false;
198
+ for (const char of output) {
199
+ if (escapeNext) {
200
+ buffer += char;
201
+ escapeNext = false;
202
+ continue;
203
+ }
204
+ if (char === "\\") {
205
+ escapeNext = true;
206
+ buffer += char;
207
+ continue;
208
+ }
209
+ if (char === '"') {
210
+ inString = !inString;
211
+ }
212
+ if (!inString) {
213
+ if (char === "{") {
214
+ depth++;
215
+ } else if (char === "}") {
216
+ depth--;
217
+ if (depth === 0) {
218
+ try {
219
+ objects.push(JSON.parse(buffer + char));
220
+ buffer = "";
221
+ continue;
222
+ } catch (e) {
223
+ console.warn("Failed to parse JSON object:", buffer + char);
224
+ buffer = "";
225
+ }
226
+ }
227
+ }
228
+ }
229
+ if (depth > 0 || buffer.length > 0) {
230
+ buffer += char;
231
+ }
232
+ }
233
+ return objects;
234
+ } catch (fallbackError) {
235
+ console.warn("Fallback go list also failed:", fallbackError);
236
+ return [];
237
+ }
238
+ }
239
+ }
240
+ function findGoFilesInProject() {
241
+ const packages = runGoList("./...");
242
+ const goFiles = [];
243
+ for (const pkg of packages) {
244
+ if (pkg.GoFiles) {
245
+ for (const file of pkg.GoFiles) {
246
+ goFiles.push(path4.join(pkg.Dir, file));
247
+ }
248
+ }
249
+ if (pkg.CgoFiles) {
250
+ for (const file of pkg.CgoFiles) {
251
+ goFiles.push(path4.join(pkg.Dir, file));
252
+ }
253
+ }
254
+ }
255
+ return goFiles;
256
+ }
257
+ function collectGoDependencies(filePath, visited = /* @__PURE__ */ new Set()) {
258
+ if (visited.has(filePath))
259
+ return [];
260
+ visited.add(filePath);
261
+ const dependencies = [filePath];
262
+ const dir = path4.dirname(filePath);
263
+ try {
264
+ const files3 = fs3.readdirSync(dir);
265
+ for (const file of files3) {
266
+ if (file.endsWith(".go") && file !== path4.basename(filePath)) {
267
+ const fullPath = path4.join(dir, file);
268
+ dependencies.push(fullPath);
269
+ }
270
+ }
271
+ } catch (error) {
272
+ console.warn(`Could not read directory ${dir}:`, error);
273
+ }
274
+ try {
275
+ const content = fs3.readFileSync(filePath, "utf-8");
276
+ const importRegex = /import\s*(?:\(\s*([\s\S]*?)\s*\)|"([^"]+)")/g;
277
+ let match;
278
+ while ((match = importRegex.exec(content)) !== null) {
279
+ if (match[2]) {
280
+ const importPath = match[2].trim();
281
+ processImport(importPath, dir, dependencies, visited);
282
+ } else if (match[1]) {
283
+ const importBlock = match[1];
284
+ const importLines = importBlock.split("\n").map((line) => line.trim()).filter((line) => line.length > 0 && !line.startsWith("//"));
285
+ for (const line of importLines) {
286
+ const lineMatch = line.match(/"([^"]+)"/);
287
+ if (lineMatch) {
288
+ const importPath = lineMatch[1].trim();
289
+ processImport(importPath, dir, dependencies, visited);
290
+ }
291
+ }
292
+ }
293
+ }
294
+ } catch (error) {
295
+ console.warn(`Could not read file ${filePath} for import parsing:`, error);
296
+ }
297
+ return [...new Set(dependencies)];
298
+ }
299
+ function processImport(importPath, currentDir, dependencies, visited) {
300
+ const firstPathElement = importPath.split("/")[0];
301
+ const isExternal = firstPathElement.includes(".");
302
+ if (!isExternal) {
303
+ const potentialPaths = [
304
+ path4.join(process.cwd(), "vendor", importPath),
305
+ path4.join(currentDir, importPath),
306
+ path4.join(process.cwd(), importPath),
307
+ path4.join(process.cwd(), "src", importPath)
308
+ ];
309
+ for (const potentialPath of potentialPaths) {
310
+ if (fs3.existsSync(potentialPath) && fs3.statSync(potentialPath).isDirectory()) {
311
+ try {
312
+ const files3 = fs3.readdirSync(potentialPath);
313
+ for (const file of files3) {
314
+ if (file.endsWith(".go") && !file.endsWith("_test.go")) {
315
+ const fullPath = path4.join(potentialPath, file);
316
+ dependencies.push(...collectGoDependencies(fullPath, visited));
317
+ }
318
+ }
319
+ break;
320
+ } catch (error) {
321
+ console.warn(`Could not read directory ${potentialPath}:`, error);
322
+ }
323
+ }
324
+ const goFilePath = potentialPath + ".go";
325
+ if (fs3.existsSync(goFilePath)) {
326
+ dependencies.push(...collectGoDependencies(goFilePath, visited));
327
+ break;
328
+ }
329
+ }
330
+ }
331
+ }
332
+ function parseGoImports(filePath) {
333
+ const dir = path4.dirname(filePath);
334
+ const packages = runGoList(dir);
335
+ if (packages.length === 0) {
336
+ return [];
337
+ }
338
+ const pkg = packages[0];
339
+ const imports = [];
340
+ if (pkg.Imports) {
341
+ for (const importPath of pkg.Imports) {
342
+ const firstPathElement = importPath.split("/")[0];
343
+ const isExternal = firstPathElement.includes(".");
344
+ imports.push({
345
+ path: importPath,
346
+ kind: "import-statement",
347
+ external: isExternal
348
+ });
349
+ }
350
+ }
351
+ try {
352
+ const content = fs3.readFileSync(filePath, "utf-8");
353
+ const importRegex = /import\s*(?:\(\s*([\s\S]*?)\s*\)|"([^"]+)")/g;
354
+ let match;
355
+ while ((match = importRegex.exec(content)) !== null) {
356
+ if (match[2]) {
357
+ const importPath = match[2].trim();
358
+ const firstPathElement = importPath.split("/")[0];
359
+ const isExternal = firstPathElement.includes(".");
360
+ if (!imports.some((imp) => imp.path === importPath)) {
361
+ imports.push({
362
+ path: importPath,
363
+ kind: "import-statement",
364
+ external: isExternal
365
+ });
366
+ }
367
+ } else if (match[1]) {
368
+ const importBlock = match[1];
369
+ const importLines = importBlock.split("\n").map((line) => line.trim()).filter((line) => line.length > 0 && !line.startsWith("//"));
370
+ for (const line of importLines) {
371
+ const lineMatch = line.match(/"([^"]+)"/);
372
+ if (lineMatch) {
373
+ const importPath = lineMatch[1].trim();
374
+ const firstPathElement = importPath.split("/")[0];
375
+ const isExternal = firstPathElement.includes(".");
376
+ if (!imports.some((imp) => imp.path === importPath)) {
377
+ imports.push({
378
+ path: importPath,
379
+ kind: "import-statement",
380
+ external: isExternal
381
+ });
382
+ }
383
+ }
384
+ }
385
+ }
386
+ }
387
+ } catch (error) {
388
+ console.warn(`Could not read file ${filePath} for import parsing:`, error);
389
+ }
390
+ return imports;
391
+ }
392
+ function findProjectRoot() {
393
+ let currentDir = process.cwd();
394
+ while (currentDir !== path4.parse(currentDir).root) {
395
+ const packageJsonPath = path4.join(currentDir, "package.json");
396
+ if (fs3.existsSync(packageJsonPath)) {
397
+ return currentDir;
398
+ }
399
+ currentDir = path4.dirname(currentDir);
400
+ }
401
+ return process.cwd();
402
+ }
403
+ function isGoAvailable() {
404
+ try {
405
+ execSync("go version", { stdio: "pipe" });
406
+ return true;
407
+ } catch {
408
+ return false;
409
+ }
410
+ }
411
+ async function generateGolingvuMetafile(testName2, entryPoints) {
412
+ if (generationQueue) {
413
+ console.log("Generation already in progress, waiting...");
414
+ return generationQueue;
415
+ }
416
+ generationQueue = (async () => {
417
+ console.log(`Generating Golang metafile for test: ${testName2}`);
418
+ console.log(`Entry points provided: ${JSON.stringify(entryPoints)}`);
419
+ console.log(`Current working directory: ${process.cwd()}`);
420
+ const inputs = {};
421
+ const outputs = {};
422
+ const signature = Date.now().toString(36);
423
+ if (!isGoAvailable()) {
424
+ console.warn("Go toolchain is not available. Using fallback method.");
425
+ return {
426
+ errors: [],
427
+ warnings: [],
428
+ metafile: {
429
+ inputs: {},
430
+ outputs: {}
431
+ }
432
+ };
433
+ }
434
+ const filteredEntryPoints = [];
435
+ for (const entryPoint of entryPoints) {
436
+ const fileName = path4.basename(entryPoint);
437
+ if (fileName.includes("_test.go") || fileName.endsWith(".test.go")) {
438
+ console.warn(`Skipping Go test file: ${fileName}`);
439
+ continue;
440
+ }
441
+ filteredEntryPoints.push(entryPoint);
442
+ }
443
+ entryPoints = filteredEntryPoints;
444
+ if (entryPoints.length === 0) {
445
+ const allGoFiles = findGoFilesInProject();
446
+ entryPoints = allGoFiles.filter((file) => {
447
+ const fileName = path4.basename(file);
448
+ return !fileName.includes("_test.go") && !fileName.endsWith(".test.go");
449
+ });
450
+ if (entryPoints.length === 0) {
451
+ console.warn("No non-test Go files found in the project");
452
+ } else {
453
+ console.log(
454
+ `Found ${entryPoints.length} non-test Go files:`,
455
+ entryPoints
456
+ );
457
+ }
458
+ }
459
+ for (let i = 0; i < entryPoints.length; i++) {
460
+ let entryPoint = entryPoints[i];
461
+ let resolvedPath = entryPoint;
462
+ if (!path4.isAbsolute(entryPoint)) {
463
+ resolvedPath = path4.join(process.cwd(), entryPoint);
464
+ }
465
+ if (!fs3.existsSync(resolvedPath)) {
466
+ console.warn(
467
+ `Entry point ${entryPoint} does not exist at ${resolvedPath}`
468
+ );
469
+ const fileName2 = path4.basename(entryPoint);
470
+ const potentialPaths = [
471
+ path4.join(process.cwd(), "example", fileName2),
472
+ path4.join(process.cwd(), fileName2),
473
+ path4.join(process.cwd(), "src", "example", fileName2),
474
+ path4.join(process.cwd(), "src", fileName2)
475
+ ];
476
+ let foundPath = "";
477
+ for (const potentialPath of potentialPaths) {
478
+ if (fs3.existsSync(potentialPath)) {
479
+ foundPath = potentialPath;
480
+ console.log(`Found ${fileName2} at: ${foundPath}`);
481
+ break;
482
+ }
483
+ }
484
+ if (!foundPath) {
485
+ console.warn(`Could not find ${fileName2} in any common locations`);
486
+ continue;
487
+ }
488
+ entryPoints[i] = foundPath;
489
+ entryPoint = foundPath;
490
+ } else {
491
+ entryPoints[i] = resolvedPath;
492
+ entryPoint = resolvedPath;
493
+ }
494
+ const fileName = path4.basename(entryPoint);
495
+ if (fileName.includes("_test.go") || fileName.endsWith(".test.go")) {
496
+ console.log(`Skipping Go test file: ${fileName}`);
497
+ continue;
498
+ }
499
+ const allDependencies = collectGoDependencies(entryPoint);
500
+ for (const dep of allDependencies) {
501
+ if (!inputs[dep]) {
502
+ const bytes = fs3.statSync(dep).size;
503
+ const imports = parseGoImports(dep);
504
+ inputs[dep] = {
505
+ bytes,
506
+ imports,
507
+ format: "esm"
508
+ // Go doesn't use ES modules, but we'll use this for consistency
509
+ };
510
+ }
511
+ }
512
+ const entryPointName = path4.basename(entryPoint, ".go");
513
+ const baseName = entryPointName;
514
+ const outputKey = `golang/core/${baseName}.golingvu.go`;
515
+ const inputBytes = {};
516
+ let totalBytes = 0;
517
+ for (const dep of allDependencies) {
518
+ const bytes = fs3.statSync(dep).size;
519
+ inputBytes[dep] = { bytesInOutput: bytes };
520
+ totalBytes += bytes;
521
+ }
522
+ outputs[outputKey] = {
523
+ imports: [],
524
+ exports: [],
525
+ entryPoint,
526
+ inputs: inputBytes,
527
+ bytes: totalBytes,
528
+ signature
529
+ };
530
+ }
531
+ if (Object.keys(inputs).length === 0) {
532
+ try {
533
+ const files3 = fs3.readdirSync(process.cwd());
534
+ const goFiles = files3.filter((file) => file.endsWith(".go"));
535
+ if (goFiles.length > 0) {
536
+ const firstGoFile = path4.join(process.cwd(), goFiles[0]);
537
+ const bytes = fs3.statSync(firstGoFile).size;
538
+ const imports = parseGoImports(firstGoFile);
539
+ inputs[firstGoFile] = {
540
+ bytes,
541
+ imports,
542
+ format: "esm"
543
+ };
544
+ outputs[`golang/core/${goFiles[0]}`] = {
545
+ imports: [],
546
+ exports: [],
547
+ entryPoint: firstGoFile,
548
+ inputs: {
549
+ [firstGoFile]: {
550
+ bytesInOutput: bytes
551
+ }
552
+ },
553
+ bytes,
554
+ signature
555
+ };
556
+ } else {
557
+ const goModPath = path4.join(process.cwd(), "go.mod");
558
+ if (fs3.existsSync(goModPath)) {
559
+ console.warn("Found go.mod but no Go files could be processed");
560
+ inputs["placeholder.go"] = {
561
+ bytes: 0,
562
+ imports: [],
563
+ format: "esm"
564
+ };
565
+ outputs["testeranto/bundles/golang/core/placeholder.go"] = {
566
+ imports: [],
567
+ exports: [],
568
+ entryPoint: "placeholder.go",
569
+ inputs: {
570
+ "placeholder.go": {
571
+ bytesInOutput: 0
572
+ }
573
+ },
574
+ bytes: 0,
575
+ signature
576
+ };
577
+ } else {
578
+ console.warn("No Go files found and not in a Go project");
579
+ }
580
+ }
581
+ } catch (error) {
582
+ console.warn("Error finding Go files:", error);
583
+ const goModPath = path4.join(process.cwd(), "go.mod");
584
+ if (fs3.existsSync(goModPath)) {
585
+ inputs["placeholder.go"] = {
586
+ bytes: 0,
587
+ imports: [],
588
+ format: "esm"
589
+ };
590
+ outputs["golang/core/placeholder.go"] = {
591
+ imports: [],
592
+ exports: [],
593
+ entryPoint: "placeholder.go",
594
+ inputs: {
595
+ "placeholder.go": {
596
+ bytesInOutput: 0
597
+ }
598
+ },
599
+ bytes: 0,
600
+ signature
601
+ };
602
+ }
603
+ }
604
+ }
605
+ const result = {
606
+ errors: [],
607
+ warnings: [],
608
+ metafile: {
609
+ inputs,
610
+ outputs
611
+ }
612
+ };
613
+ generationQueue = null;
614
+ return result;
615
+ })();
616
+ return generationQueue;
617
+ }
618
+ function writeGolingvuMetafile(testName2, metafile) {
619
+ writeGolingvuMetafileCallCount++;
620
+ console.log(`writeGolingvuMetafile called ${writeGolingvuMetafileCallCount} times`);
621
+ console.log("process.cwd()", process.cwd());
622
+ console.log("testName:", testName2);
623
+ const projectRoot = findProjectRoot();
624
+ const metafilePath = path4.join(
625
+ projectRoot,
626
+ "testeranto",
627
+ "metafiles",
628
+ "golang",
629
+ "core.json"
630
+ );
631
+ const metafileDir = path4.dirname(metafilePath);
632
+ if (!fs3.existsSync(metafileDir)) {
633
+ fs3.mkdirSync(metafileDir, { recursive: true });
634
+ }
635
+ fs3.writeFileSync(metafilePath, JSON.stringify(metafile, null, 2));
636
+ console.log(`Golang metafile written to: ${metafilePath}`);
637
+ const outputDir = path4.join(
638
+ projectRoot,
639
+ "testeranto",
640
+ "bundles",
641
+ "golang",
642
+ "core"
643
+ );
644
+ console.log("Output directory:", outputDir);
645
+ if (!fs3.existsSync(outputDir)) {
646
+ fs3.mkdirSync(outputDir, { recursive: true });
647
+ }
648
+ for (const [outputPath, outputInfo] of Object.entries(
649
+ metafile.metafile.outputs
650
+ )) {
651
+ const fileName = path4.basename(outputPath);
652
+ const fullOutputPath = path4.join(outputDir, fileName);
653
+ const outputDirPath = path4.dirname(fullOutputPath);
654
+ if (!fs3.existsSync(outputDirPath)) {
655
+ fs3.mkdirSync(outputDirPath, { recursive: true });
656
+ }
657
+ const entryPoint = outputInfo.entryPoint;
658
+ const signature = outputInfo.signature;
659
+ const entryDir = path4.dirname(entryPoint);
660
+ const entryDirName = path4.basename(entryDir);
661
+ let importPath;
662
+ if (entryDirName === "example") {
663
+ importPath = "../example";
664
+ } else {
665
+ const relativePathToEntry = path4.relative(outputDir, entryDir);
666
+ importPath = relativePathToEntry ? `./${relativePathToEntry}` : ".";
667
+ }
668
+ const entryPointBaseName = path4.basename(entryPoint, ".go");
669
+ const content = `//go:build testeranto
670
+ // +build testeranto
671
+
672
+ // This file is auto-generated by testeranto
673
+ // Signature: ${signature}
674
+ // It imports and tests: ${entryPoint}
675
+
676
+ package testeranto_test
677
+
678
+ import (
679
+ "fmt"
680
+ "os"
681
+ "testing"
682
+
683
+ // Import the original implementation
684
+ "${importPath}"
685
+ )
686
+
687
+ func TestCalculatorOperations(t *testing.T) {
688
+ // Create an instance of the Calculator
689
+ calc := &${entryPointBaseName}.Calculator{}
690
+
691
+ // Test basic operations
692
+ // This is where testeranto would run its test scenarios
693
+
694
+ // Example test: test that a new calculator has empty display
695
+ if calc.GetDisplay() != "" {
696
+ t.Errorf("Expected empty display, got: %s", calc.GetDisplay())
697
+ }
698
+
699
+ // Example test: test pressing buttons
700
+ calc.Press("2")
701
+ if calc.GetDisplay() != "2" {
702
+ t.Errorf("Expected '2', got: %s", calc.GetDisplay())
703
+ }
704
+
705
+ // Add more test scenarios based on the testeranto specification
706
+ fmt.Println("Testeranto tests completed")
707
+ }
708
+
709
+ func main() {
710
+ // This allows the file to be run as a standalone program
711
+ // while keeping it in the testeranto_test package
712
+ testing.Main(func(pat, str string) (bool, error) { return true, nil },
713
+ []testing.InternalTest{
714
+ {
715
+ Name: "TestCalculatorOperations",
716
+ F: TestCalculatorOperations,
717
+ },
718
+ },
719
+ []testing.InternalBenchmark{},
720
+ []testing.InternalExample{})
721
+ }
722
+ `;
723
+ fs3.writeFileSync(fullOutputPath, content);
724
+ console.log(`Generated Golingvu wrapper: ${fullOutputPath}`);
725
+ }
726
+ }
727
+ var generationQueue, writeGolingvuMetafileCallCount;
728
+ var init_golingvuMetafile = __esm({
729
+ "src/utils/golingvuMetafile.ts"() {
730
+ "use strict";
731
+ generationQueue = null;
732
+ writeGolingvuMetafileCallCount = 0;
733
+ }
734
+ });
735
+
736
+ // src/utils/golingvuWatcher.ts
737
+ import chokidar2 from "chokidar";
738
+ import path5 from "path";
739
+ import fs4 from "fs";
740
+ var GolingvuWatcher;
741
+ var init_golingvuWatcher = __esm({
742
+ "src/utils/golingvuWatcher.ts"() {
743
+ "use strict";
744
+ init_golingvuMetafile();
745
+ GolingvuWatcher = class {
746
+ constructor(testName2, entryPoints) {
747
+ this.watcher = null;
748
+ this.onChangeCallback = null;
749
+ this.debounceTimer = null;
750
+ this.testName = testName2;
751
+ this.entryPoints = entryPoints;
752
+ }
753
+ async start() {
754
+ const goFilesPattern = "**/*.go";
755
+ this.watcher = chokidar2.watch(goFilesPattern, {
756
+ persistent: true,
757
+ ignoreInitial: true,
758
+ cwd: process.cwd(),
759
+ ignored: [
760
+ "**/node_modules/**",
761
+ "**/.git/**",
762
+ "**/testeranto/bundles/**",
763
+ "**/testeranto/reports/**"
764
+ ],
765
+ usePolling: true,
766
+ interval: 1e3,
767
+ binaryInterval: 1e3,
768
+ depth: 99,
769
+ followSymlinks: false,
770
+ atomic: false
771
+ });
772
+ this.watcher.on("add", (filePath) => {
773
+ console.log(`File added: ${filePath}`);
774
+ this.handleFileChange("add", filePath);
775
+ }).on("change", (filePath) => {
776
+ console.log(`File changed: ${filePath}`);
777
+ this.handleFileChange("change", filePath);
778
+ }).on("unlink", (filePath) => {
779
+ console.log(`File removed: ${filePath}`);
780
+ this.handleFileChange("unlink", filePath);
781
+ }).on("addDir", (dirPath) => {
782
+ console.log(`Directory added: ${dirPath}`);
783
+ }).on("unlinkDir", (dirPath) => {
784
+ console.log(`Directory removed: ${dirPath}`);
785
+ }).on("error", (error) => {
786
+ console.error(`Source watcher error: ${error}`);
787
+ }).on("ready", () => {
788
+ console.log(
789
+ "Initial golang source file scan complete. Ready for changes."
790
+ );
791
+ const watched = this.watcher?.getWatched();
792
+ console.log(
793
+ "Number of watched directories:",
794
+ Object.keys(watched || {}).length
795
+ );
796
+ if (Object.keys(watched || {}).length === 0) {
797
+ console.error("WARNING: No directories are being watched!");
798
+ console.error("Trying to manually find and watch .go files...");
799
+ const findAllGoFiles = (dir) => {
800
+ let results = [];
801
+ const list = fs4.readdirSync(dir);
802
+ list.forEach((file) => {
803
+ const filePath = path5.join(dir, file);
804
+ const stat = fs4.statSync(filePath);
805
+ if (stat.isDirectory()) {
806
+ if (file === "node_modules" || file === ".git" || file === "testeranto") {
807
+ return;
808
+ }
809
+ results = results.concat(findAllGoFiles(filePath));
810
+ } else if (file.endsWith(".go")) {
811
+ results.push(filePath);
812
+ }
813
+ });
814
+ return results;
815
+ };
816
+ try {
817
+ const allGoFiles = findAllGoFiles(process.cwd());
818
+ console.log(`Found ${allGoFiles.length} Go files manually:`);
819
+ allGoFiles.forEach((file) => console.log(` ${file}`));
820
+ allGoFiles.forEach((file) => {
821
+ this.watcher?.add(file);
822
+ });
823
+ } catch (error) {
824
+ console.error("Error manually finding Go files:", error);
825
+ }
826
+ } else {
827
+ for (const [dir, files3] of Object.entries(watched || {})) {
828
+ console.log(`Directory: ${dir}`);
829
+ console.log(`Files: ${files3.join(", ")}`);
830
+ }
831
+ }
832
+ }).on("raw", (event, path14, details) => {
833
+ console.log(`Raw event: ${event} on path: ${path14}`);
834
+ });
835
+ const outputDir = path5.join(
836
+ process.cwd(),
837
+ "testeranto",
838
+ "bundles",
839
+ "golang",
840
+ "core"
841
+ );
842
+ if (!fs4.existsSync(outputDir)) {
843
+ fs4.mkdirSync(outputDir, { recursive: true });
844
+ }
845
+ console.log(`Watching bundle directory: ${outputDir}`);
846
+ const lastSignatures = /* @__PURE__ */ new Map();
847
+ const bundleWatcher = chokidar2.watch(
848
+ [path5.join(outputDir, "*.go"), path5.join(outputDir, "*.golingvu.go")],
849
+ {
850
+ persistent: true,
851
+ ignoreInitial: false,
852
+ // We want to capture initial files to establish baseline
853
+ awaitWriteFinish: {
854
+ stabilityThreshold: 100,
855
+ pollInterval: 50
856
+ }
857
+ }
858
+ );
859
+ bundleWatcher.on("add", (filePath) => {
860
+ this.readAndCheckSignature(filePath, lastSignatures);
861
+ }).on("change", (filePath) => {
862
+ this.readAndCheckSignature(filePath, lastSignatures);
863
+ }).on("error", (error) => console.error(`Bundle watcher error: ${error}`));
864
+ await this.regenerateMetafile();
865
+ }
866
+ async handleFileChange(event, filePath) {
867
+ if (this.debounceTimer) {
868
+ clearTimeout(this.debounceTimer);
869
+ }
870
+ this.debounceTimer = setTimeout(async () => {
871
+ const fullPath = path5.join(process.cwd(), filePath);
872
+ await new Promise((resolve) => setTimeout(resolve, 100));
873
+ if (fs4.existsSync(fullPath)) {
874
+ try {
875
+ const stats = fs4.statSync(fullPath);
876
+ console.log(`File ${filePath} changed (${stats.size} bytes)`);
877
+ } catch (error) {
878
+ console.error(`Error reading file: ${error}`);
879
+ }
880
+ }
881
+ console.log("Regenerating metafile due to file change...");
882
+ await this.regenerateMetafile();
883
+ if (this.onChangeCallback) {
884
+ this.onChangeCallback();
885
+ }
886
+ }, 300);
887
+ }
888
+ readAndCheckSignature(filePath, lastSignatures) {
889
+ try {
890
+ const content = fs4.readFileSync(filePath, "utf-8");
891
+ const signatureMatch = content.match(/\/\/ Signature: (\w+)/);
892
+ if (signatureMatch && signatureMatch[1]) {
893
+ const currentSignature = signatureMatch[1];
894
+ const lastSignature = lastSignatures.get(filePath);
895
+ if (lastSignature === void 0) {
896
+ lastSignatures.set(filePath, currentSignature);
897
+ } else if (lastSignature !== currentSignature) {
898
+ lastSignatures.set(filePath, currentSignature);
899
+ const fileName = path5.basename(filePath);
900
+ const originalFileName = fileName.replace(".golingvu.go", ".go");
901
+ const originalEntryPoint = this.entryPoints.find(
902
+ (ep) => path5.basename(ep) === originalFileName
903
+ );
904
+ if (originalEntryPoint) {
905
+ if (this.onChangeCallback) {
906
+ this.onChangeCallback();
907
+ }
908
+ }
909
+ }
910
+ }
911
+ } catch (error) {
912
+ console.error(`Error reading bundle file ${filePath}:`, error);
913
+ }
914
+ }
915
+ async regenerateMetafile() {
916
+ console.log("regenerateMetafile!");
917
+ try {
918
+ const metafile = await generateGolingvuMetafile(
919
+ this.testName,
920
+ this.entryPoints
921
+ );
922
+ writeGolingvuMetafile(this.testName, metafile);
923
+ } catch (error) {
924
+ console.error("Error regenerating golingvu metafile:", error);
925
+ }
926
+ }
927
+ onMetafileChange(callback) {
928
+ this.onChangeCallback = callback;
929
+ }
930
+ stop() {
931
+ if (this.debounceTimer) {
932
+ clearTimeout(this.debounceTimer);
933
+ this.debounceTimer = null;
934
+ }
935
+ if (this.watcher) {
936
+ this.watcher.close();
937
+ this.watcher = null;
938
+ }
939
+ }
940
+ };
941
+ }
942
+ });
943
+
944
+ // src/PM/golingvuBuild.ts
945
+ var golingvuBuild_exports = {};
946
+ __export(golingvuBuild_exports, {
947
+ GolingvuBuild: () => GolingvuBuild
948
+ });
949
+ var GolingvuBuild;
950
+ var init_golingvuBuild = __esm({
951
+ "src/PM/golingvuBuild.ts"() {
952
+ "use strict";
953
+ init_golingvuMetafile();
954
+ init_golingvuWatcher();
955
+ GolingvuBuild = class {
956
+ constructor(config, testName2) {
957
+ this.watcher = null;
958
+ this.config = config;
959
+ this.testName = testName2;
960
+ }
961
+ async build() {
962
+ const golangTests = this.config.tests.filter((test) => test[1] === "golang");
963
+ const hasGolangTests = golangTests.length > 0;
964
+ if (hasGolangTests) {
965
+ const golangEntryPoints = golangTests.map((test) => test[0]);
966
+ const metafile = await generateGolingvuMetafile(this.testName, golangEntryPoints);
967
+ writeGolingvuMetafile(this.testName, metafile);
968
+ this.watcher = new GolingvuWatcher(this.testName, golangEntryPoints);
969
+ await this.watcher.start();
970
+ return golangEntryPoints;
971
+ }
972
+ return [];
973
+ }
974
+ async rebuild() {
975
+ if (this.watcher) {
976
+ await this.watcher.regenerateMetafile();
977
+ }
978
+ }
979
+ stop() {
980
+ if (this.watcher) {
981
+ this.watcher.stop();
982
+ this.watcher = null;
983
+ }
984
+ }
985
+ onBundleChange(callback) {
986
+ if (this.watcher) {
987
+ this.watcher.onMetafileChange(callback);
988
+ }
989
+ }
990
+ };
991
+ }
992
+ });
993
+
128
994
  // src/utils/queue.ts
129
995
  var Queue;
130
996
  var init_queue = __esm({
@@ -167,38 +1033,44 @@ var init_queue = __esm({
167
1033
 
168
1034
  // src/PM/utils.ts
169
1035
  import ansiC from "ansi-colors";
170
- import path3 from "path";
171
- import fs from "fs";
1036
+ import path6 from "path";
1037
+ import fs5 from "fs";
172
1038
  import crypto from "node:crypto";
173
1039
  function runtimeLogs(runtime, reportDest) {
174
1040
  const safeDest = reportDest || `testeranto/reports/default_${Date.now()}`;
175
1041
  try {
176
- if (!fs.existsSync(safeDest)) {
177
- fs.mkdirSync(safeDest, { recursive: true });
1042
+ if (!fs5.existsSync(safeDest)) {
1043
+ fs5.mkdirSync(safeDest, { recursive: true });
178
1044
  }
179
1045
  if (runtime === "node") {
180
1046
  return {
181
- stdout: fs.createWriteStream(`${safeDest}/stdout.log`),
182
- stderr: fs.createWriteStream(`${safeDest}/stderr.log`),
183
- exit: fs.createWriteStream(`${safeDest}/exit.log`)
1047
+ stdout: fs5.createWriteStream(`${safeDest}/stdout.log`),
1048
+ stderr: fs5.createWriteStream(`${safeDest}/stderr.log`),
1049
+ exit: fs5.createWriteStream(`${safeDest}/exit.log`)
184
1050
  };
185
1051
  } else if (runtime === "web") {
186
1052
  return {
187
- info: fs.createWriteStream(`${safeDest}/info.log`),
188
- warn: fs.createWriteStream(`${safeDest}/warn.log`),
189
- error: fs.createWriteStream(`${safeDest}/error.log`),
190
- debug: fs.createWriteStream(`${safeDest}/debug.log`),
191
- exit: fs.createWriteStream(`${safeDest}/exit.log`)
1053
+ info: fs5.createWriteStream(`${safeDest}/info.log`),
1054
+ warn: fs5.createWriteStream(`${safeDest}/warn.log`),
1055
+ error: fs5.createWriteStream(`${safeDest}/error.log`),
1056
+ debug: fs5.createWriteStream(`${safeDest}/debug.log`),
1057
+ exit: fs5.createWriteStream(`${safeDest}/exit.log`)
192
1058
  };
193
1059
  } else if (runtime === "pure") {
194
1060
  return {
195
- exit: fs.createWriteStream(`${safeDest}/exit.log`)
1061
+ exit: fs5.createWriteStream(`${safeDest}/exit.log`)
196
1062
  };
197
- } else if (runtime === "pitono") {
1063
+ } else if (runtime === "python") {
198
1064
  return {
199
- stdout: fs.createWriteStream(`${safeDest}/stdout.log`),
200
- stderr: fs.createWriteStream(`${safeDest}/stderr.log`),
201
- exit: fs.createWriteStream(`${safeDest}/exit.log`)
1065
+ stdout: fs5.createWriteStream(`${safeDest}/stdout.log`),
1066
+ stderr: fs5.createWriteStream(`${safeDest}/stderr.log`),
1067
+ exit: fs5.createWriteStream(`${safeDest}/exit.log`)
1068
+ };
1069
+ } else if (runtime === "golang") {
1070
+ return {
1071
+ stdout: fs5.createWriteStream(`${safeDest}/stdout.log`),
1072
+ stderr: fs5.createWriteStream(`${safeDest}/stderr.log`),
1073
+ exit: fs5.createWriteStream(`${safeDest}/exit.log`)
202
1074
  };
203
1075
  } else {
204
1076
  throw `unknown runtime: ${runtime}`;
@@ -209,13 +1081,13 @@ function runtimeLogs(runtime, reportDest) {
209
1081
  }
210
1082
  }
211
1083
  function createLogStreams(reportDest, runtime) {
212
- if (!fs.existsSync(reportDest)) {
213
- fs.mkdirSync(reportDest, { recursive: true });
1084
+ if (!fs5.existsSync(reportDest)) {
1085
+ fs5.mkdirSync(reportDest, { recursive: true });
214
1086
  }
215
1087
  const safeDest = reportDest || `testeranto/reports/default_${Date.now()}`;
216
1088
  try {
217
- if (!fs.existsSync(safeDest)) {
218
- fs.mkdirSync(safeDest, { recursive: true });
1089
+ if (!fs5.existsSync(safeDest)) {
1090
+ fs5.mkdirSync(safeDest, { recursive: true });
219
1091
  }
220
1092
  const streams = runtimeLogs(runtime, safeDest);
221
1093
  return {
@@ -248,13 +1120,13 @@ ${error.stack}
248
1120
  async function fileHash(filePath, algorithm = "md5") {
249
1121
  return new Promise((resolve, reject) => {
250
1122
  const hash = crypto.createHash(algorithm);
251
- const fileStream = fs.createReadStream(filePath);
1123
+ const fileStream = fs5.createReadStream(filePath);
252
1124
  fileStream.on("data", (data) => {
253
1125
  hash.update(data);
254
1126
  });
255
1127
  fileStream.on("end", () => {
256
- const fileHash2 = hash.digest("hex");
257
- resolve(fileHash2);
1128
+ const fileHash3 = hash.digest("hex");
1129
+ resolve(fileHash3);
258
1130
  });
259
1131
  fileStream.on("error", (error) => {
260
1132
  reject(`Error reading file: ${error.message}`);
@@ -262,10 +1134,10 @@ async function fileHash(filePath, algorithm = "md5") {
262
1134
  });
263
1135
  }
264
1136
  async function writeFileAndCreateDir(filePath, data) {
265
- const dirPath = path3.dirname(filePath);
1137
+ const dirPath = path6.dirname(filePath);
266
1138
  try {
267
- await fs.promises.mkdir(dirPath, { recursive: true });
268
- await fs.writeFileSync(filePath, data);
1139
+ await fs5.promises.mkdir(dirPath, { recursive: true });
1140
+ await fs5.writeFileSync(filePath, data);
269
1141
  } catch (error) {
270
1142
  console.error(`Error writing file: ${error}`);
271
1143
  }
@@ -278,10 +1150,10 @@ function isValidUrl(string) {
278
1150
  return false;
279
1151
  }
280
1152
  }
281
- async function pollForFile(path12, timeout = 2e3) {
1153
+ async function pollForFile(path14, timeout = 2e3) {
282
1154
  const intervalObj = setInterval(function() {
283
- const file = path12;
284
- const fileExists = fs.existsSync(file);
1155
+ const file = path14;
1156
+ const fileExists = fs5.existsSync(file);
285
1157
  if (fileExists) {
286
1158
  clearInterval(intervalObj);
287
1159
  }
@@ -311,8 +1183,8 @@ var init_utils2 = __esm({
311
1183
  filesHash = async (files3, algorithm = "md5") => {
312
1184
  return new Promise((resolve, reject) => {
313
1185
  resolve(
314
- files3.reduce(async (mm, f2) => {
315
- return await mm + await fileHash(f2);
1186
+ files3.reduce(async (mm, f) => {
1187
+ return await mm + await fileHash(f);
316
1188
  }, Promise.resolve(""))
317
1189
  );
318
1190
  });
@@ -390,7 +1262,7 @@ var init_esbuildConfigs = __esm({
390
1262
  });
391
1263
 
392
1264
  // src/esbuildConfigs/inputFilesPlugin.ts
393
- import fs2 from "fs";
1265
+ import fs6 from "fs";
394
1266
  var otherInputs, register, inputFilesPlugin_default;
395
1267
  var init_inputFilesPlugin = __esm({
396
1268
  "src/esbuildConfigs/inputFilesPlugin.ts"() {
@@ -403,9 +1275,9 @@ var init_inputFilesPlugin = __esm({
403
1275
  sources.forEach((s) => otherInputs[entrypoint].add(s));
404
1276
  };
405
1277
  inputFilesPlugin_default = (platform, testName2) => {
406
- const f2 = `testeranto/metafiles/${platform}/${testName2}.json`;
407
- if (!fs2.existsSync(`testeranto/metafiles/${platform}`)) {
408
- fs2.mkdirSync(`testeranto/metafiles/${platform}`, { recursive: true });
1278
+ const f = `testeranto/metafiles/${platform}/${testName2}.json`;
1279
+ if (!fs6.existsSync(`testeranto/metafiles/${platform}`)) {
1280
+ fs6.mkdirSync(`testeranto/metafiles/${platform}`, { recursive: true });
409
1281
  }
410
1282
  return {
411
1283
  register,
@@ -413,7 +1285,7 @@ var init_inputFilesPlugin = __esm({
413
1285
  name: "metafileWriter",
414
1286
  setup(build) {
415
1287
  build.onEnd((result) => {
416
- fs2.writeFileSync(f2, JSON.stringify(result, null, 2));
1288
+ fs6.writeFileSync(f, JSON.stringify(result, null, 2));
417
1289
  });
418
1290
  }
419
1291
  }
@@ -423,7 +1295,7 @@ var init_inputFilesPlugin = __esm({
423
1295
  });
424
1296
 
425
1297
  // src/esbuildConfigs/featuresPlugin.ts
426
- import path4 from "path";
1298
+ import path7 from "path";
427
1299
  var featuresPlugin_default;
428
1300
  var init_featuresPlugin = __esm({
429
1301
  "src/esbuildConfigs/featuresPlugin.ts"() {
@@ -435,7 +1307,7 @@ var init_featuresPlugin = __esm({
435
1307
  if (args.resolveDir === "")
436
1308
  return;
437
1309
  return {
438
- path: path4.isAbsolute(args.path) ? args.path : path4.join(args.resolveDir, args.path),
1310
+ path: path7.isAbsolute(args.path) ? args.path : path7.join(args.resolveDir, args.path),
439
1311
  namespace: "feature-markdown"
440
1312
  };
441
1313
  });
@@ -462,7 +1334,7 @@ var init_featuresPlugin = __esm({
462
1334
  });
463
1335
 
464
1336
  // src/esbuildConfigs/rebuildPlugin.ts
465
- import fs3 from "fs";
1337
+ import fs7 from "fs";
466
1338
  var rebuildPlugin_default;
467
1339
  var init_rebuildPlugin = __esm({
468
1340
  "src/esbuildConfigs/rebuildPlugin.ts"() {
@@ -474,7 +1346,7 @@ var init_rebuildPlugin = __esm({
474
1346
  build.onEnd((result) => {
475
1347
  console.log(`${r} > build ended with ${result.errors.length} errors`);
476
1348
  if (result.errors.length > 0) {
477
- fs3.writeFileSync(
1349
+ fs7.writeFileSync(
478
1350
  `./testeranto/reports${r}_build_errors`,
479
1351
  JSON.stringify(result, null, 2)
480
1352
  );
@@ -504,7 +1376,7 @@ var init_node = __esm({
504
1376
  ...esbuildConfigs_default(config),
505
1377
  splitting: true,
506
1378
  outdir: `testeranto/bundles/node/${testName2}/`,
507
- inject: [`./node_modules/testeranto/dist/cjs-shim.js`],
1379
+ // inject: [`./node_modules/testeranto/dist/cjs-shim.js`],
508
1380
  metafile: true,
509
1381
  supported: {
510
1382
  "dynamic-import": true
@@ -532,7 +1404,7 @@ var init_node = __esm({
532
1404
 
533
1405
  // src/esbuildConfigs/web.ts
534
1406
  import { polyfillNode } from "esbuild-plugin-polyfill-node";
535
- import path5 from "path";
1407
+ import path8 from "path";
536
1408
  var web_default;
537
1409
  var init_web = __esm({
538
1410
  "src/esbuildConfigs/web.ts"() {
@@ -551,7 +1423,7 @@ var init_web = __esm({
551
1423
  treeShaking: true,
552
1424
  outdir: `testeranto/bundles/web/${testName2}`,
553
1425
  alias: {
554
- react: path5.resolve("./node_modules/react")
1426
+ react: path8.resolve("./node_modules/react")
555
1427
  },
556
1428
  metafile: true,
557
1429
  external: [
@@ -596,7 +1468,7 @@ var init_web = __esm({
596
1468
  });
597
1469
 
598
1470
  // src/esbuildConfigs/consoleDetectorPlugin.ts
599
- import fs4 from "fs";
1471
+ import fs8 from "fs";
600
1472
  var consoleDetectorPlugin;
601
1473
  var init_consoleDetectorPlugin = __esm({
602
1474
  "src/esbuildConfigs/consoleDetectorPlugin.ts"() {
@@ -605,7 +1477,7 @@ var init_consoleDetectorPlugin = __esm({
605
1477
  name: "console-detector",
606
1478
  setup(build) {
607
1479
  build.onLoad({ filter: /\.(js|ts)$/ }, async (args) => {
608
- const contents = await fs4.promises.readFile(args.path, "utf8");
1480
+ const contents = await fs8.promises.readFile(args.path, "utf8");
609
1481
  const consolePattern = /console\.(log|error|warn|info|debug|trace|dir|dirxml|table|group|groupEnd|clear|count|countReset|assert|profile|profileEnd|time|timeLog|timeEnd|timeStamp|context|memory)/g;
610
1482
  const matches = contents.match(consolePattern);
611
1483
  if (matches) {
@@ -700,8 +1572,8 @@ var init_pure = __esm({
700
1572
  });
701
1573
 
702
1574
  // src/PM/base.ts
703
- import fs5 from "fs";
704
- import path6 from "path";
1575
+ import fs9 from "fs";
1576
+ import path9 from "path";
705
1577
  var fileStreams3, fPaths, files, recorders, screenshots, PM_Base;
706
1578
  var init_base = __esm({
707
1579
  "src/PM/base.ts"() {
@@ -824,8 +1696,8 @@ var init_base = __esm({
824
1696
  }
825
1697
  async screencast(ssOpts, testName2, page) {
826
1698
  const p = ssOpts.path;
827
- const dir = path6.dirname(p);
828
- fs5.mkdirSync(dir, {
1699
+ const dir = path9.dirname(p);
1700
+ fs9.mkdirSync(dir, {
829
1701
  recursive: true
830
1702
  });
831
1703
  if (!files[testName2]) {
@@ -845,8 +1717,8 @@ var init_base = __esm({
845
1717
  }
846
1718
  async customScreenShot(ssOpts, testName2, pageUid) {
847
1719
  const p = ssOpts.path;
848
- const dir = path6.dirname(p);
849
- fs5.mkdirSync(dir, {
1720
+ const dir = path9.dirname(p);
1721
+ fs9.mkdirSync(dir, {
850
1722
  recursive: true
851
1723
  });
852
1724
  if (!files[testName2]) {
@@ -872,11 +1744,11 @@ var init_base = __esm({
872
1744
  return true;
873
1745
  }
874
1746
  existsSync(destFolder) {
875
- return fs5.existsSync(destFolder);
1747
+ return fs9.existsSync(destFolder);
876
1748
  }
877
1749
  async mkdirSync(fp) {
878
- if (!fs5.existsSync(fp)) {
879
- return fs5.mkdirSync(fp, {
1750
+ if (!fs9.existsSync(fp)) {
1751
+ return fs9.mkdirSync(fp, {
880
1752
  recursive: true
881
1753
  });
882
1754
  }
@@ -887,27 +1759,27 @@ var init_base = __esm({
887
1759
  const contents = x[1];
888
1760
  const testName2 = x[2];
889
1761
  return new Promise(async (res) => {
890
- fs5.mkdirSync(path6.dirname(filepath), {
1762
+ fs9.mkdirSync(path9.dirname(filepath), {
891
1763
  recursive: true
892
1764
  });
893
1765
  if (!files[testName2]) {
894
1766
  files[testName2] = /* @__PURE__ */ new Set();
895
1767
  }
896
1768
  files[testName2].add(filepath);
897
- await fs5.writeFileSync(filepath, contents);
1769
+ await fs9.writeFileSync(filepath, contents);
898
1770
  res(true);
899
1771
  });
900
1772
  }
901
1773
  async createWriteStream(filepath, testName2) {
902
1774
  const folder = filepath.split("/").slice(0, -1).join("/");
903
1775
  return new Promise((res) => {
904
- if (!fs5.existsSync(folder)) {
905
- return fs5.mkdirSync(folder, {
1776
+ if (!fs9.existsSync(folder)) {
1777
+ return fs9.mkdirSync(folder, {
906
1778
  recursive: true
907
1779
  });
908
1780
  }
909
- const f2 = fs5.createWriteStream(filepath);
910
- fileStreams3.push(f2);
1781
+ const f = fs9.createWriteStream(filepath);
1782
+ fileStreams3.push(f);
911
1783
  if (!files[testName2]) {
912
1784
  files[testName2] = /* @__PURE__ */ new Set();
913
1785
  }
@@ -920,15 +1792,15 @@ var init_base = __esm({
920
1792
  callback(
921
1793
  new Promise((res, rej) => {
922
1794
  tLog("testArtiFactory =>", fPath);
923
- const cleanPath = path6.resolve(fPath);
1795
+ const cleanPath = path9.resolve(fPath);
924
1796
  fPaths.push(cleanPath.replace(process.cwd(), ``));
925
1797
  const targetDir = cleanPath.split("/").slice(0, -1).join("/");
926
- fs5.mkdir(targetDir, { recursive: true }, async (error) => {
1798
+ fs9.mkdir(targetDir, { recursive: true }, async (error) => {
927
1799
  if (error) {
928
1800
  console.error(`\u2757\uFE0FtestArtiFactory failed`, targetDir, error);
929
1801
  }
930
- fs5.writeFileSync(
931
- path6.resolve(
1802
+ fs9.writeFileSync(
1803
+ path9.resolve(
932
1804
  targetDir.split("/").slice(0, -1).join("/"),
933
1805
  "manifest"
934
1806
  ),
@@ -939,16 +1811,16 @@ var init_base = __esm({
939
1811
  }
940
1812
  );
941
1813
  if (Buffer.isBuffer(value)) {
942
- fs5.writeFileSync(fPath, value, "binary");
1814
+ fs9.writeFileSync(fPath, value, "binary");
943
1815
  res();
944
1816
  } else if (`string` === typeof value) {
945
- fs5.writeFileSync(fPath, value.toString(), {
1817
+ fs9.writeFileSync(fPath, value.toString(), {
946
1818
  encoding: "utf-8"
947
1819
  });
948
1820
  res();
949
1821
  } else {
950
1822
  const pipeStream = value;
951
- const myFile = fs5.createWriteStream(fPath);
1823
+ const myFile = fs9.createWriteStream(fPath);
952
1824
  pipeStream.pipe(myFile);
953
1825
  pipeStream.on("close", () => {
954
1826
  myFile.close();
@@ -1029,7 +1901,7 @@ var init_base = __esm({
1029
1901
 
1030
1902
  // src/PM/PM_WithWebSocket.ts
1031
1903
  import { spawn } from "node:child_process";
1032
- import fs6 from "fs";
1904
+ import fs10 from "fs";
1033
1905
  import http from "http";
1034
1906
  import url from "url";
1035
1907
  import mime from "mime-types";
@@ -1054,7 +1926,18 @@ var init_PM_WithWebSocket = __esm({
1054
1926
  ws.on("message", (data) => {
1055
1927
  try {
1056
1928
  const message = JSON.parse(data.toString());
1057
- if (message.type === "executeCommand") {
1929
+ if (message.type === "chatMessage") {
1930
+ console.log(`Received chat message: ${message.content}`);
1931
+ if (this.handleChatMessage) {
1932
+ this.handleChatMessage(message.content);
1933
+ } else {
1934
+ console.log("PM_WithHelpo not available - message not processed");
1935
+ }
1936
+ return;
1937
+ }
1938
+ if (message.type === "listDirectory") {
1939
+ this.handleWebSocketListDirectory(ws, message);
1940
+ } else if (message.type === "executeCommand") {
1058
1941
  const executeMessage = message;
1059
1942
  if (message.command && message.command.trim().startsWith("aider")) {
1060
1943
  console.log(`Executing command: ${message.command}`);
@@ -1220,6 +2103,21 @@ var init_PM_WithWebSocket = __esm({
1220
2103
  processExists: !!childProcess
1221
2104
  });
1222
2105
  }
2106
+ } else if (message.type === "getChatHistory") {
2107
+ if (this.getChatHistory) {
2108
+ this.getChatHistory().then((history) => {
2109
+ ws.send(JSON.stringify({
2110
+ type: "chatHistory",
2111
+ messages: history
2112
+ }));
2113
+ }).catch((error) => {
2114
+ console.error("Error getting chat history:", error);
2115
+ ws.send(JSON.stringify({
2116
+ type: "error",
2117
+ message: "Failed to get chat history"
2118
+ }));
2119
+ });
2120
+ }
1223
2121
  }
1224
2122
  } catch (error) {
1225
2123
  console.error("Error handling WebSocket message:", error);
@@ -1240,8 +2138,12 @@ var init_PM_WithWebSocket = __esm({
1240
2138
  });
1241
2139
  }
1242
2140
  requestHandler(req, res) {
1243
- const parsedUrl = url.parse(req.url || "/");
2141
+ const parsedUrl = url.parse(req.url || "/", true);
1244
2142
  const pathname = parsedUrl.pathname || "/";
2143
+ if (pathname?.startsWith("/api/files/")) {
2144
+ this.handleFilesApi(req, res);
2145
+ return;
2146
+ }
1245
2147
  if (pathname === "/health") {
1246
2148
  res.writeHead(200, { "Content-Type": "application/json" });
1247
2149
  res.end(
@@ -1269,7 +2171,7 @@ var init_PM_WithWebSocket = __esm({
1269
2171
  ];
1270
2172
  let foundPath = null;
1271
2173
  for (const possiblePath of possiblePaths) {
1272
- if (fs6.existsSync(possiblePath)) {
2174
+ if (fs10.existsSync(possiblePath)) {
1273
2175
  foundPath = possiblePath;
1274
2176
  break;
1275
2177
  }
@@ -1279,7 +2181,7 @@ var init_PM_WithWebSocket = __esm({
1279
2181
  } else {
1280
2182
  const indexPath = this.findIndexHtml();
1281
2183
  if (indexPath) {
1282
- fs6.readFile(indexPath, (err, data) => {
2184
+ fs10.readFile(indexPath, (err, data) => {
1283
2185
  if (err) {
1284
2186
  res.writeHead(404, { "Content-Type": "text/plain" });
1285
2187
  res.end("404 Not Found");
@@ -1296,12 +2198,12 @@ var init_PM_WithWebSocket = __esm({
1296
2198
  }
1297
2199
  }
1298
2200
  }
1299
- fs6.exists(filePath, (exists) => {
2201
+ fs10.exists(filePath, (exists) => {
1300
2202
  if (!exists) {
1301
2203
  if (!processedPathname.includes(".") && processedPathname !== "/") {
1302
2204
  const indexPath = this.findIndexHtml();
1303
2205
  if (indexPath) {
1304
- fs6.readFile(indexPath, (err, data) => {
2206
+ fs10.readFile(indexPath, (err, data) => {
1305
2207
  if (err) {
1306
2208
  res.writeHead(404, { "Content-Type": "text/plain" });
1307
2209
  res.end("404 Not Found");
@@ -1328,7 +2230,7 @@ var init_PM_WithWebSocket = __esm({
1328
2230
  res.end("404 Not Found");
1329
2231
  return;
1330
2232
  }
1331
- fs6.readFile(filePath, (err, data) => {
2233
+ fs10.readFile(filePath, (err, data) => {
1332
2234
  if (err) {
1333
2235
  res.writeHead(500, { "Content-Type": "text/plain" });
1334
2236
  res.end("500 Internal Server Error");
@@ -1359,6 +2261,121 @@ var init_PM_WithWebSocket = __esm({
1359
2261
  });
1360
2262
  });
1361
2263
  }
2264
+ handleFilesApi(req, res) {
2265
+ const parsedUrl = url.parse(req.url || "/", true);
2266
+ const pathname = parsedUrl.pathname || "/";
2267
+ const query = parsedUrl.query || {};
2268
+ res.setHeader("Access-Control-Allow-Origin", "*");
2269
+ res.setHeader("Access-Control-Allow-Methods", "GET, POST, OPTIONS");
2270
+ res.setHeader("Access-Control-Allow-Headers", "Content-Type");
2271
+ if (req.method === "OPTIONS") {
2272
+ res.writeHead(200);
2273
+ res.end();
2274
+ return;
2275
+ }
2276
+ try {
2277
+ if (pathname === "/api/files/list" && req.method === "GET") {
2278
+ this.handleListDirectory(req, res, query);
2279
+ } else if (pathname === "/api/files/read" && req.method === "GET") {
2280
+ this.handleReadFile(req, res, query);
2281
+ } else if (pathname === "/api/files/exists" && req.method === "GET") {
2282
+ this.handleFileExists(req, res, query);
2283
+ } else {
2284
+ res.writeHead(404, { "Content-Type": "application/json" });
2285
+ res.end(JSON.stringify({ error: "Not found" }));
2286
+ }
2287
+ } catch (error) {
2288
+ res.writeHead(500, { "Content-Type": "application/json" });
2289
+ res.end(JSON.stringify({ error: "Internal server error" }));
2290
+ }
2291
+ }
2292
+ async handleListDirectory(req, res, query) {
2293
+ const path14 = query.path;
2294
+ if (!path14) {
2295
+ res.writeHead(400, { "Content-Type": "application/json" });
2296
+ res.end(JSON.stringify({ error: "Path parameter required" }));
2297
+ return;
2298
+ }
2299
+ try {
2300
+ const fullPath = this.resolvePath(path14);
2301
+ const items = await this.listDirectory(fullPath);
2302
+ res.writeHead(200, { "Content-Type": "application/json" });
2303
+ res.end(JSON.stringify(items));
2304
+ } catch (error) {
2305
+ console.error("Error listing directory:", error);
2306
+ res.writeHead(500, { "Content-Type": "application/json" });
2307
+ res.end(JSON.stringify({ error: "Failed to list directory" }));
2308
+ }
2309
+ }
2310
+ async handleReadFile(req, res, query) {
2311
+ const path14 = query.path;
2312
+ if (!path14) {
2313
+ res.writeHead(400, { "Content-Type": "application/json" });
2314
+ res.end(JSON.stringify({ error: "Path parameter required" }));
2315
+ return;
2316
+ }
2317
+ try {
2318
+ const fullPath = this.resolvePath(path14);
2319
+ const content = await fs10.promises.readFile(fullPath, "utf-8");
2320
+ res.writeHead(200, { "Content-Type": "text/plain" });
2321
+ res.end(content);
2322
+ } catch (error) {
2323
+ console.error("Error reading file:", error);
2324
+ res.writeHead(500, { "Content-Type": "application/json" });
2325
+ res.end(JSON.stringify({ error: "Failed to read file" }));
2326
+ }
2327
+ }
2328
+ async handleFileExists(req, res, query) {
2329
+ const path14 = query.path;
2330
+ if (!path14) {
2331
+ res.writeHead(400, { "Content-Type": "application/json" });
2332
+ res.end(JSON.stringify({ error: "Path parameter required" }));
2333
+ return;
2334
+ }
2335
+ try {
2336
+ const fullPath = this.resolvePath(path14);
2337
+ const exists = fs10.existsSync(fullPath);
2338
+ res.writeHead(200, { "Content-Type": "application/json" });
2339
+ res.end(JSON.stringify({ exists }));
2340
+ } catch (error) {
2341
+ console.error("Error checking file existence:", error);
2342
+ res.writeHead(500, { "Content-Type": "application/json" });
2343
+ res.end(JSON.stringify({ error: "Failed to check file existence" }));
2344
+ }
2345
+ }
2346
+ resolvePath(requestedPath) {
2347
+ const normalizedPath = requestedPath.replace(/\.\./g, "").replace(/^\//, "").replace(/\/+/g, "/");
2348
+ return `${process.cwd()}/${normalizedPath}`;
2349
+ }
2350
+ async listDirectory(dirPath) {
2351
+ try {
2352
+ const items = await fs10.promises.readdir(dirPath, { withFileTypes: true });
2353
+ const result = [];
2354
+ for (const item of items) {
2355
+ if (item.name.startsWith("."))
2356
+ continue;
2357
+ const fullPath = `${dirPath}/${item.name}`;
2358
+ const relativePath = fullPath.replace(process.cwd(), "").replace(/^\//, "");
2359
+ if (item.isDirectory()) {
2360
+ result.push({
2361
+ name: item.name,
2362
+ type: "folder",
2363
+ path: "/" + relativePath
2364
+ });
2365
+ } else if (item.isFile()) {
2366
+ result.push({
2367
+ name: item.name,
2368
+ type: "file",
2369
+ path: "/" + relativePath
2370
+ });
2371
+ }
2372
+ }
2373
+ return result;
2374
+ } catch (error) {
2375
+ console.error("Error listing directory:", error);
2376
+ throw error;
2377
+ }
2378
+ }
1362
2379
  findIndexHtml() {
1363
2380
  const possiblePaths = [
1364
2381
  "dist/index.html",
@@ -1366,9 +2383,9 @@ var init_PM_WithWebSocket = __esm({
1366
2383
  "../dist/index.html",
1367
2384
  "./index.html"
1368
2385
  ];
1369
- for (const path12 of possiblePaths) {
1370
- if (fs6.existsSync(path12)) {
1371
- return path12;
2386
+ for (const path14 of possiblePaths) {
2387
+ if (fs10.existsSync(path14)) {
2388
+ return path14;
1372
2389
  }
1373
2390
  }
1374
2391
  return null;
@@ -1449,6 +2466,31 @@ var init_PM_WithWebSocket = __esm({
1449
2466
  });
1450
2467
  return processId;
1451
2468
  }
2469
+ async handleWebSocketListDirectory(ws, message) {
2470
+ try {
2471
+ const path14 = message.path;
2472
+ if (!path14) {
2473
+ ws.send(JSON.stringify({
2474
+ type: "error",
2475
+ message: "Path parameter required"
2476
+ }));
2477
+ return;
2478
+ }
2479
+ const fullPath = this.resolvePath(path14);
2480
+ const items = await this.listDirectory(fullPath);
2481
+ ws.send(JSON.stringify({
2482
+ type: "directoryListing",
2483
+ path: path14,
2484
+ items
2485
+ }));
2486
+ } catch (error) {
2487
+ console.error("Error handling WebSocket directory listing:", error);
2488
+ ws.send(JSON.stringify({
2489
+ type: "error",
2490
+ message: "Failed to list directory"
2491
+ }));
2492
+ }
2493
+ }
1452
2494
  broadcast(message) {
1453
2495
  const data = typeof message === "string" ? message : JSON.stringify(message);
1454
2496
  this.clients.forEach((client) => {
@@ -1576,7 +2618,9 @@ var init_PM_WithBuild = __esm({
1576
2618
  runtime
1577
2619
  );
1578
2620
  }
1579
- console.log(`Starting ${runtime} build for ${entryPointKeys.length} entry points`);
2621
+ console.log(
2622
+ `Starting ${runtime} build for ${entryPointKeys.length} entry points`
2623
+ );
1580
2624
  if (self.broadcast) {
1581
2625
  self.broadcast({
1582
2626
  type: "buildEvent",
@@ -1598,9 +2642,13 @@ var init_PM_WithBuild = __esm({
1598
2642
  warnings: result.warnings.length
1599
2643
  };
1600
2644
  if (result.errors.length > 0) {
1601
- console.error(`Build ${runtime} failed with ${result.errors.length} errors`);
2645
+ console.error(
2646
+ `Build ${runtime} failed with ${result.errors.length} errors`
2647
+ );
1602
2648
  if (self.currentBuildReject) {
1603
- self.currentBuildReject(new Error(`Build failed with ${result.errors.length} errors`));
2649
+ self.currentBuildReject(
2650
+ new Error(`Build failed with ${result.errors.length} errors`)
2651
+ );
1604
2652
  }
1605
2653
  } else {
1606
2654
  console.log(`Build ${runtime} completed successfully`);
@@ -1622,15 +2670,18 @@ var init_PM_WithBuild = __esm({
1622
2670
  plugins: [...baseConfig.plugins || [], buildProcessTrackerPlugin]
1623
2671
  };
1624
2672
  try {
1625
- const ctx = await esbuild.context(configWithPlugin);
1626
2673
  if (this.mode === "dev") {
2674
+ const ctx = await esbuild.context(configWithPlugin);
2675
+ await ctx.rebuild();
1627
2676
  await ctx.watch();
1628
2677
  } else {
1629
- const result = await ctx.rebuild();
1630
- await ctx.dispose();
2678
+ const result = await esbuild.build(configWithPlugin);
2679
+ if (result.errors.length === 0) {
2680
+ console.log(`Successfully built ${runtime} bundle`);
2681
+ }
1631
2682
  }
1632
2683
  } catch (error) {
1633
- console.error(`Failed to start ${runtime} build context:`, error);
2684
+ console.error(`Failed to build ${runtime}:`, error);
1634
2685
  if (this.broadcast) {
1635
2686
  this.broadcast({
1636
2687
  type: "buildEvent",
@@ -1642,6 +2693,7 @@ var init_PM_WithBuild = __esm({
1642
2693
  message: error.message
1643
2694
  });
1644
2695
  }
2696
+ throw error;
1645
2697
  }
1646
2698
  }
1647
2699
  };
@@ -1691,8 +2743,16 @@ var init_logFiles = __esm({
1691
2743
  WARN: "warn.log",
1692
2744
  DEBUG: "debug.log"
1693
2745
  },
1694
- pure: {}
2746
+ pure: {},
1695
2747
  // No runtime-specific logs for pure
2748
+ python: {
2749
+ STDOUT: "stdout.log",
2750
+ STDERR: "stderr.log"
2751
+ },
2752
+ golang: {
2753
+ STDOUT: "stdout.log",
2754
+ STDERR: "stderr.log"
2755
+ }
1696
2756
  };
1697
2757
  ALL_LOGS = {
1698
2758
  ...STANDARD_LOGS,
@@ -1708,8 +2768,8 @@ var init_logFiles = __esm({
1708
2768
  });
1709
2769
 
1710
2770
  // src/utils/makePrompt.ts
1711
- import fs7 from "fs";
1712
- import path7 from "path";
2771
+ import fs11 from "fs";
2772
+ import path10 from "path";
1713
2773
  var makePrompt, makePromptInternal;
1714
2774
  var init_makePrompt = __esm({
1715
2775
  "src/utils/makePrompt.ts"() {
@@ -1720,23 +2780,23 @@ var init_makePrompt = __esm({
1720
2780
  makePrompt = async (summary, name, entryPoint, addableFiles, runtime) => {
1721
2781
  summary[entryPoint].prompt = "?";
1722
2782
  const promptPath = promptPather(entryPoint, runtime, name);
1723
- const testDir = path7.join(
2783
+ const testDir = path10.join(
1724
2784
  "testeranto",
1725
2785
  "reports",
1726
2786
  name,
1727
2787
  entryPoint.split(".").slice(0, -1).join("."),
1728
2788
  runtime
1729
2789
  );
1730
- if (!fs7.existsSync(testDir)) {
1731
- fs7.mkdirSync(testDir, { recursive: true });
2790
+ if (!fs11.existsSync(testDir)) {
2791
+ fs11.mkdirSync(testDir, { recursive: true });
1732
2792
  }
1733
- const testPaths = path7.join(testDir, LOG_FILES.TESTS);
1734
- const lintPath = path7.join(testDir, LOG_FILES.LINT_ERRORS);
1735
- const typePath = path7.join(testDir, LOG_FILES.TYPE_ERRORS);
1736
- const messagePath = path7.join(testDir, LOG_FILES.MESSAGE);
2793
+ const testPaths = path10.join(testDir, LOG_FILES.TESTS);
2794
+ const lintPath = path10.join(testDir, LOG_FILES.LINT_ERRORS);
2795
+ const typePath = path10.join(testDir, LOG_FILES.TYPE_ERRORS);
2796
+ const messagePath = path10.join(testDir, LOG_FILES.MESSAGE);
1737
2797
  try {
1738
2798
  await Promise.all([
1739
- fs7.promises.writeFile(
2799
+ fs11.promises.writeFile(
1740
2800
  promptPath,
1741
2801
  `
1742
2802
  ${addableFiles.map((x) => {
@@ -1752,10 +2812,10 @@ ${addableFiles.map((x) => {
1752
2812
  /read ${typePath}
1753
2813
  /read ${lintPath}
1754
2814
 
1755
- /read ${getLogFilesForRuntime(runtime).map((p) => `${testDir}/${p}`).join(" ")}
2815
+ /read ${getLogFilesForRuntime(runtime).map((p) => `${testDir}/${p}`).join("\n/read ")}
1756
2816
  `
1757
2817
  ),
1758
- fs7.promises.writeFile(
2818
+ fs11.promises.writeFile(
1759
2819
  messagePath,
1760
2820
  `
1761
2821
  There are 3 types of test reports.
@@ -1794,13 +2854,20 @@ Do not add error throwing/catching to the tests themselves.
1794
2854
  if (runTime === "pure") {
1795
2855
  return makePrompt(summary, name, entryPoint, addableFiles, "pure");
1796
2856
  }
2857
+ if (runTime === "golang") {
2858
+ return makePrompt(summary, name, entryPoint, addableFiles, "golang");
2859
+ }
2860
+ if (runTime === "python") {
2861
+ return makePrompt(summary, name, entryPoint, addableFiles, "python");
2862
+ }
2863
+ throw `unknown runTime: ${runTime}`;
1797
2864
  };
1798
2865
  }
1799
2866
  });
1800
2867
 
1801
2868
  // src/PM/PM_WithEslintAndTsc.ts
1802
2869
  import ts from "typescript";
1803
- import fs8 from "fs";
2870
+ import fs12 from "fs";
1804
2871
  import ansiC2 from "ansi-colors";
1805
2872
  import { ESLint } from "eslint";
1806
2873
  import tsc from "tsc-prog";
@@ -1863,7 +2930,7 @@ var init_PM_WithEslintAndTsc = __esm({
1863
2930
  );
1864
2931
  }
1865
2932
  });
1866
- fs8.writeFileSync(tscPath, results.join("\n"));
2933
+ fs12.writeFileSync(tscPath, results.join("\n"));
1867
2934
  this.typeCheckIsNowDone(entrypoint, results.length);
1868
2935
  return results.length;
1869
2936
  })();
@@ -1889,15 +2956,15 @@ var init_PM_WithEslintAndTsc = __esm({
1889
2956
  throw new Error(`Error in eslintCheck: ${e.message}`);
1890
2957
  }
1891
2958
  const filepath = lintPather(entrypoint, platform, this.name);
1892
- if (fs8.existsSync(filepath))
1893
- fs8.rmSync(filepath);
2959
+ if (fs12.existsSync(filepath))
2960
+ fs12.rmSync(filepath);
1894
2961
  const results = (await eslint.lintFiles(addableFiles)).filter((r) => r.messages.length).filter((r) => {
1895
2962
  return r.messages[0].ruleId !== null;
1896
2963
  }).map((r) => {
1897
2964
  delete r.source;
1898
2965
  return r;
1899
2966
  });
1900
- fs8.writeFileSync(filepath, await formatter.format(results));
2967
+ fs12.writeFileSync(filepath, await formatter.format(results));
1901
2968
  this.lintIsNowDone(entrypoint, results.length);
1902
2969
  return results.length;
1903
2970
  })();
@@ -1984,7 +3051,7 @@ var init_PM_WithEslintAndTsc = __esm({
1984
3051
  this.writeBigBoard = () => {
1985
3052
  const summaryPath = `./testeranto/reports/${this.name}/summary.json`;
1986
3053
  const summaryData = JSON.stringify(this.summary, null, 2);
1987
- fs8.writeFileSync(summaryPath, summaryData);
3054
+ fs12.writeFileSync(summaryPath, summaryData);
1988
3055
  this.broadcast({
1989
3056
  type: "summaryUpdate",
1990
3057
  data: this.summary
@@ -2017,6 +3084,7 @@ var init_PM_WithEslintAndTsc = __esm({
2017
3084
  });
2018
3085
 
2019
3086
  // src/PM/PM_WithGit.ts
3087
+ import fs13 from "fs";
2020
3088
  import url2 from "url";
2021
3089
  var PM_WithGit;
2022
3090
  var init_PM_WithGit = __esm({
@@ -2121,14 +3189,14 @@ var init_PM_WithGit = __esm({
2121
3189
  const parsedUrl = url2.parse(req.url || "/");
2122
3190
  const query = parsedUrl.query || "";
2123
3191
  const params = new URLSearchParams(query);
2124
- const path12 = params.get("path");
2125
- if (!path12) {
3192
+ const path14 = params.get("path");
3193
+ if (!path14) {
2126
3194
  res.writeHead(400, { "Content-Type": "application/json" });
2127
3195
  res.end(JSON.stringify({ error: "Path parameter required" }));
2128
3196
  return;
2129
3197
  }
2130
3198
  try {
2131
- const status = await this.getGitFileStatus(path12);
3199
+ const status = await this.getGitFileStatus(path14);
2132
3200
  res.writeHead(200, { "Content-Type": "application/json" });
2133
3201
  res.end(JSON.stringify(status));
2134
3202
  } catch (error) {
@@ -2230,10 +3298,10 @@ var init_PM_WithGit = __esm({
2230
3298
  res.end(JSON.stringify({ error: "Failed to get remote status" }));
2231
3299
  }
2232
3300
  }
2233
- async getGitFileStatus(path12) {
3301
+ async getGitFileStatus(path14) {
2234
3302
  try {
2235
3303
  const changes2 = await this.getGitChanges();
2236
- const fileChange = changes2.find((change) => change.path === path12);
3304
+ const fileChange = changes2.find((change) => change.path === path14);
2237
3305
  if (fileChange) {
2238
3306
  return { status: fileChange.status };
2239
3307
  }
@@ -2386,11 +3454,12 @@ ${description}` : message;
2386
3454
  const { exec } = await import("child_process");
2387
3455
  return new Promise((resolve, reject) => {
2388
3456
  exec(
2389
- "git status --porcelain",
3457
+ "git status --porcelain=v1",
2390
3458
  { cwd: process.cwd() },
2391
- (error, stdout, stderr) => {
3459
+ async (error, stdout, stderr) => {
3460
+ if (stderr) {
3461
+ }
2392
3462
  if (error) {
2393
- console.error("Error getting git changes:", error);
2394
3463
  resolve([]);
2395
3464
  return;
2396
3465
  }
@@ -2399,23 +3468,40 @@ ${description}` : message;
2399
3468
  for (const line of lines) {
2400
3469
  if (!line.trim())
2401
3470
  continue;
2402
- const status = line.substring(0, 2).trim();
2403
- const path12 = line.substring(3).trim();
3471
+ const match = line.match(/^(.{2}) (.*)$/);
3472
+ if (!match) {
3473
+ continue;
3474
+ }
3475
+ const status = match[1];
3476
+ let path14 = match[2];
3477
+ if (status === "R " && path14.includes(" -> ")) {
3478
+ const parts = path14.split(" -> ");
3479
+ path14 = parts[parts.length - 1];
3480
+ }
3481
+ path14 = path14.trim();
2404
3482
  let fileStatus = "unchanged";
2405
- if (status.startsWith("M")) {
3483
+ const firstChar = status.charAt(0);
3484
+ if (firstChar === "M" || firstChar === " ") {
2406
3485
  fileStatus = "modified";
2407
- } else if (status.startsWith("A")) {
3486
+ } else if (firstChar === "A") {
2408
3487
  fileStatus = "added";
2409
- } else if (status.startsWith("D")) {
3488
+ } else if (firstChar === "D") {
2410
3489
  fileStatus = "deleted";
2411
- } else if (status.startsWith("U") || status.includes("U")) {
3490
+ } else if (firstChar === "U") {
2412
3491
  fileStatus = "conflicted";
2413
- } else if (status.startsWith("??")) {
3492
+ } else if (status === "??") {
2414
3493
  fileStatus = "added";
3494
+ } else if (status === "R ") {
3495
+ fileStatus = "modified";
2415
3496
  }
2416
3497
  if (fileStatus !== "unchanged") {
3498
+ const fullPath = `${process.cwd()}/${path14}`;
3499
+ try {
3500
+ await fs13.promises.access(fullPath);
3501
+ } catch (error2) {
3502
+ }
2417
3503
  changes2.push({
2418
- path: path12,
3504
+ path: path14,
2419
3505
  status: fileStatus
2420
3506
  });
2421
3507
  }
@@ -2425,7 +3511,6 @@ ${description}` : message;
2425
3511
  );
2426
3512
  });
2427
3513
  } catch (error) {
2428
- console.error("Failed to get git changes:", error);
2429
3514
  return [];
2430
3515
  }
2431
3516
  }
@@ -2478,25 +3563,24 @@ ${description}` : message;
2478
3563
  });
2479
3564
 
2480
3565
  // src/PM/PM_WithProcesses.ts
2481
- import fs9, { watch } from "fs";
2482
- import path8 from "path";
3566
+ import fs14, { watch } from "fs";
3567
+ import path11 from "path";
2483
3568
  import puppeteer, { executablePath as executablePath2 } from "puppeteer-core";
2484
3569
  import ansiC3 from "ansi-colors";
2485
- var fileHashes, changes, PM_WithProcesses;
3570
+ var changes, PM_WithProcesses;
2486
3571
  var init_PM_WithProcesses = __esm({
2487
3572
  async "src/PM/PM_WithProcesses.ts"() {
2488
3573
  "use strict";
2489
3574
  init_utils();
2490
3575
  init_utils2();
2491
3576
  await init_PM_WithGit();
2492
- fileHashes = {};
2493
3577
  changes = {};
2494
3578
  PM_WithProcesses = class extends PM_WithGit {
2495
3579
  constructor(configs, name, mode2) {
2496
3580
  super(configs, name, mode2);
2497
3581
  this.logStreams = {};
2498
3582
  this.receiveFeaturesV2 = (reportDest, srcTest, platform) => {
2499
- const featureDestination = path8.resolve(
3583
+ const featureDestination = path11.resolve(
2500
3584
  process.cwd(),
2501
3585
  "reports",
2502
3586
  "features",
@@ -2504,25 +3588,25 @@ var init_PM_WithProcesses = __esm({
2504
3588
  srcTest.split(".").slice(0, -1).join(".") + ".features.txt"
2505
3589
  );
2506
3590
  const testReportPath = `${reportDest}/tests.json`;
2507
- if (!fs9.existsSync(testReportPath)) {
3591
+ if (!fs14.existsSync(testReportPath)) {
2508
3592
  console.error(`tests.json not found at: ${testReportPath}`);
2509
3593
  return;
2510
3594
  }
2511
- const testReport = JSON.parse(fs9.readFileSync(testReportPath, "utf8"));
3595
+ const testReport = JSON.parse(fs14.readFileSync(testReportPath, "utf8"));
2512
3596
  if (testReport.tests) {
2513
3597
  testReport.tests.forEach((test) => {
2514
- test.fullPath = path8.resolve(process.cwd(), srcTest);
3598
+ test.fullPath = path11.resolve(process.cwd(), srcTest);
2515
3599
  });
2516
3600
  }
2517
- testReport.fullPath = path8.resolve(process.cwd(), srcTest);
2518
- fs9.writeFileSync(testReportPath, JSON.stringify(testReport, null, 2));
3601
+ testReport.fullPath = path11.resolve(process.cwd(), srcTest);
3602
+ fs14.writeFileSync(testReportPath, JSON.stringify(testReport, null, 2));
2519
3603
  testReport.features.reduce(async (mm, featureStringKey) => {
2520
3604
  const accum = await mm;
2521
3605
  const isUrl = isValidUrl(featureStringKey);
2522
3606
  if (isUrl) {
2523
3607
  const u = new URL(featureStringKey);
2524
3608
  if (u.protocol === "file:") {
2525
- const newPath = `${process.cwd()}/testeranto/features/internal/${path8.relative(
3609
+ const newPath = `${process.cwd()}/testeranto/features/internal/${path11.relative(
2526
3610
  process.cwd(),
2527
3611
  u.pathname
2528
3612
  )}`;
@@ -2534,17 +3618,17 @@ var init_PM_WithProcesses = __esm({
2534
3618
  accum.files.push(newPath);
2535
3619
  }
2536
3620
  } else {
2537
- await fs9.promises.mkdir(path8.dirname(featureDestination), {
3621
+ await fs14.promises.mkdir(path11.dirname(featureDestination), {
2538
3622
  recursive: true
2539
3623
  });
2540
3624
  accum.strings.push(featureStringKey);
2541
3625
  }
2542
3626
  return accum;
2543
3627
  }, Promise.resolve({ files: [], strings: [] })).then(({ files: files3, strings }) => {
2544
- fs9.writeFileSync(
3628
+ fs14.writeFileSync(
2545
3629
  `testeranto/reports/${this.name}/${srcTest.split(".").slice(0, -1).join(".")}/${platform}/featurePrompt.txt`,
2546
- files3.map((f2) => {
2547
- return `/read ${f2}`;
3630
+ files3.map((f) => {
3631
+ return `/read ${f}`;
2548
3632
  }).join("\n")
2549
3633
  );
2550
3634
  });
@@ -2616,6 +3700,15 @@ var init_PM_WithProcesses = __esm({
2616
3700
  this.ports[element] = "";
2617
3701
  });
2618
3702
  }
3703
+ bddTestIsRunning(src) {
3704
+ this.summary[src] = {
3705
+ prompt: "?",
3706
+ runTimeErrors: "?",
3707
+ staticErrors: "?",
3708
+ typeErrors: "?",
3709
+ failingFeatures: {}
3710
+ };
3711
+ }
2619
3712
  async metafileOutputs(platform) {
2620
3713
  let metafilePath;
2621
3714
  if (platform === "python") {
@@ -2623,19 +3716,9 @@ var init_PM_WithProcesses = __esm({
2623
3716
  } else {
2624
3717
  metafilePath = `./testeranto/metafiles/${platform}/${this.name}.json`;
2625
3718
  }
2626
- if (!fs9.existsSync(metafilePath)) {
2627
- if (platform === "python") {
2628
- console.log(
2629
- ansiC3.yellow(
2630
- ansiC3.inverse(`Pitono metafile not found yet: ${metafilePath}`)
2631
- )
2632
- );
2633
- }
2634
- return;
2635
- }
2636
3719
  let metafile;
2637
3720
  try {
2638
- const fileContent = fs9.readFileSync(metafilePath).toString();
3721
+ const fileContent = fs14.readFileSync(metafilePath).toString();
2639
3722
  const parsedData = JSON.parse(fileContent);
2640
3723
  if (platform === "python") {
2641
3724
  metafile = parsedData.metafile || parsedData;
@@ -2653,12 +3736,6 @@ var init_PM_WithProcesses = __esm({
2653
3736
  return;
2654
3737
  }
2655
3738
  const outputs = metafile.outputs;
2656
- if (!outputs || typeof outputs !== "object") {
2657
- console.log(
2658
- ansiC3.yellow(ansiC3.inverse(`No outputs found in metafile at ${metafilePath}`))
2659
- );
2660
- return;
2661
- }
2662
3739
  Object.keys(outputs).forEach(async (k) => {
2663
3740
  const pattern = `testeranto/bundles/${platform}/${this.name}/${this.configs.src}`;
2664
3741
  if (!k.startsWith(pattern)) {
@@ -2669,7 +3746,7 @@ var init_PM_WithProcesses = __esm({
2669
3746
  return;
2670
3747
  }
2671
3748
  const addableFiles = Object.keys(output.inputs).filter((i) => {
2672
- if (!fs9.existsSync(i))
3749
+ if (!fs14.existsSync(i))
2673
3750
  return false;
2674
3751
  if (i.startsWith("node_modules"))
2675
3752
  return false;
@@ -2677,27 +3754,162 @@ var init_PM_WithProcesses = __esm({
2677
3754
  return false;
2678
3755
  return true;
2679
3756
  });
2680
- const f2 = `${k.split(".").slice(0, -1).join(".")}/`;
2681
- if (!fs9.existsSync(f2)) {
2682
- fs9.mkdirSync(f2, { recursive: true });
3757
+ const f = `${k.split(".").slice(0, -1).join(".")}/`;
3758
+ if (!fs14.existsSync(f)) {
3759
+ fs14.mkdirSync(f, { recursive: true });
2683
3760
  }
2684
- const entrypoint = output.entryPoint;
3761
+ let entrypoint = output.entryPoint;
2685
3762
  if (entrypoint) {
3763
+ entrypoint = path11.normalize(entrypoint);
2686
3764
  const changeDigest = await filesHash(addableFiles);
2687
3765
  if (changeDigest === changes[entrypoint]) {
2688
3766
  } else {
2689
3767
  changes[entrypoint] = changeDigest;
2690
- this.tscCheck({
2691
- platform,
2692
- addableFiles,
2693
- entrypoint
2694
- });
2695
- this.eslintCheck(entrypoint, platform, addableFiles);
3768
+ if (platform === "node" || platform === "web" || platform === "pure") {
3769
+ this.tscCheck({
3770
+ platform,
3771
+ addableFiles,
3772
+ entrypoint
3773
+ });
3774
+ this.eslintCheck(entrypoint, platform, addableFiles);
3775
+ } else if (platform === "python") {
3776
+ this.pythonLintCheck(entrypoint, addableFiles);
3777
+ this.pythonTypeCheck(entrypoint, addableFiles);
3778
+ }
2696
3779
  this.makePrompt(entrypoint, addableFiles, platform);
3780
+ const testName2 = this.findTestNameByEntrypoint(entrypoint, platform);
3781
+ if (testName2) {
3782
+ console.log(
3783
+ ansiC3.green(
3784
+ ansiC3.inverse(
3785
+ `Source files changed, re-queueing test: ${testName2}`
3786
+ )
3787
+ )
3788
+ );
3789
+ this.addToQueue(testName2, platform);
3790
+ } else {
3791
+ console.error(
3792
+ `Could not find test for entrypoint: ${entrypoint} (${platform})`
3793
+ );
3794
+ process.exit(-1);
3795
+ }
2697
3796
  }
2698
3797
  }
2699
3798
  });
2700
3799
  }
3800
+ findTestNameByEntrypoint(entrypoint, platform) {
3801
+ const runnables = getRunnables(this.configs.tests, this.name);
3802
+ let entryPointsMap;
3803
+ switch (platform) {
3804
+ case "node":
3805
+ entryPointsMap = runnables.nodeEntryPoints;
3806
+ break;
3807
+ case "web":
3808
+ entryPointsMap = runnables.webEntryPoints;
3809
+ break;
3810
+ case "pure":
3811
+ entryPointsMap = runnables.pureEntryPoints;
3812
+ break;
3813
+ case "python":
3814
+ entryPointsMap = runnables.pythonEntryPoints;
3815
+ break;
3816
+ case "golang":
3817
+ entryPointsMap = runnables.golangEntryPoints;
3818
+ break;
3819
+ default:
3820
+ throw "wtf";
3821
+ }
3822
+ if (!entryPointsMap) {
3823
+ console.error("idk");
3824
+ }
3825
+ if (!entryPointsMap[entrypoint]) {
3826
+ console.error("idk2");
3827
+ }
3828
+ return entryPointsMap[entrypoint];
3829
+ }
3830
+ async pythonLintCheck(entrypoint, addableFiles) {
3831
+ const reportDest = `testeranto/reports/${this.name}/${entrypoint.split(".").slice(0, -1).join(".")}/python`;
3832
+ if (!fs14.existsSync(reportDest)) {
3833
+ fs14.mkdirSync(reportDest, { recursive: true });
3834
+ }
3835
+ const lintErrorsPath = `${reportDest}/lint_errors.txt`;
3836
+ try {
3837
+ const { spawn: spawn4 } = await import("child_process");
3838
+ const child = spawn4("flake8", [entrypoint, "--max-line-length=88"], {
3839
+ stdio: ["pipe", "pipe", "pipe"]
3840
+ });
3841
+ let stderr = "";
3842
+ child.stderr.on("data", (data) => {
3843
+ stderr += data.toString();
3844
+ });
3845
+ let stdout = "";
3846
+ child.stdout.on("data", (data) => {
3847
+ stdout += data.toString();
3848
+ });
3849
+ return new Promise((resolve) => {
3850
+ child.on("close", (code) => {
3851
+ const output = stdout + stderr;
3852
+ if (output.trim()) {
3853
+ fs14.writeFileSync(lintErrorsPath, output);
3854
+ this.summary[entrypoint].staticErrors = output.split("\n").length;
3855
+ } else {
3856
+ if (fs14.existsSync(lintErrorsPath)) {
3857
+ fs14.unlinkSync(lintErrorsPath);
3858
+ }
3859
+ this.summary[entrypoint].staticErrors = 0;
3860
+ }
3861
+ resolve();
3862
+ });
3863
+ });
3864
+ } catch (error) {
3865
+ console.error(`Error running flake8 on ${entrypoint}:`, error);
3866
+ fs14.writeFileSync(
3867
+ lintErrorsPath,
3868
+ `Error running flake8: ${error.message}`
3869
+ );
3870
+ this.summary[entrypoint].staticErrors = -1;
3871
+ }
3872
+ }
3873
+ async pythonTypeCheck(entrypoint, addableFiles) {
3874
+ const reportDest = `testeranto/reports/${this.name}/${entrypoint.split(".").slice(0, -1).join(".")}/python`;
3875
+ if (!fs14.existsSync(reportDest)) {
3876
+ fs14.mkdirSync(reportDest, { recursive: true });
3877
+ }
3878
+ const typeErrorsPath = `${reportDest}/type_errors.txt`;
3879
+ try {
3880
+ const { spawn: spawn4 } = await import("child_process");
3881
+ const child = spawn4("mypy", [entrypoint], {
3882
+ stdio: ["pipe", "pipe", "pipe"]
3883
+ });
3884
+ let stderr = "";
3885
+ child.stderr.on("data", (data) => {
3886
+ stderr += data.toString();
3887
+ });
3888
+ let stdout = "";
3889
+ child.stdout.on("data", (data) => {
3890
+ stdout += data.toString();
3891
+ });
3892
+ return new Promise((resolve) => {
3893
+ child.on("close", (code) => {
3894
+ const output = stdout + stderr;
3895
+ if (output.trim()) {
3896
+ fs14.writeFileSync(typeErrorsPath, output);
3897
+ this.summary[entrypoint].typeErrors = output.split("\n").length;
3898
+ } else {
3899
+ if (fs14.existsSync(typeErrorsPath)) {
3900
+ fs14.unlinkSync(typeErrorsPath);
3901
+ }
3902
+ this.summary[entrypoint].typeErrors = 0;
3903
+ }
3904
+ resolve();
3905
+ });
3906
+ });
3907
+ } catch (error) {
3908
+ console.error(`Error running mypy on ${entrypoint}:`, error);
3909
+ fs14.writeFileSync(typeErrorsPath, `Error running mypy: ${error.message}`);
3910
+ this.summary[entrypoint].typeErrors = -1;
3911
+ }
3912
+ }
2701
3913
  async start() {
2702
3914
  try {
2703
3915
  await this.startBuildProcesses();
@@ -2709,8 +3921,8 @@ var init_PM_WithProcesses = __esm({
2709
3921
  this.mapping().forEach(async ([command, func]) => {
2710
3922
  globalThis[command] = func;
2711
3923
  });
2712
- if (!fs9.existsSync(`testeranto/reports/${this.name}`)) {
2713
- fs9.mkdirSync(`testeranto/reports/${this.name}`);
3924
+ if (!fs14.existsSync(`testeranto/reports/${this.name}`)) {
3925
+ fs14.mkdirSync(`testeranto/reports/${this.name}`);
2714
3926
  }
2715
3927
  try {
2716
3928
  this.browser = await puppeteer.launch(puppeteerConfigs);
@@ -2721,132 +3933,92 @@ var init_PM_WithProcesses = __esm({
2721
3933
  executablePath2
2722
3934
  );
2723
3935
  }
3936
+ const runnables = getRunnables(this.configs.tests, this.name);
2724
3937
  const {
2725
3938
  nodeEntryPoints,
2726
3939
  webEntryPoints,
2727
3940
  pureEntryPoints,
2728
3941
  pythonEntryPoints,
2729
3942
  golangEntryPoints
2730
- } = getRunnables(this.configs.tests, this.name);
3943
+ } = runnables;
3944
+ console.log(
3945
+ ansiC3.blue(
3946
+ `Runnables for ${this.name}:
3947
+ Node: ${JSON.stringify(nodeEntryPoints, null, 2)}
3948
+ Web: ${JSON.stringify(webEntryPoints, null, 2)}
3949
+ Pure: ${JSON.stringify(pureEntryPoints, null, 2)}
3950
+ Python: ${JSON.stringify(pythonEntryPoints, null, 2)}
3951
+ Golang: ${JSON.stringify(golangEntryPoints, null, 2)}`
3952
+ )
3953
+ );
2731
3954
  [
2732
- [
2733
- nodeEntryPoints,
2734
- this.launchNode,
2735
- "node",
2736
- (w) => {
2737
- this.nodeMetafileWatcher = w;
2738
- }
2739
- ],
2740
- [
2741
- webEntryPoints,
2742
- this.launchWeb,
2743
- "web",
2744
- (w) => {
2745
- this.webMetafileWatcher = w;
2746
- }
2747
- ],
2748
- [
2749
- pureEntryPoints,
2750
- this.launchPure,
2751
- "pure",
2752
- (w) => {
2753
- this.importMetafileWatcher = w;
2754
- }
2755
- ],
2756
- [
2757
- pythonEntryPoints,
2758
- this.launchPython,
2759
- "python",
2760
- (w) => {
2761
- this.pitonoMetafileWatcher = w;
3955
+ ["node", nodeEntryPoints],
3956
+ ["web", webEntryPoints],
3957
+ ["pure", pureEntryPoints],
3958
+ ["python", pythonEntryPoints],
3959
+ ["golang", golangEntryPoints]
3960
+ ].forEach(([runtime, entryPoints]) => {
3961
+ Object.keys(entryPoints).forEach((entryPoint) => {
3962
+ const reportDest = `testeranto/reports/${this.name}/${entryPoint.split(".").slice(0, -1).join(".")}/${runtime}`;
3963
+ if (!fs14.existsSync(reportDest)) {
3964
+ fs14.mkdirSync(reportDest, { recursive: true });
2762
3965
  }
2763
- ],
2764
- [
2765
- golangEntryPoints,
2766
- this.launchGolang,
2767
- "golang",
2768
- (w) => {
2769
- }
2770
- ]
3966
+ this.addToQueue(entryPoint, runtime);
3967
+ });
3968
+ });
3969
+ [
3970
+ ["node", nodeEntryPoints],
3971
+ ["web", webEntryPoints],
3972
+ ["pure", pureEntryPoints],
3973
+ ["python", pythonEntryPoints],
3974
+ ["golang", golangEntryPoints]
2771
3975
  ].forEach(
2772
- async ([eps, launcher, runtime, watcher]) => {
2773
- let metafile;
2774
- if (runtime === "python") {
2775
- metafile = `./testeranto/metafiles/python/core.json`;
2776
- const metafileDir = path8.dirname(metafile);
2777
- if (!fs9.existsSync(metafileDir)) {
2778
- fs9.mkdirSync(metafileDir, { recursive: true });
2779
- }
2780
- } else {
2781
- metafile = `./testeranto/metafiles/${runtime}/${this.name}.json`;
2782
- }
2783
- if (runtime !== "python") {
3976
+ async ([runtime, entryPoints]) => {
3977
+ if (Object.keys(entryPoints).length === 0)
3978
+ return;
3979
+ const metafile = `./testeranto/metafiles/${runtime}/${this.name}.json`;
3980
+ try {
2784
3981
  await pollForFile(metafile);
2785
- }
2786
- Object.entries(eps).forEach(
2787
- async ([inputFile, outputFile]) => {
2788
- this.launchers[inputFile] = () => launcher(inputFile, outputFile);
2789
- this.launchers[inputFile]();
2790
- try {
2791
- if (fs9.existsSync(outputFile)) {
2792
- watch(outputFile, async (e, filename) => {
2793
- const hash = await fileHash(outputFile);
2794
- if (fileHashes[inputFile] !== hash) {
2795
- fileHashes[inputFile] = hash;
2796
- console.log(
2797
- ansiC3.yellow(ansiC3.inverse(`< ${e} ${filename}`))
2798
- );
2799
- this.launchers[inputFile]();
2800
- }
2801
- });
2802
- } else {
2803
- console.log(
2804
- ansiC3.yellow(
2805
- ansiC3.inverse(
2806
- `File not found, skipping watch: ${outputFile}`
2807
- )
2808
- )
2809
- );
2810
- }
2811
- } catch (e) {
2812
- console.error(e);
2813
- }
2814
- }
2815
- );
2816
- this.metafileOutputs(runtime);
2817
- if (runtime === "python") {
2818
- const checkFileExists = () => {
2819
- if (fs9.existsSync(metafile)) {
3982
+ let timeoutId;
3983
+ const watcher = watch(metafile, async (e, filename) => {
3984
+ clearTimeout(timeoutId);
3985
+ timeoutId = setTimeout(async () => {
2820
3986
  console.log(
2821
- ansiC3.green(ansiC3.inverse(`Pitono metafile found: ${metafile}`))
2822
- );
2823
- watcher(
2824
- watch(metafile, async (e, filename) => {
2825
- console.log(
2826
- ansiC3.yellow(
2827
- ansiC3.inverse(`< ${e} ${filename} (${runtime})`)
2828
- )
2829
- );
2830
- this.metafileOutputs(runtime);
2831
- })
3987
+ ansiC3.yellow(ansiC3.inverse(`< ${e} ${filename} (${runtime})`))
2832
3988
  );
2833
- this.metafileOutputs(runtime);
2834
- } else {
2835
- setTimeout(checkFileExists, 1e3);
2836
- }
2837
- };
2838
- checkFileExists();
2839
- } else {
2840
- if (fs9.existsSync(metafile)) {
2841
- watcher(
2842
- watch(metafile, async (e, filename) => {
3989
+ try {
3990
+ await this.metafileOutputs(runtime);
2843
3991
  console.log(
2844
- ansiC3.yellow(ansiC3.inverse(`< ${e} ${filename} (${runtime})`))
3992
+ ansiC3.blue(
3993
+ `Metafile processed, checking queue for tests to run`
3994
+ )
2845
3995
  );
2846
- this.metafileOutputs(runtime);
2847
- })
2848
- );
3996
+ this.checkQueue();
3997
+ } catch (error) {
3998
+ console.error(`Error processing metafile changes:`, error);
3999
+ }
4000
+ }, 300);
4001
+ });
4002
+ switch (runtime) {
4003
+ case "node":
4004
+ this.nodeMetafileWatcher = watcher;
4005
+ break;
4006
+ case "web":
4007
+ this.webMetafileWatcher = watcher;
4008
+ break;
4009
+ case "pure":
4010
+ this.importMetafileWatcher = watcher;
4011
+ break;
4012
+ case "python":
4013
+ this.pitonoMetafileWatcher = watcher;
4014
+ break;
4015
+ case "golang":
4016
+ this.golangMetafileWatcher = watcher;
4017
+ break;
2849
4018
  }
4019
+ await this.metafileOutputs(runtime);
4020
+ } catch (error) {
4021
+ console.error(`Error setting up watcher for ${runtime}:`, error);
2850
4022
  }
2851
4023
  }
2852
4024
  );
@@ -2890,78 +4062,159 @@ var init_PM_WithProcesses = __esm({
2890
4062
  "../dist/index.html",
2891
4063
  "./index.html"
2892
4064
  ];
2893
- for (const path12 of possiblePaths) {
2894
- if (fs9.existsSync(path12)) {
2895
- return path12;
4065
+ for (const path14 of possiblePaths) {
4066
+ if (fs14.existsSync(path14)) {
4067
+ return path14;
2896
4068
  }
2897
4069
  }
2898
4070
  return null;
2899
4071
  }
2900
4072
  addToQueue(src, runtime) {
2901
- this.queue.push(src);
2902
- console.log(
2903
- ansiC3.green(
2904
- ansiC3.inverse(`Added ${src} (${runtime}) to the processing queue`)
2905
- )
2906
- );
2907
- this.checkQueue();
4073
+ if (src.includes("testeranto/bundles")) {
4074
+ const runnables = getRunnables(this.configs.tests, this.name);
4075
+ const allEntryPoints = [
4076
+ ...Object.entries(runnables.nodeEntryPoints),
4077
+ ...Object.entries(runnables.webEntryPoints),
4078
+ ...Object.entries(runnables.pureEntryPoints),
4079
+ ...Object.entries(runnables.pythonEntryPoints),
4080
+ ...Object.entries(runnables.golangEntryPoints)
4081
+ ];
4082
+ const normalizedSrc = path11.normalize(src);
4083
+ for (const [testName2, bundlePath] of allEntryPoints) {
4084
+ const normalizedBundlePath = path11.normalize(bundlePath);
4085
+ if (normalizedSrc.endsWith(normalizedBundlePath)) {
4086
+ src = testName2;
4087
+ break;
4088
+ }
4089
+ }
4090
+ }
4091
+ this.cleanupTestProcesses(src);
4092
+ if (!this.queue.includes(src)) {
4093
+ this.queue.push(src);
4094
+ console.log(
4095
+ ansiC3.green(
4096
+ ansiC3.inverse(`Added ${src} (${runtime}) to the processing queue`)
4097
+ )
4098
+ );
4099
+ this.checkQueue();
4100
+ } else {
4101
+ console.log(
4102
+ ansiC3.yellow(
4103
+ ansiC3.inverse(`Test ${src} is already in the queue, skipping`)
4104
+ )
4105
+ );
4106
+ }
2908
4107
  }
2909
- checkQueue() {
2910
- const x = this.queue.pop();
2911
- if (!x) {
2912
- ansiC3.inverse(`The following queue is empty`);
2913
- return;
4108
+ cleanupTestProcesses(testName2) {
4109
+ const processesToCleanup = [];
4110
+ for (const [processId, processInfo] of this.allProcesses.entries()) {
4111
+ if (processInfo.testName === testName2 && processInfo.status === "running") {
4112
+ processesToCleanup.push(processId);
4113
+ }
2914
4114
  }
2915
- const test = this.configs.tests.find((t) => t[0] === x);
2916
- if (!test)
2917
- throw `test is undefined ${x}`;
2918
- const runtime = test[1];
2919
- const runnables = getRunnables(this.configs.tests, this.name);
2920
- let dest;
2921
- switch (runtime) {
2922
- case "node":
2923
- dest = runnables.nodeEntryPoints[x];
2924
- if (dest) {
2925
- this.launchNode(x, dest);
2926
- } else {
2927
- console.error(`No destination found for node test: ${x}`);
4115
+ processesToCleanup.forEach((processId) => {
4116
+ const processInfo = this.allProcesses.get(processId);
4117
+ if (processInfo) {
4118
+ if (processInfo.child) {
4119
+ try {
4120
+ processInfo.child.kill();
4121
+ } catch (error) {
4122
+ console.error(`Error killing process ${processId}:`, error);
4123
+ }
2928
4124
  }
2929
- break;
2930
- case "web":
2931
- dest = runnables.webEntryPoints[x];
2932
- if (dest) {
2933
- this.launchWeb(x, dest);
2934
- } else {
2935
- console.error(`No destination found for web test: ${x}`);
2936
- }
2937
- break;
2938
- case "pure":
2939
- dest = runnables.pureEntryPoints[x];
2940
- if (dest) {
2941
- this.launchPure(x, dest);
2942
- } else {
2943
- console.error(`No destination found for pure test: ${x}`);
2944
- }
2945
- break;
2946
- case "python":
2947
- dest = runnables.pythonEntryPoints[x];
2948
- if (dest) {
2949
- this.launchPython(x, dest);
2950
- } else {
2951
- console.error(`No destination found for python test: ${x}`);
2952
- }
2953
- break;
2954
- case "golang":
2955
- dest = runnables.golangEntryPoints[x];
2956
- if (dest) {
2957
- this.launchGolang(x, dest);
2958
- } else {
2959
- console.error(`No destination found for golang test: ${x}`);
4125
+ this.allProcesses.set(processId, {
4126
+ ...processInfo,
4127
+ status: "exited",
4128
+ exitCode: -1,
4129
+ error: "Killed due to source file change"
4130
+ });
4131
+ this.runningProcesses.delete(processId);
4132
+ this.broadcast({
4133
+ type: "processExited",
4134
+ processId,
4135
+ exitCode: -1,
4136
+ timestamp: (/* @__PURE__ */ new Date()).toISOString(),
4137
+ logs: ["Process killed due to source file change"]
4138
+ });
4139
+ }
4140
+ });
4141
+ }
4142
+ checkQueue() {
4143
+ while (this.queue.length > 0) {
4144
+ const x = this.queue.pop();
4145
+ if (!x)
4146
+ continue;
4147
+ let isRunning = false;
4148
+ for (const processInfo of this.allProcesses.values()) {
4149
+ if (processInfo.testName === x && processInfo.status === "running") {
4150
+ isRunning = true;
4151
+ break;
2960
4152
  }
2961
- break;
2962
- default:
2963
- console.error(`Unknown runtime: ${runtime} for test ${x}`);
2964
- break;
4153
+ }
4154
+ if (isRunning) {
4155
+ console.log(
4156
+ ansiC3.yellow(
4157
+ `Skipping ${x} - already running, will be re-queued when current run completes`
4158
+ )
4159
+ );
4160
+ continue;
4161
+ }
4162
+ const test = this.configs.tests.find((t) => t[0] === x);
4163
+ if (!test) {
4164
+ console.error(`test is undefined ${x}`);
4165
+ continue;
4166
+ }
4167
+ const runtime = test[1];
4168
+ const runnables = getRunnables(this.configs.tests, this.name);
4169
+ let dest;
4170
+ switch (runtime) {
4171
+ case "node":
4172
+ dest = runnables.nodeEntryPoints[x];
4173
+ if (dest) {
4174
+ this.launchNode(x, dest);
4175
+ } else {
4176
+ console.error(`No destination found for node test: ${x}`);
4177
+ }
4178
+ break;
4179
+ case "web":
4180
+ dest = runnables.webEntryPoints[x];
4181
+ if (dest) {
4182
+ this.launchWeb(x, dest);
4183
+ } else {
4184
+ console.error(`No destination found for web test: ${x}`);
4185
+ }
4186
+ break;
4187
+ case "pure":
4188
+ dest = runnables.pureEntryPoints[x];
4189
+ if (dest) {
4190
+ this.launchPure(x, dest);
4191
+ } else {
4192
+ console.error(`No destination found for pure test: ${x}`);
4193
+ }
4194
+ break;
4195
+ case "python":
4196
+ dest = runnables.pythonEntryPoints[x];
4197
+ if (dest) {
4198
+ this.launchPython(x, dest);
4199
+ } else {
4200
+ console.error(`No destination found for python test: ${x}`);
4201
+ }
4202
+ break;
4203
+ case "golang":
4204
+ dest = runnables.golangEntryPoints[x];
4205
+ if (dest) {
4206
+ this.launchGolang(x, dest);
4207
+ } else {
4208
+ console.error(`No destination found for golang test: ${x}`);
4209
+ }
4210
+ break;
4211
+ default:
4212
+ console.error(`Unknown runtime: ${runtime} for test ${x}`);
4213
+ break;
4214
+ }
4215
+ }
4216
+ if (this.queue.length === 0) {
4217
+ console.log(ansiC3.inverse(`The queue is empty`));
2965
4218
  }
2966
4219
  }
2967
4220
  onBuildDone() {
@@ -2972,16 +4225,173 @@ var init_PM_WithProcesses = __esm({
2972
4225
  }
2973
4226
  });
2974
4227
 
4228
+ // src/PM/PM_WithHelpo.ts
4229
+ import { spawnSync } from "node:child_process";
4230
+ import fs15 from "fs";
4231
+ import path12 from "path";
4232
+ var PM_WithHelpo;
4233
+ var init_PM_WithHelpo = __esm({
4234
+ async "src/PM/PM_WithHelpo.ts"() {
4235
+ "use strict";
4236
+ await init_PM_WithProcesses();
4237
+ PM_WithHelpo = class extends PM_WithProcesses {
4238
+ constructor(configs, name, mode2) {
4239
+ super(configs, name, mode2);
4240
+ this.aiderProcess = null;
4241
+ this.MAX_HISTORY_SIZE = 10 * 1024;
4242
+ // 10KB
4243
+ this.isAiderAtPrompt = false;
4244
+ this.chatHistoryPath = path12.join(
4245
+ process.cwd(),
4246
+ "testeranto",
4247
+ "helpo_chat_history.json"
4248
+ );
4249
+ this.initializeChatHistory();
4250
+ this.startAiderProcess();
4251
+ }
4252
+ initializeChatHistory() {
4253
+ fs15.writeFileSync(this.chatHistoryPath, JSON.stringify([]));
4254
+ const messagePath = path12.join(
4255
+ process.cwd(),
4256
+ "testeranto",
4257
+ "helpo_chat_message.txt"
4258
+ );
4259
+ const messageDir = path12.dirname(messagePath);
4260
+ if (!fs15.existsSync(messageDir)) {
4261
+ fs15.mkdirSync(messageDir, { recursive: true });
4262
+ }
4263
+ fs15.writeFileSync(messagePath, "");
4264
+ }
4265
+ startAiderProcess() {
4266
+ }
4267
+ async processAiderResponse(response) {
4268
+ const cleanResponse = response.trim();
4269
+ if (!cleanResponse) {
4270
+ return;
4271
+ }
4272
+ const assistantMessage = {
4273
+ type: "assistant",
4274
+ content: cleanResponse,
4275
+ timestamp: (/* @__PURE__ */ new Date()).toISOString()
4276
+ };
4277
+ await this.addToChatHistory(assistantMessage);
4278
+ const history = await this.getChatHistory();
4279
+ this.broadcast({
4280
+ type: "chatHistory",
4281
+ messages: history
4282
+ });
4283
+ await this.trimChatHistory();
4284
+ }
4285
+ restartAiderProcess() {
4286
+ if (this.aiderProcess) {
4287
+ this.aiderProcess.kill();
4288
+ }
4289
+ this.startAiderProcess();
4290
+ }
4291
+ isAiderAvailable() {
4292
+ try {
4293
+ const whichAider = spawnSync("which", ["aider"]);
4294
+ return whichAider.status === 0;
4295
+ } catch (error) {
4296
+ return false;
4297
+ }
4298
+ }
4299
+ async addToChatHistory(message) {
4300
+ const history = await this.getChatHistory();
4301
+ history.push(message);
4302
+ fs15.writeFileSync(this.chatHistoryPath, JSON.stringify(history, null, 2));
4303
+ console.log(
4304
+ `Added message to chat history: ${message.content.substring(0, 50)}...`
4305
+ );
4306
+ }
4307
+ async trimChatHistory() {
4308
+ const history = await this.getChatHistory();
4309
+ let currentSize = Buffer.from(JSON.stringify(history)).length;
4310
+ while (currentSize > this.MAX_HISTORY_SIZE && history.length > 0) {
4311
+ history.shift();
4312
+ currentSize = Buffer.from(JSON.stringify(history)).length;
4313
+ }
4314
+ fs15.writeFileSync(this.chatHistoryPath, JSON.stringify(history, null, 2));
4315
+ }
4316
+ async getChatHistory() {
4317
+ try {
4318
+ const data = fs15.readFileSync(this.chatHistoryPath, "utf-8");
4319
+ return JSON.parse(data);
4320
+ } catch (error) {
4321
+ return [];
4322
+ }
4323
+ }
4324
+ async handleChatMessage(userMessage) {
4325
+ const userChatMessage = {
4326
+ type: "user",
4327
+ content: userMessage,
4328
+ timestamp: (/* @__PURE__ */ new Date()).toISOString()
4329
+ };
4330
+ await this.addToChatHistory(userChatMessage);
4331
+ const history = await this.getChatHistory();
4332
+ this.broadcast({
4333
+ type: "chatHistory",
4334
+ messages: history
4335
+ });
4336
+ console.log(`User message recorded: ${userMessage}`);
4337
+ if (!this.aiderProcess) {
4338
+ console.log(
4339
+ "Aider process is not available - message recorded but not processed"
4340
+ );
4341
+ return;
4342
+ }
4343
+ setTimeout(() => {
4344
+ try {
4345
+ if (this.aiderProcess) {
4346
+ const messagePath = path12.join(
4347
+ process.cwd(),
4348
+ "testeranto",
4349
+ "helpo_chat_message.txt"
4350
+ );
4351
+ fs15.writeFileSync(messagePath, "");
4352
+ const ptyProcess = this.aiderProcess;
4353
+ ptyProcess.write(
4354
+ "PROCESS_CHAT_HISTORY_AND_RESPOND: Read the chat history and write your response ONLY to testeranto/helpo_chat_message.txt. Do NOT print to stdout.\n"
4355
+ );
4356
+ } else {
4357
+ console.log("Aider process is not available");
4358
+ }
4359
+ } catch (error) {
4360
+ console.error("Error writing to aider process:", error);
4361
+ }
4362
+ }, 100);
4363
+ }
4364
+ // Override WebSocket message handling to include chat messages
4365
+ setupWebSocketHandlers() {
4366
+ }
4367
+ // This method should be called when a WebSocket message is received
4368
+ handleWebSocketMessage(ws, message) {
4369
+ try {
4370
+ const parsedMessage = JSON.parse(message.toString());
4371
+ if (parsedMessage.type === "chatMessage") {
4372
+ this.handleChatMessage(parsedMessage.content);
4373
+ } else {
4374
+ super.handleWebSocketMessage?.(ws, message);
4375
+ }
4376
+ } catch (error) {
4377
+ console.error("Error handling WebSocket message:", error);
4378
+ }
4379
+ }
4380
+ };
4381
+ }
4382
+ });
4383
+
2975
4384
  // src/PM/main.ts
2976
4385
  var main_exports = {};
2977
4386
  __export(main_exports, {
2978
4387
  PM_Main: () => PM_Main
2979
4388
  });
2980
- import { spawn as spawn2 } from "node:child_process";
4389
+ import { spawn as spawn3 } from "node:child_process";
2981
4390
  import ansiColors from "ansi-colors";
2982
4391
  import net from "net";
2983
- import fs10 from "fs";
4392
+ import fs16 from "fs";
2984
4393
  import ansiC4 from "ansi-colors";
4394
+ import path13 from "node:path";
2985
4395
  var files2, screenshots2, PM_Main;
2986
4396
  var init_main = __esm({
2987
4397
  async "src/PM/main.ts"() {
@@ -2989,20 +4399,21 @@ var init_main = __esm({
2989
4399
  init_utils();
2990
4400
  init_queue();
2991
4401
  init_utils2();
2992
- await init_PM_WithProcesses();
4402
+ await init_PM_WithHelpo();
2993
4403
  files2 = {};
2994
4404
  screenshots2 = {};
2995
- PM_Main = class extends PM_WithProcesses {
4405
+ PM_Main = class extends PM_WithHelpo {
2996
4406
  constructor() {
2997
4407
  super(...arguments);
2998
4408
  this.launchPure = async (src, dest) => {
4409
+ console.log(ansiC4.green(ansiC4.inverse(`pure < ${src}`)));
2999
4410
  const processId = `pure-${src}-${Date.now()}`;
3000
4411
  const command = `pure test: ${src}`;
3001
4412
  const purePromise = (async () => {
3002
4413
  this.bddTestIsRunning(src);
3003
4414
  const reportDest = `testeranto/reports/${this.name}/${src.split(".").slice(0, -1).join(".")}/pure`;
3004
- if (!fs10.existsSync(reportDest)) {
3005
- fs10.mkdirSync(reportDest, { recursive: true });
4415
+ if (!fs16.existsSync(reportDest)) {
4416
+ fs16.mkdirSync(reportDest, { recursive: true });
3006
4417
  }
3007
4418
  const destFolder = dest.replace(".mjs", "");
3008
4419
  let argz = "";
@@ -3065,6 +4476,22 @@ var init_main = __esm({
3065
4476
  `pure ! ${src} failed to execute. No "tests.json" file was generated. Check the logs for more info`
3066
4477
  )
3067
4478
  );
4479
+ const testsJsonPath = `${reportDest}/tests.json`;
4480
+ if (!fs16.existsSync(testsJsonPath)) {
4481
+ fs16.writeFileSync(
4482
+ testsJsonPath,
4483
+ JSON.stringify(
4484
+ {
4485
+ tests: [],
4486
+ features: [],
4487
+ givens: [],
4488
+ fullPath: src
4489
+ },
4490
+ null,
4491
+ 2
4492
+ )
4493
+ );
4494
+ }
3068
4495
  logs.exit.write(e2.stack);
3069
4496
  logs.exit.write(-1);
3070
4497
  this.bddTestIsNowDone(src, -1);
@@ -3073,6 +4500,22 @@ var init_main = __esm({
3073
4500
  });
3074
4501
  });
3075
4502
  } catch (e3) {
4503
+ const testsJsonPath = `${reportDest}/tests.json`;
4504
+ if (!fs16.existsSync(testsJsonPath)) {
4505
+ fs16.writeFileSync(
4506
+ testsJsonPath,
4507
+ JSON.stringify(
4508
+ {
4509
+ tests: [],
4510
+ features: [],
4511
+ givens: [],
4512
+ fullPath: src
4513
+ },
4514
+ null,
4515
+ 2
4516
+ )
4517
+ );
4518
+ }
3076
4519
  logs.writeExitCode(-1, e3);
3077
4520
  console.log(
3078
4521
  ansiC4.red(
@@ -3087,6 +4530,7 @@ var init_main = __esm({
3087
4530
  statusMessagePretty(-1, src, "pure");
3088
4531
  throw e3;
3089
4532
  } finally {
4533
+ await this.generatePromptFiles(reportDest, src);
3090
4534
  for (let i = 0; i <= portsToUse.length; i++) {
3091
4535
  if (portsToUse[i]) {
3092
4536
  this.ports[portsToUse[i]] = "";
@@ -3104,83 +4548,25 @@ var init_main = __esm({
3104
4548
  );
3105
4549
  };
3106
4550
  this.launchNode = async (src, dest) => {
4551
+ console.log(ansiC4.green(ansiC4.inverse(`node < ${src}`)));
3107
4552
  const processId = `node-${src}-${Date.now()}`;
3108
4553
  const command = `node test: ${src}`;
3109
4554
  const nodePromise = (async () => {
3110
- this.bddTestIsRunning(src);
3111
- const reportDest = `testeranto/reports/${this.name}/${src.split(".").slice(0, -1).join(".")}/node`;
3112
- if (!fs10.existsSync(reportDest)) {
3113
- fs10.mkdirSync(reportDest, { recursive: true });
3114
- }
3115
- let testResources = "";
3116
- const testConfig = this.configs.tests.find((t) => {
3117
- return t[0] === src;
3118
- });
3119
- if (!testConfig) {
3120
- console.log(
3121
- ansiC4.inverse(
3122
- `missing test config! Exiting ungracefully for '${src}'`
3123
- )
3124
- );
3125
- process.exit(-1);
3126
- }
3127
- const testConfigResource = testConfig[2];
3128
- const portsToUse = [];
3129
- if (testConfigResource.ports === 0) {
3130
- const t = {
3131
- name: src,
3132
- ports: [],
3133
- fs: reportDest,
3134
- browserWSEndpoint: this.browser.wsEndpoint()
3135
- };
3136
- testResources = JSON.stringify(t);
3137
- } else if (testConfigResource.ports > 0) {
3138
- const openPorts = Object.entries(this.ports).filter(
3139
- ([portnumber, portopen]) => portopen === ""
3140
- );
3141
- if (openPorts.length >= testConfigResource.ports) {
3142
- for (let i = 0; i < testConfigResource.ports; i++) {
3143
- portsToUse.push(openPorts[i][0]);
3144
- this.ports[openPorts[i][0]] = src;
3145
- }
3146
- testResources = JSON.stringify({
3147
- scheduled: true,
3148
- name: src,
3149
- ports: portsToUse,
3150
- fs: reportDest,
3151
- browserWSEndpoint: this.browser.wsEndpoint()
3152
- });
3153
- } else {
3154
- console.log(
3155
- ansiC4.red(
3156
- `node: cannot run ${src} because there are no open ports ATM. This job will be enqueued and run again run a port is available`
3157
- )
3158
- );
3159
- this.queue.push(src);
3160
- return [Math.random(), testResources];
3161
- }
3162
- } else {
3163
- console.error("negative port makes no sense", src);
3164
- process.exit(-1);
3165
- }
3166
- const builtfile = dest;
3167
- let haltReturns = false;
3168
- const ipcfile = "/tmp/tpipe_" + Math.random();
3169
- const child = spawn2("node", [builtfile, testResources, ipcfile], {
3170
- stdio: ["pipe", "pipe", "pipe", "ipc"]
3171
- });
3172
- let buffer = new Buffer("");
3173
- const server = net.createServer((socket) => {
4555
+ try {
4556
+ const { reportDest, testResources, portsToUse } = await this.setupTestEnvironment(src, "node");
4557
+ const builtfile = dest;
4558
+ const ipcfile = "/tmp/tpipe_" + Math.random();
4559
+ const logs = createLogStreams(reportDest, "node");
4560
+ let buffer = Buffer.from("");
3174
4561
  const queue = new Queue();
3175
- socket.on("data", (data) => {
4562
+ const onData = (data) => {
3176
4563
  buffer = Buffer.concat([buffer, data]);
3177
4564
  for (let b = 0; b < buffer.length + 1; b++) {
3178
4565
  const c = buffer.slice(0, b);
3179
- let d;
3180
4566
  try {
3181
- d = JSON.parse(c.toString());
4567
+ const d = JSON.parse(c.toString());
3182
4568
  queue.enqueue(d);
3183
- buffer = buffer.slice(b, buffer.length + 1);
4569
+ buffer = buffer.slice(b);
3184
4570
  b = 0;
3185
4571
  } catch (e) {
3186
4572
  }
@@ -3190,85 +4576,39 @@ var init_main = __esm({
3190
4576
  if (message) {
3191
4577
  this.mapping().forEach(async ([command2, func]) => {
3192
4578
  if (message[0] === command2) {
3193
- const x = message.slice(1, -1);
3194
- const r = await this[command2](...x);
3195
- if (!haltReturns) {
4579
+ const args = message.slice(1, -1);
4580
+ try {
4581
+ const result = await this[command2](...args);
3196
4582
  child.send(
3197
4583
  JSON.stringify({
3198
- payload: r,
4584
+ payload: result,
3199
4585
  key: message[message.length - 1]
3200
4586
  })
3201
4587
  );
4588
+ } catch (error) {
4589
+ console.error(`Error handling command ${command2}:`, error);
3202
4590
  }
3203
4591
  }
3204
4592
  });
3205
4593
  }
3206
4594
  }
4595
+ };
4596
+ const server = await this.createIpcServer(onData, ipcfile);
4597
+ const child = spawn3("node", [builtfile, testResources, ipcfile], {
4598
+ stdio: ["pipe", "pipe", "pipe", "ipc"]
3207
4599
  });
3208
- });
3209
- const logs = createLogStreams(reportDest, "node");
3210
- return new Promise((resolve, reject) => {
3211
- server.listen(ipcfile, () => {
3212
- child.stdout?.on("data", (data) => {
3213
- logs.stdout?.write(data);
3214
- });
3215
- child.stderr?.on("data", (data) => {
3216
- logs.stderr?.write(data);
3217
- });
3218
- child.on("close", (code) => {
3219
- const exitCode = code === null ? -1 : code;
3220
- if (exitCode < 0) {
3221
- logs.writeExitCode(
3222
- exitCode,
3223
- new Error("Process crashed or was terminated")
3224
- );
3225
- } else {
3226
- logs.writeExitCode(exitCode);
3227
- }
3228
- logs.closeAll();
3229
- server.close();
3230
- if (exitCode === 255) {
3231
- console.log(
3232
- ansiColors.red(
3233
- `node ! ${src} failed to execute. No "tests.json" file was generated. Check ${reportDest}/stderr.log for more info`
3234
- )
3235
- );
3236
- this.bddTestIsNowDone(src, -1);
3237
- statusMessagePretty(-1, src, "node");
3238
- reject(new Error(`Process exited with code ${exitCode}`));
3239
- } else if (exitCode === 0) {
3240
- this.bddTestIsNowDone(src, 0);
3241
- statusMessagePretty(0, src, "node");
3242
- resolve();
3243
- } else {
3244
- this.bddTestIsNowDone(src, exitCode);
3245
- statusMessagePretty(exitCode, src, "node");
3246
- reject(new Error(`Process exited with code ${exitCode}`));
3247
- }
3248
- haltReturns = true;
3249
- });
3250
- child.on("error", (e) => {
3251
- console.log("error");
3252
- haltReturns = true;
3253
- console.log(
3254
- ansiC4.red(
3255
- ansiC4.inverse(
3256
- `${src} errored with: ${e.name}. Check error logs for more info`
3257
- )
3258
- )
3259
- );
3260
- this.bddTestIsNowDone(src, -1);
3261
- statusMessagePretty(-1, src, "node");
3262
- reject(e);
3263
- });
3264
- });
3265
- }).finally(() => {
3266
- for (let i = 0; i <= portsToUse.length; i++) {
3267
- if (portsToUse[i]) {
3268
- this.ports[portsToUse[i]] = "";
3269
- }
4600
+ try {
4601
+ await this.handleChildProcess(child, logs, reportDest, src, "node");
4602
+ await this.generatePromptFiles(reportDest, src);
4603
+ } finally {
4604
+ server.close();
4605
+ this.cleanupPorts(portsToUse);
3270
4606
  }
3271
- });
4607
+ } catch (error) {
4608
+ if (error.message !== "No ports available") {
4609
+ throw error;
4610
+ }
4611
+ }
3272
4612
  })();
3273
4613
  this.addPromiseProcess(
3274
4614
  processId,
@@ -3280,13 +4620,14 @@ var init_main = __esm({
3280
4620
  );
3281
4621
  };
3282
4622
  this.launchWeb = async (src, dest) => {
4623
+ console.log(ansiC4.green(ansiC4.inverse(`web < ${src}`)));
3283
4624
  const processId = `web-${src}-${Date.now()}`;
3284
4625
  const command = `web test: ${src}`;
3285
4626
  const webPromise = (async () => {
3286
4627
  this.bddTestIsRunning(src);
3287
4628
  const reportDest = `testeranto/reports/${this.name}/${src.split(".").slice(0, -1).join(".")}/web`;
3288
- if (!fs10.existsSync(reportDest)) {
3289
- fs10.mkdirSync(reportDest, { recursive: true });
4629
+ if (!fs16.existsSync(reportDest)) {
4630
+ fs16.mkdirSync(reportDest, { recursive: true });
3290
4631
  }
3291
4632
  const destFolder = dest.replace(".mjs", "");
3292
4633
  const webArgz = JSON.stringify({
@@ -3373,9 +4714,26 @@ var init_main = __esm({
3373
4714
  )
3374
4715
  )
3375
4716
  );
4717
+ const testsJsonPath = `${reportDest}/tests.json`;
4718
+ if (!fs16.existsSync(testsJsonPath)) {
4719
+ fs16.writeFileSync(
4720
+ testsJsonPath,
4721
+ JSON.stringify(
4722
+ {
4723
+ tests: [],
4724
+ features: [],
4725
+ givens: [],
4726
+ fullPath: src
4727
+ },
4728
+ null,
4729
+ 2
4730
+ )
4731
+ );
4732
+ }
3376
4733
  this.bddTestIsNowDone(src, -1);
3377
4734
  reject(e);
3378
- }).finally(() => {
4735
+ }).finally(async () => {
4736
+ await this.generatePromptFiles(reportDest, src);
3379
4737
  close();
3380
4738
  });
3381
4739
  }).catch((error) => {
@@ -3393,117 +4751,68 @@ var init_main = __esm({
3393
4751
  );
3394
4752
  };
3395
4753
  this.launchPython = async (src, dest) => {
4754
+ console.log(ansiC4.green(ansiC4.inverse(`python < ${src}`)));
3396
4755
  const processId = `python-${src}-${Date.now()}`;
3397
4756
  const command = `python test: ${src}`;
3398
4757
  const pythonPromise = (async () => {
3399
- this.bddTestIsRunning(src);
3400
- const reportDest = `testeranto/reports/${this.name}/${src.split(".").slice(0, -1).join(".")}/python`;
3401
- if (!fs10.existsSync(reportDest)) {
3402
- fs10.mkdirSync(reportDest, { recursive: true });
3403
- }
3404
- let testResources = "";
3405
- const testConfig = this.configs.tests.find((t) => t[0] === src);
3406
- if (!testConfig) {
3407
- console.log(
3408
- ansiColors.inverse(
3409
- `missing test config! Exiting ungracefully for '${src}'`
3410
- )
3411
- );
3412
- process.exit(-1);
3413
- }
3414
- const testConfigResource = testConfig[2];
3415
- const portsToUse = [];
3416
- if (testConfigResource.ports === 0) {
3417
- testResources = JSON.stringify({
3418
- scheduled: true,
3419
- name: src,
3420
- ports: portsToUse,
3421
- fs: reportDest,
3422
- browserWSEndpoint: this.browser.wsEndpoint()
4758
+ try {
4759
+ const { reportDest, testResources, portsToUse } = await this.setupTestEnvironment(src, "python");
4760
+ const logs = createLogStreams(reportDest, "python");
4761
+ const venvPython = `./venv/bin/python3`;
4762
+ const pythonCommand = fs16.existsSync(venvPython) ? venvPython : "python3";
4763
+ const ipcfile = "/tmp/tpipe_python_" + Math.random();
4764
+ const child = spawn3(pythonCommand, [src, testResources, ipcfile], {
4765
+ stdio: ["pipe", "pipe", "pipe", "ipc"]
3423
4766
  });
3424
- } else if (testConfigResource.ports > 0) {
3425
- const openPorts = Object.entries(this.ports).filter(
3426
- ([, status]) => status === ""
3427
- );
3428
- if (openPorts.length >= testConfigResource.ports) {
3429
- for (let i = 0; i < testConfigResource.ports; i++) {
3430
- portsToUse.push(openPorts[i][0]);
3431
- this.ports[openPorts[i][0]] = src;
4767
+ let buffer = Buffer.from("");
4768
+ const queue = new Queue();
4769
+ const onData = (data) => {
4770
+ buffer = Buffer.concat([buffer, data]);
4771
+ for (let b = 0; b < buffer.length + 1; b++) {
4772
+ const c = buffer.slice(0, b);
4773
+ try {
4774
+ const d = JSON.parse(c.toString());
4775
+ queue.enqueue(d);
4776
+ buffer = buffer.slice(b);
4777
+ b = 0;
4778
+ } catch (e) {
4779
+ }
3432
4780
  }
3433
- testResources = JSON.stringify({
3434
- scheduled: true,
3435
- name: src,
3436
- ports: portsToUse,
3437
- fs: reportDest,
3438
- browserWSEndpoint: this.browser.wsEndpoint()
3439
- });
3440
- } else {
3441
- console.log(
3442
- ansiColors.red(
3443
- `python: cannot run ${src} because there are no open ports ATM. This job will be enqueued and run again when a port is available`
3444
- )
3445
- );
3446
- this.queue.push(src);
3447
- return;
3448
- }
3449
- } else {
3450
- console.error("negative port makes no sense", src);
3451
- process.exit(-1);
3452
- }
3453
- const logs = createLogStreams(reportDest, "python");
3454
- const child = spawn2("python3", [src, testResources], {
3455
- stdio: ["pipe", "pipe", "pipe"]
3456
- });
3457
- return new Promise((resolve, reject) => {
3458
- child.stdout?.on("data", (data) => {
3459
- logs.stdout?.write(data);
3460
- });
3461
- child.stderr?.on("data", (data) => {
3462
- logs.stderr?.write(data);
3463
- });
3464
- child.on("close", (code) => {
3465
- const exitCode = code === null ? -1 : code;
3466
- if (exitCode < 0) {
3467
- logs.writeExitCode(
3468
- exitCode,
3469
- new Error("Process crashed or was terminated")
3470
- );
3471
- } else {
3472
- logs.writeExitCode(exitCode);
3473
- }
3474
- logs.closeAll();
3475
- if (exitCode === 0) {
3476
- this.bddTestIsNowDone(src, 0);
3477
- statusMessagePretty(0, src, "python");
3478
- resolve();
3479
- } else {
3480
- console.log(
3481
- ansiColors.red(
3482
- `python ! ${src} failed to execute. Check ${reportDest}/stderr.log for more info`
3483
- )
3484
- );
3485
- this.bddTestIsNowDone(src, exitCode);
3486
- statusMessagePretty(exitCode, src, "python");
3487
- reject(new Error(`Process exited with code ${exitCode}`));
4781
+ while (queue.size() > 0) {
4782
+ const message = queue.dequeue();
4783
+ if (message) {
4784
+ this.mapping().forEach(async ([command2, func]) => {
4785
+ if (message[0] === command2) {
4786
+ const args = message.slice(1, -1);
4787
+ try {
4788
+ const result = await this[command2](...args);
4789
+ child.send(
4790
+ JSON.stringify({
4791
+ payload: result,
4792
+ key: message[message.length - 1]
4793
+ })
4794
+ );
4795
+ } catch (error) {
4796
+ console.error(`Error handling command ${command2}:`, error);
4797
+ }
4798
+ }
4799
+ });
4800
+ }
3488
4801
  }
3489
- });
3490
- child.on("error", (e) => {
3491
- console.log(
3492
- ansiColors.red(
3493
- ansiColors.inverse(
3494
- `python: ${src} errored with: ${e.name}. Check error logs for more info`
3495
- )
3496
- )
3497
- );
3498
- this.bddTestIsNowDone(src, -1);
3499
- statusMessagePretty(-1, src, "python");
3500
- reject(e);
3501
- });
3502
- }).finally(() => {
3503
- portsToUse.forEach((port) => {
3504
- this.ports[port] = "";
3505
- });
3506
- });
4802
+ };
4803
+ const server = await this.createIpcServer(onData, ipcfile);
4804
+ try {
4805
+ await this.handleChildProcess(child, logs, reportDest, src, "python");
4806
+ await this.generatePromptFiles(reportDest, src);
4807
+ } finally {
4808
+ server.close();
4809
+ this.cleanupPorts(portsToUse);
4810
+ }
4811
+ } catch (error) {
4812
+ if (error.message !== "No ports available") {
4813
+ throw error;
4814
+ }
4815
+ }
3507
4816
  })();
3508
4817
  this.addPromiseProcess(
3509
4818
  processId,
@@ -3515,152 +4824,88 @@ var init_main = __esm({
3515
4824
  );
3516
4825
  };
3517
4826
  this.launchGolang = async (src, dest) => {
4827
+ console.log(ansiC4.green(ansiC4.inverse(`goland < ${src}`)));
3518
4828
  const processId = `golang-${src}-${Date.now()}`;
3519
4829
  const command = `golang test: ${src}`;
3520
4830
  const golangPromise = (async () => {
3521
- this.bddTestIsRunning(src);
3522
- const reportDest = `testeranto/reports/${this.name}/${src.split(".").slice(0, -1).join(".")}/golang`;
3523
- if (!fs10.existsSync(reportDest)) {
3524
- fs10.mkdirSync(reportDest, { recursive: true });
3525
- }
3526
- let testResources = "";
3527
- const testConfig = this.configs.tests.find((t) => t[0] === src);
3528
- if (!testConfig) {
3529
- console.log(
3530
- ansiColors.inverse(
3531
- `golang: missing test config! Exiting ungracefully for '${src}'`
3532
- )
3533
- );
3534
- process.exit(-1);
3535
- }
3536
- const testConfigResource = testConfig[2];
3537
- const portsToUse = [];
3538
- if (testConfigResource.ports === 0) {
3539
- testResources = JSON.stringify({
3540
- scheduled: true,
3541
- name: src,
3542
- ports: portsToUse,
3543
- fs: reportDest,
3544
- browserWSEndpoint: this.browser.wsEndpoint()
3545
- });
3546
- } else if (testConfigResource.ports > 0) {
3547
- const openPorts = Object.entries(this.ports).filter(
3548
- ([, status]) => status === ""
3549
- );
3550
- if (openPorts.length >= testConfigResource.ports) {
3551
- for (let i = 0; i < testConfigResource.ports; i++) {
3552
- portsToUse.push(openPorts[i][0]);
3553
- this.ports[openPorts[i][0]] = src;
4831
+ try {
4832
+ const { reportDest, testResources, portsToUse } = await this.setupTestEnvironment(src, "golang");
4833
+ const logs = createLogStreams(reportDest, "golang");
4834
+ const ipcfile = "/tmp/tpipe_golang_" + Math.random().toString(36).substring(2);
4835
+ let buffer = Buffer.from("");
4836
+ const queue = new Queue();
4837
+ const onData = (data) => {
4838
+ buffer = Buffer.concat([buffer, data]);
4839
+ for (let b = 0; b < buffer.length + 1; b++) {
4840
+ const c = buffer.slice(0, b);
4841
+ try {
4842
+ const d = JSON.parse(c.toString());
4843
+ queue.enqueue(d);
4844
+ buffer = buffer.slice(b);
4845
+ b = 0;
4846
+ } catch (e) {
4847
+ }
3554
4848
  }
3555
- testResources = JSON.stringify({
3556
- scheduled: true,
3557
- name: src,
3558
- ports: portsToUse,
3559
- fs: reportDest,
3560
- browserWSEndpoint: this.browser.wsEndpoint()
3561
- });
3562
- } else {
3563
- console.log(
3564
- ansiColors.red(
3565
- `golang: cannot run ${src} because there are no open ports ATM. This job will be enqueued and run again when a port is available`
3566
- )
3567
- );
3568
- this.queue.push(src);
3569
- return;
4849
+ while (queue.size() > 0) {
4850
+ const message = queue.dequeue();
4851
+ if (message) {
4852
+ this.mapping().forEach(async ([command2, func]) => {
4853
+ if (message[0] === command2) {
4854
+ const args = message.slice(1, -1);
4855
+ try {
4856
+ const result = await this[command2](...args);
4857
+ } catch (error) {
4858
+ console.error(`Error handling command ${command2}:`, error);
4859
+ }
4860
+ }
4861
+ });
4862
+ }
4863
+ }
4864
+ };
4865
+ const server = await this.createIpcServer(onData, ipcfile);
4866
+ let currentDir = path13.dirname(src);
4867
+ let goModDir = null;
4868
+ while (currentDir !== path13.parse(currentDir).root) {
4869
+ if (fs16.existsSync(path13.join(currentDir, "go.mod"))) {
4870
+ goModDir = currentDir;
4871
+ break;
4872
+ }
4873
+ currentDir = path13.dirname(currentDir);
3570
4874
  }
3571
- } else {
3572
- console.error("negative port makes no sense", src);
3573
- process.exit(-1);
3574
- }
3575
- const buildDir = path.dirname(dest);
3576
- const binaryName = path.basename(dest, ".go");
3577
- const binaryPath = path.join(buildDir, binaryName);
3578
- const logs = createLogStreams(reportDest, "golang");
3579
- const compileProcess = spawn2("go", ["build", "-o", binaryPath, dest]);
3580
- return new Promise((resolve, reject) => {
3581
- compileProcess.stdout?.on("data", (data) => {
3582
- logs.stdout?.write(data);
3583
- });
3584
- compileProcess.stderr?.on("data", (data) => {
3585
- logs.stderr?.write(data);
3586
- });
3587
- compileProcess.on("close", (compileCode) => {
3588
- if (compileCode !== 0) {
3589
- console.log(
3590
- ansiColors.red(
3591
- `golang ! ${src} failed to compile. Check ${reportDest}/stderr.log for more info`
3592
- )
3593
- );
3594
- this.bddTestIsNowDone(src, compileCode || -1);
3595
- statusMessagePretty(compileCode || -1, src, "golang");
3596
- reject(new Error(`Compilation failed with code ${compileCode}`));
3597
- return;
4875
+ if (!goModDir) {
4876
+ console.error(`Could not find go.mod file for test ${src}`);
4877
+ goModDir = path13.dirname(src);
4878
+ console.error(`Falling back to: ${goModDir}`);
4879
+ }
4880
+ const relativeTestPath = path13.relative(goModDir, src);
4881
+ const child = spawn3(
4882
+ "go",
4883
+ ["test", "-v", "-json", "./" + path13.dirname(relativeTestPath)],
4884
+ {
4885
+ stdio: ["pipe", "pipe", "pipe"],
4886
+ env: {
4887
+ ...process.env,
4888
+ TEST_RESOURCES: testResources,
4889
+ IPC_FILE: ipcfile,
4890
+ GO111MODULE: "on"
4891
+ },
4892
+ cwd: goModDir
3598
4893
  }
3599
- const child = spawn2(binaryPath, [testResources], {
3600
- stdio: ["pipe", "pipe", "pipe"]
3601
- });
3602
- child.stdout?.on("data", (data) => {
3603
- logs.stdout?.write(data);
3604
- });
3605
- child.stderr?.on("data", (data) => {
3606
- logs.stderr?.write(data);
3607
- });
3608
- child.on("close", (code) => {
3609
- const exitCode = code === null ? -1 : code;
3610
- if (exitCode < 0) {
3611
- logs.writeExitCode(
3612
- exitCode,
3613
- new Error("Process crashed or was terminated")
3614
- );
3615
- } else {
3616
- logs.writeExitCode(exitCode);
3617
- }
3618
- logs.closeAll();
3619
- if (exitCode === 0) {
3620
- this.bddTestIsNowDone(src, 0);
3621
- statusMessagePretty(0, src, "golang");
3622
- resolve();
3623
- } else {
3624
- console.log(
3625
- ansiColors.red(
3626
- `golang ! ${src} failed to execute. Check ${reportDest}/stderr.log for more info`
3627
- )
3628
- );
3629
- this.bddTestIsNowDone(src, exitCode);
3630
- statusMessagePretty(exitCode, src, "golang");
3631
- reject(new Error(`Process exited with code ${exitCode}`));
3632
- }
3633
- });
3634
- child.on("error", (e) => {
3635
- console.log(
3636
- ansiColors.red(
3637
- ansiColors.inverse(
3638
- `golang: ${src} errored with: ${e.name}. Check error logs for more info`
3639
- )
3640
- )
3641
- );
3642
- this.bddTestIsNowDone(src, -1);
3643
- statusMessagePretty(-1, src, "golang");
3644
- reject(e);
3645
- });
3646
- });
3647
- compileProcess.on("error", (e) => {
3648
- console.log(
3649
- ansiColors.red(
3650
- ansiColors.inverse(
3651
- `golang: ${src} compilation errored with: ${e.name}. Check error logs for more info`
3652
- )
3653
- )
3654
- );
3655
- this.bddTestIsNowDone(src, -1);
3656
- statusMessagePretty(-1, src, "golang");
3657
- reject(e);
3658
- });
3659
- }).finally(() => {
3660
- portsToUse.forEach((port) => {
3661
- this.ports[port] = "";
3662
- });
3663
- });
4894
+ );
4895
+ await this.handleChildProcess(child, logs, reportDest, src, "golang");
4896
+ await this.generatePromptFiles(reportDest, src);
4897
+ await this.processGoTestOutput(reportDest, src);
4898
+ server.close();
4899
+ try {
4900
+ fs16.unlinkSync(ipcfile);
4901
+ } catch (e) {
4902
+ }
4903
+ this.cleanupPorts(portsToUse);
4904
+ } catch (error) {
4905
+ if (error.message !== "No ports available") {
4906
+ throw error;
4907
+ }
4908
+ }
3664
4909
  })();
3665
4910
  this.addPromiseProcess(
3666
4911
  processId,
@@ -3672,184 +4917,241 @@ var init_main = __esm({
3672
4917
  );
3673
4918
  };
3674
4919
  }
3675
- };
3676
- }
3677
- });
3678
-
3679
- // src/utils/golingvuMetafile.ts
3680
- var golingvuMetafile_exports = {};
3681
- __export(golingvuMetafile_exports, {
3682
- generateGolangMetafile: () => generateGolangMetafile,
3683
- writeGolangMetafile: () => writeGolangMetafile
3684
- });
3685
- import fs11 from "fs";
3686
- import path9 from "path";
3687
- async function generateGolangMetafile(testName2, entryPoints) {
3688
- const outputs = {};
3689
- for (const entryPoint of entryPoints) {
3690
- try {
3691
- const entryDir = path9.dirname(entryPoint);
3692
- const goFiles = fs11.readdirSync(entryDir).filter((file) => file.endsWith(".go")).map((file) => path9.join(entryDir, file));
3693
- const inputs = {};
3694
- let totalBytes = 0;
3695
- for (const file of goFiles) {
4920
+ async setupTestEnvironment(src, runtime) {
4921
+ this.bddTestIsRunning(src);
4922
+ const reportDest = `testeranto/reports/${this.name}/${src.split(".").slice(0, -1).join(".")}/${runtime}`;
4923
+ if (!fs16.existsSync(reportDest)) {
4924
+ fs16.mkdirSync(reportDest, { recursive: true });
4925
+ }
4926
+ const testConfig = this.configs.tests.find((t) => t[0] === src);
4927
+ if (!testConfig) {
4928
+ console.log(
4929
+ ansiC4.inverse(`missing test config! Exiting ungracefully for '${src}'`)
4930
+ );
4931
+ process.exit(-1);
4932
+ }
4933
+ const testConfigResource = testConfig[2];
4934
+ const portsToUse = [];
4935
+ let testResources = "";
4936
+ if (testConfigResource.ports === 0) {
4937
+ testResources = JSON.stringify({
4938
+ name: src,
4939
+ ports: [],
4940
+ fs: reportDest,
4941
+ browserWSEndpoint: this.browser.wsEndpoint()
4942
+ });
4943
+ } else if (testConfigResource.ports > 0) {
4944
+ const openPorts = Object.entries(this.ports).filter(
4945
+ ([, status]) => status === ""
4946
+ );
4947
+ if (openPorts.length >= testConfigResource.ports) {
4948
+ for (let i = 0; i < testConfigResource.ports; i++) {
4949
+ portsToUse.push(openPorts[i][0]);
4950
+ this.ports[openPorts[i][0]] = src;
4951
+ }
4952
+ testResources = JSON.stringify({
4953
+ scheduled: true,
4954
+ name: src,
4955
+ ports: portsToUse,
4956
+ fs: reportDest,
4957
+ browserWSEndpoint: this.browser.wsEndpoint()
4958
+ });
4959
+ } else {
4960
+ console.log(
4961
+ ansiC4.red(
4962
+ `${runtime}: cannot run ${src} because there are no open ports ATM. This job will be enqueued and run again when a port is available`
4963
+ )
4964
+ );
4965
+ this.queue.push(src);
4966
+ throw new Error("No ports available");
4967
+ }
4968
+ } else {
4969
+ console.error("negative port makes no sense", src);
4970
+ process.exit(-1);
4971
+ }
4972
+ return {
4973
+ reportDest,
4974
+ testConfig,
4975
+ testConfigResource,
4976
+ portsToUse,
4977
+ testResources
4978
+ };
4979
+ }
4980
+ cleanupPorts(portsToUse) {
4981
+ portsToUse.forEach((port) => {
4982
+ this.ports[port] = "";
4983
+ });
4984
+ }
4985
+ createIpcServer(onData, ipcfile) {
4986
+ return new Promise((resolve, reject) => {
4987
+ const server = net.createServer((socket) => {
4988
+ socket.on("data", onData);
4989
+ });
4990
+ server.listen(ipcfile, (err) => {
4991
+ if (err)
4992
+ reject(err);
4993
+ else
4994
+ resolve(server);
4995
+ });
4996
+ server.on("error", reject);
4997
+ });
4998
+ }
4999
+ handleChildProcess(child, logs, reportDest, src, runtime) {
5000
+ return new Promise((resolve, reject) => {
5001
+ child.stdout?.on("data", (data) => {
5002
+ logs.stdout?.write(data);
5003
+ });
5004
+ child.stderr?.on("data", (data) => {
5005
+ logs.stderr?.write(data);
5006
+ });
5007
+ child.on("close", (code) => {
5008
+ const exitCode = code === null ? -1 : code;
5009
+ if (exitCode < 0) {
5010
+ logs.writeExitCode(
5011
+ exitCode,
5012
+ new Error("Process crashed or was terminated")
5013
+ );
5014
+ } else {
5015
+ logs.writeExitCode(exitCode);
5016
+ }
5017
+ logs.closeAll();
5018
+ if (exitCode === 0) {
5019
+ this.bddTestIsNowDone(src, 0);
5020
+ statusMessagePretty(0, src, runtime);
5021
+ resolve();
5022
+ } else {
5023
+ console.log(
5024
+ ansiColors.red(
5025
+ `${runtime} ! ${src} failed to execute. Check ${reportDest}/stderr.log for more info`
5026
+ )
5027
+ );
5028
+ this.bddTestIsNowDone(src, exitCode);
5029
+ statusMessagePretty(exitCode, src, runtime);
5030
+ reject(new Error(`Process exited with code ${exitCode}`));
5031
+ }
5032
+ });
5033
+ child.on("error", (e) => {
5034
+ console.log(
5035
+ ansiC4.red(
5036
+ ansiC4.inverse(
5037
+ `${src} errored with: ${e.name}. Check error logs for more info`
5038
+ )
5039
+ )
5040
+ );
5041
+ this.bddTestIsNowDone(src, -1);
5042
+ statusMessagePretty(-1, src, runtime);
5043
+ reject(e);
5044
+ });
5045
+ });
5046
+ }
5047
+ async processGoTestOutput(reportDest, src) {
5048
+ const testsJsonPath = `${reportDest}/tests.json`;
5049
+ const stdoutPath = `${reportDest}/stdout.log`;
5050
+ if (fs16.existsSync(stdoutPath)) {
5051
+ try {
5052
+ const stdoutContent = fs16.readFileSync(stdoutPath, "utf-8");
5053
+ const lines = stdoutContent.split("\n").filter((line) => line.trim());
5054
+ const testResults = {
5055
+ tests: [],
5056
+ features: [],
5057
+ givens: [],
5058
+ fullPath: path13.resolve(process.cwd(), src)
5059
+ };
5060
+ for (const line of lines) {
5061
+ try {
5062
+ const event = JSON.parse(line);
5063
+ if (event.Action === "pass" || event.Action === "fail") {
5064
+ testResults.tests.push({
5065
+ name: event.Test || event.Package,
5066
+ status: event.Action === "pass" ? "passed" : "failed",
5067
+ time: event.Elapsed ? `${event.Elapsed}s` : "0s"
5068
+ });
5069
+ }
5070
+ } catch (e) {
5071
+ }
5072
+ }
5073
+ fs16.writeFileSync(testsJsonPath, JSON.stringify(testResults, null, 2));
5074
+ return;
5075
+ } catch (error) {
5076
+ console.error("Error processing go test output:", error);
5077
+ }
5078
+ }
5079
+ const basicTestResult = {
5080
+ tests: [],
5081
+ features: [],
5082
+ givens: [],
5083
+ fullPath: path13.resolve(process.cwd(), src)
5084
+ };
5085
+ fs16.writeFileSync(testsJsonPath, JSON.stringify(basicTestResult, null, 2));
5086
+ }
5087
+ async generatePromptFiles(reportDest, src) {
3696
5088
  try {
3697
- const stats = fs11.statSync(file);
3698
- inputs[file] = { bytesInOutput: stats.size };
3699
- totalBytes += stats.size;
3700
- } catch {
3701
- inputs[file] = { bytesInOutput: 0 };
5089
+ if (!fs16.existsSync(reportDest)) {
5090
+ fs16.mkdirSync(reportDest, { recursive: true });
5091
+ }
5092
+ const messagePath = `${reportDest}/message.txt`;
5093
+ const messageContent = `There are 3 types of test reports.
5094
+ 1) bdd (highest priority)
5095
+ 2) type checker
5096
+ 3) static analysis (lowest priority)
5097
+
5098
+ "tests.json" is the detailed result of the bdd tests.
5099
+ if these files do not exist, then something has gone badly wrong and needs to be addressed.
5100
+
5101
+ "type_errors.txt" is the result of the type checker.
5102
+ if this file does not exist, then type check passed without errors;
5103
+
5104
+ "lint_errors.txt" is the result of the static analysis.
5105
+ if this file does not exist, then static analysis passed without errors;
5106
+
5107
+ BDD failures are the highest priority. Focus on passing BDD tests before addressing other concerns.
5108
+ Do not add error throwing/catching to the tests themselves.`;
5109
+ fs16.writeFileSync(messagePath, messageContent);
5110
+ const promptPath = `${reportDest}/prompt.txt`;
5111
+ const promptContent = `/read node_modules/testeranto/docs/index.md
5112
+ /read node_modules/testeranto/docs/style.md
5113
+ /read node_modules/testeranto/docs/testing.ai.txt
5114
+ /read node_modules/testeranto/src/CoreTypes.ts
5115
+
5116
+ /read ${reportDest}/tests.json
5117
+ /read ${reportDest}/type_errors.txt
5118
+ /read ${reportDest}/lint_errors.txt
5119
+
5120
+ /read ${reportDest}/stdout.log
5121
+ /read ${reportDest}/stderr.log
5122
+ /read ${reportDest}/exit.log
5123
+ /read ${reportDest}/message.txt`;
5124
+ fs16.writeFileSync(promptPath, promptContent);
5125
+ } catch (error) {
5126
+ console.error(`Failed to generate prompt files for ${src}:`, error);
3702
5127
  }
3703
5128
  }
3704
- if (!inputs[entryPoint]) {
5129
+ getGolangSourceFiles(src) {
5130
+ const testDir = path13.dirname(src);
5131
+ const files3 = [];
3705
5132
  try {
3706
- const entryStats = fs11.statSync(entryPoint);
3707
- inputs[entryPoint] = { bytesInOutput: entryStats.size };
3708
- totalBytes += entryStats.size;
3709
- } catch {
3710
- inputs[entryPoint] = { bytesInOutput: 0 };
5133
+ const dirContents = fs16.readdirSync(testDir);
5134
+ dirContents.forEach((file) => {
5135
+ if (file.endsWith(".go")) {
5136
+ files3.push(path13.join(testDir, file));
5137
+ }
5138
+ });
5139
+ } catch (error) {
5140
+ console.error(`Error reading directory ${testDir}:`, error);
5141
+ }
5142
+ if (!files3.includes(src)) {
5143
+ files3.push(src);
3711
5144
  }
5145
+ return files3;
3712
5146
  }
3713
- const outputPath = `testeranto/bundles/golang/${testName2}/${entryPoint}`;
3714
- outputs[outputPath] = {
3715
- entryPoint,
3716
- // Use the source file path, not the bundle path
3717
- inputs,
3718
- bytes: totalBytes
3719
- };
3720
- } catch (error) {
3721
- console.error(`Error processing Go entry point ${entryPoint}:`, error);
3722
- }
3723
- }
3724
- const allInputs = {};
3725
- const allGoFiles = /* @__PURE__ */ new Set();
3726
- for (const entryPoint of entryPoints) {
3727
- try {
3728
- const entryDir = path9.dirname(entryPoint);
3729
- const goFiles = fs11.readdirSync(entryDir).filter((file) => file.endsWith(".go")).map((file) => path9.join(entryDir, file));
3730
- goFiles.forEach((file) => allGoFiles.add(file));
3731
- allGoFiles.add(entryPoint);
3732
- } catch (error) {
3733
- console.error(`Error processing Go entry point ${entryPoint} for source files:`, error);
3734
- }
3735
- }
3736
- for (const filePath of Array.from(allGoFiles)) {
3737
- try {
3738
- const stats = fs11.statSync(filePath);
3739
- allInputs[filePath] = {
3740
- bytes: stats.size,
3741
- imports: []
3742
- // Go files don't have imports like JS
3743
- };
3744
- } catch {
3745
- allInputs[filePath] = {
3746
- bytes: 0,
3747
- imports: []
3748
- };
3749
- }
3750
- }
3751
- const esbuildOutputs = {};
3752
- for (const [outputPath, output] of Object.entries(outputs)) {
3753
- esbuildOutputs[outputPath] = {
3754
- bytes: output.bytes,
3755
- inputs: output.inputs,
3756
- entryPoint: output.entryPoint
3757
5147
  };
3758
5148
  }
3759
- return {
3760
- errors: [],
3761
- warnings: [],
3762
- metafile: {
3763
- inputs: allInputs,
3764
- outputs: esbuildOutputs
3765
- }
3766
- };
3767
- }
3768
- function writeGolangMetafile(testName2, metafile) {
3769
- const metafileDir = path9.join(
3770
- process.cwd(),
3771
- "testeranto",
3772
- "metafiles",
3773
- "golang"
3774
- );
3775
- fs11.mkdirSync(metafileDir, { recursive: true });
3776
- const metafilePath = path9.join(metafileDir, `${testName2}.json`);
3777
- fs11.writeFileSync(metafilePath, JSON.stringify(metafile, null, 2));
3778
- }
3779
- var init_golingvuMetafile = __esm({
3780
- "src/utils/golingvuMetafile.ts"() {
3781
- "use strict";
3782
- }
3783
- });
3784
-
3785
- // src/utils/pitonoMetafile.ts
3786
- var pitonoMetafile_exports = {};
3787
- __export(pitonoMetafile_exports, {
3788
- generatePitonoMetafile: () => generatePitonoMetafile,
3789
- writePitonoMetafile: () => writePitonoMetafile
3790
- });
3791
- import fs12 from "fs";
3792
- import path10 from "path";
3793
- import { execSync } from "child_process";
3794
- async function generatePitonoMetafile(testName2, entryPoints) {
3795
- return {
3796
- testName: testName2,
3797
- entryPoints,
3798
- timestamp: Date.now()
3799
- };
3800
- }
3801
- function writePitonoMetafile(testName2, metafile) {
3802
- const metafilePath = path10.join(process.cwd(), "testeranto", "pitono", testName2, "metafile.json");
3803
- const metafileDir = path10.dirname(metafilePath);
3804
- if (!fs12.existsSync(metafileDir)) {
3805
- fs12.mkdirSync(metafileDir, { recursive: true });
3806
- }
3807
- fs12.writeFileSync(metafilePath, JSON.stringify(metafile, null, 2));
3808
- console.log(`Pitono metafile written to: ${metafilePath}`);
3809
- try {
3810
- const command = `pitono-core-generator ${testName2} ${metafile.entryPoints.join(" ")}`;
3811
- execSync(command, { stdio: "inherit" });
3812
- console.log(`Pitono core.json generated successfully for ${testName2}`);
3813
- } catch (error) {
3814
- console.error(`Failed to generate Pitono core.json with installed command: ${error}`);
3815
- try {
3816
- const pythonCommand = `python ${process.cwd()}/pitono/core_generator.py ${testName2} ${metafile.entryPoints.join(" ")}`;
3817
- execSync(pythonCommand, { stdio: "inherit" });
3818
- console.log(`Pitono core.json generated successfully using direct Python execution`);
3819
- } catch (fallbackError) {
3820
- console.error(`Direct Python execution also failed: ${fallbackError}`);
3821
- try {
3822
- const coreData = {
3823
- testName: testName2,
3824
- entryPoints: metafile.entryPoints,
3825
- outputs: {},
3826
- metafile: {
3827
- inputs: {},
3828
- outputs: {}
3829
- },
3830
- timestamp: Date.now(),
3831
- runtime: "pitono"
3832
- };
3833
- const coreFilePath = path10.join(process.cwd(), "testeranto", "pitono", testName2, "core.json");
3834
- fs12.writeFileSync(coreFilePath, JSON.stringify(coreData, null, 2));
3835
- console.log(`Pitono core.json created manually as fallback`);
3836
- } catch (manualError) {
3837
- console.error(`Even manual creation failed: ${manualError}`);
3838
- }
3839
- }
3840
- }
3841
- }
3842
- var init_pitonoMetafile = __esm({
3843
- "src/utils/pitonoMetafile.ts"() {
3844
- "use strict";
3845
- }
3846
5149
  });
3847
5150
 
3848
5151
  // src/testeranto.ts
3849
5152
  init_utils();
3850
5153
  import ansiC5 from "ansi-colors";
3851
- import fs13 from "fs";
3852
- import path11 from "path";
5154
+ import fs17 from "fs";
3853
5155
  import readline from "readline";
3854
5156
 
3855
5157
  // src/utils/buildTemplates.ts
@@ -3887,33 +5189,403 @@ var AppHtml = () => `
3887
5189
  </html>
3888
5190
  `;
3889
5191
 
3890
- // src/web.html.ts
3891
- var web_html_default = (jsfilePath, htmlFilePath, cssfilePath) => `
3892
- <!DOCTYPE html>
3893
- <html lang="en">
5192
+ // src/utils/pitonoMetafile.ts
5193
+ import fs from "fs";
5194
+ import path2 from "path";
5195
+ function resolvePythonImport(importPath, currentFile) {
5196
+ if (importPath.startsWith(".")) {
5197
+ const currentDir = path2.dirname(currentFile);
5198
+ let dotCount = 0;
5199
+ let remainingPath = importPath;
5200
+ while (remainingPath.startsWith(".")) {
5201
+ dotCount++;
5202
+ remainingPath = remainingPath.substring(1);
5203
+ }
5204
+ if (remainingPath.startsWith("/")) {
5205
+ remainingPath = remainingPath.substring(1);
5206
+ }
5207
+ let baseDir = currentDir;
5208
+ for (let i = 1; i < dotCount; i++) {
5209
+ baseDir = path2.dirname(baseDir);
5210
+ }
5211
+ if (remainingPath.length === 0) {
5212
+ const initPath = path2.join(baseDir, "__init__.py");
5213
+ if (fs.existsSync(initPath)) {
5214
+ return initPath;
5215
+ }
5216
+ return null;
5217
+ }
5218
+ const resolvedPath = path2.join(baseDir, remainingPath);
5219
+ const extensions = [".py", "/__init__.py"];
5220
+ for (const ext of extensions) {
5221
+ const potentialPath = resolvedPath + ext;
5222
+ if (fs.existsSync(potentialPath)) {
5223
+ return potentialPath;
5224
+ }
5225
+ }
5226
+ if (fs.existsSync(resolvedPath) && fs.statSync(resolvedPath).isDirectory()) {
5227
+ const initPath = path2.join(resolvedPath, "__init__.py");
5228
+ if (fs.existsSync(initPath)) {
5229
+ return initPath;
5230
+ }
5231
+ }
5232
+ return null;
5233
+ }
5234
+ const dirs = [
5235
+ path2.dirname(currentFile),
5236
+ process.cwd(),
5237
+ ...process.env.PYTHONPATH ? process.env.PYTHONPATH.split(path2.delimiter) : []
5238
+ ];
5239
+ for (const dir of dirs) {
5240
+ const potentialPaths = [
5241
+ path2.join(dir, importPath + ".py"),
5242
+ path2.join(dir, importPath, "__init__.py"),
5243
+ path2.join(dir, importPath.replace(/\./g, "/") + ".py"),
5244
+ path2.join(dir, importPath.replace(/\./g, "/"), "__init__.py")
5245
+ ];
5246
+ for (const potentialPath of potentialPaths) {
5247
+ if (fs.existsSync(potentialPath)) {
5248
+ return potentialPath;
5249
+ }
5250
+ }
5251
+ }
5252
+ return null;
5253
+ }
5254
+ function parsePythonImports(filePath) {
5255
+ try {
5256
+ const content = fs.readFileSync(filePath, "utf-8");
5257
+ const imports = [];
5258
+ const importRegex = /^import\s+([\w., ]+)/gm;
5259
+ const fromImportRegex = /^from\s+([\w.]+)\s+import/gm;
5260
+ let match;
5261
+ while ((match = importRegex.exec(content)) !== null) {
5262
+ const importPaths = match[1].split(",").map((p) => p.trim());
5263
+ for (const importPath of importPaths) {
5264
+ const resolvedPath = resolvePythonImport(importPath, filePath);
5265
+ imports.push({
5266
+ path: importPath,
5267
+ kind: "import-statement",
5268
+ external: resolvedPath === null,
5269
+ original: importPath
5270
+ });
5271
+ }
5272
+ }
5273
+ while ((match = fromImportRegex.exec(content)) !== null) {
5274
+ const importPath = match[1];
5275
+ const resolvedPath = resolvePythonImport(importPath, filePath);
5276
+ imports.push({
5277
+ path: importPath,
5278
+ kind: "import-statement",
5279
+ external: resolvedPath === null,
5280
+ original: importPath
5281
+ });
5282
+ }
5283
+ return imports;
5284
+ } catch (error) {
5285
+ console.warn(`Could not parse imports for ${filePath}:`, error);
5286
+ return [];
5287
+ }
5288
+ }
5289
+ function collectDependencies(filePath, visited = /* @__PURE__ */ new Set()) {
5290
+ if (visited.has(filePath))
5291
+ return [];
5292
+ visited.add(filePath);
5293
+ const dependencies = [filePath];
5294
+ const imports = parsePythonImports(filePath);
5295
+ for (const imp of imports) {
5296
+ if (!imp.external && imp.path) {
5297
+ const resolvedPath = resolvePythonImport(imp.path, filePath);
5298
+ if (resolvedPath && fs.existsSync(resolvedPath)) {
5299
+ dependencies.push(...collectDependencies(resolvedPath, visited));
5300
+ }
5301
+ }
5302
+ }
5303
+ return [...new Set(dependencies)];
5304
+ }
5305
+ async function generatePitonoMetafile(testName2, entryPoints) {
5306
+ const inputs = {};
5307
+ const outputs = {};
5308
+ const signature = Date.now().toString(36);
5309
+ for (const entryPoint of entryPoints) {
5310
+ if (!fs.existsSync(entryPoint)) {
5311
+ console.warn(`Entry point ${entryPoint} does not exist`);
5312
+ continue;
5313
+ }
5314
+ const allDependencies = collectDependencies(entryPoint);
5315
+ for (const dep of allDependencies) {
5316
+ if (!inputs[dep]) {
5317
+ const bytes = fs.statSync(dep).size;
5318
+ const imports = parsePythonImports(dep);
5319
+ inputs[dep] = {
5320
+ bytes,
5321
+ imports
5322
+ };
5323
+ }
5324
+ }
5325
+ const entryPointName = path2.basename(entryPoint, ".py");
5326
+ const outputKey = `python/core/${entryPointName}.py`;
5327
+ const inputBytes = {};
5328
+ let totalBytes = 0;
5329
+ for (const dep of allDependencies) {
5330
+ const bytes = fs.statSync(dep).size;
5331
+ inputBytes[dep] = { bytesInOutput: bytes };
5332
+ totalBytes += bytes;
5333
+ }
5334
+ outputs[outputKey] = {
5335
+ imports: [],
5336
+ exports: [],
5337
+ entryPoint,
5338
+ inputs: inputBytes,
5339
+ bytes: totalBytes,
5340
+ signature
5341
+ };
5342
+ }
5343
+ if (Object.keys(inputs).length === 0) {
5344
+ inputs["placeholder.py"] = {
5345
+ bytes: 0,
5346
+ imports: []
5347
+ };
5348
+ outputs["testeranto/bundles/python/core/placeholder.py"] = {
5349
+ imports: [],
5350
+ exports: [],
5351
+ entryPoint: "placeholder.py",
5352
+ inputs: {
5353
+ "placeholder.py": {
5354
+ bytesInOutput: 0
5355
+ }
5356
+ },
5357
+ bytes: 0,
5358
+ signature: "placeholder"
5359
+ };
5360
+ }
5361
+ return {
5362
+ errors: [],
5363
+ warnings: [],
5364
+ metafile: {
5365
+ inputs,
5366
+ outputs
5367
+ }
5368
+ };
5369
+ }
5370
+ function writePitonoMetafile(testName2, metafile) {
5371
+ const projectRoot = process.cwd();
5372
+ const metafilePath = path2.join(
5373
+ projectRoot,
5374
+ "testeranto",
5375
+ "metafiles",
5376
+ "python",
5377
+ "core.json"
5378
+ );
5379
+ const metafileDir = path2.dirname(metafilePath);
5380
+ if (!fs.existsSync(metafileDir)) {
5381
+ fs.mkdirSync(metafileDir, { recursive: true });
5382
+ }
5383
+ fs.writeFileSync(metafilePath, JSON.stringify(metafile, null, 2));
5384
+ const outputDir = path2.join(
5385
+ projectRoot,
5386
+ "testeranto",
5387
+ "bundles",
5388
+ "python",
5389
+ "core"
5390
+ );
5391
+ if (!fs.existsSync(outputDir)) {
5392
+ fs.mkdirSync(outputDir, { recursive: true });
5393
+ }
5394
+ for (const [outputPath, outputInfo] of Object.entries(
5395
+ metafile.metafile.outputs
5396
+ )) {
5397
+ const fileName = path2.basename(outputPath);
5398
+ const fullOutputPath = path2.join(outputDir, fileName);
5399
+ const outputDirPath = path2.dirname(fullOutputPath);
5400
+ if (!fs.existsSync(outputDirPath)) {
5401
+ fs.mkdirSync(outputDirPath, { recursive: true });
5402
+ }
5403
+ const entryPoint = outputInfo.entryPoint;
5404
+ const signature = outputInfo.signature;
5405
+ const content = `# This file is auto-generated by testeranto
5406
+ # Signature: ${signature}
5407
+ # It runs tests from: ${entryPoint}
3894
5408
 
3895
- <head>
3896
- <script type="module" src="${jsfilePath}"></script>
3897
- <link rel="stylesheet" href="${cssfilePath}">
3898
- </head>
5409
+ import os
5410
+ import sys
3899
5411
 
3900
- <body>
3901
- <div id="root">
3902
- </div>
3903
- </body>
5412
+ # Add the original entry point to the path
5413
+ sys.path.insert(0, os.path.dirname(os.path.abspath("${entryPoint}")))
3904
5414
 
3905
- </html>
5415
+ # Import and run the tests
5416
+ try:
5417
+ # Import the module
5418
+ module_name = os.path.basename("${entryPoint}").replace('.py', '')
5419
+ module = __import__(module_name)
5420
+
5421
+ # Run the tests if there's a main block
5422
+ if hasattr(module, 'main'):
5423
+ module.main()
5424
+ else:
5425
+ print(f"No main function found in {module_name}")
5426
+ except Exception as e:
5427
+ print(f"Error running tests from ${entryPoint}: {e}")
5428
+ sys.exit(1)
3906
5429
  `;
5430
+ fs.writeFileSync(fullOutputPath, content);
5431
+ }
5432
+ }
5433
+
5434
+ // src/utils/pitonoWatcher.ts
5435
+ import chokidar from "chokidar";
5436
+ import path3 from "path";
5437
+ import fs2 from "fs";
5438
+ var PitonoWatcher = class {
5439
+ constructor(testName2, entryPoints) {
5440
+ this.watcher = null;
5441
+ this.onChangeCallback = null;
5442
+ this.testName = testName2;
5443
+ this.entryPoints = entryPoints;
5444
+ }
5445
+ async start() {
5446
+ const pythonFilesPattern = "**/*.py";
5447
+ this.watcher = chokidar.watch(pythonFilesPattern, {
5448
+ persistent: true,
5449
+ ignoreInitial: true,
5450
+ cwd: process.cwd(),
5451
+ ignored: [
5452
+ "**/node_modules/**",
5453
+ "**/.git/**",
5454
+ "**/testeranto/bundles/**",
5455
+ "**/testeranto/reports/**"
5456
+ ],
5457
+ usePolling: true,
5458
+ interval: 1e3,
5459
+ binaryInterval: 1e3,
5460
+ depth: 99,
5461
+ followSymlinks: false,
5462
+ atomic: false
5463
+ });
5464
+ this.watcher.on("add", (filePath) => {
5465
+ this.handleFileChange("add", filePath);
5466
+ }).on("change", (filePath) => {
5467
+ this.handleFileChange("change", filePath);
5468
+ }).on("unlink", (filePath) => {
5469
+ this.handleFileChange("unlink", filePath);
5470
+ }).on("error", (error) => {
5471
+ console.error(`Source watcher error: ${error}`);
5472
+ }).on("ready", () => {
5473
+ console.log(
5474
+ "Initial python source file scan complete. Ready for changes."
5475
+ );
5476
+ });
5477
+ const outputDir = path3.join(
5478
+ process.cwd(),
5479
+ `testeranto/bundles/python/${this.testName}`
5480
+ );
5481
+ if (!fs2.existsSync(outputDir)) {
5482
+ fs2.mkdirSync(outputDir, { recursive: true });
5483
+ }
5484
+ const lastSignatures = /* @__PURE__ */ new Map();
5485
+ const bundleWatcher = chokidar.watch(path3.join(outputDir, "*.py"), {
5486
+ persistent: true,
5487
+ ignoreInitial: false,
5488
+ awaitWriteFinish: {
5489
+ stabilityThreshold: 100,
5490
+ pollInterval: 50
5491
+ }
5492
+ });
5493
+ bundleWatcher.on("add", (filePath) => {
5494
+ this.readAndCheckSignature(filePath, lastSignatures);
5495
+ }).on("change", (filePath) => {
5496
+ this.readAndCheckSignature(filePath, lastSignatures);
5497
+ }).on("error", (error) => console.error(`Bundle watcher error: ${error}`));
5498
+ await this.regenerateMetafile();
5499
+ }
5500
+ async handleFileChange(event, filePath) {
5501
+ await new Promise((resolve) => setTimeout(resolve, 100));
5502
+ await this.regenerateMetafile();
5503
+ if (this.onChangeCallback) {
5504
+ this.onChangeCallback();
5505
+ }
5506
+ }
5507
+ readAndCheckSignature(filePath, lastSignatures) {
5508
+ try {
5509
+ const content = fs2.readFileSync(filePath, "utf-8");
5510
+ const signatureMatch = content.match(/# Signature: (\w+)/);
5511
+ if (signatureMatch && signatureMatch[1]) {
5512
+ const currentSignature = signatureMatch[1];
5513
+ const lastSignature = lastSignatures.get(filePath);
5514
+ if (lastSignature === void 0) {
5515
+ lastSignatures.set(filePath, currentSignature);
5516
+ } else if (lastSignature !== currentSignature) {
5517
+ lastSignatures.set(filePath, currentSignature);
5518
+ if (this.onChangeCallback) {
5519
+ this.onChangeCallback();
5520
+ }
5521
+ }
5522
+ }
5523
+ } catch (error) {
5524
+ console.error(`Error reading bundle file ${filePath}:`, error);
5525
+ }
5526
+ }
5527
+ async regenerateMetafile() {
5528
+ try {
5529
+ const metafile = await generatePitonoMetafile(
5530
+ this.testName,
5531
+ this.entryPoints
5532
+ );
5533
+ writePitonoMetafile(this.testName, metafile);
5534
+ } catch (error) {
5535
+ console.error("Error regenerating pitono metafile:", error);
5536
+ }
5537
+ }
5538
+ onMetafileChange(callback) {
5539
+ this.onChangeCallback = callback;
5540
+ }
5541
+ stop() {
5542
+ if (this.watcher) {
5543
+ this.watcher.close();
5544
+ this.watcher = null;
5545
+ }
5546
+ }
5547
+ };
5548
+
5549
+ // src/PM/pitonoBuild.ts
5550
+ var PitonoBuild = class {
5551
+ constructor(config, testName2) {
5552
+ this.watcher = null;
5553
+ this.config = config;
5554
+ this.testName = testName2;
5555
+ }
5556
+ async build() {
5557
+ const pythonTests = this.config.tests.filter((test) => test[1] === "python");
5558
+ const hasPythonTests = pythonTests.length > 0;
5559
+ if (hasPythonTests) {
5560
+ const pythonEntryPoints = pythonTests.map((test) => test[0]);
5561
+ const metafile = await generatePitonoMetafile(this.testName, pythonEntryPoints);
5562
+ writePitonoMetafile(this.testName, metafile);
5563
+ this.watcher = new PitonoWatcher(this.testName, pythonEntryPoints);
5564
+ await this.watcher.start();
5565
+ return pythonEntryPoints;
5566
+ }
5567
+ return [];
5568
+ }
5569
+ async rebuild() {
5570
+ if (this.watcher) {
5571
+ await this.watcher.regenerateMetafile();
5572
+ }
5573
+ }
5574
+ stop() {
5575
+ if (this.watcher) {
5576
+ this.watcher.stop();
5577
+ this.watcher = null;
5578
+ }
5579
+ }
5580
+ onBundleChange(callback) {
5581
+ if (this.watcher) {
5582
+ this.watcher.onMetafileChange(callback);
5583
+ }
5584
+ }
5585
+ };
3907
5586
 
3908
5587
  // src/testeranto.ts
3909
- if (!process.env.GITHUB_CLIENT_ID) {
3910
- console.error(`env var "GITHUB_CLIENT_ID" needs to be set!`);
3911
- process.exit(-1);
3912
- }
3913
- if (!process.env.GITHUB_CLIENT_SECRET) {
3914
- console.error(`env var "GITHUB_CLIENT_SECRET" needs to be set!`);
3915
- process.exit(-1);
3916
- }
5588
+ var { GolingvuBuild: GolingvuBuild2 } = await Promise.resolve().then(() => (init_golingvuBuild(), golingvuBuild_exports));
3917
5589
  readline.emitKeypressEvents(process.stdin);
3918
5590
  if (process.stdin.isTTY)
3919
5591
  process.stdin.setRawMode(true);
@@ -3923,9 +5595,8 @@ if (mode !== "once" && mode !== "dev") {
3923
5595
  console.error(`The 3rd argument should be 'dev' or 'once', not '${mode}'.`);
3924
5596
  process.exit(-1);
3925
5597
  }
3926
- var f = process.cwd() + "/testeranto.config.ts";
3927
- console.log("config file:", f);
3928
- import(f).then(async (module) => {
5598
+ var configFilePath = process.cwd() + "/testeranto.config.ts";
5599
+ import(configFilePath).then(async (module) => {
3929
5600
  const pckge = (await import(`${process.cwd()}/package.json`)).default;
3930
5601
  const bigConfig = module.default;
3931
5602
  const project = bigConfig.projects[testName];
@@ -3934,7 +5605,7 @@ import(f).then(async (module) => {
3934
5605
  process.exit(-1);
3935
5606
  }
3936
5607
  try {
3937
- fs13.writeFileSync(
5608
+ fs17.writeFileSync(
3938
5609
  `${process.cwd()}/testeranto/projects.json`,
3939
5610
  JSON.stringify(Object.keys(bigConfig.projects), null, 2)
3940
5611
  );
@@ -3949,7 +5620,7 @@ import(f).then(async (module) => {
3949
5620
  process.exit(-1);
3950
5621
  }
3951
5622
  if (!rawConfig.tests) {
3952
- console.error(testName, "appears to have no tests: ", f);
5623
+ console.error(testName, "appears to have no tests: ", configFilePath);
3953
5624
  console.error(`here is the config:`);
3954
5625
  console.log(JSON.stringify(rawConfig));
3955
5626
  process.exit(-1);
@@ -3970,88 +5641,16 @@ import(f).then(async (module) => {
3970
5641
  const { PM_Main: PM_Main2 } = await init_main().then(() => main_exports);
3971
5642
  pm = new PM_Main2(config, testName, mode);
3972
5643
  await pm.start();
3973
- fs13.writeFileSync(`${process.cwd()}/testeranto/projects.html`, AppHtml());
5644
+ fs17.writeFileSync(`${process.cwd()}/testeranto/projects.html`, AppHtml());
3974
5645
  Object.keys(bigConfig.projects).forEach((projectName) => {
3975
- console.log(`testeranto/reports/${projectName}`);
3976
- if (!fs13.existsSync(`testeranto/reports/${projectName}`)) {
3977
- fs13.mkdirSync(`testeranto/reports/${projectName}`);
5646
+ if (!fs17.existsSync(`testeranto/reports/${projectName}`)) {
5647
+ fs17.mkdirSync(`testeranto/reports/${projectName}`);
3978
5648
  }
3979
- fs13.writeFileSync(
5649
+ fs17.writeFileSync(
3980
5650
  `testeranto/reports/${projectName}/config.json`,
3981
5651
  JSON.stringify(config, null, 2)
3982
5652
  );
3983
5653
  });
3984
- const getSecondaryEndpointsPoints = (runtime) => {
3985
- const meta = (ts2, st) => {
3986
- ts2.forEach((t) => {
3987
- if (t[1] === runtime) {
3988
- st.add(t[0]);
3989
- }
3990
- if (Array.isArray(t[3])) {
3991
- meta(t[3], st);
3992
- }
3993
- });
3994
- return st;
3995
- };
3996
- return Array.from(meta(config.tests, /* @__PURE__ */ new Set()));
3997
- };
3998
- [...getSecondaryEndpointsPoints("python")].forEach(async (sourceFilePath) => {
3999
- console.log(`Pitono test found: ${sourceFilePath}`);
4000
- });
4001
- const golangTests = config.tests.filter((test) => test[1] === "golang");
4002
- const hasGolangTests = golangTests.length > 0;
4003
- if (hasGolangTests) {
4004
- const { generateGolangMetafile: generateGolangMetafile2, writeGolangMetafile: writeGolangMetafile2 } = await Promise.resolve().then(() => (init_golingvuMetafile(), golingvuMetafile_exports));
4005
- const golangEntryPoints = golangTests.map((test) => test[0]);
4006
- const metafile = await generateGolangMetafile2(testName, golangEntryPoints);
4007
- writeGolangMetafile2(testName, metafile);
4008
- }
4009
- const pitonoTests = config.tests.filter((test) => test[1] === "python");
4010
- const hasPitonoTests = pitonoTests.length > 0;
4011
- if (hasPitonoTests) {
4012
- const { generatePitonoMetafile: generatePitonoMetafile2 } = await Promise.resolve().then(() => (init_pitonoMetafile(), pitonoMetafile_exports));
4013
- const pitonoEntryPoints = pitonoTests.map((test) => test[0]);
4014
- const metafile = await generatePitonoMetafile2(testName, pitonoEntryPoints);
4015
- const pitonoMetafilePath = `${process.cwd()}/testeranto/metafiles/python`;
4016
- await fs13.promises.mkdir(pitonoMetafilePath, { recursive: true });
4017
- fs13.writeFileSync(
4018
- `${pitonoMetafilePath}/core.json`,
4019
- JSON.stringify(metafile, null, 2)
4020
- );
4021
- console.log(
4022
- ansiC5.green(
4023
- ansiC5.inverse(`Python metafile written to: ${pitonoMetafilePath}/core.json`)
4024
- )
4025
- );
4026
- pitonoEntryPoints.forEach((entryPoint) => {
4027
- if (pm) {
4028
- pm.addToQueue(entryPoint, "python");
4029
- }
4030
- });
4031
- }
4032
- Promise.resolve(
4033
- Promise.all(
4034
- [...getSecondaryEndpointsPoints("web")].map(async (sourceFilePath) => {
4035
- const sourceFileSplit = sourceFilePath.split("/");
4036
- const sourceDir = sourceFileSplit.slice(0, -1);
4037
- const sourceFileName = sourceFileSplit[sourceFileSplit.length - 1];
4038
- const sourceFileNameMinusJs = sourceFileName.split(".").slice(0, -1).join(".");
4039
- const htmlFilePath = path11.normalize(
4040
- `${process.cwd()}/testeranto/bundles/web/${testName}/${sourceDir.join(
4041
- "/"
4042
- )}/${sourceFileNameMinusJs}.html`
4043
- );
4044
- const jsfilePath = `./${sourceFileNameMinusJs}.mjs`;
4045
- const cssFilePath = `./${sourceFileNameMinusJs}.css`;
4046
- return fs13.promises.mkdir(path11.dirname(htmlFilePath), { recursive: true }).then(
4047
- (x2) => fs13.writeFileSync(
4048
- htmlFilePath,
4049
- web_html_default(jsfilePath, htmlFilePath, cssFilePath)
4050
- )
4051
- );
4052
- })
4053
- )
4054
- );
4055
5654
  const {
4056
5655
  nodeEntryPoints,
4057
5656
  nodeEntryPointSidecars,
@@ -4060,39 +5659,53 @@ import(f).then(async (module) => {
4060
5659
  pureEntryPoints,
4061
5660
  pureEntryPointSidecars,
4062
5661
  pythonEntryPoints,
4063
- pythonEntryPointSidecars
5662
+ pythonEntryPointSidecars,
5663
+ golangEntryPoints,
5664
+ golangEntryPointSidecars
4064
5665
  } = getRunnables(config.tests, testName);
4065
- const x = [
5666
+ console.log("Node entry points:", Object.keys(nodeEntryPoints));
5667
+ console.log("Web entry points:", Object.keys(webEntryPoints));
5668
+ console.log("Pure entry points:", Object.keys(pureEntryPoints));
5669
+ const golangTests = config.tests.filter((test) => test[1] === "golang");
5670
+ const hasGolangTests = golangTests.length > 0;
5671
+ if (hasGolangTests) {
5672
+ const golingvuBuild = new GolingvuBuild2(config, testName);
5673
+ const golangEntryPoints2 = await golingvuBuild.build();
5674
+ golingvuBuild.onBundleChange(() => {
5675
+ Object.keys(golangEntryPoints2).forEach((entryPoint) => {
5676
+ if (pm) {
5677
+ pm.addToQueue(entryPoint, "golang");
5678
+ }
5679
+ });
5680
+ });
5681
+ }
5682
+ const pitonoTests = config.tests.filter((test) => test[1] === "python");
5683
+ const hasPitonoTests = pitonoTests.length > 0;
5684
+ if (hasPitonoTests) {
5685
+ const pitonoBuild = new PitonoBuild(config, testName);
5686
+ const pitonoEntryPoints = await pitonoBuild.build();
5687
+ pitonoBuild.onBundleChange(() => {
5688
+ Object.keys(pitonoEntryPoints).forEach((entryPoint) => {
5689
+ if (pm) {
5690
+ pm.addToQueue(entryPoint, "python");
5691
+ }
5692
+ });
5693
+ });
5694
+ }
5695
+ [
4066
5696
  ["pure", Object.keys(pureEntryPoints)],
4067
5697
  ["node", Object.keys(nodeEntryPoints)],
4068
5698
  ["web", Object.keys(webEntryPoints)],
4069
- ["python", Object.keys(pythonEntryPoints)]
4070
- ];
4071
- x.forEach(async ([runtime, keys]) => {
5699
+ ["python", Object.keys(pythonEntryPoints)],
5700
+ ["golang", Object.keys(golangEntryPoints)]
5701
+ ].forEach(async ([runtime, keys]) => {
4072
5702
  keys.forEach(async (k) => {
4073
- const folder = `testeranto/reports/${testName}/${k.split(".").slice(0, -1).join(".")}/${runtime}`;
4074
- await fs13.mkdirSync(folder, { recursive: true });
5703
+ fs17.mkdirSync(
5704
+ `testeranto/reports/${testName}/${k.split(".").slice(0, -1).join(".")}/${runtime}`,
5705
+ { recursive: true }
5706
+ );
4075
5707
  });
4076
5708
  });
4077
- [
4078
- [pureEntryPoints, pureEntryPointSidecars, "pure"],
4079
- [webEntryPoints, webEntryPointSidecars, "web"],
4080
- [nodeEntryPoints, nodeEntryPointSidecars, "node"],
4081
- [pythonEntryPoints, pythonEntryPointSidecars, "python"]
4082
- ].forEach(
4083
- ([eps, eps2, runtime]) => {
4084
- [...Object.keys(eps), ...Object.keys(eps2)].forEach((ep) => {
4085
- const fp = path11.resolve(
4086
- `testeranto`,
4087
- `reports`,
4088
- testName,
4089
- ep.split(".").slice(0, -1).join("."),
4090
- runtime
4091
- );
4092
- fs13.mkdirSync(fp, { recursive: true });
4093
- });
4094
- }
4095
- );
4096
5709
  process.stdin.on("keypress", (str, key) => {
4097
5710
  if (key.name === "q") {
4098
5711
  console.log("Testeranto is shutting down gracefully...");