@voltro/cli 0.47.0 → 0.49.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 (101) hide show
  1. package/CHANGELOG.md +147 -0
  2. package/dist/{apiBuild-FpHCWiv6.js → apiBuild-QmYHaCF4.js} +1 -1
  3. package/dist/apiBuild-dZbHdqMg.js +2 -0
  4. package/dist/bin.js +1 -1
  5. package/dist/{build-zVygXxGB.js → build-Bi4O_g7T.js} +6 -6
  6. package/dist/{checkCommand-D0dAKciE.js → checkCommand-D8vjQXQt.js} +3 -3
  7. package/dist/{checkCommand-B2Fw73lu.js → checkCommand-udbQpphy.js} +1 -1
  8. package/dist/{codegenCommand-BTtsnRus.js → codegenCommand-DApSH7hK.js} +39 -46
  9. package/dist/{codemodRunner-DSZjgyCL.js → codemodRunner-De1_316I.js} +562 -492
  10. package/dist/{commands-BrFKxnYW.js → commands-a5PxCaIg.js} +68 -60
  11. package/dist/{dashboardCommand-D9SjDc8E.js → dashboardCommand-DaoUUqJS.js} +1 -1
  12. package/dist/dataCommand-CJv_OMoS.js +1156 -0
  13. package/dist/dataProfile-Du3ztYxv.js +51 -0
  14. package/dist/{dbCommand-jbrmzwW_.js → dbCommand-Bf7Cy0mn.js} +5 -5
  15. package/dist/dbCommand-Bnl7MSGC.js +2 -0
  16. package/dist/declaredSchemaGates-BlcwObhb.js +25 -0
  17. package/dist/{dev-RjB7eE_B.js → dev-C31Nvlbv.js} +31 -30
  18. package/dist/{dev-CaIfZnw5.js → dev-DFVuzOj7.js} +1 -1
  19. package/dist/{doctorCommand-D7X29cw6.js → doctorCommand-B3uraeAe.js} +32 -14
  20. package/dist/doctorCommand-CPL6EhrW.js +2 -0
  21. package/dist/doctorDecidedSchema-BlbWgCD_.js +23 -0
  22. package/dist/{dormancyCommand-BGOP27fz.js → dormancyCommand-QUXQ9yoz.js} +1 -1
  23. package/dist/{embeddingsCommand-D72E22bw.js → embeddingsCommand-Zw1-rYSF.js} +1 -1
  24. package/dist/{envCommand-BHSxz6wC.js → envCommand-DtaJ4xEf.js} +1 -1
  25. package/dist/{evolveCommand-C2ofGGlz.js → evolveCommand-JDD3hE1i.js} +2 -2
  26. package/dist/{frameworkTableAssembly-BvZ0Lil_.js → frameworkTableAssembly-BwJVEKLr.js} +96 -119
  27. package/dist/frameworkTableAssembly-CVDB2hCq.js +2 -0
  28. package/dist/index.js +1 -1
  29. package/dist/{infoCommand-CuNl9cbh.js → infoCommand-COsUC1DB.js} +1 -1
  30. package/dist/{migrate-odCPGHPq.js → migrate-D3MK9BpK.js} +4 -4
  31. package/dist/{runtimeTrace-C_OKr0jY.js → runtimeTrace-Di6fcndp.js} +1 -1
  32. package/dist/{sdkgen-D9trW7sl.js → sdkgen-CIi5gM17.js} +1 -1
  33. package/dist/serveCommand-CzSDngKm.js +2 -0
  34. package/dist/serveCommand-N3udT49p.js +2362 -0
  35. package/dist/serveEntry.js +5 -5
  36. package/dist/{subcommandNames-CKG5Dz3a.js → subcommandNames-DpYs3DXr.js} +12 -2
  37. package/dist/{updateCommand-BlyXavoG.js → updateCommand-2BfbeMvp.js} +1 -1
  38. package/dist/updateCommand-CtYm7aKH.js +2 -0
  39. package/dist/{webhooksCommand-BqcWcbuW.js → webhooksCommand-CwX9IzvJ.js} +1 -1
  40. package/package.json +29 -17
  41. package/templates/AGENTS.md +1 -1
  42. package/templates/agent-docs/_index.md +1 -1
  43. package/templates/agent-docs/cli.md +117 -4
  44. package/templates/agent-docs/database/migrations.md +19 -5
  45. package/templates/agent-docs/whats-new.md +51 -14
  46. package/templates/apps/api-ai/package.json +7 -7
  47. package/templates/apps/api-auth/package.json +8 -8
  48. package/templates/apps/api-backend/package.json +7 -7
  49. package/templates/apps/api-backend-deactivation/package.json +7 -7
  50. package/templates/apps/api-backend-mail/package.json +8 -8
  51. package/templates/apps/api-backend-mariadb/package.json +9 -9
  52. package/templates/apps/api-backend-sqlite/package.json +8 -8
  53. package/templates/apps/api-backend-storage/package.json +8 -8
  54. package/templates/apps/api-cms/package.json +10 -10
  55. package/templates/apps/api-collab/package.json +8 -8
  56. package/templates/apps/api-data-advanced/package.json +8 -8
  57. package/templates/apps/api-durable/package.json +8 -8
  58. package/templates/apps/api-feature-flags/package.json +9 -9
  59. package/templates/apps/api-governance/package.json +8 -8
  60. package/templates/apps/api-kv/package.json +8 -8
  61. package/templates/apps/api-moderation/package.json +8 -8
  62. package/templates/apps/api-observability/package.json +8 -8
  63. package/templates/apps/api-ratelimit/package.json +8 -8
  64. package/templates/apps/api-rbac/package.json +8 -8
  65. package/templates/apps/api-rest/package.json +7 -7
  66. package/templates/apps/api-saas/package.json +11 -11
  67. package/templates/apps/api-saas-starter/package.json +10 -10
  68. package/templates/apps/api-search/package.json +8 -8
  69. package/templates/apps/api-status/package.json +8 -8
  70. package/templates/apps/api-versioning/package.json +8 -8
  71. package/templates/apps/api-webhooks/package.json +9 -9
  72. package/templates/apps/changelog/package.json +6 -6
  73. package/templates/apps/edge-functions/package.json +2 -2
  74. package/templates/apps/frontend-admin/package.json +8 -8
  75. package/templates/apps/frontend-app/package.json +9 -9
  76. package/templates/apps/frontend-auth/package.json +8 -8
  77. package/templates/apps/frontend-blank/package.json +7 -7
  78. package/templates/apps/frontend-cms/package.json +9 -9
  79. package/templates/apps/frontend-collab/package.json +10 -10
  80. package/templates/apps/frontend-contact/package.json +7 -7
  81. package/templates/apps/frontend-dashboard/package.json +7 -7
  82. package/templates/apps/frontend-docs/package.json +7 -7
  83. package/templates/apps/frontend-i18n/package.json +6 -6
  84. package/templates/apps/frontend-landing/package.json +7 -7
  85. package/templates/apps/frontend-portal/package.json +8 -8
  86. package/templates/apps/frontend-saas/package.json +8 -8
  87. package/templates/apps/frontend-spa/package.json +7 -7
  88. package/templates/apps/frontend-ssr/package.json +7 -7
  89. package/templates/apps/frontend-ssr-api/package.json +8 -8
  90. package/templates/apps/frontend-static-blog/package.json +6 -6
  91. package/templates/apps/frontend-status/package.json +8 -8
  92. package/templates/apps/mobile-app/package.json +4 -4
  93. package/dist/apiBuild-BsooZpw2.js +0 -2
  94. package/dist/dataCommand-Dl11q14e.js +0 -975
  95. package/dist/dataProfile-Cm0YVKSy.js +0 -18
  96. package/dist/dbCommand-BUD4Fd8v.js +0 -2
  97. package/dist/doctorCommand-5zv6PN-G.js +0 -2
  98. package/dist/frameworkTableAssembly-DDKtwsy2.js +0 -2
  99. package/dist/serveCommand-BU0wfV6V.js +0 -1931
  100. package/dist/serveCommand-Bwrn_9Fn.js +0 -2
  101. package/dist/updateCommand-CT5AvVg7.js +0 -2
@@ -0,0 +1,51 @@
1
+ import { DATA_TRANSFERS_TABLE as e } from "@voltro/database";
2
+ //#region src/importRunStatus.ts
3
+ var t = async (t, n) => {
4
+ let r = (await t.query({
5
+ table: e,
6
+ predicate: {
7
+ column: "id",
8
+ op: "eq",
9
+ value: n
10
+ },
11
+ order: [],
12
+ take: 1,
13
+ skip: 0,
14
+ projection: void 0
15
+ }).catch(() => []))[0];
16
+ return r === void 0 ? null : {
17
+ ...r,
18
+ startedAt: new Date(r.startedAt),
19
+ finishedAt: r.finishedAt === null || r.finishedAt === void 0 ? null : new Date(r.finishedAt)
20
+ };
21
+ }, n = (e) => {
22
+ if (e !== null) return e.failure !== null && e.failure !== void 0 && String(e.failure) !== "" ? "failed" : e.finishedAt === null ? void 0 : "ok";
23
+ }, r = (e) => {
24
+ let t = n(e);
25
+ return t === "ok" ? 0 : t === "failed" ? 1 : 2;
26
+ }, i = (e) => e === null ? " waiting — no record visible yet (the instance may still be opening the bundle)" : e.failure !== null && e.failure !== void 0 && String(e.failure) !== "" ? ` FAILED — ${String(e.failure)}` : e.finishedAt === null ? ` importing — ${e.rowsWritten} row(s) across ${e.tablesWritten} table(s)` + (e.staged === !0 ? " (staged; the target still holds its own rows)" : "") : ` done — ${e.rowsWritten} row(s) across ${e.tablesWritten} table(s)`, a = async (e) => {
27
+ let t = e.intervalMs ?? 1e3, r = Date.now() + (e.timeoutMs ?? 864e5), i = e.notFoundGraceMs ?? 3e4, a = e.sleep ?? ((e) => new Promise((t) => {
28
+ setTimeout(t, e);
29
+ })), o = Date.now(), s = !1, c = null;
30
+ for (;;) {
31
+ if (c = await e.read(), c !== null && (s = !0), e.onTick?.(c), n(c) !== void 0 || Date.now() >= r) return c;
32
+ if (!s && Date.now() - o >= i) return null;
33
+ await a(t);
34
+ }
35
+ }, o = /^[A-Za-z0-9_-]{1,64}$/, s = async (e, t = {}) => {
36
+ let { resolve: n, sep: r } = await import("node:path"), { existsSync: i } = await import("node:fs"), a = n(process.cwd(), "data-profiles"), s = t.allowPath === !0 ? [
37
+ e,
38
+ `${e}.profile.ts`,
39
+ `data-profiles/${e}.ts`,
40
+ `data-profiles/${e}.profile.ts`
41
+ ].map((e) => n(process.cwd(), e)) : o.test(e) ? [n(a, `${e}.ts`), n(a, `${e}.profile.ts`)] : [];
42
+ if (t.allowPath !== !0 && s.length === 0) throw Error(`data profile '${e}' is not a valid profile name. A profile is named, not pathed: use letters, digits, \`_\` or \`-\` only, and put the file in \`data-profiles/\`.`);
43
+ let c = s.find((e) => i(e));
44
+ if (!c) throw Error(`data profile '${e}' not found (looked for: ${s.join(", ")})`);
45
+ if (t.allowPath !== !0 && !c.startsWith(a + r)) throw Error(`data profile '${e}' resolved outside data-profiles/ — refusing to load it`);
46
+ let l = await import(c), u = l.default ?? l.profile;
47
+ if (!u) throw Error(`data profile '${c}' has no default export`);
48
+ return u;
49
+ };
50
+ //#endregion
51
+ export { t as a, r as i, a as n, n as o, i as r, s as t };
@@ -1,4 +1,4 @@
1
- import { t as e } from "./subcommandNames-CKG5Dz3a.js";
1
+ import { n as e } from "./subcommandNames-DpYs3DXr.js";
2
2
  import { n as t, r as n } from "./nodeEnvironment-cGFAj1J8.js";
3
3
  import { t as r } from "./cliError-BmdYnghb.js";
4
4
  import { n as i } from "./appModuleLoader-C9r9mxZt.js";
@@ -6,7 +6,7 @@ import { a, i as o, n as s, t as c } from "./cliArgs-D4p8n7EE.js";
6
6
  import { r as l } from "./dialectDriver-czCHYpeH.js";
7
7
  import { a as u } from "./connectionConfig-Bk9IC7D0.js";
8
8
  import { i as d, n as f, r as p, s as m, t as h } from "./seedRunner-Dgsiwk_e.js";
9
- import { n as g, s as _, y as v } from "./frameworkTableAssembly-BvZ0Lil_.js";
9
+ import { g, n as _, s as v } from "./frameworkTableAssembly-BwJVEKLr.js";
10
10
  import { b as y, x as b } from "./fileConventions-Cof68_BL.js";
11
11
  import { r as x, t as S } from "./inspectGateHint-BjnFubmH.js";
12
12
  import { basename as ee, join as C, relative as w, resolve as T } from "node:path";
@@ -962,7 +962,7 @@ var Pe = (e) => typeof e != "string", Fe = (e, t, n, r) => {
962
962
  }, Z = async (e) => {
963
963
  let t = await It(e);
964
964
  if (t.length === 0) return;
965
- let n = await g({ root: e });
965
+ let n = await _({ root: e });
966
966
  return Lt(Rt([
967
967
  ...t,
968
968
  ...ae,
@@ -971,8 +971,8 @@ var Pe = (e) => typeof e != "string", Fe = (e, t, n, r) => {
971
971
  }, Q = async (e, t, n) => {
972
972
  let r;
973
973
  try {
974
- let t = await _(e);
975
- await J(n, v(t, (e, t) => {
974
+ let t = await v(e);
975
+ await J(n, g(t, (e, t) => {
976
976
  B.info(`db apply: ${e}`, t ?? {});
977
977
  }));
978
978
  } catch (e) {
@@ -0,0 +1,2 @@
1
+ import { s as e } from "./dbCommand-Bf7Cy0mn.js";
2
+ export { e as runDbCommand };
@@ -0,0 +1,25 @@
1
+ //#region src/declaredSchemaGates.ts
2
+ var e = (e) => ({
3
+ traces: e.declared?.traces ?? !0,
4
+ undo: e.declared?.undo ?? !0,
5
+ cdc: e.cdcDialect !== void 0
6
+ }), t = (e) => {
7
+ let t = e.nodeEnv ?? "<unset>", n = (t) => e.declared?.[t] === void 0 ? "the default (the same one in every environment)" : `app.config.ts \`schema: { ${t}: ${String(e.declared[t])} }\``, r = (e, t, n) => ` ${e ? "+" : "-"} ${t.padEnd(22)} ${n}`;
8
+ return `The three tables whose presence is DECIDED rather than implied by your source tree —
9
+ compare these against the other process's environment before anything else:
10
+
11
+ ${r(e.gates.traces, "_voltro_traces", n("traces"))}\n${r(e.gates.undo, "_voltro_undo_log", n("undo"))}\n${r(e.gates.cdc, "_voltro_cdc_offsets", `DB_DIALECT=${e.cdcDialect ?? "<no out-of-band CDC>"}`)}\n\nNone of them reads a runtime flag or NODE_ENV any more (this process: NODE_ENV=${t}).\nIf you are upgrading FROM a version where they did, the two sides recorded different sets —\nre-run \`voltro db apply\` once on this version and both will agree.`;
12
+ }, n = (e) => {
13
+ let t = [{
14
+ key: "traces",
15
+ table: "_voltro_traces",
16
+ envVar: "VOLTRO_TRACING_PERSIST"
17
+ }, {
18
+ key: "undo",
19
+ table: "_voltro_undo_log",
20
+ envVar: "VOLTRO_UNDO"
21
+ }].filter((t) => e.runtime[t.key] && !e.gates[t.key]);
22
+ if (t.length !== 0) return `refusing to boot — a runtime flag asks for a table the deployment does not declare:\n\n${t.map(({ key: e, table: t, envVar: n }) => ` \`${n}\` turns ${e} capture ON, but \`${t}\` is not in this app's declared schema.\n Declare it: \`schema: { ${e}: true }\` in app.config.ts.`).join("\n\n")}\n\nThe declaration has to live in app.config.ts rather than in the environment because the\npre-deploy migrate job runs with its OWN env block. A flag set on the pods and not on the\njob produces a green apply and a schema fingerprint no container can reproduce.`;
23
+ };
24
+ //#endregion
25
+ export { e as n, n as r, t };
@@ -10,7 +10,8 @@ import { n as ne, r as S } from "./dialectDriver-czCHYpeH.js";
10
10
  import { a as C, i as re, n as ie, t as ae } from "./connectionConfig-Bk9IC7D0.js";
11
11
  import { a as oe, c as se, i as ce, n as le, o as ue, r as de, t as fe } from "./seedRunner-Dgsiwk_e.js";
12
12
  import { r as pe } from "./devActivity-Dx_3nnGv.js";
13
- import { C as me, E as w, S as he, T as ge, _ as _e, b as ve, d as ye, f as be, g as xe, h as Se, m as Ce, o as we, p as T, r as Te, u as Ee, v as De, w as Oe, x as ke } from "./frameworkTableAssembly-BvZ0Lil_.js";
13
+ import { C as w, S as me, _ as he, b as ge, d as _e, f as ve, h as ye, l as be, m as xe, o as Se, p as Ce, r as we, u as T, v as Te, x as Ee, y as De } from "./frameworkTableAssembly-BwJVEKLr.js";
14
+ import { n as Oe, r as ke } from "./declaredSchemaGates-BlcwObhb.js";
14
15
  import { A as Ae, D as je, M as Me, P as Ne, S as Pe, _ as Fe, a as E, b as D, c as Ie, g as O, k as Le, n as Re, o as ze, p as Be, s as Ve, t as He, v as Ue, w as We, x as Ge, y as k } from "./fileConventions-Cof68_BL.js";
15
16
  import { A as Ke, C as qe, D as A, E as j, N as Je, O as Ye, S as Xe, T as Ze, _ as Qe, a as $e, b as et, c as tt, d as nt, f as rt, g as it, h as at, i as ot, l as st, m as ct, o as lt, p as ut, r as dt, s as ft, t as pt, u as mt, v as ht, w as M, x as gt, y as _t } from "./inspect-B7U7Cl_Z.js";
16
17
  import { t as vt } from "./manifestBuild-BK42hu0k.js";
@@ -4311,7 +4312,7 @@ var rc = (e) => {
4311
4312
  for (let n of e) {
4312
4313
  let e = n.dashboard ?? [];
4313
4314
  if (e.length === 0) continue;
4314
- let r = ge(n.name), i = /* @__PURE__ */ new Set();
4315
+ let r = me(n.name), i = /* @__PURE__ */ new Set();
4315
4316
  for (let a of e) {
4316
4317
  if (i.has(a.id)) throw Error(`plugin "${n.name}" declares duplicate dashboard mount id "${a.id}"`);
4317
4318
  i.add(a.id), t.push({
@@ -4384,7 +4385,7 @@ var rc = (e) => {
4384
4385
  if (r.length === 0) return [];
4385
4386
  let i = await _p(n);
4386
4387
  return r.map((e) => {
4387
- let n = ge(e.name), r = {
4388
+ let n = me(e.name), r = {
4388
4389
  pluginName: e.name,
4389
4390
  pluginAlias: n,
4390
4391
  apiName: t,
@@ -4400,7 +4401,7 @@ var rc = (e) => {
4400
4401
  pluginContributions: await vp(e, t, n),
4401
4402
  pluginErrorImports: e.flatMap((e) => (e.errorSchemas ?? []).map((e) => e.import)),
4402
4403
  pluginRpcImports: e.flatMap((e) => (e.rpcClientDescriptors ?? []).map((t) => ({
4403
- tag: Oe(e, t.tag),
4404
+ tag: Ee(e, t.tag),
4404
4405
  kind: t.kind,
4405
4406
  module: t.import.module,
4406
4407
  name: t.import.name
@@ -6482,7 +6483,7 @@ ${r.join("\n")}\n A deployment with no producer waits forever and looks exactly
6482
6483
  for (let i of r) {
6483
6484
  if (Wh.has(i.name)) continue;
6484
6485
  let r = P(e, i.name);
6485
- i.isDirectory() ? await n(r) : i.isFile() && (O.test(i.name) && !Fe.test(i.name) || Fe.test(i.name) || Ae.test(i.name) || Me.test(i.name) || je.test(i.name) || D.test(i.name) || k.test(i.name) || Ge.test(i.name) || Pe.test(i.name) || E.test(i.name) || Le.test(i.name) || lf.test(i.name) || Ce.test(i.name) || Se.test(i.name) || We.test(i.name) || Be.test(i.name) || Ue.test(i.name) || He.test(i.name) || Ve.test(i.name) || Re.test(i.name) || Ie.test(i.name) || ze.test(i.name)) && t.push(r);
6486
+ i.isDirectory() ? await n(r) : i.isFile() && (O.test(i.name) && !Fe.test(i.name) || Fe.test(i.name) || Ae.test(i.name) || Me.test(i.name) || je.test(i.name) || D.test(i.name) || k.test(i.name) || Ge.test(i.name) || Pe.test(i.name) || E.test(i.name) || Le.test(i.name) || lf.test(i.name) || _e.test(i.name) || ve.test(i.name) || We.test(i.name) || Be.test(i.name) || Ue.test(i.name) || He.test(i.name) || Ve.test(i.name) || Re.test(i.name) || Ie.test(i.name) || ze.test(i.name)) && t.push(r);
6486
6487
  }
6487
6488
  };
6488
6489
  return await n(e), t;
@@ -6719,9 +6720,9 @@ ${r.join("\n")}\n A deployment with no producer waits forever and looks exactly
6719
6720
  });
6720
6721
  let x = e.filter((e) => be.test(N(e))), ne = x.length > 0 ? await T(x, Z.child("connections")) : [], S = {
6721
6722
  workflows: c.length > 0 || u.length > 0,
6722
- schedules: d.length > 0 || e.some((e) => we(N(e))),
6723
+ schedules: d.length > 0 || e.some((e) => Se(N(e))),
6723
6724
  webhooks: e.some((e) => Le.test(N(e))),
6724
- agents: e.some((e) => Ce.test(N(e))),
6725
+ agents: e.some((e) => _e.test(N(e))),
6725
6726
  connections: x.length > 0
6726
6727
  };
6727
6728
  return xr(), {
@@ -6958,16 +6959,16 @@ ${r.join("\n")}\n A deployment with no producer waits forever and looks exactly
6958
6959
  version: Ih,
6959
6960
  logFile: fe.path
6960
6961
  }), g(n, Z);
6961
- let ge = await pe({
6962
+ let me = await pe({
6962
6963
  project: N(n),
6963
6964
  cliVersion: Ih
6964
6965
  });
6965
- if (ge.kind === "not-personal") return Z.error(`voltro dev needs a personal login — the stored credential belongs to no user.
6966
- ${ge.message}`), 1;
6967
- ge.kind === "reported" && ge.seat === "claimed" && Z.info("cloud: this machine now counts toward your organisation's seats (voltro cloud whoami)");
6968
- let be = process.env.VOLTRO_DEV_HEALTH_PORT, Se = be === void 0 ? C + 1 : Number(be), we;
6969
- Se > 0 && Number.isFinite(Se) && (we = await bm({
6970
- port: Se,
6966
+ if (me.kind === "not-personal") return Z.error(`voltro dev needs a personal login — the stored credential belongs to no user.
6967
+ ${me.message}`), 1;
6968
+ me.kind === "reported" && me.seat === "claimed" && Z.info("cloud: this machine now counts toward your organisation's seats (voltro cloud whoami)");
6969
+ let ve = process.env.VOLTRO_DEV_HEALTH_PORT, be = ve === void 0 ? C + 1 : Number(ve), Se;
6970
+ be > 0 && Number.isFinite(be) && (Se = await bm({
6971
+ port: be,
6971
6972
  log: {
6972
6973
  info: (e, t) => Z.debug(e, t),
6973
6974
  warn: (e, t) => Z.warn(e, t)
@@ -6982,9 +6983,9 @@ ${r.join("\n")}\n A deployment with no producer waits forever and looks exactly
6982
6983
  });
6983
6984
  let T = await Gh(n);
6984
6985
  Z.info(`discovered ${T.length} files`, { count: T.length });
6985
- let { pluginContributions: Oe, pluginErrorImports: Ae, pluginRpcImports: je } = await yp(v?.plugins ?? [], v?.name ?? N(n), n), Me = await Et({
6986
+ let { pluginContributions: Ee, pluginErrorImports: Ae, pluginRpcImports: je } = await yp(v?.plugins ?? [], v?.name ?? N(n), n), Me = await Et({
6986
6987
  root: n,
6987
- ...Oe.length > 0 ? { pluginContributions: Oe } : {},
6988
+ ...Ee.length > 0 ? { pluginContributions: Ee } : {},
6988
6989
  ...Ae.length > 0 ? { pluginErrorImports: Ae } : {},
6989
6990
  ...je.length > 0 ? { pluginRpcImports: je } : {},
6990
6991
  ...v?.name === void 0 ? {} : { apiName: v.name }
@@ -7036,11 +7037,11 @@ ${r.join("\n")}\n A deployment with no producer waits forever and looks exactly
7036
7037
  "apikeys:issue:other"
7037
7038
  ].some((t) => e.has(t)) && !e.has("admin:full") && Z.warn("apiKeys is enabled but no role declares any of apikeys:issue:self / :org / :other. The management routes are mounted and every issue request will fail its guard — the capability is on and reachable by nobody. Grant the right one in your role map (`:self` lets a user mint their own key, `:org` a shared one, `:other` on behalf of a colleague).");
7038
7039
  }
7039
- let bt = (typeof yt == "object" ? yt.prefix : void 0) ?? "voltro_", xt, Ct = yt ? [Ui({ resolveByHash: (e, t) => xt ? xt.resolveByHash(e, t) : Promise.resolve(null) }, { prefix: bt })] : [], Rt = zh([...M?.auth?.strategies ?? [], ...Ct], Bs(M?.plugins ?? []), M?.auth?.anonymousTenantRequired ?? !1, M?.auth, () => vt.current), zt = ha({ resolveSubject: Rt }), Bt = Ee({
7040
+ let bt = (typeof yt == "object" ? yt.prefix : void 0) ?? "voltro_", xt, Ct = yt ? [Ui({ resolveByHash: (e, t) => xt ? xt.resolveByHash(e, t) : Promise.resolve(null) }, { prefix: bt })] : [], Rt = zh([...M?.auth?.strategies ?? [], ...Ct], Bs(M?.plugins ?? []), M?.auth?.anonymousTenantRequired ?? !1, M?.auth, () => vt.current), zt = ha({ resolveSubject: Rt }), Bt = Oe({
7040
7041
  nodeEnv: process.env.NODE_ENV,
7041
7042
  cdcDialect: Fe,
7042
7043
  declared: M?.schema
7043
- }), Vt = ye({
7044
+ }), Vt = ke({
7044
7045
  gates: Bt,
7045
7046
  runtime: {
7046
7047
  traces: mm(),
@@ -7048,7 +7049,7 @@ ${r.join("\n")}\n A deployment with no producer waits forever and looks exactly
7048
7049
  }
7049
7050
  });
7050
7051
  if (Vt !== void 0) throw r(`dev: ${Vt}`);
7051
- let Ht = Te({
7052
+ let Ht = we({
7052
7053
  mix: it,
7053
7054
  plugins: M?.plugins ?? [],
7054
7055
  gates: Bt,
@@ -7089,9 +7090,9 @@ ${r.join("\n")}\n A deployment with no producer waits forever and looks exactly
7089
7090
  count: Yt.length,
7090
7091
  mounts: Yt.map((e) => `${e.fullId} (${e.slot})`)
7091
7092
  });
7092
- let en = ke(M?.plugins ?? []);
7093
+ let en = Te(M?.plugins ?? []);
7093
7094
  en.length > 0 && Z.info("plugin schema contributions", { plugins: en.map((e) => `${e.pluginName}: ${e.tables}t/${e.migrations}m`) });
7094
- let tn = me(M?.plugins ?? []);
7095
+ let tn = ge(M?.plugins ?? []);
7095
7096
  if (tn.length > 0) {
7096
7097
  let e = [
7097
7098
  ...E.map((e) => e.descriptor.name),
@@ -7102,7 +7103,7 @@ ${r.join("\n")}\n A deployment with no producer waits forever and looks exactly
7102
7103
  ...E.filter((e) => e.descriptor.overridesPlugin === !0).map((e) => e.descriptor.name),
7103
7104
  ...D.filter((e) => e.descriptor.overridesPlugin === !0).map((e) => e.descriptor.name),
7104
7105
  ...O.filter((e) => e.descriptor.overridesPlugin === !0).map((e) => e.descriptor.name)
7105
- ]), n = he(tn, e, t);
7106
+ ]), n = De(tn, e, t);
7106
7107
  tn.length - n.length > 0 && Z.info(`plugin routes overridden by app procedures: ${[...t].join(", ")}`);
7107
7108
  for (let e of n) e.kind === "query" ? E.push({
7108
7109
  file: e.file,
@@ -7122,14 +7123,14 @@ ${r.join("\n")}\n A deployment with no producer waits forever and looks exactly
7122
7123
  routes: tn.map((e) => `${e.plugin.name}:${e.descriptor.name} (${e.kind})`)
7123
7124
  });
7124
7125
  }
7125
- let an = Z.child("agent"), sn = T.filter((e) => xe.test(N(e)));
7126
+ let an = Z.child("agent"), sn = T.filter((e) => Ce.test(N(e)));
7126
7127
  if (sn.length > 0) {
7127
- let e = await De(sn, an);
7128
+ let e = await ye(sn, an);
7128
7129
  e > 0 && an.info("wired tool handlers", { tools: e });
7129
7130
  }
7130
- let cn = T.filter((e) => Ce.test(N(e))), ln = [];
7131
+ let cn = T.filter((e) => _e.test(N(e))), ln = [];
7131
7132
  if (cn.length > 0) {
7132
- let e = await _e(cn, an);
7133
+ let e = await xe(cn, an);
7133
7134
  ln = e.agents.map((e) => e.descriptor.name);
7134
7135
  for (let t of e.agents) for (let e of yf(t)) e.kind === "action" ? O.push({
7135
7136
  file: e.file,
@@ -7364,7 +7365,7 @@ ${r.join("\n")}\n A deployment with no producer waits forever and looks exactly
7364
7365
  dialect: hi,
7365
7366
  env: t,
7366
7367
  tables: I.length
7367
- }), we?.set({
7368
+ }), Se?.set({
7368
7369
  phase: "migrating",
7369
7370
  tablesTotal: I.length
7370
7371
  });
@@ -7393,7 +7394,7 @@ ${r.join("\n")}\n A deployment with no producer waits forever and looks exactly
7393
7394
  if (c.kind === "refused-blocked" || c.kind === "prod-mismatch") throw Z.error(Fr(c, r.id)), Error("auto-migrate refused — see error above");
7394
7395
  Z.info(Fr(c, r.id), { durationMs: Date.now() - e });
7395
7396
  } catch (e) {
7396
- throw Z.error("auto-migrate failed — aborting boot", { err: e }), we?.set({
7397
+ throw Z.error("auto-migrate failed — aborting boot", { err: e }), Se?.set({
7397
7398
  phase: "error",
7398
7399
  error: e instanceof Error ? e.message : String(e)
7399
7400
  }), e;
@@ -7414,7 +7415,7 @@ ${r.join("\n")}\n A deployment with no producer waits forever and looks exactly
7414
7415
  if ((M?.plugins ?? []).some((e) => (e.extendSchema?.migrations?.length ?? 0) > 0) && Ei !== "memory") {
7415
7416
  let e = (await S(Ei)).makeSqlLayer(Q());
7416
7417
  try {
7417
- let t = await z.runPromise(ve(M.plugins).pipe(z.provide(e))), n = t.filter((e) => e.status === "applied"), r = t.filter((e) => e.status === "skipped");
7418
+ let t = await z.runPromise(he(M.plugins).pipe(z.provide(e))), n = t.filter((e) => e.status === "applied"), r = t.filter((e) => e.status === "skipped");
7418
7419
  Z.info("plugin migrations complete", {
7419
7420
  applied: n.map((e) => `${e.pluginName}:${e.migrationId} (${e.durationMs}ms)`),
7420
7421
  skippedCount: r.length
@@ -8924,7 +8925,7 @@ ${r.join("\n")}\n A deployment with no producer waits forever and looks exactly
8924
8925
  port: C,
8925
8926
  ws: `ws://localhost:${C}/ws`,
8926
8927
  store: Y
8927
- }), we?.set({ phase: "ready" }), process.send?.({ type: vl }), process.channel?.unref(), Y === "postgres" && Z.info("postgres change-data-capture", { enabled: (process.env.CDC ?? "1") !== "0" }), await ns();
8928
+ }), Se?.set({ phase: "ready" }), process.send?.({ type: vl }), process.channel?.unref(), Y === "postgres" && Z.info("postgres change-data-capture", { enabled: (process.env.CDC ?? "1") !== "0" }), await ns();
8928
8929
  try {
8929
8930
  await Nt({
8930
8931
  id: oe,
@@ -1,3 +1,3 @@
1
- import { c as e, d as t, f as n, i as r, u as i } from "./dev-RjB7eE_B.js";
1
+ import { c as e, d as t, f as n, i as r, u as i } from "./dev-C31Nvlbv.js";
2
2
  import "./dialectDriver-czCHYpeH.js";
3
3
  export { r as buildStore, e as loadApiConfig, i as loadDiscovered, t as runDev, n as walk };
@@ -1,8 +1,8 @@
1
- import { Ht as e, Ut as t, Vt as n } from "./dev-RjB7eE_B.js";
1
+ import { Ht as e, Ut as t, Vt as n } from "./dev-C31Nvlbv.js";
2
2
  import { at as r, it as i, ot as a, s as o, st as s, t as c, w as l, y as u } from "./webDev-B4IEMB0n.js";
3
- import { w as d } from "./frameworkTableAssembly-BvZ0Lil_.js";
3
+ import { x as d } from "./frameworkTableAssembly-BwJVEKLr.js";
4
4
  import { n as f } from "./pageConvention-cEiRxdab.js";
5
- import { r as p, u as m } from "./apiBuild-FpHCWiv6.js";
5
+ import { r as p, u as m } from "./apiBuild-QmYHaCF4.js";
6
6
  import { n as h, r as g, t as ee } from "./cliOutput-D1tSBoRM.js";
7
7
  import { n as _, t as te } from "./tsconfigPaths-BWXBWgcl.js";
8
8
  import { n as ne, r as re } from "./fileTaxonomy-CJfgOllU.js";
@@ -1350,7 +1350,7 @@ var le = /* @__PURE__ */ new Set([
1350
1350
  let t = Wt.get(e);
1351
1351
  if (t !== void 0) return t;
1352
1352
  let n = (async () => {
1353
- let { walk: t, loadDiscovered: n } = await import("./dev-CaIfZnw5.js"), r = await t(e);
1353
+ let { walk: t, loadDiscovered: n } = await import("./dev-DFVuzOj7.js"), r = await t(e);
1354
1354
  return {
1355
1355
  files: r,
1356
1356
  discovered: await n(r)
@@ -1459,7 +1459,7 @@ var le = /* @__PURE__ */ new Set([
1459
1459
  }
1460
1460
  }, J = async (r) => {
1461
1461
  try {
1462
- let { loadApiConfig: i } = await import("./dev-CaIfZnw5.js"), { discovered: a } = await U(r), o = e(await i(r)), s = {
1462
+ let { loadApiConfig: i } = await import("./dev-DFVuzOj7.js"), { discovered: a } = await U(r), o = e(await i(r)), s = {
1463
1463
  queries: a.queries,
1464
1464
  mutations: a.mutations,
1465
1465
  actions: a.actions,
@@ -1543,7 +1543,7 @@ var le = /* @__PURE__ */ new Set([
1543
1543
  }, nn = async (e) => nt({
1544
1544
  hasWorkflows: async () => (await U(e)).discovered.workflows.length > 0,
1545
1545
  openStore: async () => {
1546
- let { loadApiConfig: t, buildStore: n } = await import("./dev-CaIfZnw5.js"), r = await t(e);
1546
+ let { loadApiConfig: t, buildStore: n } = await import("./dev-DFVuzOj7.js"), r = await t(e);
1547
1547
  if (r === null) throw Error("no app.config.ts in this directory");
1548
1548
  let i = await n(r, void 0);
1549
1549
  return {
@@ -1623,7 +1623,7 @@ var le = /* @__PURE__ */ new Set([
1623
1623
  }
1624
1624
  }, ln = async (e) => {
1625
1625
  try {
1626
- let { loadApiConfig: t } = await import("./dev-CaIfZnw5.js"), n = (await t(e))?.doctor?.scopeVocabulary;
1626
+ let { loadApiConfig: t } = await import("./dev-DFVuzOj7.js"), n = (await t(e))?.doctor?.scopeVocabulary;
1627
1627
  if (typeof n != "string") return [];
1628
1628
  let [r, i] = n.split("#");
1629
1629
  if (r === void 0 || i === void 0) return [];
@@ -1640,10 +1640,10 @@ var le = /* @__PURE__ */ new Set([
1640
1640
  findings: []
1641
1641
  });
1642
1642
  try {
1643
- let { offlineManifest: n, toInput: r } = await import("./checkCommand-B2Fw73lu.js"), { buildAppGraph: i, checkAppGraph: a } = await import("./appGraph-zuMGKVYX.js"), o = await n(e), s = r(o.manifest, o.tables), c = await ln(e), l = [.../* @__PURE__ */ new Set([...s.scopes ?? [], ...c])];
1643
+ let { offlineManifest: n, toInput: r } = await import("./checkCommand-udbQpphy.js"), { buildAppGraph: i, checkAppGraph: a } = await import("./appGraph-zuMGKVYX.js"), o = await n(e), s = r(o.manifest, o.tables), c = await ln(e), l = [.../* @__PURE__ */ new Set([...s.scopes ?? [], ...c])];
1644
1644
  if (l.length === 0) {
1645
1645
  try {
1646
- let { loadAppSchemaInputs: t } = await import("./frameworkTableAssembly-DDKtwsy2.js");
1646
+ let { loadAppSchemaInputs: t } = await import("./frameworkTableAssembly-CVDB2hCq.js");
1647
1647
  await t(e);
1648
1648
  } catch {
1649
1649
  return t("app-not-importable");
@@ -1694,7 +1694,7 @@ var le = /* @__PURE__ */ new Set([
1694
1694
  if (n === void 0 || r.length === 0) return;
1695
1695
  let i = [];
1696
1696
  try {
1697
- let { loadApiConfig: t } = await import("./dev-CaIfZnw5.js");
1697
+ let { loadApiConfig: t } = await import("./dev-DFVuzOj7.js");
1698
1698
  i = (await t(e))?.locales ?? [];
1699
1699
  } catch {
1700
1700
  return;
@@ -1725,7 +1725,7 @@ var le = /* @__PURE__ */ new Set([
1725
1725
  }, pn = async (e) => {
1726
1726
  let { discovered: t } = await U(e), n = [];
1727
1727
  try {
1728
- let { loadApiConfig: t } = await import("./dev-CaIfZnw5.js");
1728
+ let { loadApiConfig: t } = await import("./dev-DFVuzOj7.js");
1729
1729
  n = ((await t(e))?.plugins ?? []).map((e) => {
1730
1730
  let t = (e.extendSchema?.tables ?? []).map((e) => {
1731
1731
  let t = e;
@@ -1869,6 +1869,23 @@ var le = /* @__PURE__ */ new Set([
1869
1869
  for (let e of n.unchecked.slice(0, $)) console.log(` ✗ ${e.tag} — ${e.why}\n ${e.path}`);
1870
1870
  return n.unchecked.length > $ && console.log(` … and ${n.unchecked.length - $} more — \`voltro doctor --json\` prints every one (\`authz.unchecked\`).`), i === void 0 ? (console.log(`\nNo ${X} yet, so this run is advisory. To start the ratchet:`), console.log("\n voltro doctor --write-authz-allowlist\n"), console.log("That records today's unchecked handlers as DEBT and fails every run after on"), console.log("anything NEW. Fix a handler and its line stops mattering — the scan reports it as"), console.log("guarded whether or not the line is still there."), !1) : (console.log(`\n${n.unchecked.length} executor(s) with no access check are not in ${X}.`), console.log("Add a guard, or add the tag to that file if it is genuinely open."), console.log("\nBefore hand-rolling another check: `guards: [{ action, resourceType, resource }]`"), console.log("answers \"may this subject act on THIS row\" declaratively, and an app whose"), console.log("relationships live in its own tables registers its own tuple source rather than"), console.log("copying data into a framework table. See the authorization docs."), !0);
1871
1871
  }, yn = async (e) => {
1872
+ try {
1873
+ let { loadApiConfig: t } = await import("./dev-DFVuzOj7.js"), { decidedSchemaReport: n } = await import("./doctorDecidedSchema-BlbWgCD_.js"), r = await t(e);
1874
+ return r == null ? null : n({
1875
+ ...r.schema ? { declared: r.schema } : {},
1876
+ ...r.store === void 0 ? {} : { store: r.store },
1877
+ nodeEnv: process.env.NODE_ENV
1878
+ });
1879
+ } catch {
1880
+ return null;
1881
+ }
1882
+ }, bn = async (e) => {
1883
+ let t = await yn(e);
1884
+ if (t !== null) {
1885
+ console.log(""), console.log("• framework tables whose presence is DECIDED rather than implied by your source tree:");
1886
+ for (let e of t.text.split("\n")) console.log(` ${e}`);
1887
+ }
1888
+ }, xn = async (e) => {
1872
1889
  if (e.includes("--help") || e.includes("-h")) return console.log(Ut), 0;
1873
1890
  let t = e.includes("--strict"), n = e.find((e) => !e.startsWith("-")), o = b(n ?? process.cwd());
1874
1891
  if (g(e)) return ee(), h({
@@ -1886,14 +1903,15 @@ var le = /* @__PURE__ */ new Set([
1886
1903
  authz: await gn(o),
1887
1904
  ungrantedScopes: await Q(o),
1888
1905
  neverEmittedEvents: await Z(o),
1889
- stalledRuns: await nn(o)
1906
+ stalledRuns: await nn(o),
1907
+ decidedSchema: await yn(o)
1890
1908
  }), 0;
1891
1909
  let c = ct(o, t);
1892
- z(o), At(o), Ht(o), ne(o), await It(o), await an(o), await rn(o), await Gt(o), await Xt(o), await Yt(o), await Zt(o), await pn(o), await un(o), await cn(o), await dn(o);
1910
+ z(o), At(o), Ht(o), ne(o), await It(o), await an(o), await rn(o), await Gt(o), await Xt(o), await Yt(o), await bn(o), await Zt(o), await pn(o), await un(o), await cn(o), await dn(o);
1893
1911
  let l = await tn(o), u = await vn(o, e.includes("--write-authz-allowlist")), d = await Qt(o), f = await en(o), p = await fn(o), m = s(r(o));
1894
1912
  m !== void 0 && (console.log(""), console.log(m));
1895
1913
  let _ = a(i(o));
1896
1914
  return _ !== void 0 && console.log(`\n${_}`), l || u || d || p || f ? Math.max(c, 1) : c;
1897
1915
  };
1898
1916
  //#endregion
1899
- export { B as C, Y as E, V as S, Q as T, Ht as _, gn as a, ct as b, G as c, L as d, ot as f, z as g, At as h, J as i, on as l, qt as m, st as n, Z as o, W as p, jt as r, sn as s, Ut as t, R as u, It as v, q as w, Tt as x, yn as y };
1917
+ export { B as C, Y as E, V as S, Q as T, Ht as _, gn as a, ct as b, G as c, L as d, ot as f, z as g, At as h, J as i, on as l, qt as m, st as n, Z as o, W as p, jt as r, sn as s, Ut as t, R as u, It as v, q as w, Tt as x, xn as y };
@@ -0,0 +1,2 @@
1
+ import { b as e, y as t } from "./doctorCommand-B3uraeAe.js";
2
+ export { t as runDoctorCommand, e as runServePreflight };
@@ -0,0 +1,23 @@
1
+ import { n as e, t } from "./declaredSchemaGates-BlcwObhb.js";
2
+ //#region src/doctorDecidedSchema.ts
3
+ var n = (e) => e === "mariadb" || e === "mssql" ? e : void 0, r = (r) => {
4
+ let i = n(r.store), a = e({
5
+ nodeEnv: r.nodeEnv,
6
+ ...i ? { cdcDialect: i } : {},
7
+ ...r.declared ? { declared: r.declared } : {}
8
+ }), o = ["traces", "undo"].filter((e) => r.declared?.[e] !== void 0);
9
+ return {
10
+ traces: a.traces,
11
+ undo: a.undo,
12
+ cdc: a.cdc,
13
+ declaredInConfig: o,
14
+ text: t({
15
+ gates: a,
16
+ nodeEnv: r.nodeEnv,
17
+ ...i ? { cdcDialect: i } : {},
18
+ ...r.declared ? { declared: r.declared } : {}
19
+ })
20
+ };
21
+ };
22
+ //#endregion
23
+ export { r as decidedSchemaReport };
@@ -1,4 +1,4 @@
1
- import { c as e, i as t } from "./dev-RjB7eE_B.js";
1
+ import { c as e, i as t } from "./dev-C31Nvlbv.js";
2
2
  import { n, t as r } from "./cliArgs-D4p8n7EE.js";
3
3
  import { r as i } from "./appPort-B_HpJ_ck.js";
4
4
  import { resolve as a } from "node:path";
@@ -1,4 +1,4 @@
1
- import { c as e, i as t } from "./dev-RjB7eE_B.js";
1
+ import { c as e, i as t } from "./dev-C31Nvlbv.js";
2
2
  import { Effect as n } from "effect";
3
3
  import { embedMany as r } from "@voltro/ai";
4
4
  //#region src/embeddingsBackfill.ts
@@ -1,4 +1,4 @@
1
- import { c as e } from "./dev-RjB7eE_B.js";
1
+ import { c as e } from "./dev-C31Nvlbv.js";
2
2
  import { _t as t, gt as n, mt as r, pt as i } from "./webDev-B4IEMB0n.js";
3
3
  import { join as a } from "node:path";
4
4
  import { promises as o } from "node:fs";
@@ -1,6 +1,6 @@
1
1
  import { n as e } from "./cliOutput-D1tSBoRM.js";
2
- import { t } from "./checkCommand-D0dAKciE.js";
3
- import { i as n, n as r } from "./codemodRunner-DSZjgyCL.js";
2
+ import { t } from "./checkCommand-D8vjQXQt.js";
3
+ import { i as n, n as r } from "./codemodRunner-De1_316I.js";
4
4
  import { basename as i, join as a, resolve as o } from "node:path";
5
5
  import { branchNamespaceName as s, planBranchProvision as c } from "@voltro/database";
6
6
  import { readFile as l } from "node:fs/promises";