@repo-os/repoos 0.5.45

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 (362) hide show
  1. package/LICENSE.md +110 -0
  2. package/README.md +272 -0
  3. package/dist/.build-info.json +4 -0
  4. package/dist/.build-stamp.json +3 -0
  5. package/dist/cli/colors.d.ts +13 -0
  6. package/dist/cli/colors.js +37 -0
  7. package/dist/cli/index.d.ts +2 -0
  8. package/dist/cli/index.js +221 -0
  9. package/dist/commands/check.d.ts +170 -0
  10. package/dist/commands/check.js +1227 -0
  11. package/dist/commands/docs.d.ts +2 -0
  12. package/dist/commands/docs.js +70 -0
  13. package/dist/commands/gc.d.ts +1 -0
  14. package/dist/commands/gc.js +57 -0
  15. package/dist/commands/init.d.ts +9 -0
  16. package/dist/commands/init.js +699 -0
  17. package/dist/commands/screenshots.d.ts +7 -0
  18. package/dist/commands/screenshots.js +77 -0
  19. package/dist/commands/serve.d.ts +55 -0
  20. package/dist/commands/serve.js +204 -0
  21. package/dist/commands/status.d.ts +140 -0
  22. package/dist/commands/status.js +569 -0
  23. package/dist/commands/stop.d.ts +1 -0
  24. package/dist/commands/stop.js +59 -0
  25. package/dist/commands/tasks.d.ts +47 -0
  26. package/dist/commands/tasks.js +334 -0
  27. package/dist/commands/tunnel.d.ts +1 -0
  28. package/dist/commands/tunnel.js +1271 -0
  29. package/dist/commands/ui-harness.d.ts +53 -0
  30. package/dist/commands/ui-harness.js +62 -0
  31. package/dist/commands/ui-smoke.d.ts +6 -0
  32. package/dist/commands/ui-smoke.js +220 -0
  33. package/dist/commands/upgrade.d.ts +15 -0
  34. package/dist/commands/upgrade.js +188 -0
  35. package/dist/core/auth-store.d.ts +81 -0
  36. package/dist/core/auth-store.js +530 -0
  37. package/dist/core/auth.d.ts +75 -0
  38. package/dist/core/auth.js +124 -0
  39. package/dist/core/bootstrap.d.ts +41 -0
  40. package/dist/core/bootstrap.js +236 -0
  41. package/dist/core/build.d.ts +92 -0
  42. package/dist/core/build.js +249 -0
  43. package/dist/core/canary.d.ts +10 -0
  44. package/dist/core/canary.js +14 -0
  45. package/dist/core/check-failure-summary.d.ts +10 -0
  46. package/dist/core/check-failure-summary.js +34 -0
  47. package/dist/core/config.d.ts +160 -0
  48. package/dist/core/config.js +1288 -0
  49. package/dist/core/context-pack.d.ts +74 -0
  50. package/dist/core/context-pack.js +778 -0
  51. package/dist/core/db.d.ts +236 -0
  52. package/dist/core/db.js +747 -0
  53. package/dist/core/detect.d.ts +69 -0
  54. package/dist/core/detect.js +251 -0
  55. package/dist/core/docs.d.ts +76 -0
  56. package/dist/core/docs.js +225 -0
  57. package/dist/core/frontmatter.d.ts +29 -0
  58. package/dist/core/frontmatter.js +215 -0
  59. package/dist/core/git.d.ts +505 -0
  60. package/dist/core/git.js +1453 -0
  61. package/dist/core/indexer.d.ts +33 -0
  62. package/dist/core/indexer.js +282 -0
  63. package/dist/core/input.d.ts +66 -0
  64. package/dist/core/input.js +222 -0
  65. package/dist/core/logger.d.ts +70 -0
  66. package/dist/core/logger.js +138 -0
  67. package/dist/core/models.d.ts +45 -0
  68. package/dist/core/models.js +291 -0
  69. package/dist/core/net-probe.d.ts +4 -0
  70. package/dist/core/net-probe.js +20 -0
  71. package/dist/core/providers/deepinfra.d.ts +23 -0
  72. package/dist/core/providers/deepinfra.js +44 -0
  73. package/dist/core/providers/index.d.ts +24 -0
  74. package/dist/core/providers/index.js +59 -0
  75. package/dist/core/providers/openrouter.d.ts +28 -0
  76. package/dist/core/providers/openrouter.js +82 -0
  77. package/dist/core/providers/spend.d.ts +86 -0
  78. package/dist/core/providers/spend.js +286 -0
  79. package/dist/core/providers/types.d.ts +56 -0
  80. package/dist/core/providers/types.js +39 -0
  81. package/dist/core/repoos.d.ts +59 -0
  82. package/dist/core/repoos.js +221 -0
  83. package/dist/core/runtime.d.ts +35 -0
  84. package/dist/core/runtime.js +167 -0
  85. package/dist/core/skills-registry.d.ts +39 -0
  86. package/dist/core/skills-registry.js +148 -0
  87. package/dist/core/skills-registry.test.d.ts +1 -0
  88. package/dist/core/skills-registry.test.js +52 -0
  89. package/dist/core/sysmem.d.ts +7 -0
  90. package/dist/core/sysmem.js +55 -0
  91. package/dist/core/tailscale.d.ts +2 -0
  92. package/dist/core/tailscale.js +19 -0
  93. package/dist/core/task.d.ts +53 -0
  94. package/dist/core/task.js +310 -0
  95. package/dist/core/toml-line.d.ts +20 -0
  96. package/dist/core/toml-line.js +52 -0
  97. package/dist/core/toml-validate.d.ts +44 -0
  98. package/dist/core/toml-validate.js +335 -0
  99. package/dist/core/tunnel-assistant.d.ts +30 -0
  100. package/dist/core/tunnel-assistant.js +65 -0
  101. package/dist/core/tunnel-registry.d.ts +96 -0
  102. package/dist/core/tunnel-registry.js +267 -0
  103. package/dist/core/tunnel-registry.test.d.ts +1 -0
  104. package/dist/core/tunnel-registry.test.js +309 -0
  105. package/dist/core/tunnel.d.ts +103 -0
  106. package/dist/core/tunnel.js +320 -0
  107. package/dist/core/types.d.ts +811 -0
  108. package/dist/core/types.js +27 -0
  109. package/dist/core/worktree-gc.d.ts +57 -0
  110. package/dist/core/worktree-gc.js +194 -0
  111. package/dist/server/__tests__/integration-job.test.d.ts +1 -0
  112. package/dist/server/__tests__/integration-job.test.js +129 -0
  113. package/dist/server/agents.d.ts +1020 -0
  114. package/dist/server/agents.js +4070 -0
  115. package/dist/server/attachments.d.ts +51 -0
  116. package/dist/server/attachments.js +130 -0
  117. package/dist/server/auto-engineering.d.ts +45 -0
  118. package/dist/server/auto-engineering.js +275 -0
  119. package/dist/server/branchless-release.d.ts +22 -0
  120. package/dist/server/branchless-release.js +67 -0
  121. package/dist/server/built-in-agents.d.ts +305 -0
  122. package/dist/server/built-in-agents.js +1838 -0
  123. package/dist/server/cto-monitor.d.ts +35 -0
  124. package/dist/server/cto-monitor.js +281 -0
  125. package/dist/server/cto.d.ts +125 -0
  126. package/dist/server/cto.js +590 -0
  127. package/dist/server/deployments.d.ts +119 -0
  128. package/dist/server/deployments.js +325 -0
  129. package/dist/server/diff-snapshot.d.ts +20 -0
  130. package/dist/server/diff-snapshot.js +73 -0
  131. package/dist/server/done.d.ts +160 -0
  132. package/dist/server/done.js +488 -0
  133. package/dist/server/freeform.d.ts +55 -0
  134. package/dist/server/freeform.js +179 -0
  135. package/dist/server/handoff.d.ts +99 -0
  136. package/dist/server/handoff.js +575 -0
  137. package/dist/server/hetzner.d.ts +45 -0
  138. package/dist/server/hetzner.js +117 -0
  139. package/dist/server/icons.d.ts +8 -0
  140. package/dist/server/icons.js +195 -0
  141. package/dist/server/integration-job.d.ts +75 -0
  142. package/dist/server/integration-job.js +144 -0
  143. package/dist/server/integration-orchestrator.d.ts +211 -0
  144. package/dist/server/integration-orchestrator.js +1299 -0
  145. package/dist/server/integration-status.d.ts +48 -0
  146. package/dist/server/integration-status.js +71 -0
  147. package/dist/server/live-index.d.ts +295 -0
  148. package/dist/server/live-index.js +452 -0
  149. package/dist/server/model-test.d.ts +20 -0
  150. package/dist/server/model-test.js +100 -0
  151. package/dist/server/ntfy.d.ts +57 -0
  152. package/dist/server/ntfy.js +112 -0
  153. package/dist/server/pm-attachments.d.ts +35 -0
  154. package/dist/server/pm-attachments.js +181 -0
  155. package/dist/server/pm-runs.d.ts +58 -0
  156. package/dist/server/pm-runs.js +80 -0
  157. package/dist/server/preview.d.ts +174 -0
  158. package/dist/server/preview.js +641 -0
  159. package/dist/server/release.d.ts +88 -0
  160. package/dist/server/release.js +449 -0
  161. package/dist/server/reload.d.ts +194 -0
  162. package/dist/server/reload.js +586 -0
  163. package/dist/server/remote-validation.d.ts +132 -0
  164. package/dist/server/remote-validation.js +478 -0
  165. package/dist/server/repo-lock.d.ts +36 -0
  166. package/dist/server/repo-lock.js +141 -0
  167. package/dist/server/review-guard.d.ts +14 -0
  168. package/dist/server/review-guard.js +159 -0
  169. package/dist/server/review.d.ts +243 -0
  170. package/dist/server/review.js +1211 -0
  171. package/dist/server/routes/agents.d.ts +6 -0
  172. package/dist/server/routes/agents.js +28 -0
  173. package/dist/server/routes/auth.d.ts +60 -0
  174. package/dist/server/routes/auth.js +755 -0
  175. package/dist/server/routes/config.d.ts +20 -0
  176. package/dist/server/routes/config.js +347 -0
  177. package/dist/server/routes/debugger.d.ts +33 -0
  178. package/dist/server/routes/debugger.js +360 -0
  179. package/dist/server/routes/deployments.d.ts +3 -0
  180. package/dist/server/routes/deployments.js +16 -0
  181. package/dist/server/routes/docs.d.ts +8 -0
  182. package/dist/server/routes/docs.js +135 -0
  183. package/dist/server/routes/helpers.d.ts +21 -0
  184. package/dist/server/routes/helpers.js +171 -0
  185. package/dist/server/routes/index.d.ts +19 -0
  186. package/dist/server/routes/index.js +18 -0
  187. package/dist/server/routes/info.d.ts +17 -0
  188. package/dist/server/routes/info.js +177 -0
  189. package/dist/server/routes/inputs.d.ts +7 -0
  190. package/dist/server/routes/inputs.js +125 -0
  191. package/dist/server/routes/model-providers.d.ts +27 -0
  192. package/dist/server/routes/model-providers.js +94 -0
  193. package/dist/server/routes/models.d.ts +3 -0
  194. package/dist/server/routes/models.js +36 -0
  195. package/dist/server/routes/notify.d.ts +2 -0
  196. package/dist/server/routes/notify.js +17 -0
  197. package/dist/server/routes/playground.d.ts +29 -0
  198. package/dist/server/routes/playground.js +81 -0
  199. package/dist/server/routes/release.d.ts +20 -0
  200. package/dist/server/routes/release.js +86 -0
  201. package/dist/server/routes/router.d.ts +12 -0
  202. package/dist/server/routes/router.js +32 -0
  203. package/dist/server/routes/skill-registry.d.ts +5 -0
  204. package/dist/server/routes/skill-registry.js +51 -0
  205. package/dist/server/routes/tasks.d.ts +58 -0
  206. package/dist/server/routes/tasks.js +1442 -0
  207. package/dist/server/routes/transcribe.d.ts +2 -0
  208. package/dist/server/routes/transcribe.js +124 -0
  209. package/dist/server/routes/types.d.ts +68 -0
  210. package/dist/server/routes/types.js +1 -0
  211. package/dist/server/routes/ui.d.ts +5 -0
  212. package/dist/server/routes/ui.js +81 -0
  213. package/dist/server/routes/utils.d.ts +3 -0
  214. package/dist/server/routes/utils.js +23 -0
  215. package/dist/server/serve-reaper.d.ts +135 -0
  216. package/dist/server/serve-reaper.js +491 -0
  217. package/dist/server/server.d.ts +49 -0
  218. package/dist/server/server.js +2171 -0
  219. package/dist/server/supervisor.d.ts +89 -0
  220. package/dist/server/supervisor.js +231 -0
  221. package/dist/server/system.d.ts +198 -0
  222. package/dist/server/system.js +480 -0
  223. package/dist/server/task-check.d.ts +45 -0
  224. package/dist/server/task-check.js +71 -0
  225. package/dist/server/task-transitions.d.ts +51 -0
  226. package/dist/server/task-transitions.js +78 -0
  227. package/dist/server/task-watchdog.d.ts +158 -0
  228. package/dist/server/task-watchdog.js +681 -0
  229. package/dist/server/test-run.d.ts +28 -0
  230. package/dist/server/test-run.js +81 -0
  231. package/dist/server/watcher.d.ts +21 -0
  232. package/dist/server/watcher.js +194 -0
  233. package/dist/server/write.d.ts +94 -0
  234. package/dist/server/write.js +345 -0
  235. package/dist/ui/assets/AgentsView-CF4wRvHh.css +1 -0
  236. package/dist/ui/assets/AgentsView-D-myL-kA.js +1 -0
  237. package/dist/ui/assets/ContextView-D3TC-RSp.css +1 -0
  238. package/dist/ui/assets/ContextView-DsOqAdyE.js +4 -0
  239. package/dist/ui/assets/DashboardView-BOhsIJqO.js +1 -0
  240. package/dist/ui/assets/DashboardView-Ck9o0RP2.css +1 -0
  241. package/dist/ui/assets/DeploymentsView--iIUVfEH.css +1 -0
  242. package/dist/ui/assets/DeploymentsView-DXu_FYR2.js +1 -0
  243. package/dist/ui/assets/InputsView-24HVbVPk.js +1 -0
  244. package/dist/ui/assets/InputsView-BLb7GHtx.css +1 -0
  245. package/dist/ui/assets/LoginView-6QlGg6cx.css +1 -0
  246. package/dist/ui/assets/LoginView-BqupI0Lt.js +1 -0
  247. package/dist/ui/assets/ReleasesView-BEG1A0YH.css +1 -0
  248. package/dist/ui/assets/ReleasesView-CAgMuxpe.js +3 -0
  249. package/dist/ui/assets/SettingsView-CA-NYSMK.css +1 -0
  250. package/dist/ui/assets/SettingsView-O3iZSnjg.js +3 -0
  251. package/dist/ui/assets/WorkView-D8Tl6qwy.js +1 -0
  252. package/dist/ui/assets/WorkView-DMYL2s3W.css +1 -0
  253. package/dist/ui/assets/abnfDiagram-VCTEODGH-J5lkSnEE.js +1 -0
  254. package/dist/ui/assets/arc-BHZnmhhM.js +1 -0
  255. package/dist/ui/assets/architecture-7GRP2DOG-pLdFt-xS.js +1 -0
  256. package/dist/ui/assets/architectureDiagram-5GKGNRK7-C3k89uKX.js +36 -0
  257. package/dist/ui/assets/array-BifhSqXX.js +1 -0
  258. package/dist/ui/assets/blockDiagram-I7D4REHJ-AWNoBzop.js +129 -0
  259. package/dist/ui/assets/button-lbikqSph.js +1 -0
  260. package/dist/ui/assets/c4Diagram-7LVT6UL2-DKG1D5gd.js +38 -0
  261. package/dist/ui/assets/channel-gA4qBv3A.js +1 -0
  262. package/dist/ui/assets/chunk-2Q5K7J3B-C1jixKkw.js +1 -0
  263. package/dist/ui/assets/chunk-4HAMMTFA-D1YR8lF_.js +62 -0
  264. package/dist/ui/assets/chunk-5VM5RSS4-ZNzvKenW.js +15 -0
  265. package/dist/ui/assets/chunk-75Z2AOVW-5GuBxfsL.js +2 -0
  266. package/dist/ui/assets/chunk-DU6HZSFF-DfdNNqwa.js +127 -0
  267. package/dist/ui/assets/chunk-F27PBJKO-BPZzinQ4.js +1 -0
  268. package/dist/ui/assets/chunk-FOHPRMQF-l2z4K2jD.js +161 -0
  269. package/dist/ui/assets/chunk-GMAD6QVW-DGWvSKj5.js +72 -0
  270. package/dist/ui/assets/chunk-GVQU2GXP-D6Aw75wJ.js +1 -0
  271. package/dist/ui/assets/chunk-IMKFNOWR-B8mMBKCW.js +231 -0
  272. package/dist/ui/assets/chunk-JWPE2WC7-DVXcaiue.js +1 -0
  273. package/dist/ui/assets/chunk-L3NEJ4N5-D5OJuXYE.js +1 -0
  274. package/dist/ui/assets/chunk-OSK3NFVY-B7r9w2UW.js +10 -0
  275. package/dist/ui/assets/chunk-P2QGCYS3-C74X4AQX.js +1 -0
  276. package/dist/ui/assets/chunk-POPQ4Y6H-C5_u1gUS.js +1 -0
  277. package/dist/ui/assets/chunk-PWAF6VOD-DfoTLtxn.js +1 -0
  278. package/dist/ui/assets/chunk-SHT3W25Y-D40m2eqz.js +168 -0
  279. package/dist/ui/assets/chunk-SVP7TREG-euxi0Kap.js +88 -0
  280. package/dist/ui/assets/chunk-TICWLB2K-fkdxngzN.js +206 -0
  281. package/dist/ui/assets/chunk-XXDRQBXY-DFBUG-OT.js +1 -0
  282. package/dist/ui/assets/chunk-Y2CYZVJY-DsF7k-Jl.js +1 -0
  283. package/dist/ui/assets/classDiagram-ZZMXUADV-BzW8bq2P.js +1 -0
  284. package/dist/ui/assets/classDiagram-v2-VYDZK3BY-BzW8bq2P.js +1 -0
  285. package/dist/ui/assets/cose-bilkent-JH36ORCC-BTcgMon1.js +1 -0
  286. package/dist/ui/assets/cynefin-OW5HDTMX-B5m_COsS.js +1 -0
  287. package/dist/ui/assets/cynefinDiagram-5FMLGOSQ-C-AG6CGe.js +62 -0
  288. package/dist/ui/assets/cytoscape.esm-FBntH-9t.js +321 -0
  289. package/dist/ui/assets/dagre-GXQ25YYZ-DDfDnp8L.js +4 -0
  290. package/dist/ui/assets/dagre-PrKaheQc.js +1 -0
  291. package/dist/ui/assets/defaultLocale-BFoDCU3G.js +1 -0
  292. package/dist/ui/assets/diagram-S7CK7UJ4-DjQZAlEY.js +30 -0
  293. package/dist/ui/assets/diagram-UQ7AKVKN-DAZ9yp1B.js +41 -0
  294. package/dist/ui/assets/diagram-VSXAHHWV-BWepUKJD.js +3 -0
  295. package/dist/ui/assets/diagram-VX7I27RA-EcV1J81b.js +24 -0
  296. package/dist/ui/assets/diagram-Z3DM3KII-Dbz7XU_K.js +24 -0
  297. package/dist/ui/assets/dist-DTg6UBE_.js +1 -0
  298. package/dist/ui/assets/ebnfDiagram-PWID7BFC-BUyQw8Mm.js +1 -0
  299. package/dist/ui/assets/erDiagram-RLTQ6QDP-WVf8ukKt.js +99 -0
  300. package/dist/ui/assets/eventmodeling-NTZA5JFV-DHqyLOAn.js +1 -0
  301. package/dist/ui/assets/flowDiagram-HODETNUW-CYk_ze5K.js +1 -0
  302. package/dist/ui/assets/ganttDiagram-EL5Y4UJY-rB4MZuB-.js +292 -0
  303. package/dist/ui/assets/gitGraph-4MIJSDKK-BOTWM8dY.js +1 -0
  304. package/dist/ui/assets/gitGraphDiagram-WWUBYQGX-eYscuhtP.js +106 -0
  305. package/dist/ui/assets/graphlib-DS17s2tU.js +1 -0
  306. package/dist/ui/assets/index-BACBfnga.css +1 -0
  307. package/dist/ui/assets/index-BOQ-ust6.js +26 -0
  308. package/dist/ui/assets/info-A6RAGUB7-_67wOORe.js +1 -0
  309. package/dist/ui/assets/infoDiagram-27XIBGKW-XVXbddTA.js +2 -0
  310. package/dist/ui/assets/init-C-OQMol4.js +1 -0
  311. package/dist/ui/assets/ishikawaDiagram-5VMMS53U-ClLNiEru.js +70 -0
  312. package/dist/ui/assets/journeyDiagram-3NMN7TZE-NRawjR6i.js +139 -0
  313. package/dist/ui/assets/kanban-definition-UXKFOSKX-BgSzBfIx.js +89 -0
  314. package/dist/ui/assets/katex-DolUETbr.js +257 -0
  315. package/dist/ui/assets/line-KAyfuul4.js +1 -0
  316. package/dist/ui/assets/linear-cCCPOpu7.js +1 -0
  317. package/dist/ui/assets/mermaid-parser.core-CgXZk1iN.js +7 -0
  318. package/dist/ui/assets/mermaid.core-BUUkChHW.js +44 -0
  319. package/dist/ui/assets/mindmap-definition-YA3MSWOX-Cpn7vW4r.js +96 -0
  320. package/dist/ui/assets/ordinal-BDEzSJ7C.js +1 -0
  321. package/dist/ui/assets/packet-AYTQ26CC-0lZwM-d6.js +1 -0
  322. package/dist/ui/assets/path-COt_16Va.js +1 -0
  323. package/dist/ui/assets/pegDiagram-XKGWAZYB-impy0inn.js +1 -0
  324. package/dist/ui/assets/pie-WAS4IAKB-CqfdGHYg.js +1 -0
  325. package/dist/ui/assets/pieDiagram-E7YTZNPT-CxjL4I1h.js +39 -0
  326. package/dist/ui/assets/quadrantDiagram-AXDQQJYC-Cjd1QMIe.js +7 -0
  327. package/dist/ui/assets/radar-RG4KPBEZ-CRkQIwiv.js +1 -0
  328. package/dist/ui/assets/railroad-74A4TZTK-i67XSWTB.js +1 -0
  329. package/dist/ui/assets/railroad-abnf-HS5TGJTU-Cv9m5aS3.js +1 -0
  330. package/dist/ui/assets/railroad-ebnf-LZEXJU2U-C5ZIn-Jh.js +1 -0
  331. package/dist/ui/assets/railroad-peg-WCYAUIDC-CGra9Oq-.js +1 -0
  332. package/dist/ui/assets/railroadDiagram-O6MQD6OU-_pK0qyaY.js +1 -0
  333. package/dist/ui/assets/releases-B0WNV-SY.js +1 -0
  334. package/dist/ui/assets/repoos-cto-square.webp +0 -0
  335. package/dist/ui/assets/repoos-helpful-pm-square.webp +0 -0
  336. package/dist/ui/assets/repoos-orchestrator-square.webp +0 -0
  337. package/dist/ui/assets/repoos-performance-agent-square.webp +0 -0
  338. package/dist/ui/assets/repoos-ross-from-friends-square.webp +0 -0
  339. package/dist/ui/assets/repoos-tech-debt-agent-square.webp +0 -0
  340. package/dist/ui/assets/requirementDiagram-BXWQKSXE-CRrFX-yw.js +84 -0
  341. package/dist/ui/assets/rough.esm-By172zw-.js +1 -0
  342. package/dist/ui/assets/sankeyDiagram-P5KCCOFB-X_xFRj9E.js +40 -0
  343. package/dist/ui/assets/sequenceDiagram-WJ2MYXX4-Byb49lKf.js +162 -0
  344. package/dist/ui/assets/sizeCapture-INFHLROL-B0uUizjq.js +1 -0
  345. package/dist/ui/assets/src-BH-TyZbA.js +1 -0
  346. package/dist/ui/assets/stateDiagram-D77RDMKH-CzaPrqYF.js +1 -0
  347. package/dist/ui/assets/stateDiagram-v2-MP3YSRHH-BCXckz7K.js +1 -0
  348. package/dist/ui/assets/swimlanes-42K2YHIH-Cx_1lnqr.js +1 -0
  349. package/dist/ui/assets/swimlanesDiagram-VR7AAH4N-54qsKi6A.js +8 -0
  350. package/dist/ui/assets/timeline-definition-24CTP7MA-B1IbZPQ-.js +120 -0
  351. package/dist/ui/assets/treeView-Q6P3EWNA-DFWhVE3d.js +1 -0
  352. package/dist/ui/assets/treemap-WGGIJYW6-BmbYPThn.js +1 -0
  353. package/dist/ui/assets/vendor-ui-DPm7zLxi.js +3 -0
  354. package/dist/ui/assets/vendor-vue-CobgyEJp.js +1 -0
  355. package/dist/ui/assets/vennDiagram-4TSXK5OY-Ae2AtRpt.js +34 -0
  356. package/dist/ui/assets/wardley-WFR3VGLG-BtD4X4tL.js +1 -0
  357. package/dist/ui/assets/wardleyDiagram-VM6X3IG4-B3YN2fTd.js +78 -0
  358. package/dist/ui/assets/xychartDiagram-S5SC5T6Z-CIzJfMKA.js +7 -0
  359. package/dist/ui/favicon.svg +11 -0
  360. package/dist/ui/index.html +49 -0
  361. package/dist/ui/sw.js +48 -0
  362. package/package.json +91 -0
@@ -0,0 +1,55 @@
1
+ /**
2
+ * Memory facts the OS won't give you straight. `os.freemem()` counts only
3
+ * fully-idle pages — on macOS that is near-zero at all times because the kernel
4
+ * fills unused RAM with reclaimable cache and inactive pages. This module
5
+ * reports the number that actually matters: how much the OS can hand back on
6
+ * demand without swapping.
7
+ */
8
+ import { execFileSync } from "node:child_process";
9
+ import { readFileSync } from "node:fs";
10
+ import { freemem, platform } from "node:os";
11
+ function run(cmd, args) {
12
+ try {
13
+ return execFileSync(cmd, args, {
14
+ encoding: "utf8",
15
+ stdio: ["ignore", "pipe", "ignore"],
16
+ timeout: 4000,
17
+ });
18
+ }
19
+ catch {
20
+ return null;
21
+ }
22
+ }
23
+ /**
24
+ * Bytes the OS can reclaim on demand without swapping:
25
+ * free + inactive + speculative + purgeable (macOS, via `vm_stat`), or
26
+ * `MemAvailable` (Linux, via `/proc/meminfo`). Falls back to `os.freemem()`
27
+ * when the platform probe is unavailable or fails.
28
+ */
29
+ export function availableMemBytes() {
30
+ const p = platform();
31
+ if (p === "darwin") {
32
+ const out = run("vm_stat", []);
33
+ if (out) {
34
+ const pageSize = Number(out.match(/page size of (\d+) bytes/)?.[1]) || 4096;
35
+ const pages = (label) => Number(out.match(new RegExp(`${label}:\\s+(\\d+)\\.`))?.[1]) || 0;
36
+ const reclaimable = pages("Pages free") +
37
+ pages("Pages inactive") +
38
+ pages("Pages speculative") +
39
+ pages("Pages purgeable");
40
+ if (reclaimable > 0)
41
+ return reclaimable * pageSize;
42
+ }
43
+ }
44
+ else if (p === "linux") {
45
+ try {
46
+ const avail = readFileSync("/proc/meminfo", "utf8").match(/^MemAvailable:\s+(\d+)\s+kB/m);
47
+ if (avail)
48
+ return Number(avail[1]) * 1024;
49
+ }
50
+ catch {
51
+ /* fall through */
52
+ }
53
+ }
54
+ return freemem();
55
+ }
@@ -0,0 +1,2 @@
1
+ /** This machine's Tailscale IPv4 address, or null if Tailscale isn't installed/running. */
2
+ export declare function detectTailscaleIPv4(): string | null;
@@ -0,0 +1,19 @@
1
+ /**
2
+ * Best-effort Tailscale detection, used to pick a sane default bind host.
3
+ */
4
+ import { execFileSync } from "node:child_process";
5
+ /** This machine's Tailscale IPv4 address, or null if Tailscale isn't installed/running. */
6
+ export function detectTailscaleIPv4() {
7
+ try {
8
+ const out = execFileSync("tailscale", ["ip", "-4"], {
9
+ timeout: 1500,
10
+ stdio: ["ignore", "pipe", "ignore"],
11
+ })
12
+ .toString()
13
+ .trim();
14
+ return out || null;
15
+ }
16
+ catch {
17
+ return null;
18
+ }
19
+ }
@@ -0,0 +1,53 @@
1
+ import { type Task, type Status, type Assignee, type TaskGitInfo } from "./types.js";
2
+ export declare const ACTIVITY_HEADING = "## Activity";
3
+ /** User-attached screenshots section (0123). Rendered into the body, kept before `## Activity`. */
4
+ export declare const SCREENSHOTS_HEADING = "## Screenshots";
5
+ /** The user's verbatim freeform prompt, preserved so an agent rewrite can't lose it. */
6
+ export declare const ORIGINAL_PROMPT_HEADING = "## Original prompt";
7
+ /** ISO-8601 UTC timestamp to the second, e.g. 2026-06-01T09:14:02Z. */
8
+ export declare function utcTimestamp(): string;
9
+ /**
10
+ * Normalize a legacy date-only or partial timestamp to full ISO-8601 UTC.
11
+ * `2026-06-01` → `2026-06-01T00:00:00Z`. Null passthrough.
12
+ */
13
+ export declare function normalizeTimestamp(value: string | null): string | null;
14
+ /**
15
+ * Append a single activity entry to the body's Activity section.
16
+ * Creates the section if it does not exist. The Activity section is always
17
+ * the last thing in the body — append-only invariant.
18
+ */
19
+ export declare function appendActivityEntry(body: string, line: string): string;
20
+ /**
21
+ * Extract a top-level `## Heading` section from a body — the heading line
22
+ * through the last line before the next `## ` heading (or EOF), trimmed of
23
+ * surrounding blank lines. Returns null when the heading is absent.
24
+ */
25
+ export declare function extractSection(body: string, heading: string): string | null;
26
+ /**
27
+ * Remove the `## Heading` section (see {@link extractSection}) from a body,
28
+ * collapsing the blank lines it leaves behind. Unchanged when the heading is
29
+ * absent.
30
+ */
31
+ export declare function removeSection(body: string, heading: string): string;
32
+ /**
33
+ * Single change-recording helper. Every mutation path MUST call this.
34
+ * Stamps `updated_at` and appends an activity log entry onto `task.body`.
35
+ *
36
+ * @param task The task to record a change on (mutated in-place).
37
+ * @param entry The activity line content after the timestamp,
38
+ * e.g. `status inbox→ready · nick`.
39
+ */
40
+ export declare function recordChange(task: Task, entry: string): void;
41
+ /** Latest successful-close-out timestamp recorded in the append-only activity log. */
42
+ export declare function releasedAtFromActivity(body: string): string | null;
43
+ export interface ParseTaskArgs {
44
+ content: string;
45
+ absPath: string;
46
+ root: string;
47
+ defaultStatus: Status;
48
+ defaultAssignee: Assignee;
49
+ git?: TaskGitInfo;
50
+ }
51
+ export declare function parseTask(args: ParseTaskArgs): Task;
52
+ /** Build the file content for a Task, preserving unknown frontmatter. */
53
+ export declare function serializeTask(task: Task): string;
@@ -0,0 +1,310 @@
1
+ /**
2
+ * Turn a markdown file (content + path) into a normalized Task, and turn a
3
+ * Task back into file content for writing. Normalization is forgiving: missing
4
+ * fields get sensible derived defaults so even a bare markdown file becomes a
5
+ * usable task.
6
+ */
7
+ import { basename, relative } from "node:path";
8
+ import { parseDocument, serializeDocument } from "./frontmatter.js";
9
+ import { STATUSES } from "./types.js";
10
+ import { emptyGitInfo } from "./git.js";
11
+ /** Canonical frontmatter key order, so writes produce tidy, stable diffs. */
12
+ const KEY_ORDER = [
13
+ "id",
14
+ "title",
15
+ "type",
16
+ "status",
17
+ "needs_input",
18
+ "needs_input_reason",
19
+ "needs_merge",
20
+ "no_source_change",
21
+ "priority",
22
+ "area",
23
+ "assigned_to",
24
+ "created_by",
25
+ "branch",
26
+ "tags",
27
+ "agent_override",
28
+ "cli_override",
29
+ "model_override",
30
+ "pm_agent_override",
31
+ "pm_cli_override",
32
+ "pm_model_override",
33
+ "review_agent_override",
34
+ "review_cli_override",
35
+ "review_model_override",
36
+ "hotfix",
37
+ "hotfix_target",
38
+ "created_at",
39
+ "updated_at",
40
+ ];
41
+ export const ACTIVITY_HEADING = "## Activity";
42
+ /** User-attached screenshots section (0123). Rendered into the body, kept before `## Activity`. */
43
+ export const SCREENSHOTS_HEADING = "## Screenshots";
44
+ /** The user's verbatim freeform prompt, preserved so an agent rewrite can't lose it. */
45
+ export const ORIGINAL_PROMPT_HEADING = "## Original prompt";
46
+ /**
47
+ * A release is a successful close-out event, not any prose mentioning a
48
+ * release. `markTaskReleased` is the sole writer of this exact marker.
49
+ */
50
+ const RELEASE_ACTIVITY = /^- (\d{4}-\d{2}-\d{2}T[^\s]+) · status [a-z]+→done, release:success\r?$/gmu;
51
+ /** ISO-8601 UTC timestamp to the second, e.g. 2026-06-01T09:14:02Z. */
52
+ export function utcTimestamp() {
53
+ return new Date().toISOString().replace(/\.\d{3}Z$/, "Z");
54
+ }
55
+ /**
56
+ * Normalize a legacy date-only or partial timestamp to full ISO-8601 UTC.
57
+ * `2026-06-01` → `2026-06-01T00:00:00Z`. Null passthrough.
58
+ */
59
+ export function normalizeTimestamp(value) {
60
+ if (!value)
61
+ return null;
62
+ if (/^\d{4}-\d{2}-\d{2}$/.test(value))
63
+ return `${value}T00:00:00Z`;
64
+ return value;
65
+ }
66
+ /**
67
+ * Append a single activity entry to the body's Activity section.
68
+ * Creates the section if it does not exist. The Activity section is always
69
+ * the last thing in the body — append-only invariant.
70
+ */
71
+ export function appendActivityEntry(body, line) {
72
+ const trimmed = body.replace(/\s+$/, "");
73
+ const headingIndex = trimmed.lastIndexOf(`\n${ACTIVITY_HEADING}\n`);
74
+ if (headingIndex === -1) {
75
+ return `${trimmed}\n\n${ACTIVITY_HEADING}\n\n${line}\n`;
76
+ }
77
+ return `${trimmed}\n${line}\n`;
78
+ }
79
+ /** The line index where a top-level `## Heading` section starts, or -1. */
80
+ function sectionStart(lines, heading) {
81
+ return lines.findIndex((l) => l.trim() === heading);
82
+ }
83
+ /** The line index of the next top-level `## ` heading after `from`, or `lines.length`. */
84
+ function nextSection(lines, from) {
85
+ for (let i = from; i < lines.length; i++) {
86
+ if (/^##\s/.test(lines[i].trim()))
87
+ return i;
88
+ }
89
+ return lines.length;
90
+ }
91
+ /**
92
+ * Extract a top-level `## Heading` section from a body — the heading line
93
+ * through the last line before the next `## ` heading (or EOF), trimmed of
94
+ * surrounding blank lines. Returns null when the heading is absent.
95
+ */
96
+ export function extractSection(body, heading) {
97
+ const lines = body.split("\n");
98
+ const start = sectionStart(lines, heading);
99
+ if (start === -1)
100
+ return null;
101
+ return lines
102
+ .slice(start, nextSection(lines, start + 1))
103
+ .join("\n")
104
+ .trim();
105
+ }
106
+ /**
107
+ * Remove the `## Heading` section (see {@link extractSection}) from a body,
108
+ * collapsing the blank lines it leaves behind. Unchanged when the heading is
109
+ * absent.
110
+ */
111
+ export function removeSection(body, heading) {
112
+ const lines = body.split("\n");
113
+ const start = sectionStart(lines, heading);
114
+ if (start === -1)
115
+ return body;
116
+ const end = nextSection(lines, start + 1);
117
+ const before = lines.slice(0, start).join("\n").replace(/\s+$/, "");
118
+ const after = lines.slice(end).join("\n").replace(/^\s+/, "");
119
+ return [before, after].filter(Boolean).join("\n\n");
120
+ }
121
+ /**
122
+ * Single change-recording helper. Every mutation path MUST call this.
123
+ * Stamps `updated_at` and appends an activity log entry onto `task.body`.
124
+ *
125
+ * @param task The task to record a change on (mutated in-place).
126
+ * @param entry The activity line content after the timestamp,
127
+ * e.g. `status inbox→ready · nick`.
128
+ */
129
+ export function recordChange(task, entry) {
130
+ task.updated_at = utcTimestamp();
131
+ task.body = appendActivityEntry(task.body, `- ${task.updated_at} · ${entry}`);
132
+ }
133
+ /** Latest successful-close-out timestamp recorded in the append-only activity log. */
134
+ export function releasedAtFromActivity(body) {
135
+ let releasedAt = null;
136
+ for (const match of body.matchAll(RELEASE_ACTIVITY))
137
+ releasedAt = match[1];
138
+ return releasedAt;
139
+ }
140
+ function deriveIdFromFilename(file) {
141
+ const name = basename(file).replace(/\.[^.]+$/, "");
142
+ const m = name.match(/^(\d{2,})/);
143
+ if (m)
144
+ return m[1];
145
+ return name;
146
+ }
147
+ function deriveTitleFromBody(body, fallback) {
148
+ const h1 = body.match(/^\s*#\s+(.+)$/m);
149
+ if (h1)
150
+ return h1[1].trim();
151
+ return fallback;
152
+ }
153
+ function normalizeStatus(raw, fallback) {
154
+ const s = String(raw ?? "").toLowerCase();
155
+ return STATUSES.includes(s) ? s : fallback;
156
+ }
157
+ function resolveAssignee(raw) {
158
+ const v = raw.toLowerCase().trim();
159
+ if (v === "ai" || v === "agent")
160
+ return "ai";
161
+ if (v === "" || v === "unassigned" || v === "none")
162
+ return "unassigned";
163
+ return "human";
164
+ }
165
+ export function parseTask(args) {
166
+ const { content, absPath, root, defaultStatus, defaultAssignee } = args;
167
+ const { data, body } = parseDocument(content);
168
+ const relPath = relative(root, absPath).split("\\").join("/");
169
+ const id = String(data.id ?? deriveIdFromFilename(absPath));
170
+ const title = String(data.title ?? deriveTitleFromBody(body, id));
171
+ const assignedTo = String(data.assigned_to ?? "");
172
+ const assignee = resolveAssignee(assignedTo || (defaultAssignee === "unassigned" ? "" : defaultAssignee));
173
+ // collect unknown keys to preserve on write
174
+ const known = new Set(KEY_ORDER);
175
+ const extra = {};
176
+ for (const [k, v] of Object.entries(data)) {
177
+ if (!known.has(k))
178
+ extra[k] = v;
179
+ }
180
+ // Per-task agent override fields
181
+ const agentOverride = typeof data.agent_override === "string" && data.agent_override ? data.agent_override : null;
182
+ const cliOverride = typeof data.cli_override === "string" && data.cli_override ? data.cli_override : null;
183
+ const modelOverride = typeof data.model_override === "string" && data.model_override ? data.model_override : null;
184
+ // Per-task PM agent override fields
185
+ const pmAgentOverride = typeof data.pm_agent_override === "string" && data.pm_agent_override
186
+ ? data.pm_agent_override
187
+ : null;
188
+ const pmCliOverride = typeof data.pm_cli_override === "string" && data.pm_cli_override ? data.pm_cli_override : null;
189
+ const pmModelOverride = typeof data.pm_model_override === "string" && data.pm_model_override
190
+ ? data.pm_model_override
191
+ : null;
192
+ // Per-task reviewer agent override fields
193
+ const reviewAgentOverride = typeof data.review_agent_override === "string" && data.review_agent_override
194
+ ? data.review_agent_override
195
+ : null;
196
+ const reviewCliOverride = typeof data.review_cli_override === "string" && data.review_cli_override
197
+ ? data.review_cli_override
198
+ : null;
199
+ const reviewModelOverride = typeof data.review_model_override === "string" && data.review_model_override
200
+ ? data.review_model_override
201
+ : null;
202
+ // read created_at with fallback to deprecated created
203
+ const created_at = data.created_at
204
+ ? String(data.created_at)
205
+ : data.created
206
+ ? String(data.created)
207
+ : null;
208
+ // read updated_at with fallback to deprecated updated
209
+ const updated_at = data.updated_at
210
+ ? String(data.updated_at)
211
+ : data.updated
212
+ ? String(data.updated)
213
+ : null;
214
+ return {
215
+ id,
216
+ title,
217
+ type: String(data.type ?? "feature"),
218
+ status: normalizeStatus(data.status, "inbox"),
219
+ needsInput: data.needs_input === true,
220
+ needsInputReason: typeof data.needs_input_reason === "string" ? data.needs_input_reason : undefined,
221
+ needsMerge: data.needs_merge === true,
222
+ noSourceChange: data.no_source_change === true,
223
+ priority: String(data.priority ?? "p2"),
224
+ area: String(data.area ?? "general"),
225
+ assignee,
226
+ assignedTo: assignedTo || (assignee === "unassigned" ? "" : assignee),
227
+ createdBy: String(data.created_by ?? ""),
228
+ branch: String(data.branch ?? ""),
229
+ tags: Array.isArray(data.tags) ? data.tags.map(String) : [],
230
+ created_at,
231
+ updated_at,
232
+ releasedAt: releasedAtFromActivity(body),
233
+ path: relPath,
234
+ absPath,
235
+ body,
236
+ extra,
237
+ agentOverride,
238
+ cliOverride,
239
+ modelOverride,
240
+ pmAgentOverride,
241
+ pmCliOverride,
242
+ pmModelOverride,
243
+ reviewAgentOverride,
244
+ reviewCliOverride,
245
+ reviewModelOverride,
246
+ hotfix: data.hotfix === true ? true : undefined,
247
+ hotfixTarget: data.hotfix === true ? (data.hotfix_target === "main" ? "main" : "branch") : undefined,
248
+ git: args.git ?? emptyGitInfo(),
249
+ };
250
+ }
251
+ /** Build the file content for a Task, preserving unknown frontmatter. */
252
+ export function serializeTask(task) {
253
+ const data = {
254
+ id: task.id,
255
+ title: task.title,
256
+ type: task.type,
257
+ status: task.status,
258
+ priority: task.priority,
259
+ area: task.area,
260
+ assigned_to: task.assignedTo || (task.assignee === "ai" ? "ai" : ""),
261
+ created_by: task.createdBy,
262
+ branch: task.branch,
263
+ };
264
+ if (task.tags.length)
265
+ data.tags = task.tags;
266
+ // Only ever write `needs_input` / `needs_merge` when true — false is the
267
+ // default and is never persisted, so clearing the flag removes the key.
268
+ // The reason is only ever meaningful alongside the flag itself — clearing
269
+ // needsInput (or never setting a reason) must never leave a stale reason
270
+ // behind to be misread on a later re-escalation.
271
+ if (task.needsInput) {
272
+ data.needs_input = true;
273
+ if (task.needsInputReason)
274
+ data.needs_input_reason = task.needsInputReason;
275
+ }
276
+ if (task.needsMerge)
277
+ data.needs_merge = true;
278
+ if (task.noSourceChange)
279
+ data.no_source_change = true;
280
+ if (task.agentOverride)
281
+ data.agent_override = task.agentOverride;
282
+ if (task.cliOverride)
283
+ data.cli_override = task.cliOverride;
284
+ if (task.modelOverride)
285
+ data.model_override = task.modelOverride;
286
+ if (task.pmAgentOverride)
287
+ data.pm_agent_override = task.pmAgentOverride;
288
+ if (task.pmCliOverride)
289
+ data.pm_cli_override = task.pmCliOverride;
290
+ if (task.pmModelOverride)
291
+ data.pm_model_override = task.pmModelOverride;
292
+ if (task.reviewAgentOverride)
293
+ data.review_agent_override = task.reviewAgentOverride;
294
+ if (task.reviewCliOverride)
295
+ data.review_cli_override = task.reviewCliOverride;
296
+ if (task.reviewModelOverride)
297
+ data.review_model_override = task.reviewModelOverride;
298
+ if (task.hotfix) {
299
+ data.hotfix = true;
300
+ data.hotfix_target = task.hotfixTarget ?? "branch";
301
+ }
302
+ if (task.created_at)
303
+ data.created_at = normalizeTimestamp(task.created_at);
304
+ if (task.updated_at)
305
+ data.updated_at = normalizeTimestamp(task.updated_at);
306
+ // re-attach preserved unknown keys
307
+ for (const [k, v] of Object.entries(task.extra))
308
+ data[k] = v;
309
+ return serializeDocument(data, task.body, KEY_ORDER);
310
+ }
@@ -0,0 +1,20 @@
1
+ /**
2
+ * Line-level helpers shared by RepoOS's small TOML readers and writers
3
+ * (config.ts, tunnel.ts).
4
+ *
5
+ * The readers used to strip comments with `line.replace(/#.*$/, "")`, which
6
+ * also cut quoted values at the first `#`. The Agents page then saved that
7
+ * cut value back, which is how the reviewer's instructions in repoos.toml lost
8
+ * everything after "with exactly `" (the next character was the `#` of
9
+ * `## Verdict`). Anything with a `#0348`-style task reference hit the same.
10
+ */
11
+ /** Drop a trailing `# comment`, ignoring `#` inside "double" or 'single' quoted strings. */
12
+ export declare function stripTomlComment(line: string): string;
13
+ /**
14
+ * Turn a quoted TOML scalar back into its string. Double-quoted values are
15
+ * decoded with JSON rules, which is exactly how the writers encode them
16
+ * (`JSON.stringify`), so `\"` and `\\` round-trip instead of gaining a
17
+ * backslash on every save. A value that isn't valid JSON (for example a
18
+ * hand-written literal `\d`) falls back to stripping the outer quotes.
19
+ */
20
+ export declare function unquoteTomlString(s: string): string;
@@ -0,0 +1,52 @@
1
+ /**
2
+ * Line-level helpers shared by RepoOS's small TOML readers and writers
3
+ * (config.ts, tunnel.ts).
4
+ *
5
+ * The readers used to strip comments with `line.replace(/#.*$/, "")`, which
6
+ * also cut quoted values at the first `#`. The Agents page then saved that
7
+ * cut value back, which is how the reviewer's instructions in repoos.toml lost
8
+ * everything after "with exactly `" (the next character was the `#` of
9
+ * `## Verdict`). Anything with a `#0348`-style task reference hit the same.
10
+ */
11
+ /** Drop a trailing `# comment`, ignoring `#` inside "double" or 'single' quoted strings. */
12
+ export function stripTomlComment(line) {
13
+ let quote = null;
14
+ for (let i = 0; i < line.length; i++) {
15
+ const ch = line[i];
16
+ if (quote) {
17
+ if (quote === '"' && ch === "\\") {
18
+ i++; // skip the escaped character, including an escaped quote
19
+ continue;
20
+ }
21
+ if (ch === quote)
22
+ quote = null;
23
+ }
24
+ else if (ch === '"' || ch === "'") {
25
+ quote = ch;
26
+ }
27
+ else if (ch === "#") {
28
+ return line.slice(0, i);
29
+ }
30
+ }
31
+ return line;
32
+ }
33
+ /**
34
+ * Turn a quoted TOML scalar back into its string. Double-quoted values are
35
+ * decoded with JSON rules, which is exactly how the writers encode them
36
+ * (`JSON.stringify`), so `\"` and `\\` round-trip instead of gaining a
37
+ * backslash on every save. A value that isn't valid JSON (for example a
38
+ * hand-written literal `\d`) falls back to stripping the outer quotes.
39
+ */
40
+ export function unquoteTomlString(s) {
41
+ if (s.length >= 2 && s.startsWith('"') && s.endsWith('"')) {
42
+ try {
43
+ const decoded = JSON.parse(s);
44
+ if (typeof decoded === "string")
45
+ return decoded;
46
+ }
47
+ catch {
48
+ /* not JSON-compatible: fall through */
49
+ }
50
+ }
51
+ return s.replace(/^["']|["']$/g, "");
52
+ }
@@ -0,0 +1,44 @@
1
+ /**
2
+ * Dependency-free TOML syntax validator (#0375).
3
+ *
4
+ * The Settings page's raw editor writes `repoos.toml` verbatim, so a malformed
5
+ * save must be rejected *before* it reaches disk — `loadConfig`'s reader is
6
+ * deliberately forgiving (it skips lines it can't parse), which would turn a
7
+ * typo into a silently-ignored config instead of an error the user can see.
8
+ *
9
+ * This is a validator, not a parser: it walks the document and reports the
10
+ * first structural problem it finds (unterminated string/array, missing `=`,
11
+ * bad table header, invalid scalar) with a 1-based line number. It accepts the
12
+ * TOML shapes RepoOS itself emits plus the common hand-written ones (dotted
13
+ * and quoted keys, literal strings, single-line arrays, dates/times,
14
+ * hex/octal/binary numbers). It deliberately does not enforce key uniqueness
15
+ * or table-redefinition rules — those are valid-TOML concerns that never
16
+ * affect what `loadConfig` reads, and rejecting on them would make the escape
17
+ * hatch stricter than the loader it feeds.
18
+ *
19
+ * Crucially, it rejects the *valid TOML* shapes that `parseFlatToml`
20
+ * (`config.ts`) cannot read: multi-line strings, multi-line arrays, and inline
21
+ * tables. Those would otherwise sail through a save and then be silently
22
+ * misread (the first line of a multi-line array parses as the string `"["`,
23
+ * an inline table as a plain string), so a whole save could take no effect
24
+ * with no error — the exact silent-config failure this gate exists to stop.
25
+ */
26
+ export interface TomlValidationResult {
27
+ ok: boolean;
28
+ /** Human-readable reason, without a line prefix. Present when `ok` is false. */
29
+ error?: string;
30
+ /** 1-based line the problem was found on. Present when `ok` is false. */
31
+ line?: number;
32
+ }
33
+ /**
34
+ * Validate a TOML document's syntax. Returns `{ ok: true }` when the whole
35
+ * document is structurally well-formed, or `{ ok: false, error, line }` with
36
+ * the first problem found. Never throws on malformed input.
37
+ */
38
+ export declare function validateToml(source: string): TomlValidationResult;
39
+ /**
40
+ * Format a validation failure for display, with the line folded into the
41
+ * message so callers that only carry a string (the HTTP JSON error, the store)
42
+ * still surface it.
43
+ */
44
+ export declare function formatTomlError(result: TomlValidationResult): string;