@voltro/cli 0.55.0 → 0.57.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 (175) hide show
  1. package/CHANGELOG.md +691 -0
  2. package/bin/voltro.mjs +24 -0
  3. package/dist/apiBuild-B83Cb2Rv.js +2 -0
  4. package/dist/{apiBuild-CMvLJM_K.js → apiBuild-DDr2aNFd.js} +119 -88
  5. package/dist/bin.js +1 -1
  6. package/dist/{build-S0QOzqPT.js → build-QKP6Bm0J.js} +308 -279
  7. package/dist/buildReport-52gHKgfO.js +64 -0
  8. package/dist/{checkCommand-DNkY5kwF.js → checkCommand-BISqx1OJ.js} +1 -1
  9. package/dist/{checkCommand-fbj9GDjN.js → checkCommand-DUtMWjcR.js} +6 -6
  10. package/dist/{clusterCmd-DrVFCzSj.js → clusterCmd-CdLB1GkT.js} +1 -1
  11. package/dist/{codegen-SIepQtUl.js → codegen-Bth5lUTU.js} +2 -1
  12. package/dist/codegen-DbH7NbCR.js +2 -0
  13. package/dist/{codegenCommand-3TDJezom.js → codegenCommand-DnVuDxwT.js} +11 -11
  14. package/dist/{codemodRunner-C2zxZUIw.js → codemodRunner-BlQPfjzA.js} +222 -0
  15. package/dist/{commands-BBYJ7Q3B.js → commands-CRbxgxv0.js} +35 -35
  16. package/dist/{dashboardCommand-D2kmyCLL.js → dashboardCommand-Bf_-Ne3P.js} +5 -5
  17. package/dist/{dataCommand-BEPPQiTl.js → dataCommand-BoBJJ-Gb.js} +3 -3
  18. package/dist/{dbCommand-DZTmOFT4.js → dbCommand-CMAIz-Bf.js} +457 -441
  19. package/dist/dbCommand-DHi_RuDl.js +2 -0
  20. package/dist/dev-Bl9HqtV7.js +3 -0
  21. package/dist/{dev-Ca_A_S9v.js → dev-DOEJXicj.js} +2623 -2485
  22. package/dist/{doctorCommand-CGZJK_4o.js → doctorCommand-BrWu67JZ.js} +524 -280
  23. package/dist/doctorCommand-DrQv9SL3.js +2 -0
  24. package/dist/{dormancyCommand-DY2rYpTa.js → dormancyCommand-xn2y-pJm.js} +1 -1
  25. package/dist/{embeddingsCommand-BoCqZsgp.js → embeddingsCommand-Cn5MbRDM.js} +1 -1
  26. package/dist/emptyResultHeadline-Csa5fZOF.js +18 -0
  27. package/dist/{envCommand-Bxy2fOjc.js → envCommand-UJmJIbs9.js} +8 -8
  28. package/dist/{evolveCommand-BsbZ-XDg.js → evolveCommand-Db30twUy.js} +2 -2
  29. package/dist/frameworkTableAssembly-B96WCNJA.js +2 -0
  30. package/dist/{frameworkTableAssembly-Do-cf6RJ.js → frameworkTableAssembly-vfkzuzEo.js} +131 -104
  31. package/dist/index.js +1 -1
  32. package/dist/{infoCommand-EmM3jPKD.js → infoCommand-BjVXpMlP.js} +1 -1
  33. package/dist/inspect-B0hL41s0.js +2 -0
  34. package/dist/inspect-DZnan87F.js +1500 -0
  35. package/dist/{inspectCmd-niF97fAq.js → inspectCmd-CP-G0sVK.js} +1 -1
  36. package/dist/{inspectFetch-EMuhTG_9.js → inspectFetch-BU1NyzxV.js} +36 -24
  37. package/dist/{inspectMetrics-CGF94puw.js → inspectMetrics-BY0Sjb2F.js} +19 -19
  38. package/dist/{logsCmd-B6oNsfaZ.js → logsCmd-C5y9HyrG.js} +59 -54
  39. package/dist/{manifestBuild-DjX5MoXy.js → manifestBuild-DnbFKF6w.js} +1 -1
  40. package/dist/manifestBuild-UXrnUcXP.js +2 -0
  41. package/dist/{migrate-CGFZS-1a.js → migrate-DtC3lu7H.js} +4 -4
  42. package/dist/precompressAssets-YhTi1aWp.js +40 -0
  43. package/dist/{probeCommand-Bs3iVBSL.js → probeCommand-C5fuN6Z2.js} +2 -2
  44. package/dist/{runtimeTrace-C1BTpHGQ.js → runtimeTrace-BQL_lfz6.js} +1 -1
  45. package/dist/{scheduleCmd-DQRu6BZC.js → scheduleCmd-DYBUfo_T.js} +1 -1
  46. package/dist/{sdkgen-CXMwLg9n.js → sdkgen-CMUPrDjH.js} +1 -1
  47. package/dist/{seedRunner-Dgsiwk_e.js → seedRunner-DISBKow-.js} +16 -16
  48. package/dist/serveCommand-B_w-Mpb_.js +2544 -0
  49. package/dist/serveCommand-Dtb48ffg.js +2 -0
  50. package/dist/serveEntry.js +1 -1
  51. package/dist/{start-EOV7s1NZ.js → start-YaUehtDV.js} +580 -558
  52. package/dist/{start-DH7cat4-.js → start-s25GAIgn.js} +1 -1
  53. package/dist/startEntry.js +1 -1
  54. package/dist/staticCachePolicy-CIyj6DbS.js +15 -0
  55. package/dist/{test-DO27-x2P.js → test-jipIQ5Mx.js} +1 -1
  56. package/dist/{tracesCmd-DgtgOUdi.js → tracesCmd-C1qKa94g.js} +69 -64
  57. package/dist/{updateCommand-C_jN1w18.js → updateCommand-C9n_Z_oG.js} +8 -2
  58. package/dist/updateCommand-DsXEAHbd.js +2 -0
  59. package/dist/webDev-B6ZMX42w.js +2 -0
  60. package/dist/{webDev-B7vNj4Bq.js → webDev-BgdkyjP6.js} +1379 -1303
  61. package/dist/{webhooksCommand-B1LVcyO3.js → webhooksCommand-CYXTNvXq.js} +2 -2
  62. package/dist/{workflowsCmd-BGF-mRZ5.js → workflowsCmd-g-DNpaUc.js} +1 -1
  63. package/package.json +55 -19
  64. package/templates/AGENTS.core.md +20 -1
  65. package/templates/AGENTS.md +21 -2
  66. package/templates/agent-docs/_index.md +1 -1
  67. package/templates/agent-docs/_manifest.json +2 -2
  68. package/templates/agent-docs/ai.md +1 -1
  69. package/templates/agent-docs/authentication.md +34 -19
  70. package/templates/agent-docs/cli.md +170 -0
  71. package/templates/agent-docs/configuration.md +29 -4
  72. package/templates/agent-docs/data.md +145 -5
  73. package/templates/agent-docs/database/scaling.md +50 -2
  74. package/templates/agent-docs/deployment.md +75 -1
  75. package/templates/agent-docs/internationalization.md +32 -0
  76. package/templates/agent-docs/local-first-mobile.md +9 -2
  77. package/templates/agent-docs/observability.md +227 -0
  78. package/templates/agent-docs/plugins/audit.md +21 -5
  79. package/templates/agent-docs/plugins/billing.md +17 -0
  80. package/templates/agent-docs/plugins/broadcast.md +2 -1
  81. package/templates/agent-docs/plugins/ratelimit.md +6 -1
  82. package/templates/agent-docs/plugins/row-history.md +11 -0
  83. package/templates/agent-docs/plugins.md +19 -0
  84. package/templates/agent-docs/reference.md +1 -0
  85. package/templates/agent-docs/scheduling.md +23 -0
  86. package/templates/agent-docs/schema-driven-ui.md +81 -0
  87. package/templates/agent-docs/templates/appshells.md +3 -3
  88. package/templates/agent-docs/whats-new.md +133 -77
  89. package/templates/apps/api-ai/package.json +6 -6
  90. package/templates/apps/api-auth/package.json +8 -8
  91. package/templates/apps/api-backend/package.json +7 -7
  92. package/templates/apps/api-backend-deactivation/package.json +7 -7
  93. package/templates/apps/api-backend-mail/package.json +8 -8
  94. package/templates/apps/api-backend-mariadb/package.json +9 -9
  95. package/templates/apps/api-backend-sqlite/package.json +8 -8
  96. package/templates/apps/api-backend-storage/package.json +8 -8
  97. package/templates/apps/api-cms/package.json +9 -9
  98. package/templates/apps/api-collab/package.json +8 -8
  99. package/templates/apps/api-data-advanced/package.json +8 -8
  100. package/templates/apps/api-durable/package.json +8 -8
  101. package/templates/apps/api-feature-flags/package.json +9 -9
  102. package/templates/apps/api-governance/package.json +8 -8
  103. package/templates/apps/api-kv/package.json +8 -8
  104. package/templates/apps/api-moderation/package.json +8 -8
  105. package/templates/apps/api-observability/package.json +8 -8
  106. package/templates/apps/api-ratelimit/package.json +8 -8
  107. package/templates/apps/api-rbac/package.json +8 -8
  108. package/templates/apps/api-rest/package.json +7 -7
  109. package/templates/apps/api-row-history/package.json +8 -8
  110. package/templates/apps/api-saas/package.json +11 -11
  111. package/templates/apps/api-saas-starter/package.json +10 -10
  112. package/templates/apps/api-search/package.json +8 -8
  113. package/templates/apps/api-status/package.json +8 -8
  114. package/templates/apps/api-webhooks/package.json +9 -9
  115. package/templates/apps/changelog/package.json +7 -7
  116. package/templates/apps/changelog/src/pages/[locale]/page.tsx +7 -1
  117. package/templates/apps/edge-functions/package.json +2 -2
  118. package/templates/apps/frontend-admin/package.json +7 -8
  119. package/templates/apps/frontend-admin/src/pages/(marketing)/layout.tsx +1 -2
  120. package/templates/apps/frontend-admin/src/pages/admin/layout.tsx +1 -2
  121. package/templates/apps/frontend-app/package.json +8 -9
  122. package/templates/apps/frontend-app/src/pages/layout.tsx +1 -2
  123. package/templates/apps/frontend-auth/package.json +7 -8
  124. package/templates/apps/frontend-auth/src/components/AuthShell.tsx +1 -2
  125. package/templates/apps/frontend-blank/package.json +6 -7
  126. package/templates/apps/frontend-blank/src/pages/layout.tsx +1 -2
  127. package/templates/apps/frontend-cms/package.json +8 -9
  128. package/templates/apps/frontend-cms/src/pages/(app)/layout.tsx +1 -2
  129. package/templates/apps/frontend-collab/README.md +7 -2
  130. package/templates/apps/frontend-collab/package.json +9 -10
  131. package/templates/apps/frontend-collab/src/pages/layout.tsx +1 -2
  132. package/templates/apps/frontend-collab/src/pages/page.test.tsx +8 -4
  133. package/templates/apps/frontend-collab/src/pages/page.tsx +10 -5
  134. package/templates/apps/frontend-contact/package.json +7 -7
  135. package/templates/apps/frontend-contact/src/components/ContactForm.island.tsx +1 -1
  136. package/templates/apps/frontend-dashboard/package.json +6 -7
  137. package/templates/apps/frontend-dashboard/src/pages/(marketing)/layout.tsx +1 -2
  138. package/templates/apps/frontend-dashboard/src/pages/dashboard/layout.tsx +1 -2
  139. package/templates/apps/frontend-docs/package.json +8 -8
  140. package/templates/apps/frontend-i18n/package.json +6 -6
  141. package/templates/apps/frontend-landing/package.json +7 -7
  142. package/templates/apps/frontend-portal/package.json +7 -8
  143. package/templates/apps/frontend-portal/src/pages/(portal)/layout.tsx +1 -2
  144. package/templates/apps/frontend-saas/package.json +7 -8
  145. package/templates/apps/frontend-saas/src/pages/(marketing)/layout.tsx +1 -2
  146. package/templates/apps/frontend-saas/src/pages/dashboard/layout.tsx +1 -2
  147. package/templates/apps/frontend-spa/package.json +6 -7
  148. package/templates/apps/frontend-spa/src/pages/layout.tsx +1 -2
  149. package/templates/apps/frontend-ssr/package.json +6 -7
  150. package/templates/apps/frontend-ssr/src/pages/layout.tsx +1 -2
  151. package/templates/apps/frontend-ssr-api/package.json +7 -8
  152. package/templates/apps/frontend-ssr-api/src/pages/layout.tsx +1 -2
  153. package/templates/apps/frontend-static-blog/package.json +8 -8
  154. package/templates/apps/frontend-static-blog/src/components/ReadingProgress.island.tsx +1 -1
  155. package/templates/apps/frontend-static-blog/src/pages/[locale]/page.tsx +7 -1
  156. package/templates/apps/frontend-status/package.json +7 -8
  157. package/templates/apps/frontend-status/src/pages/layout.tsx +1 -2
  158. package/templates/apps/mobile-app/package.json +4 -4
  159. package/templates/baselines/compose/docker/api.Dockerfile +61 -5
  160. package/templates/baselines/compose/docker/web.Dockerfile +55 -10
  161. package/templates/baselines/compose-mariadb/docker/api.Dockerfile +61 -5
  162. package/templates/baselines/compose-mariadb/docker/web.Dockerfile +55 -10
  163. package/dist/apiBuild-Cl0IDx8c.js +0 -2
  164. package/dist/codegen-CN6vMM4J.js +0 -2
  165. package/dist/dbCommand-BTyBGhIA.js +0 -2
  166. package/dist/dev-DfVZaoys.js +0 -3
  167. package/dist/doctorCommand-djmqEcDC.js +0 -2
  168. package/dist/frameworkTableAssembly-Df2Ymp2f.js +0 -2
  169. package/dist/inspect-DCqILJ1G.js +0 -1197
  170. package/dist/inspect-DGJwpOAb.js +0 -2
  171. package/dist/manifestBuild-CJ2zvPvT.js +0 -2
  172. package/dist/serveCommand-C7IrCD58.js +0 -2445
  173. package/dist/serveCommand-Cjt5S9hD.js +0 -2
  174. package/dist/updateCommand-nnFjDbl4.js +0 -2
  175. package/dist/webDev-1XpVnYkW.js +0 -2
@@ -0,0 +1,64 @@
1
+ import { join as e } from "node:path";
2
+ import { existsSync as t, readFileSync as n, readdirSync as r, statSync as i } from "node:fs";
3
+ import { gzipSync as a } from "node:zlib";
4
+ //#region src/buildReport.ts
5
+ var o = 9, s = (e) => a(e, { level: o }).length, c = (n) => {
6
+ let a = 0, o = 0, s = (t) => {
7
+ for (let n of r(t, { withFileTypes: !0 })) {
8
+ let r = e(t, n.name);
9
+ n.isDirectory() ? s(r) : (a += i(r).size, o += 1);
10
+ }
11
+ };
12
+ return t(n) && s(n), {
13
+ bytes: a,
14
+ files: o
15
+ };
16
+ }, l = (a) => {
17
+ let o = e(a, ".framework", "dist"), l = e(o, "index.html");
18
+ if (!t(l)) return null;
19
+ let u = n(l, "utf8"), d = (r) => {
20
+ let i = e(o, r.replace(/^\//, ""));
21
+ if (!t(i)) return null;
22
+ let a = n(i);
23
+ return {
24
+ file: r,
25
+ gzip: s(a),
26
+ raw: a.length
27
+ };
28
+ }, f = [...u.matchAll(/(?:src|href)="(\/assets\/[^"]+\.js)"/g)].map((e) => e[1]), p = [...u.matchAll(/href="(\/assets\/[^"]+\.css)"/g)].map((e) => e[1]), m = f.map(d).filter((e) => e !== null), h = p.map(d).filter((e) => e !== null), g = e(o, "assets"), _ = 0, v = 0;
29
+ if (t(g)) for (let t of r(g)) t.endsWith(".js") && (_ += s(n(e(g, t))), v += 1);
30
+ let y = e(o, "server", "ssrEntry.js"), b = c(e(a, ".framework", "dist-web", "startBundle")), x = c(e(a, ".framework", "dist-api", "serveBundle"));
31
+ return {
32
+ firstLoad: m,
33
+ firstLoadGzip: m.reduce((e, t) => e + t.gzip, 0),
34
+ css: h,
35
+ cssGzip: h.reduce((e, t) => e + t.gzip, 0),
36
+ totalGzip: _,
37
+ chunkCount: v,
38
+ ssrEntryBytes: t(y) ? i(y).size : 0,
39
+ startBundleBytes: b.bytes,
40
+ startBundleFiles: b.files,
41
+ serveBundleBytes: x.bytes,
42
+ serveBundleFiles: x.files
43
+ };
44
+ }, u = (e) => `${(e / 1024).toFixed(1)} KB`, d = (e) => `${(e / 1e6).toFixed(2)} MB`, f = (e) => {
45
+ if (e === null) return [];
46
+ let t = [
47
+ "",
48
+ "build report — what a visitor downloads",
49
+ ""
50
+ ];
51
+ t.push(` first load ${u(e.firstLoadGzip).padStart(10)} gz ${e.firstLoad.length} file(s), entry + modulepreload`), e.css.length > 0 && t.push(` css ${u(e.cssGzip).padStart(10)} gz ${e.css.length} stylesheet(s)`), t.push(` all chunks ${u(e.totalGzip).padStart(10)} gz ${e.chunkCount} chunk(s), eager + lazy`);
52
+ let n = [...e.firstLoad].sort((e, t) => t.gzip - e.gzip).slice(0, 5);
53
+ if (n.length > 0) {
54
+ t.push("");
55
+ for (let r of n) {
56
+ let n = e.firstLoadGzip === 0 ? 0 : Math.round(r.gzip / e.firstLoadGzip * 100);
57
+ t.push(` ${u(r.gzip).padStart(10)} gz ${String(n).padStart(3)}% ${r.file}`);
58
+ }
59
+ }
60
+ let r = n[0];
61
+ return r !== void 0 && e.firstLoadGzip > 0 && r.gzip > e.firstLoadGzip / 2 && (t.push(""), t.push(` ⚠ one chunk is ${Math.round(r.gzip / e.firstLoadGzip * 100)}% of the first load: ${r.file}`), t.push(" Every visitor downloads it before the page is interactive. If that is"), t.push(" data rather than code (a content glob, a locale catalog, a dataset),"), t.push(" it usually belongs behind a dynamic import or a build-time index.")), (e.ssrEntryBytes > 0 || e.startBundleFiles > 0 || e.serveBundleFiles > 0) && (t.push(""), t.push(" server artefacts (what the image ships and a cold boot loads)"), e.ssrEntryBytes > 0 && t.push(` ssr bundle ${d(e.ssrEntryBytes).padStart(10)}`), e.startBundleFiles > 0 && t.push(` start bundle ${d(e.startBundleBytes).padStart(10)} ${e.startBundleFiles} file(s)`), e.serveBundleFiles > 0 && t.push(` serve bundle ${d(e.serveBundleBytes).padStart(10)} ${e.serveBundleFiles} file(s)`)), t.push(""), t;
62
+ };
63
+ //#endregion
64
+ export { l as collectBuildReport, f as formatBuildReport };
@@ -1,2 +1,2 @@
1
- import { a as e, i as t, o as n } from "./checkCommand-fbj9GDjN.js";
1
+ import { a as e, i as t, o as n } from "./checkCommand-DUtMWjcR.js";
2
2
  export { t as offlineManifest, e as runCheckCommand, n as toInput };
@@ -1,10 +1,10 @@
1
1
  import { t as e } from "./cliArgs-D4p8n7EE.js";
2
- import { a as t, l as n } from "./codegen-SIepQtUl.js";
2
+ import { a as t, l as n } from "./codegen-Bth5lUTU.js";
3
3
  import { r } from "./appGraph-yRuKjOba.js";
4
4
  import { n as i } from "./cliOutput-D1tSBoRM.js";
5
- import { n as a, o, r as s, t as c } from "./inspectFetch-EMuhTG_9.js";
5
+ import { n as a, o, r as s, t as c } from "./inspectFetch-BU1NyzxV.js";
6
6
  import { r as l } from "./fileTaxonomy-CbyMQYx_.js";
7
- import { S as u } from "./doctorCommand-CGZJK_4o.js";
7
+ import { S as u } from "./doctorCommand-BrWu67JZ.js";
8
8
  import { resolve as d } from "node:path";
9
9
  import { readdirSync as f, statSync as p } from "node:fs";
10
10
  import { isReactivityChannelKey as m } from "@voltro/protocol";
@@ -170,9 +170,9 @@ var h = (e) => (e === void 0 ? [] : typeof e == "string" ? [e] : e).filter((e) =
170
170
  let t = e.severity === "error" ? "✗ error" : "⚠ warn", n = e.file ? ` (${e.file})` : "";
171
171
  return `${t} ${e.rule} ${e.node}${n}\n ${e.breaks.join("; ")}\n fix: ${e.fix}`;
172
172
  }).join("\n"), O = async (e) => {
173
- let { walk: t, loadDiscovered: n, loadApiConfig: r } = await import("./dev-DfVZaoys.js"), { buildRpcEntry: i } = await import("./manifestBuild-CJ2zvPvT.js"), { buildCapabilityManifest: a } = await import("./inspect-DGJwpOAb.js"), { relative: o } = await import("node:path"), s = await n(await t(e)), c = await r(e).then((e) => e?.plugins ?? []).catch(() => []);
173
+ let { walk: t, loadDiscovered: n, loadApiConfig: r } = await import("./dev-Bl9HqtV7.js"), { buildRpcEntry: i } = await import("./manifestBuild-UXrnUcXP.js"), { buildCapabilityManifest: a } = await import("./inspect-B0hL41s0.js"), { relative: o } = await import("node:path"), s = await n(await t(e), { root: e }), c = await r(e).then((e) => e?.plugins ?? []).catch(() => []);
174
174
  try {
175
- let { mergePluginRoutesInto: e } = await import("./dev-DfVZaoys.js");
175
+ let { mergePluginRoutesInto: e } = await import("./dev-Bl9HqtV7.js");
176
176
  e({
177
177
  plugins: c,
178
178
  queries: s.queries,
@@ -189,7 +189,7 @@ var h = (e) => (e === void 0 ? [] : typeof e == "string" ? [e] : e).filter((e) =
189
189
  ...s.mutations.map((e) => l(e.descriptor, "mutation", e.file)),
190
190
  ...s.actions.map((e) => l(e.descriptor, "action", e.file)),
191
191
  ...s.streams.map((e) => l(e.descriptor, "stream", e.file))
192
- ], { assembleFrameworkTables: d } = await import("./frameworkTableAssembly-Df2Ymp2f.js"), f = await d({ root: e }).catch((e) => (console.warn(`\n⚠ plugin tables could not be collected — this report is INCOMPLETE.\n ${e instanceof Error ? e.message.split("\n")[0] : String(e)}\n`), [])), p = new Set(s.tables.map((e) => e.tableName)), m = [...[...p].map((e) => ({ name: e })), ...f.map((e) => e.tableName).filter((e) => !p.has(e)).map((e) => ({
192
+ ], { assembleFrameworkTables: d } = await import("./frameworkTableAssembly-B96WCNJA.js"), f = await d({ root: e }).catch((e) => (console.warn(`\n⚠ plugin tables could not be collected — this report is INCOMPLETE.\n ${e instanceof Error ? e.message.split("\n")[0] : String(e)}\n`), [])), p = new Set(s.tables.map((e) => e.tableName)), m = [...[...p].map((e) => ({ name: e })), ...f.map((e) => e.tableName).filter((e) => !p.has(e)).map((e) => ({
193
193
  name: e,
194
194
  framework: !0
195
195
  }))], h = c;
@@ -1,5 +1,5 @@
1
1
  import { n as e } from "./cliOutput-D1tSBoRM.js";
2
- import { n as t, o as n, r, t as i } from "./inspectFetch-EMuhTG_9.js";
2
+ import { n as t, o as n, r, t as i } from "./inspectFetch-BU1NyzxV.js";
3
3
  import { ansi as a } from "@voltro/logger";
4
4
  //#region src/clusterCmd.ts
5
5
  var o = () => {
@@ -10,7 +10,8 @@ import { isAgentDescriptor as m } from "@voltro/ai/agent";
10
10
  var h = /* @__PURE__ */ new Set(/* @__PURE__ */ "crypto.fs.path.os.net.http.https.http2.tls.dns.dgram.stream.zlib.child_process.worker_threads.cluster.readline.vm.module.perf_hooks.async_hooks.inspector.v8.process.tty.repl.constants.sys.string_decoder".split(".")), g = (e) => e.startsWith("node:") || h.has(e) || e === "@voltro/workflow" ? !0 : e === "@voltro/database/wire" ? !1 : e === "@voltro/database" || e.startsWith("@voltro/database/") || e === "@voltro/runtime" || e.startsWith("@voltro/runtime/") ? !0 : e === "@voltro/ai/agent" || e === "@voltro/ai/events" ? !1 : !!(e === "@voltro/ai" || e.startsWith("@voltro/ai/") || [
11
11
  "@voltro/protocol/session",
12
12
  "@voltro/protocol/jwt",
13
- "@voltro/protocol/apikey"
13
+ "@voltro/protocol/apikey",
14
+ "@voltro/protocol/identity"
14
15
  ].includes(e) || e === "@voltro/env/server" || e.startsWith("@effect/cluster") || e.startsWith("@effect/sql") || e === "@effect/platform-node" || [
15
16
  "pg",
16
17
  "postgres",
@@ -0,0 +1,2 @@
1
+ import { t as e } from "./codegen-Bth5lUTU.js";
2
+ export { e as checkRpcGroupFreshness };
@@ -1,17 +1,17 @@
1
- import { Dn as e, En as t, V as n, l as r, u as i } from "./dev-Ca_A_S9v.js";
2
- import { n as a } from "./frameworkTableAssembly-Do-cf6RJ.js";
3
- import { i as o, r as s } from "./codegen-SIepQtUl.js";
1
+ import { Fn as e, In as t, l as n, q as r, u as i } from "./dev-DOEJXicj.js";
2
+ import { n as a } from "./frameworkTableAssembly-vfkzuzEo.js";
3
+ import { i as o, r as s } from "./codegen-Bth5lUTU.js";
4
4
  import { n as c, r as l } from "./mobileCommand-D9O6iq3D.js";
5
5
  import { basename as u, relative as d, resolve as f } from "node:path";
6
6
  //#region src/codegenCommand.ts
7
- var p = async (t) => {
8
- let { config: i, present: a, error: o } = await r(t);
7
+ var p = async (e) => {
8
+ let { config: i, present: a, error: o } = await n(e);
9
9
  if (a && i === null) return {
10
10
  kind: "refused",
11
11
  reason: "app.config.ts exists but could not be loaded" + (o === void 0 ? "" : ` — ${o instanceof Error ? o.message : String(o)}`)
12
12
  };
13
- let c = i?.plugins ?? [], { pluginContributions: l, pluginErrorImports: d, pluginRpcImports: f, pluginAliases: p } = await n(c, i?.name ?? u(t), t), h = await s({
14
- root: t,
13
+ let c = i?.plugins ?? [], { pluginContributions: l, pluginErrorImports: d, pluginRpcImports: f, pluginAliases: p } = await r(c, i?.name ?? u(e), e), h = await s({
14
+ root: e,
15
15
  ...l.length > 0 ? { pluginContributions: l } : {},
16
16
  ...d.length > 0 ? { pluginErrorImports: d } : {},
17
17
  ...f.length > 0 ? { pluginRpcImports: f } : {},
@@ -19,7 +19,7 @@ var p = async (t) => {
19
19
  ...i?.name === void 0 ? {} : { apiName: i.name }
20
20
  });
21
21
  if (!h) return { kind: "nothing-to-write" };
22
- let g = await m(t, i), _ = await e(h, g);
22
+ let g = await m(e, i), _ = await t(h, g);
23
23
  return {
24
24
  kind: "wrote",
25
25
  file: h,
@@ -29,9 +29,9 @@ var p = async (t) => {
29
29
  tables: g.size,
30
30
  dts: _
31
31
  };
32
- }, m = async (e, n) => {
33
- let r = await o(e), { tables: s } = await i(r), c = await a({ root: e });
34
- return t(s, c, n?.analytics?.tables ?? []);
32
+ }, m = async (t, n) => {
33
+ let r = await o(t), { tables: s } = await i(r, { root: t }), c = await a({ root: t });
34
+ return e(s, c, n?.analytics?.tables ?? []);
35
35
  }, h = async (e) => {
36
36
  let t = f(e.find((e) => !e.startsWith("-")) ?? process.cwd()), n = await l(t);
37
37
  if (n.apis.kind !== "not-a-mobile-app") return c(t, n);
@@ -6185,6 +6185,228 @@ var S = (e, t, n) => {
6185
6185
  "Partial registries (`Partial<Record<WidgetKind, …>>` or per-kind lookups)",
6186
6186
  "need nothing."
6187
6187
  ].join("\n")
6188
+ }),
6189
+ w({
6190
+ version: "0.56.0",
6191
+ id: "0.56.0/01_inspect_answers_are_observations",
6192
+ title: "inspect answers are `Observation`s — the payload is `.data`",
6193
+ kind: "manual",
6194
+ reach: "beyond-source",
6195
+ appliesTo: ({ text: e }) => e.find("/_voltro/inspect").length > 0,
6196
+ note: [
6197
+ "Every 2xx `/_voltro/inspect/*` response is now an envelope:",
6198
+ "",
6199
+ " { data, scope, origin, completeness, capturedAt }",
6200
+ "",
6201
+ "What you read before is `.data`. So:",
6202
+ "",
6203
+ " curl …/_voltro/inspect/subscriptions | jq .resume",
6204
+ " curl …/_voltro/inspect/subscriptions | jq .data.resume # now",
6205
+ "",
6206
+ "The other four fields are the point of the change, not decoration:",
6207
+ "",
6208
+ " • `scope.kind` — `process` (this replica only), `shared-store` (every",
6209
+ " replica would answer the same), `fleet` (assembled), `declaration`",
6210
+ " (from the source tree). A `process` answer on a multi-replica",
6211
+ " deployment is a SAMPLE, and it used to look identical to a fleet-wide",
6212
+ " one.",
6213
+ " • `origin.replicaId` / `origin.instanceId` — which process answered, and",
6214
+ " which generation of it. Query twice and you can now tell whether you",
6215
+ " reached the same one.",
6216
+ " • `completeness.fleetSize` — how many replicas exist. ABSENT when it",
6217
+ " could not be determined; never `1` as a guess.",
6218
+ " • `capturedAt` — the ORIGIN’s clock. Do not compare it with another",
6219
+ " replica’s.",
6220
+ "",
6221
+ "Check anything that reads these endpoints outside your TypeScript sources:",
6222
+ "dashboards, `jq` filters in alerts, runbook commands, CI health checks,",
6223
+ "scrape configs. A reader that pulls a field straight off the top level now",
6224
+ "reads `undefined` — which in a health check is the failure mode worth",
6225
+ "looking for first, because `undefined` and \"zero\" render the same in most",
6226
+ "alerting rules."
6227
+ ].join("\n")
6228
+ }),
6229
+ w({
6230
+ version: "0.56.0",
6231
+ id: "0.56.0/02_broadcast_gap_is_one_object",
6232
+ title: "attachBroadcastBus's onGap now receives a single BroadcastGap object",
6233
+ kind: "manual",
6234
+ appliesTo: ({ project: e }) => e.getSourceFiles().some((e) => e.getFullText().includes("attachBroadcastBus")),
6235
+ note: [
6236
+ "`attachBroadcastBus({ onGap })` now receives ONE argument — a `BroadcastGap`",
6237
+ "— instead of `(origin, missed)`.",
6238
+ "",
6239
+ " before: onGap: (origin, missed) => refreshAll(`missed ${missed} from ${origin}`)",
6240
+ " after: onGap: (gap) => refreshAll(gap.reason)",
6241
+ "",
6242
+ "`gap.reason` is a ready-made sentence for your log line. `gap.origin` and",
6243
+ "`gap.missed` are still there and still EXACT — but they are optional now,",
6244
+ "because the bus reports two kinds of hole and only one of them has a peer",
6245
+ "to blame:",
6246
+ "",
6247
+ " • a peer's serial jumped → `{ reason, origin, missed }`",
6248
+ " • this replica was not subscribed for a while, or the transport re-dialled",
6249
+ " → `{ reason }` alone",
6250
+ "",
6251
+ "The recovery is the same for both: re-run every live query. If your handler",
6252
+ "reads `origin`/`missed`, guard them — a hole with no peer is now reachable.",
6253
+ "",
6254
+ "Related, and needing no change from you: `attachBroadcastBus` no longer",
6255
+ "rejects when the broker is unreachable at attach time. It warns, keeps the",
6256
+ "local path working, retries in the background, and reports the time it spent",
6257
+ "unsubscribed as a gap. If you wrapped the call in a try/catch to survive a",
6258
+ "restarting broker, that catch is now dead code."
6259
+ ].join("\n")
6260
+ }),
6261
+ w({
6262
+ version: "0.56.0",
6263
+ id: "0.56.0/03_outbox_drain_needs_an_identity",
6264
+ title: "drainOutbox now requires claimedBy — the fleet-wide exactly-once gate",
6265
+ kind: "manual",
6266
+ appliesTo: ({ project: e }) => e.getSourceFiles().some((e) => e.getFullText().includes("drainOutbox")),
6267
+ note: [
6268
+ "`drainOutbox({ … })` now requires a `claimedBy: string`.",
6269
+ "",
6270
+ "Why: the drain used to read every `pending` row and run its handler. Every",
6271
+ "replica runs the drain, so every effect was dispatched once PER REPLICA — on",
6272
+ "the happy path, every time. Rows are now claimed atomically",
6273
+ "(`pending → delivering`) and a racing replica loses the row instead of",
6274
+ "duplicating the side effect.",
6275
+ "",
6276
+ "What to pass: an id for this PROCESS, not for the replica. A replica name",
6277
+ "survives a restart (`POD_NAME` on a StatefulSet, `VOLTRO_REPLICA_ID` by",
6278
+ "definition) while the work does not, so a pod that died mid-delivery would",
6279
+ "look like it still held its own claim:",
6280
+ "",
6281
+ " import { instanceId } from '@voltro/protocol/identity'",
6282
+ " await drainOutbox({ store, handlers, claimedBy: instanceId() })",
6283
+ "",
6284
+ "Also new and optional: `claimLeaseMs` (default 5 minutes) — how long a claim",
6285
+ "stands before another replica may take the row. Set it ABOVE your slowest",
6286
+ "handler. A lease shorter than a real delivery hands the same row to a second",
6287
+ "replica while the first is still working, which is the duplicate this",
6288
+ "mechanism removes, reintroduced by a number.",
6289
+ "",
6290
+ "If you do NOT call `drainOutbox` yourself, there is nothing to do: `voltro",
6291
+ "dev` and `voltro serve` pass the identity for you."
6292
+ ].join("\n")
6293
+ }),
6294
+ w({
6295
+ version: "0.56.0",
6296
+ id: "0.56.0/04_reaction_dedupe_is_one_claim",
6297
+ title: "runReaction's dedupe is a single atomic claim",
6298
+ kind: "manual",
6299
+ appliesTo: ({ project: e }) => e.getSourceFiles().some((e) => {
6300
+ let t = e.getFullText();
6301
+ return t.includes("runReaction") || t.includes("ReactionRunDeps");
6302
+ }),
6303
+ note: [
6304
+ "`ReactionRunDeps.dedupe` changed from `{ has, add }` to `{ claim }`:",
6305
+ "",
6306
+ " // before",
6307
+ " dedupe: { has: (k) => seen.has(k), add: (k) => { seen.add(k) } }",
6308
+ " // after",
6309
+ " dedupe: { claim: (k) => (seen.has(k) ? false : (seen.add(k), true)) }",
6310
+ "",
6311
+ "Why it is not a rename. `has` then `add` is a read followed by a write, and",
6312
+ "two callers both read \"not seen\" before either writes — so `dedupeKey`, the",
6313
+ "field `defineReaction` refuses to boot without, let the same change act once",
6314
+ "per replica. Every single-instance run confirmed it worked, which is why it",
6315
+ "survived: the gate was real in exactly the configuration that cannot observe",
6316
+ "it.",
6317
+ "",
6318
+ "The claim is also taken BEFORE the act now, not after. That is what makes it",
6319
+ "a gate rather than a report, and it has a cost worth knowing: an act that",
6320
+ "THROWS has already consumed its key and is not re-run by a later duplicate.",
6321
+ "Durability belongs to the workflow the act starts, not to the trigger.",
6322
+ "",
6323
+ "If you do NOT call `runReaction` yourself, there is nothing to do. `voltro",
6324
+ "dev` and `voltro serve` now pass a durable, fleet-wide claimer",
6325
+ "(`_voltro_change_claims`), so a reaction acts once across the whole fleet",
6326
+ "instead of once per replica — no code change on your side."
6327
+ ].join("\n")
6328
+ }),
6329
+ w({
6330
+ version: "0.56.0",
6331
+ id: "0.56.0/05_plugin_bind_context_claims_a_change",
6332
+ title: "PluginBindContext requires claimChange; change identity moved to @voltro/database",
6333
+ kind: "manual",
6334
+ appliesTo: ({ project: e }) => e.getSourceFiles().some((e) => {
6335
+ let t = e.getFullText();
6336
+ return t.includes("PluginBindContext") || t.includes("changeDigest") || t.includes("OccurrenceCounter") || t.includes("composeChangeKey") || t.includes("parseChangeKey");
6337
+ }),
6338
+ note: [
6339
+ "Two changes, both narrow.",
6340
+ "",
6341
+ "1. `PluginBindContext` now has a REQUIRED `claimChange(scope, key) =>",
6342
+ " Promise<boolean>`. The framework supplies it on both boot paths, so a",
6343
+ " plugin only READS it — nothing to do unless you construct a",
6344
+ " `PluginBindContext` yourself, which in practice means a unit-test",
6345
+ " harness:",
6346
+ "",
6347
+ " const ctx: PluginBindContext = {",
6348
+ " scheduleCoordinated: …,",
6349
+ " claimChange: () => Promise.resolve(true), // add this",
6350
+ " }",
6351
+ "",
6352
+ " In a real harness, decide what the case is testing before reaching for",
6353
+ " `true`: a stub that always claims asserts the SINGLE-replica behaviour.",
6354
+ " To exercise a fleet, share one claim ledger across the stubs — a `Set`",
6355
+ " of `${scope}/${key}` is enough.",
6356
+ "",
6357
+ " Why it is required rather than optional: an absent gate reads exactly",
6358
+ " like a gate that passed, and every consumer of this field is counting or",
6359
+ " sending something. `plugin-billing` accrued a usage unit per metered row",
6360
+ " change on EVERY replica, so a tenant on two pods was invoiced twice.",
6361
+ "",
6362
+ "2. The change-identity helpers moved from `@voltro/plugin-cdc-out` to",
6363
+ " `@voltro/database`, beside `ChangeEvent` itself:",
6364
+ "",
6365
+ " -import { changeDigest, composeChangeKey, OccurrenceCounter } from '@voltro/plugin-cdc-out'",
6366
+ " +import { changeDigest, composeChangeKey, OccurrenceCounter } from '@voltro/database'",
6367
+ "",
6368
+ " `parseChangeKey` moved with them. `canonicalJson` did NOT become public:",
6369
+ " it is internal to the digest, and `@voltro/runtime` already exports a",
6370
+ " different function of that name."
6371
+ ].join("\n")
6372
+ }),
6373
+ w({
6374
+ version: "0.56.0",
6375
+ id: "0.56.0/06_serve_is_api_only",
6376
+ title: "`voltro serve` on a WEB app now refuses — use `voltro start`",
6377
+ kind: "manual",
6378
+ reach: "beyond-source",
6379
+ appliesTo: (e) => e.text.scanned === 0 || e.text.find("voltro serve").length > 0,
6380
+ note: [
6381
+ "`voltro serve` is the production server for an API app. On a WEB app it now",
6382
+ "refuses with a one-line message instead of what it used to do.",
6383
+ "",
6384
+ " web app, production voltro start . (unchanged)",
6385
+ " web app, development voltro dev . (unchanged)",
6386
+ " api app voltro serve . (unchanged)",
6387
+ "",
6388
+ "Nothing changes for an api. For a web app the old behaviour was not a working",
6389
+ "alternative that is being taken away:",
6390
+ "",
6391
+ " • In production it already failed — the serve fast path requires an api",
6392
+ " serve bundle, which a web build never produces, so it exited 1 pointing",
6393
+ " at an artefact that cannot exist.",
6394
+ " • Below production it ran a SECOND vite build without Tailwind, without the",
6395
+ " image pipeline and without the islands entries, then served it through",
6396
+ " `vite preview`. With Tailwind that build aborts. Without it, it succeeds",
6397
+ " and DELETES `dist/server`, the island shells and every pre-rendered page —",
6398
+ " after which `voltro start` cannot boot at all.",
6399
+ "",
6400
+ "Search your Dockerfiles, compose files, CI jobs, Procfiles and runbooks:",
6401
+ "",
6402
+ " grep -rn \"voltro serve\" .",
6403
+ "",
6404
+ "and change the ones that point at a WEB app to `voltro start`. An api entry",
6405
+ "stays as it is. (The shipped Dockerfiles already run the precompiled bundle",
6406
+ "directly — `node .framework/dist-web/startBundle/startEntry.js` for web,",
6407
+ "`node .framework/dist-api/serveBundle/serveEntry.js` for an api — which is",
6408
+ "faster still and needs no CLI in the runtime image.)"
6409
+ ].join("\n")
6188
6410
  })
6189
6411
  ], J = /* @__PURE__ */ new Set([
6190
6412
  "node_modules",