@voltro/data-transfer 0.81.0 → 0.82.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.
package/dist/index.js CHANGED
@@ -1,18 +1,18 @@
1
1
  import { Cause as e, Data as t, Effect as n, Exit as r, Metric as i, MetricBoundaries as a, Runtime as o, Schedule as s, Schema as c, Stream as l } from "effect";
2
- import { DATA_TRANSFERS_TABLE as u, REPLACE_IN_PROGRESS_TABLE as d, STAGING_TABLE_PREFIX as f, _voltroDataTransfersTable as p, classifyConstraintViolation as m, derivedRowId as h, ensureTableRegistered as g, eq as _, extractDbCause as v, getTable as y, inSet as b, isNotNull as x, or as S, recordsTable as C, registerTable as ee, streamTable as w, suspendWriteRecorders as te, suspendWriteRecordersEffect as ne, unregisterTable as re } from "@voltro/database";
3
- import { fingerprintSchema as T } from "@voltro/database/sql";
4
- import { createCipheriv as ie, createDecipheriv as ae, createHash as oe, createHmac as se, randomBytes as ce, randomUUID as le, scrypt as ue } from "node:crypto";
5
- import { copyFile as E, createReadStream as de, createWriteStream as D, existsSync as fe, rename as pe, statSync as O, unlinkSync as k } from "node:fs";
6
- import { STORAGE_REFS_TABLE as A, fromNodeReadable as me, getObjectStream as j, putObjectStream as he, toNodeReadable as M } from "@voltro/plugin-storage";
7
- import * as N from "node:zlib";
8
- import { PassThrough as P, Readable as ge } from "node:stream";
9
- import { SqlClient as F } from "@effect/sql";
10
- import { mkdir as I, readdir as L, stat as _e } from "node:fs/promises";
11
- import { basename as R, delimiter as z, dirname as ve, join as B, resolve as ye, sep as be } from "node:path";
12
- import { promisify as xe } from "node:util";
13
- import { spawn as Se } from "node:child_process";
2
+ import { DATA_TRANSFERS_TABLE as u, REPLACE_IN_PROGRESS_TABLE as d, STAGING_TABLE_PREFIX as f, _voltroDataTransfersTable as p, classifyConstraintViolation as m, derivedRowId as h, ensureTableRegistered as g, eq as _, extractDbCause as v, getTable as y, inSet as b, isNotNull as x, or as S, recordsTable as ee, registerTable as te, streamTable as C, suspendWriteRecorders as ne, suspendWriteRecordersEffect as re, unregisterTable as ie } from "@voltro/database";
3
+ import { fingerprintSchema as w } from "@voltro/database/sql";
4
+ import { createCipheriv as ae, createDecipheriv as oe, createHash as T, createHmac as se, randomBytes as ce, randomUUID as le, scrypt as ue } from "node:crypto";
5
+ import { copyFile as de, createReadStream as fe, createWriteStream as pe, existsSync as E, rename as D, statSync as me, unlinkSync as he } from "node:fs";
6
+ import { STORAGE_REFS_TABLE as O, fromNodeReadable as ge, getObjectStream as _e, putObjectStream as k, toNodeReadable as A } from "@voltro/plugin-storage";
7
+ import * as j from "node:zlib";
8
+ import { PassThrough as M, Readable as ve } from "node:stream";
9
+ import { SqlClient as N } from "@effect/sql";
10
+ import { mkdir as P, readdir as ye, stat as be } from "node:fs/promises";
11
+ import { basename as F, delimiter as xe, dirname as Se, join as I, resolve as L, sep as Ce } from "node:path";
12
+ import { promisify as we } from "node:util";
13
+ import { spawn as Te } from "node:child_process";
14
14
  //#region src/consistency.ts
15
- var Ce = (e) => {
15
+ var Ee = (e) => {
16
16
  switch (e) {
17
17
  case "postgres": return ["SET TRANSACTION ISOLATION LEVEL REPEATABLE READ"];
18
18
  case "mysql":
@@ -22,7 +22,7 @@ var Ce = (e) => {
22
22
  case "turso": return [];
23
23
  default: return [];
24
24
  }
25
- }, we = {
25
+ }, De = {
26
26
  email: { fake: "email" },
27
27
  fullName: { fake: "fullName" },
28
28
  firstName: { fake: "firstName" },
@@ -37,7 +37,7 @@ var Ce = (e) => {
37
37
  date: "dateShift",
38
38
  secret: "null",
39
39
  freeText: "redact"
40
- }, Te = (e) => {
40
+ }, Oe = (e) => {
41
41
  let t = {};
42
42
  for (let n of e.tables) {
43
43
  let e = {};
@@ -49,15 +49,15 @@ var Ce = (e) => {
49
49
  t[n.name] = e;
50
50
  }
51
51
  return t;
52
- }, Ee = (e, t, n, r) => {
52
+ }, ke = (e, t, n, r) => {
53
53
  let i = r.columns?.[`${e}.${t}`];
54
54
  if (i) return i;
55
55
  if (n?.sensitive) {
56
56
  let e = n.sensitive.class;
57
- return r.classes?.[e] ?? we[e] ?? "redact";
57
+ return r.classes?.[e] ?? De[e] ?? "redact";
58
58
  }
59
59
  return n?.safe ? r.onSafe ?? "keep" : n?.columnType === "id" || n?.columnType === "reference" ? "keep" : r.onUnclassified ?? "error";
60
- }, De = (e, t) => se("sha256", e).update(t == null ? "∅" : String(t)).digest(), V = (e, t) => e.readUInt32BE(t * 4 % (e.length - 4)), Oe = [
60
+ }, Ae = (e, t) => se("sha256", e).update(t == null ? "∅" : String(t)).digest(), R = (e, t) => e.readUInt32BE(t * 4 % (e.length - 4)), je = [
61
61
  "Ada",
62
62
  "Alan",
63
63
  "Grace",
@@ -70,7 +70,7 @@ var Ce = (e) => {
70
70
  "Guido",
71
71
  "Margaret",
72
72
  "Bjarne"
73
- ], ke = [
73
+ ], Me = [
74
74
  "Lovelace",
75
75
  "Turing",
76
76
  "Hopper",
@@ -83,7 +83,7 @@ var Ce = (e) => {
83
83
  "Rossum",
84
84
  "Hamilton",
85
85
  "Stroustrup"
86
- ], Ae = [
86
+ ], Ne = [
87
87
  "Maple",
88
88
  "Oak",
89
89
  "Cedar",
@@ -92,7 +92,7 @@ var Ce = (e) => {
92
92
  "Birch",
93
93
  "Willow",
94
94
  "Ash"
95
- ], je = [
95
+ ], Pe = [
96
96
  "Initech",
97
97
  "Hooli",
98
98
  "Umbrella",
@@ -101,23 +101,23 @@ var Ce = (e) => {
101
101
  "Soylent",
102
102
  "Stark",
103
103
  "Wayne"
104
- ], H = (e, t, n) => e[V(t, n) % e.length], Me = (e, t, n) => {
105
- let r = De(n, `${e}:${String(t)}`), i = V(r, 1) % 1e4;
104
+ ], z = (e, t, n) => e[R(t, n) % e.length], Fe = (e, t, n) => {
105
+ let r = Ae(n, `${e}:${String(t)}`), i = R(r, 1) % 1e4;
106
106
  switch (e) {
107
- case "email": return `${H(Oe, r, 0).toLowerCase()}.${H(ke, r, 2).toLowerCase()}${i}@example.com`;
108
- case "fullName": return `${H(Oe, r, 0)} ${H(ke, r, 1)}`;
109
- case "firstName": return H(Oe, r, 0);
110
- case "lastName": return H(ke, r, 1);
111
- case "username": return `${H(Oe, r, 0).toLowerCase()}${i}`;
112
- case "phone": return `+1${String(V(r, 0) % 1e10).padStart(10, "0")}`;
113
- case "address": return `${V(r, 0) % 9899 + 100} ${H(Ae, r, 1)} St`;
114
- case "company": return H(je, r, 0);
107
+ case "email": return `${z(je, r, 0).toLowerCase()}.${z(Me, r, 2).toLowerCase()}${i}@example.com`;
108
+ case "fullName": return `${z(je, r, 0)} ${z(Me, r, 1)}`;
109
+ case "firstName": return z(je, r, 0);
110
+ case "lastName": return z(Me, r, 1);
111
+ case "username": return `${z(je, r, 0).toLowerCase()}${i}`;
112
+ case "phone": return `+1${String(R(r, 0) % 1e10).padStart(10, "0")}`;
113
+ case "address": return `${R(r, 0) % 9899 + 100} ${z(Ne, r, 1)} St`;
114
+ case "company": return z(Pe, r, 0);
115
115
  case "url": return `https://example.com/${r.toString("hex").slice(0, 12)}`;
116
- case "ip": return `${V(r, 0) % 256}.${V(r, 1) % 256}.${V(r, 2) % 256}.${V(r, 3) % 254 + 1}`;
117
- case "creditCard": return Ne(`4${r.toString("hex").replace(/\D/g, "").padEnd(14, "0").slice(0, 14)}`);
116
+ case "ip": return `${R(r, 0) % 256}.${R(r, 1) % 256}.${R(r, 2) % 256}.${R(r, 3) % 254 + 1}`;
117
+ case "creditCard": return Ie(`4${r.toString("hex").replace(/\D/g, "").padEnd(14, "0").slice(0, 14)}`);
118
118
  default: return `${e}_${r.toString("hex").slice(0, 8)}`;
119
119
  }
120
- }, Ne = (e) => {
120
+ }, Ie = (e) => {
121
121
  let t = e.slice(0, 15).split("").map(Number), n = 0;
122
122
  t.forEach((e, t) => {
123
123
  let r = e;
@@ -125,29 +125,29 @@ var Ce = (e) => {
125
125
  });
126
126
  let r = (10 - n % 10) % 10;
127
127
  return e.slice(0, 15) + String(r);
128
- }, Pe = 864e5, Fe = (e, t) => {
128
+ }, Le = 864e5, Re = (e, t) => {
129
129
  let n = e instanceof Date ? e.getTime() : Date.parse(String(e));
130
130
  if (Number.isNaN(n)) return e;
131
- let r = V(De(t, "date-shift-offset"), 0) % 730 - 365, i = new Date(n + r * Pe);
131
+ let r = R(Ae(t, "date-shift-offset"), 0) % 730 - 365, i = new Date(n + r * Le);
132
132
  return e instanceof Date ? i : i.toISOString();
133
- }, U = (e, t) => {
133
+ }, B = (e, t) => {
134
134
  if (t.value === null || t.value === void 0) return null;
135
135
  if (e === "error") throw Error(`masking: unresolved 'error' action for ${t.table}.${t.column}`);
136
136
  if (e === "keep") return t.value;
137
137
  if (e === "null") return null;
138
138
  if (e === "redact") return t.columnType === "text" || typeof t.value == "string" ? "[redacted]" : null;
139
- if (e === "hash") return De(t.seed, t.value).toString("hex").slice(0, 16);
140
- if (e === "dateShift") return Fe(t.value, t.seed);
141
- if (typeof e == "object" && "fake" in e) return Me(e.fake, t.value, t.seed);
139
+ if (e === "hash") return Ae(t.seed, t.value).toString("hex").slice(0, 16);
140
+ if (e === "dateShift") return Re(t.value, t.seed);
141
+ if (typeof e == "object" && "fake" in e) return Fe(e.fake, t.value, t.seed);
142
142
  if (typeof e == "object" && "custom" in e) return e.custom(t);
143
- if (typeof e == "object" && "json" in e) return Ie(e, t);
143
+ if (typeof e == "object" && "json" in e) return ze(e, t);
144
144
  throw Error(`masking: '${t.table}.${t.column}' resolved to an action this build does not understand (${JSON.stringify(e)}). Refusing to copy the value through. Valid actions: 'keep' | 'null' | 'redact' | 'hash' | 'dateShift' | { fake: '<class>' } | { custom: fn } | { json: { fields, rest? } }.`);
145
- }, Ie = (e, t) => {
146
- let { fields: n, rest: r = "redact" } = e.json, i = typeof t.value == "string" ? Le(t.value) : {
145
+ }, ze = (e, t) => {
146
+ let { fields: n, rest: r = "redact" } = e.json, i = typeof t.value == "string" ? Be(t.value) : {
147
147
  ok: !0,
148
148
  value: t.value
149
149
  };
150
- if (!i.ok) return U(r, {
150
+ if (!i.ok) return B(r, {
151
151
  ...t,
152
152
  columnType: "text"
153
153
  });
@@ -158,12 +158,12 @@ var Ce = (e) => {
158
158
  let a = {};
159
159
  for (let [o, s] of Object.entries(e)) {
160
160
  let e = n[o] ?? r, c = `${i}.${o}`;
161
- a[o] = typeof e == "object" && "json" in e ? Ie(e, {
161
+ a[o] = typeof e == "object" && "json" in e ? ze(e, {
162
162
  ...t,
163
163
  value: s,
164
164
  column: c,
165
165
  columnType: "json"
166
- }) : U(e, {
166
+ }) : B(e, {
167
167
  ...t,
168
168
  value: s,
169
169
  column: c,
@@ -172,7 +172,7 @@ var Ce = (e) => {
172
172
  }
173
173
  return a;
174
174
  }
175
- return U(r, {
175
+ return B(r, {
176
176
  ...t,
177
177
  value: e,
178
178
  column: i,
@@ -180,7 +180,7 @@ var Ce = (e) => {
180
180
  });
181
181
  }, o = a(i.value, t.column);
182
182
  return typeof t.value == "string" ? JSON.stringify(o) : o;
183
- }, Le = (e) => {
183
+ }, Be = (e) => {
184
184
  try {
185
185
  return {
186
186
  ok: !0,
@@ -189,7 +189,7 @@ var Ce = (e) => {
189
189
  } catch {
190
190
  return { ok: !1 };
191
191
  }
192
- }, Re = (e) => {
192
+ }, Ve = (e) => {
193
193
  if (typeof e == "string") return e === "keep" || e === "null" || e === "redact" || e === "hash" || e === "dateShift" || e === "error";
194
194
  if (typeof e != "object" || !e) return !1;
195
195
  if ("fake" in e) return typeof e.fake == "string";
@@ -198,18 +198,18 @@ var Ce = (e) => {
198
198
  let t = e.json;
199
199
  if (typeof t != "object" || !t) return !1;
200
200
  let { fields: n, rest: r } = t;
201
- return typeof n != "object" || !n ? !1 : Object.values(n).every(Re) && (r === void 0 || Re(r));
201
+ return typeof n != "object" || !n ? !1 : Object.values(n).every(Ve) && (r === void 0 || Ve(r));
202
202
  }
203
203
  return !1;
204
- }, ze = (e, t, n) => {
204
+ }, He = (e, t, n) => {
205
205
  let r = {}, i = [], a = [];
206
206
  for (let o of e) for (let e of o.columns) {
207
- let s = `${o.name}.${e.name}`, c = Ee(o.name, e.name, t[o.name]?.[e.name], n);
207
+ let s = `${o.name}.${e.name}`, c = ke(o.name, e.name, t[o.name]?.[e.name], n);
208
208
  if (c === "error") {
209
209
  i.push(s);
210
210
  continue;
211
211
  }
212
- if (!Re(c)) {
212
+ if (!Ve(c)) {
213
213
  a.push({
214
214
  column: s,
215
215
  action: c
@@ -223,7 +223,7 @@ var Ce = (e) => {
223
223
  unclassified: i,
224
224
  invalid: a
225
225
  };
226
- }, Be = [
226
+ }, Ue = [
227
227
  {
228
228
  name: "email",
229
229
  re: /[\w.+-]+@[\w-]+\.[\w.-]+/
@@ -240,7 +240,7 @@ var Ce = (e) => {
240
240
  name: "creditCard",
241
241
  re: /\b(?:\d[ -]?){13,16}\b/
242
242
  }
243
- ], Ve = (e, t, n) => {
243
+ ], We = (e, t, n) => {
244
244
  let r = [], i = /* @__PURE__ */ new Set();
245
245
  for (let [a, o] of Object.entries(n)) {
246
246
  if (!a.startsWith(`${t}.`) || o !== "keep") continue;
@@ -248,7 +248,7 @@ var Ce = (e) => {
248
248
  for (let a of e) {
249
249
  let e = a[n];
250
250
  if (typeof e != "string" || e.length === 0) continue;
251
- let o = Be.find((t) => t.re.test(e));
251
+ let o = Ue.find((t) => t.re.test(e));
252
252
  if (o && !i.has(n)) {
253
253
  i.add(n), r.push({
254
254
  table: t,
@@ -261,9 +261,9 @@ var Ce = (e) => {
261
261
  }
262
262
  }
263
263
  return r;
264
- }, He = (e, t, n, r, i) => {
264
+ }, Ge = (e, t, n, r, i) => {
265
265
  let a = {};
266
- for (let [o, s] of Object.entries(e)) a[o] = U(n[`${t}.${o}`] ?? "keep", {
266
+ for (let [o, s] of Object.entries(e)) a[o] = B(n[`${t}.${o}`] ?? "keep", {
267
267
  value: s,
268
268
  table: t,
269
269
  column: o,
@@ -271,9 +271,17 @@ var Ce = (e) => {
271
271
  ...i?.[o] ? { columnType: i[o] } : {}
272
272
  });
273
273
  return a;
274
- }, Ue = /* @__PURE__ */ new Map([
274
+ }, Ke = /* @__PURE__ */ new Map([
275
+ ["_voltro_aggregate_meta", "materialized refresh generations computed HERE — a foreign row would claim that the target refreshed its own source data"],
276
+ ["_voltro_aggregate_rows", "materialized rows tied to this deployment’s refresh generation — the target recomputes them from its own data"],
277
+ ["_voltro_timeline", "captured source mutations from this deployment — foreign rows invent local timeline history"],
278
+ ["_voltro_timeline_meta", "capture epoch and source cursor of this database — foreign metadata claims continuity with another database"],
279
+ ["_voltro_timeline_leases", "active capture readers of this database — foreign leases claim readers that do not exist here"],
280
+ ["_voltro_timeline_slots", "bounded capture slots belonging to this source epoch — foreign slots invent local mutation history"],
281
+ ["_voltro_plugin_migrations", "plugin migration steps applied to this database — a foreign ledger would skip steps that the target has not run"],
275
282
  ["_voltro_migration_plans", "the schema fingerprint THIS deployment applied — a foreign row makes the next boot refuse"],
276
283
  ["_voltro_migrations", "which file-based migrations ran HERE — a foreign row marks unrun migrations as done"],
284
+ ["_voltro_plugin_migrations", "which plugin migration steps ran HERE — a foreign row marks a plugin's unrun steps as done"],
277
285
  ["_voltro_schema_owner", "which app owns THIS database — a foreign row hands the target's schema to the source app, so the target's own app refuses to boot on it"],
278
286
  ["_voltro_deploys", "the deploy THIS database is in the middle of, with the baseline to undo it from — a foreign row makes the next apply undo a deploy the target never started"],
279
287
  ["_voltro_devices", "devices paired with THIS deployment — token hashes; a foreign row makes a device paired elsewhere authenticate here"],
@@ -319,6 +327,7 @@ var Ce = (e) => {
319
327
  ["_voltro_workflow_start_receipts", "the caller-facing identity of a start placed HERE, resolved through this deployment's placements — a foreign receipt names a run the target never accepted"],
320
328
  ["_voltro_workflow_control_requests", "cancel/resume traffic issued against executions HERE — a foreign row claims an operation nobody asked the target to perform"],
321
329
  ["_voltro_workflow_queued_cancellations", "cancellations waiting on a run that is queued HERE — a foreign row cancels something the target has not queued"],
330
+ ["_voltro_workflow_restart_withdrawals", "withdrawal fences for restart requests issued HERE — a foreign row would block a target restart that its operator never withdrew"],
322
331
  ["_voltro_workflow_restart_requests", "restarts pending against this deployment's generations — a foreign row restarts a generation the target never entered"],
323
332
  ["_voltro_workflow_retry_requests", "retry intents an operator raised against runs HERE, keyed by their own request id — a foreign row binds the target to an intent nobody raised against it, and lets a later observation read somebody else's execution"],
324
333
  ["_voltro_workflow_parent_closures", "which parents are still waiting on children in flight HERE — a foreign row holds a parent open against a child the target is not running"],
@@ -327,8 +336,13 @@ var Ce = (e) => {
327
336
  ["_voltro_notification_deliveries", "the notification attempts this deployment made — a foreign row claims a send the target never performed"],
328
337
  ["_voltro_notification_held", "notifications waiting to be SENT from here — a foreign row makes the target deliver something queued elsewhere"],
329
338
  ["_voltro_webhook_event_stats", "per-deployment delivery counters a backoff decision reads — foreign counts steer the target's retries"],
330
- ["_voltro_webhook_rate_windows", "the live rate-limit windows this deployment is inside — a foreign window throttles or releases wrongly"]
331
- ]), We = /* @__PURE__ */ new Map([
339
+ ["_voltro_webhook_rate_windows", "the live rate-limit windows this deployment is inside — a foreign window throttles or releases wrongly"],
340
+ ["cluster_runners", "the workflow runners of THIS deployment and their addresses — a foreign row routes shards to a runner that does not exist here"],
341
+ ["cluster_locks", "the shard leases THIS deployment's runners hold — a foreign row holds a shard for nobody, and its work stalls"],
342
+ ["cluster_messages", "workflow messages in flight HERE — a foreign row makes the target run work that was started, and may be running, elsewhere"],
343
+ ["cluster_replies", "replies to those messages — a foreign row answers a request the target never sent"],
344
+ ["cluster_migrations", "which engine migrations ran HERE — a foreign row marks the target's engine tables migrated when they are not"]
345
+ ]), qe = /* @__PURE__ */ new Map([
332
346
  ["_voltro_agent_threads", "conversations the app's users had — app data"],
333
347
  ["_voltro_agent_messages", "the messages in those conversations — app data"],
334
348
  ["_voltro_prompts", "prompt definitions the app authored — app data"],
@@ -364,21 +378,21 @@ var Ce = (e) => {
364
378
  ["_voltro_comment_threads", "the threads those comments hang on — app data"],
365
379
  ["_voltro_comment_reactions", "the reactions the app's users left — app data"],
366
380
  ["_voltro_comment_reads", "which comments each user has read — app data, and losing it re-marks everything unread"]
367
- ]), W = (e) => Ue.has(e), Ge = (e) => Ue.get(e), Ke = (e, t) => {
381
+ ]), V = (e) => Ke.has(e), Je = (e) => Ke.get(e), Ye = (e, t) => {
368
382
  if (e.length === 0) return;
369
- let n = e.map((e) => ` ${e} — ${Ge(e) ?? "describes this deployment"}`);
383
+ let n = e.map((e) => ` ${e} — ${Je(e) ?? "describes this deployment"}`);
370
384
  return `${t} ${e.length} table(s) that describe a deployment rather than its data:\n${n.join("\n")}\n A row from another environment is not stale there, it is a false statement about this one.`;
371
- }, G = class extends c.TaggedError()("BundleError", {
385
+ }, H = class extends c.TaggedError()("BundleError", {
372
386
  reason: c.String,
373
387
  path: c.optional(c.String)
374
- }) {}, qe = class extends c.TaggedError()("CodecError", {
388
+ }) {}, Xe = class extends c.TaggedError()("CodecError", {
375
389
  table: c.String,
376
390
  reason: c.String
377
- }) {}, Je = class extends c.TaggedError()("IntegrityError", {
391
+ }) {}, Ze = class extends c.TaggedError()("IntegrityError", {
378
392
  what: c.String,
379
393
  expected: c.String,
380
394
  actual: c.String
381
- }) {}, Ye = class extends t.TaggedError("CompressionError") {}, Xe = class extends c.TaggedError()("ScopeError", { reason: c.String }) {}, Ze = class extends c.TaggedError()("RowsRefusedError", {
395
+ }) {}, Qe = class extends t.TaggedError("CompressionError") {}, U = class extends c.TaggedError()("ScopeError", { reason: c.String }) {}, $e = class extends c.TaggedError()("RowsRefusedError", {
382
396
  rows: c.Array(c.Struct({
383
397
  table: c.String,
384
398
  id: c.String,
@@ -392,29 +406,29 @@ var Ce = (e) => {
392
406
  refused: c.Number,
393
407
  primary: c.Number
394
408
  }))
395
- }) {}, Qe = class extends c.TaggedError()("SchemaDriftError", {
409
+ }) {}, et = class extends c.TaggedError()("SchemaDriftError", {
396
410
  bundleFingerprint: c.String,
397
411
  targetFingerprint: c.String,
398
412
  diff: c.Array(c.String)
399
- }) {}, K = class extends t.TaggedError("NativeToolError") {
413
+ }) {}, W = class extends t.TaggedError("NativeToolError") {
400
414
  get message() {
401
415
  let e = this.stderr?.trim(), t = this.hint?.trim();
402
416
  return `${this.tool}: ${this.reason}${e ? `\n${e}` : ""}${t ? `\n\nhint: ${t}` : ""}`;
403
417
  }
404
- }, $e = class extends c.TaggedError()("MaskingError", {
418
+ }, tt = class extends c.TaggedError()("MaskingError", {
405
419
  unclassified: c.Array(c.String),
406
420
  invalidActions: c.optional(c.Array(c.String))
407
- }) {}, et = class extends c.TaggedError()("ImportModeError", {
421
+ }) {}, nt = class extends c.TaggedError()("ImportModeError", {
408
422
  mode: c.String,
409
423
  reason: c.String
410
- }) {}, tt = class extends c.TaggedError()("CrossDialectError", {
424
+ }) {}, rt = class extends c.TaggedError()("CrossDialectError", {
411
425
  sourceDialect: c.String,
412
426
  targetDialect: c.String,
413
427
  blocking: c.Array(c.String)
414
- }) {}, nt = (e, t) => e.tables.find((e) => e.name === t)?.columns.find((e) => e.type === "id")?.name ?? "id", rt = (e, t) => (e.tables.find((e) => e.name === t)?.columns ?? []).filter((e) => e.references).map((e) => ({
428
+ }) {}, it = (e, t) => e.tables.find((e) => e.name === t)?.columns.find((e) => e.type === "id")?.name ?? "id", at = (e, t) => (e.tables.find((e) => e.name === t)?.columns ?? []).filter((e) => e.references).map((e) => ({
415
429
  col: e.name,
416
430
  refTable: e.references.table
417
- })), it = (e, t, r) => n.gen(function* () {
431
+ })), ot = (e, t, r) => n.gen(function* () {
418
432
  let i = r.maxDepth ?? 12, a = new Set(r.pinned ?? []), o = /* @__PURE__ */ new Map(), s = /* @__PURE__ */ new Map(), c = /* @__PURE__ */ new Map(), u = (e) => {
419
433
  let t = s.get(e) ?? /* @__PURE__ */ new Set();
420
434
  return s.set(e, t), t;
@@ -432,10 +446,10 @@ var Ce = (e) => {
432
446
  for (let t of n) d(t.refTable, e[t.col]);
433
447
  };
434
448
  }, p = (r, i) => {
435
- let a = f(r, nt(t, r), rt(t, r));
436
- return l.runForEach(w(e, {
449
+ let a = f(r, it(t, r), at(t, r));
450
+ return l.runForEach(C(e, {
437
451
  table: r,
438
- pk: nt(t, r),
452
+ pk: it(t, r),
439
453
  ...i === void 0 ? {} : { where: i }
440
454
  }), (e) => n.sync(() => a(e)));
441
455
  }, m = n.gen(function* () {
@@ -444,7 +458,7 @@ var Ce = (e) => {
444
458
  c.clear();
445
459
  for (let [n, r] of e) {
446
460
  let e = [...r].filter((e) => !s.get(n)?.has(e));
447
- e.length !== 0 && (yield* p(n, b(nt(t, n), e)));
461
+ e.length !== 0 && (yield* p(n, b(it(t, n), e)));
448
462
  }
449
463
  }
450
464
  });
@@ -467,24 +481,24 @@ var Ce = (e) => {
467
481
  }
468
482
  }
469
483
  return o;
470
- }), at = (e, t) => ({
484
+ }), st = (e, t) => ({
471
485
  tables: [...e.keys()],
472
486
  predicateFor: (n) => {
473
487
  let r = e.get(n);
474
- return r ? b(nt(t, n), [...r]) : void 0;
488
+ return r ? b(it(t, n), [...r]) : void 0;
475
489
  }
476
- }), ot = "tenantId", st = (e, t, r) => n.gen(function* () {
490
+ }), ct = "tenantId", lt = (e, t, r) => n.gen(function* () {
477
491
  let i = t.tables.map((e) => e.name), a = new Map(t.tables.map((e) => [e.name, e]));
478
492
  if (e.kind === "all") {
479
493
  let t = new Set(e.exclude ?? []);
480
494
  return {
481
- tables: i.filter((e) => !W(e) && !t.has(e)),
495
+ tables: i.filter((e) => !V(e) && !t.has(e)),
482
496
  predicateFor: () => void 0
483
497
  };
484
498
  }
485
499
  if (e.kind === "tables") {
486
500
  let t = e.tables ?? [], r = new Set(i), a = t.filter((e) => !r.has(e));
487
- if (a.length > 0) return yield* n.fail(new Xe({ reason: `scope { kind: 'tables' } names ${a.length} table(s) that are not in the schema: ${a.join(", ")}. Refusing to write a bundle that silently omits them. Known tables: ${i.length}.` }));
501
+ if (a.length > 0) return yield* n.fail(new U({ reason: `scope { kind: 'tables' } names ${a.length} table(s) that are not in the schema: ${a.join(", ")}. Refusing to write a bundle that silently omits them. Known tables: ${i.length}.` }));
488
502
  let o = new Set(t);
489
503
  return {
490
504
  tables: i.filter((e) => o.has(e)),
@@ -492,30 +506,30 @@ var Ce = (e) => {
492
506
  };
493
507
  }
494
508
  let o = e.tenantId;
495
- if (o === void 0 || o === "") return yield* n.fail(new Xe({ reason: "scope { kind: 'tenant' } requires a tenantId — pass --tenant <id> (CLI) or scope.tenantId (API). Refusing to fall back to an unfiltered export." }));
496
- let s = r.tenantTables ? r.tenantTables.filter((e) => a.has(e)) : i.filter((e) => a.get(e)?.columns.some((e) => e.name === ot) ?? !1);
497
- if (s.length === 0) return yield* n.fail(new Xe({ reason: r.tenantTables ? "tenant scope: none of the provided tenantTables exist in the schema — nothing to filter." : `tenant scope: no table carries a '${ot}' column — nothing to filter. A tenant export of a schema without tenant-scoped tables would be the full database; refusing.` }));
498
- let c = yield* it(r.store, t, {
499
- seeds: Object.fromEntries(s.map((e) => [e, _(ot, o)])),
509
+ if (o === void 0 || o === "") return yield* n.fail(new U({ reason: "scope { kind: 'tenant' } requires a tenantId — pass --tenant <id> (CLI) or scope.tenantId (API). Refusing to fall back to an unfiltered export." }));
510
+ let s = r.tenantTables ? r.tenantTables.filter((e) => a.has(e)) : i.filter((e) => a.get(e)?.columns.some((e) => e.name === ct) ?? !1);
511
+ if (s.length === 0) return yield* n.fail(new U({ reason: r.tenantTables ? "tenant scope: none of the provided tenantTables exist in the schema — nothing to filter." : `tenant scope: no table carries a '${ct}' column — nothing to filter. A tenant export of a schema without tenant-scoped tables would be the full database; refusing.` }));
512
+ let c = yield* ot(r.store, t, {
513
+ seeds: Object.fromEntries(s.map((e) => [e, _(ct, o)])),
500
514
  pinned: s,
501
515
  children: { roots: s }
502
516
  }), l = [...c.entries()].filter(([, e]) => e.size > 0).map(([e]) => e), u = new Set(s);
503
517
  return {
504
518
  tables: [...s, ...l],
505
- predicateFor: (e) => u.has(e) ? _(ot, o) : c.has(e) ? b(nt(t, e), [...c.get(e)]) : void 0
519
+ predicateFor: (e) => u.has(e) ? _(ct, o) : c.has(e) ? b(it(t, e), [...c.get(e)]) : void 0
506
520
  };
507
- }), ct = (e, t) => ({
521
+ }), ut = (e, t) => ({
508
522
  list: t,
509
- open: (t) => j(e, t)
510
- }), lt = (e) => ({
511
- write: (t, n, r) => he(e, t, n, r),
523
+ open: (t) => _e(e, t)
524
+ }), dt = (e) => ({
525
+ write: (t, n, r) => k(e, t, n, r),
512
526
  has: (t) => e.head(t).pipe(n.map((e) => e !== null))
513
- }), ut = (e, t) => n.tryPromise({
527
+ }), ft = (e, t) => n.tryPromise({
514
528
  try: async () => {
515
529
  let { createWriteStream: n } = await import("node:fs"), r = await import("node:fs/promises"), { createHash: i, randomUUID: a } = await import("node:crypto"), { pipeline: o } = await import("node:stream/promises"), { Transform: s } = await import("node:stream"), c = await import("node:path"), l = c.join(t, `.tmp-${a()}`), u = i("sha256"), d = 0, f = new s({ transform(e, t, n) {
516
530
  u.update(e), d += e.length, n(null, e);
517
531
  } });
518
- await o(await M(e.stream), f, n(l));
532
+ await o(await A(e.stream), f, n(l));
519
533
  let p = u.digest("hex"), m = c.join(t, p);
520
534
  try {
521
535
  await r.access(m), await r.rm(l, { force: !0 });
@@ -528,30 +542,30 @@ var Ce = (e) => {
528
542
  contentType: e.contentType
529
543
  };
530
544
  },
531
- catch: (e) => new G({
545
+ catch: (e) => new H({
532
546
  reason: `asset write failed: ${String(e?.message ?? e)}`,
533
547
  path: t
534
548
  })
535
- }), dt = (e, t, r) => n.gen(function* () {
536
- let i = yield* n.promise(() => import("node:path")), { createReadStream: a } = yield* n.promise(() => import("node:fs")), { createHash: o } = yield* n.promise(() => import("node:crypto")), s = i.join(t, r.sha256), c = o("sha256"), u = me("bundle", () => a(s)).pipe(l.tap((e) => n.sync(() => c.update(e))));
549
+ }), pt = (e, t, r) => n.gen(function* () {
550
+ let i = yield* n.promise(() => import("node:path")), { createReadStream: a } = yield* n.promise(() => import("node:fs")), { createHash: o } = yield* n.promise(() => import("node:crypto")), s = i.join(t, r.sha256), c = o("sha256"), u = ge("bundle", () => a(s)).pipe(l.tap((e) => n.sync(() => c.update(e))));
537
551
  yield* e.write(r.key, u, {
538
552
  contentType: r.contentType,
539
553
  totalSize: r.size
540
554
  });
541
555
  let d = c.digest("hex");
542
- if (d !== r.sha256) return yield* n.fail(new Je({
556
+ if (d !== r.sha256) return yield* n.fail(new Ze({
543
557
  what: `asset ${r.key}`,
544
558
  expected: r.sha256,
545
559
  actual: d
546
560
  }));
547
- }), ft = {
561
+ }), mt = {
548
562
  done: () => !1,
549
563
  mark: () => n.void
550
- }, pt = (e) => typeof e == "object" && !!e && e.status === 404, mt = (e) => n.gen(function* () {
551
- let t = e.progress ?? ft, r = 0, i = 0, a = 0, o = 0, s = /* @__PURE__ */ new Set(), c = /* @__PURE__ */ new Set(), u = [];
552
- return yield* l.runForEach(e.source.list(), (l) => (a++, t.done(l.key) || c.has(l.key) ? n.void : (c.add(l.key), e.source.open(l.key).pipe(n.map((e) => e), n.catchIf(pt, () => n.sync(() => {
564
+ }, ht = (e) => typeof e == "object" && !!e && e.status === 404, gt = (e) => n.gen(function* () {
565
+ let t = e.progress ?? mt, r = 0, i = 0, a = 0, o = 0, s = /* @__PURE__ */ new Set(), c = /* @__PURE__ */ new Set(), u = [];
566
+ return yield* l.runForEach(e.source.list(), (l) => (a++, t.done(l.key) || c.has(l.key) ? n.void : (c.add(l.key), e.source.open(l.key).pipe(n.map((e) => e), n.catchIf(ht, () => n.sync(() => {
553
567
  u.push(l.key);
554
- })), n.flatMap((a) => a === void 0 ? n.void : ut(a, e.assetsDir).pipe(n.flatMap((e) => {
568
+ })), n.flatMap((a) => a === void 0 ? n.void : ft(a, e.assetsDir).pipe(n.flatMap((e) => {
555
569
  let n = {
556
570
  key: l.key,
557
571
  sha256: e.sha256,
@@ -559,7 +573,7 @@ var Ce = (e) => {
559
573
  contentType: e.contentType
560
574
  };
561
575
  return r++, i += e.size, s.has(e.sha256) || (s.add(e.sha256), o += e.size), t.mark(l.key, n);
562
- }))))))).pipe(n.mapError((e) => e instanceof G ? e : new G({ reason: `asset export failed: ${String(e)}` }))), {
576
+ }))))))).pipe(n.mapError((e) => e instanceof H ? e : new H({ reason: `asset export failed: ${String(e)}` }))), {
563
577
  count: r,
564
578
  totalBytes: i,
565
579
  references: a,
@@ -567,18 +581,18 @@ var Ce = (e) => {
567
581
  objectBytes: o,
568
582
  missing: u
569
583
  };
570
- }), ht = (e) => me("bundle", () => de(e)).pipe(l.decodeText(), l.splitLines, l.filter((e) => e.trim().length > 0), l.map((e) => JSON.parse(e)), l.mapError((t) => t instanceof G ? t : new G({
584
+ }), _t = (e) => ge("bundle", () => fe(e)).pipe(l.decodeText(), l.splitLines, l.filter((e) => e.trim().length > 0), l.map((e) => JSON.parse(e)), l.mapError((t) => t instanceof H ? t : new H({
571
585
  reason: `asset index unreadable: ${String(t)}`,
572
586
  path: e
573
- }))), gt = (e) => n.gen(function* () {
574
- let t = e.progress ?? ft, r = 0, i = /* @__PURE__ */ new Set(), a = /* @__PURE__ */ new Set();
575
- return yield* l.runForEach(ht(e.indexPath), (o) => t.done(o.key) || a.has(o.key) ? n.void : (a.add(o.key), dt(e.sink, e.assetsDir, o)).pipe(n.andThen(n.sync(() => {
587
+ }))), vt = (e) => n.gen(function* () {
588
+ let t = e.progress ?? mt, r = 0, i = /* @__PURE__ */ new Set(), a = /* @__PURE__ */ new Set();
589
+ return yield* l.runForEach(_t(e.indexPath), (o) => t.done(o.key) || a.has(o.key) ? n.void : (a.add(o.key), pt(e.sink, e.assetsDir, o)).pipe(n.andThen(n.sync(() => {
576
590
  r++, i.add(o.sha256);
577
591
  })), n.andThen(t.mark(o.key, o)))), {
578
592
  count: r,
579
593
  objects: i.size
580
594
  };
581
- }), _t = () => typeof N.createZstdCompress == "function", vt = (e) => e === "none" ? "none" : e === "gzip" ? "gzip" : _t() ? "zstd" : "gzip", yt = (e) => e === "zstd" ? ".zst" : e === "gzip" ? ".gz" : "", bt = (e) => e === "zstd" ? N.createZstdCompress() : e === "gzip" ? N.createGzip() : new P(), xt = (e) => e === "zstd" ? N.createZstdDecompress() : e === "gzip" ? N.createGunzip() : new P(), St = 1, Ct = c.Struct({
595
+ }), yt = () => typeof j.createZstdCompress == "function", bt = (e) => e === "none" ? "none" : e === "gzip" ? "gzip" : yt() ? "zstd" : "gzip", xt = (e) => e === "zstd" ? ".zst" : e === "gzip" ? ".gz" : "", St = (e) => e === "zstd" ? j.createZstdCompress() : e === "gzip" ? j.createGzip() : new M(), Ct = (e) => e === "zstd" ? j.createZstdDecompress() : e === "gzip" ? j.createGunzip() : new M(), wt = 1, Tt = c.Struct({
582
596
  name: c.String,
583
597
  file: c.String,
584
598
  rowCount: c.Number,
@@ -588,12 +602,12 @@ var Ce = (e) => {
588
602
  value: c.String
589
603
  }),
590
604
  primaryKey: c.String
591
- }), wt = c.Struct({
605
+ }), Et = c.Struct({
592
606
  kind: c.Literal("all", "tenant", "tables"),
593
607
  tenantId: c.optional(c.String),
594
608
  tables: c.optional(c.Array(c.String)),
595
609
  exclude: c.optional(c.Array(c.String))
596
- }), Tt = c.Struct({
610
+ }), Dt = c.Struct({
597
611
  count: c.Number,
598
612
  totalBytes: c.Number,
599
613
  index: c.optional(c.String)
@@ -604,23 +618,23 @@ c.Struct({
604
618
  size: c.Number,
605
619
  contentType: c.String
606
620
  });
607
- var Et = c.Struct({
621
+ var Ot = c.Struct({
608
622
  formatVersion: c.Number,
609
623
  createdAt: c.String,
610
624
  source: c.Struct({
611
625
  dialect: c.String,
612
626
  schemaFingerprint: c.String
613
627
  }),
614
- scope: wt,
628
+ scope: Et,
615
629
  consistency: c.Literal("live", "snapshot"),
616
630
  compression: c.Literal("zstd", "gzip", "none"),
617
- tables: c.Array(Ct),
618
- assets: Tt,
631
+ tables: c.Array(Tt),
632
+ assets: Dt,
619
633
  masking: c.optional(c.Struct({
620
634
  policyId: c.optional(c.String),
621
635
  transformed: c.Array(c.String)
622
636
  }))
623
- }), Dt = c.encodeSync(c.parseJson(Et)), Ot = c.decodeUnknownSync(c.parseJson(Et)), kt = "manifest.json", At = "README.md", jt = "data", Mt = "assets", Nt = "assets/index.ndjson", Pt = ".ledger.json", Ft = (e) => e.kind === "tenant" ? `tenant \`${e.tenantId}\`` : e.kind === "tables" ? `tables \`${(e.tables ?? []).join(", ")}\`` : "all tables", It = (e, t) => {
637
+ }), kt = c.encodeSync(c.parseJson(Ot)), At = c.decodeUnknownSync(c.parseJson(Ot)), jt = "manifest.json", Mt = "README.md", Nt = "data", Pt = "assets", Ft = "assets/index.ndjson", It = ".ledger.json", Lt = (e) => e.kind === "tenant" ? `tenant \`${e.tenantId}\`` : e.kind === "tables" ? `tables \`${(e.tables ?? []).join(", ")}\`` : "all tables", Rt = (e, t) => {
624
638
  let n = e.tables.reduce((e, t) => e + t.rowCount, 0), r = e.masking ? `✅ **Masked at the source** — ${e.masking.transformed.length} column(s) transformed${e.masking.policyId ? ` (policy \`${e.masking.policyId}\`)` : ""}. Personal data was replaced with realistic, referentially-consistent fakes before any byte was written.` : "⚠️ **NOT masked — this bundle contains REAL data (PII included).** Treat it as production data: do not copy it into a lower environment or share it without review. To produce a safe copy, re-export under a masking profile (`--profile`).", i = e.masking && e.masking.transformed.length > 0 ? `\n\nMasked columns: ${e.masking.transformed.map((e) => `\`${e}\``).join(", ")}.` : "", a = e.assets.count > 0 ? `${e.assets.count} object(s), ${e.assets.totalBytes} bytes` : "none", o = e.tables.map((e) => `| \`${e.name}\` | ${e.rowCount} |`).join("\n");
625
639
  return `# Voltro data export
626
640
 
@@ -634,7 +648,7 @@ The machine-readable manifest is \`manifest.json\`; this file is a human summary
634
648
  | **Format version** | ${e.formatVersion} |
635
649
  | **Consistency** | ${e.consistency} |
636
650
  | **Compression** | ${e.compression} |
637
- | **Scope** | ${Ft(e.scope)} |
651
+ | **Scope** | ${Lt(e.scope)} |
638
652
  | **Tables** | ${e.tables.length} |
639
653
  | **Rows (total)** | ${n} |
640
654
  | **Assets** | ${a} |
@@ -659,39 +673,39 @@ voltro data import <this-directory>
659
673
  voltro data import <this-directory> --target api --api-url <url> --token <secret>
660
674
  \`\`\`
661
675
  `;
662
- }, Lt = i.counter("voltro_data_transfer_rows", { description: "Rows exported/imported by @voltro/data-transfer, tagged by phase + table." }), Rt = a.exponential({
676
+ }, zt = i.counter("voltro_data_transfer_rows", { description: "Rows exported/imported by @voltro/data-transfer, tagged by phase + table." }), Bt = a.exponential({
663
677
  start: .01,
664
678
  factor: 2,
665
679
  count: 16
666
- }), zt = i.histogram("voltro_data_transfer_table_seconds", Rt, "Per-table export/import duration in seconds, tagged by phase."), q = (e, t) => {
680
+ }), Vt = i.histogram("voltro_data_transfer_table_seconds", Bt, "Per-table export/import duration in seconds, tagged by phase."), G = (e, t) => {
667
681
  if (e) try {
668
682
  e(t);
669
683
  } catch {}
670
- }, Bt = (e, t, r, a, o, s) => n.Do.pipe(n.bind("start", () => n.clockWith((e) => e.currentTimeMillis)), n.bind("result", () => s), n.tap(({ start: r, result: a }) => n.clockWith((e) => e.currentTimeMillis).pipe(n.flatMap((s) => n.zipRight(zt.pipe(i.tagged("phase", e), i.update((s - r) / 1e3)), Lt.pipe(i.tagged("phase", e), i.tagged("table", t), i.update(o(a))))))), n.map(({ result: e }) => e), n.withSpan(`data-transfer.${e}.table`, { attributes: {
684
+ }, Ht = (e, t, r, a, o, s) => n.Do.pipe(n.bind("start", () => n.clockWith((e) => e.currentTimeMillis)), n.bind("result", () => s), n.tap(({ start: r, result: a }) => n.clockWith((e) => e.currentTimeMillis).pipe(n.flatMap((s) => n.zipRight(Vt.pipe(i.tagged("phase", e), i.update((s - r) / 1e3)), zt.pipe(i.tagged("phase", e), i.tagged("table", t), i.update(o(a))))))), n.map(({ result: e }) => e), n.withSpan(`data-transfer.${e}.table`, { attributes: {
671
685
  table: t,
672
686
  index: r,
673
687
  tableCount: a,
674
688
  phase: e
675
- } })), Vt = () => ({
689
+ } })), Ut = () => ({
676
690
  tables: {},
677
691
  assets: {}
678
- }), Ht = (e) => n.tryPromise(async () => {
692
+ }), Wt = (e) => n.tryPromise(async () => {
679
693
  let t = await (await import("node:fs/promises")).readFile(e, "utf8");
680
694
  return JSON.parse(t);
681
- }).pipe(n.orElseSucceed(Vt)), J = (e, t) => n.tryPromise({
695
+ }).pipe(n.orElseSucceed(Ut)), K = (e, t) => n.tryPromise({
682
696
  try: async () => {
683
697
  let n = await import("node:fs/promises"), { randomUUID: r } = await import("node:crypto"), i = `${e}.tmp-${r()}`;
684
698
  await n.writeFile(i, JSON.stringify(t)), await n.rename(i, e);
685
699
  },
686
- catch: (t) => new G({
700
+ catch: (t) => new H({
687
701
  reason: `ledger write failed: ${String(t?.message ?? t)}`,
688
702
  path: e
689
703
  })
690
- }), Ut = (e, t) => t in e.tables, Wt = (e, t) => t in e.assets, Gt = /* @__PURE__ */ new Set([
704
+ }), Gt = (e, t) => t in e.tables, Kt = (e, t) => t in e.assets, qt = /* @__PURE__ */ new Set([
691
705
  "json",
692
706
  "array",
693
707
  "vector"
694
- ]), Kt = (e) => typeof e == "object" && !!e && !Array.isArray(e) && typeof e.$v == "string", qt = (e) => Buffer.from(e).toString("base64"), Jt = (e) => new Uint8Array(Buffer.from(e, "base64")), Yt = (e) => e instanceof Date ? e.toISOString() : typeof e == "number" ? new Date(e).toISOString() : String(e), Xt = (e, t) => e == null ? null : t !== void 0 && Gt.has(t) ? e : t === "bytes" ? qt(e) : t === "timestamp" || t === "date" ? Yt(e) : typeof e == "bigint" ? {
708
+ ]), Jt = (e) => typeof e == "object" && !!e && !Array.isArray(e) && typeof e.$v == "string", Yt = (e) => Buffer.from(e).toString("base64"), Xt = (e) => new Uint8Array(Buffer.from(e, "base64")), Zt = (e) => e instanceof Date ? e.toISOString() : typeof e == "number" ? new Date(e).toISOString() : String(e), Qt = (e, t) => e == null ? null : t !== void 0 && qt.has(t) ? e : t === "bytes" ? Yt(e) : t === "timestamp" || t === "date" ? Zt(e) : typeof e == "bigint" ? {
695
709
  $v: "bigint",
696
710
  d: e.toString()
697
711
  } : typeof e == "number" && !Number.isFinite(e) ? {
@@ -702,30 +716,30 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
702
716
  d: e.toISOString()
703
717
  } : e instanceof Uint8Array ? {
704
718
  $v: "bytes",
705
- d: qt(e)
706
- } : e, Zt = (e) => {
719
+ d: Yt(e)
720
+ } : e, $t = (e) => {
707
721
  switch (e.$v) {
708
722
  case "bigint": return BigInt(e.d);
709
723
  case "number": return Number(e.d);
710
724
  case "date": return new Date(e.d);
711
- case "bytes": return Jt(e.d);
725
+ case "bytes": return Xt(e.d);
712
726
  default: return e;
713
727
  }
714
- }, Qt = (e, t) => e == null ? null : t !== void 0 && Gt.has(t) ? e : Kt(e) ? Zt(e) : t === "bytes" ? Jt(e) : t === "timestamp" || t === "date" ? new Date(e) : e, $t = (e, t) => {
728
+ }, en = (e, t) => e == null ? null : t !== void 0 && qt.has(t) ? e : Jt(e) ? $t(e) : t === "bytes" ? Xt(e) : t === "timestamp" || t === "date" ? new Date(e) : e, tn = (e, t) => {
715
729
  let n = {};
716
- for (let [r, i] of Object.entries(e)) n[r] = Xt(i, t[r]);
730
+ for (let [r, i] of Object.entries(e)) n[r] = Qt(i, t[r]);
717
731
  return n;
718
- }, en = (e, t) => {
732
+ }, nn = (e, t) => {
719
733
  let n = {};
720
- for (let [r, i] of Object.entries(e)) n[r] = Qt(i, t[r]);
734
+ for (let [r, i] of Object.entries(e)) n[r] = en(i, t[r]);
721
735
  return n;
722
- }, tn = new TextEncoder(), nn = (e, t) => e.pipe(l.map((e) => tn.encode(`${JSON.stringify($t(e, t))}\n`))), rn = (e, t, r) => e.pipe(l.decodeText(), l.splitLines, l.filter((e) => e.trim().length > 0), l.mapEffect((e) => n.try({
723
- try: () => en(JSON.parse(e), r),
724
- catch: (e) => new qe({
736
+ }, rn = new TextEncoder(), an = (e, t) => e.pipe(l.map((e) => rn.encode(`${JSON.stringify(tn(e, t))}\n`))), on = (e, t, r) => e.pipe(l.decodeText(), l.splitLines, l.filter((e) => e.trim().length > 0), l.mapEffect((e) => n.try({
737
+ try: () => nn(JSON.parse(e), r),
738
+ catch: (e) => new Xe({
725
739
  table: t,
726
740
  reason: String(e?.message ?? e)
727
741
  })
728
- }))), an = (e, t) => {
742
+ }))), sn = (e, t) => {
729
743
  let n = new Set(e), r = /* @__PURE__ */ new Map();
730
744
  for (let e of t.tables) {
731
745
  if (!n.has(e.name)) continue;
@@ -745,39 +759,39 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
745
759
  };
746
760
  for (let t of e) n.has(t) && s(t);
747
761
  return i;
748
- }, Y = (e) => {
762
+ }, q = (e) => {
749
763
  let t = e, n = [];
750
764
  typeof t?._tag == "string" && t._tag !== "" && n.push(t._tag);
751
765
  let r = typeof t?.message == "string" ? t.message.trim() : "";
752
- if (r === "" ? t?.cause !== void 0 && t.cause !== null && n.push(Y(t.cause)) : n.push(r), n.length === 0) {
766
+ if (r === "" ? t?.cause !== void 0 && t.cause !== null && n.push(q(t.cause)) : n.push(r), n.length === 0) {
753
767
  let t = String(e ?? "").trim();
754
- return t === "" || t === "[object Object]" ? on(e) : t;
768
+ return t === "" || t === "[object Object]" ? cn(e) : t;
755
769
  }
756
770
  return n.join(": ");
757
- }, on = (e) => {
771
+ }, cn = (e) => {
758
772
  try {
759
773
  let t = JSON.stringify(e);
760
774
  return t === void 0 || t === "{}" ? "unknown error (no message, cause or tag)" : t;
761
775
  } catch {
762
776
  return "unknown error (not serialisable)";
763
777
  }
764
- }, sn = (e, t) => {
778
+ }, ln = (e, t) => {
765
779
  let n = e.tables.find((e) => e.name === t), r = {};
766
780
  for (let e of n?.columns ?? []) e.generatedAs === void 0 && (r[e.name] = e.type);
767
781
  return r;
768
- }, cn = (e, t) => (e.tables.find((e) => e.name === t)?.columns ?? []).filter((e) => e.generatedAs !== void 0).map((e) => e.name), ln = (e, t) => {
782
+ }, un = (e, t) => (e.tables.find((e) => e.name === t)?.columns ?? []).filter((e) => e.generatedAs !== void 0).map((e) => e.name), dn = (e, t) => {
769
783
  if (t.length === 0) return e;
770
784
  let n = { ...e };
771
785
  for (let e of t) delete n[e];
772
786
  return n;
773
- }, un = (e, t) => {
787
+ }, fn = (e, t) => {
774
788
  let n = e.tables.find((e) => e.name === t);
775
789
  if (n === void 0) return { refusal: `${t}: not in the schema snapshot, so its primary key is unknown.` };
776
790
  let r = n.columns.find((e) => e.type === "id");
777
791
  if (r !== void 0) return { column: r.name };
778
792
  let i = n.indexes.find((e) => e.name === `${t}_pkey`)?.columns ?? n.primaryKey ?? [];
779
793
  return i.length === 1 ? { column: i[0] } : i.length > 1 ? { refusal: `${t}: composite primary key (${i.join(", ")}). Keyset export orders by ONE column; ordering by the first alone would split equal values across pages and drop or duplicate rows. Exclude this table from the scope, or give it a single-column key.` } : { refusal: `${t}: no primary key, so there is no stable order to paginate by. A keyset export would return rows in an order the database may change between pages. Exclude this table from the scope.` };
780
- }, dn = (e, t, r) => n.tryPromise({
794
+ }, pn = (e, t, r) => n.tryPromise({
781
795
  try: async () => {
782
796
  let { createWriteStream: n } = await import("node:fs"), i = await import("node:fs/promises"), { createHash: a, randomUUID: o } = await import("node:crypto"), { pipeline: s } = await import("node:stream/promises"), { Readable: c, Transform: u } = await import("node:stream"), d = a("sha256"), f = 0, p = new u({ transform(e, t, n) {
783
797
  d.update(e);
@@ -786,7 +800,7 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
786
800
  n(null, e);
787
801
  } }), m = c.fromWeb(l.toReadableStream(e)), h = `${t}.tmp-${o()}`;
788
802
  try {
789
- await s(m, p, bt(r), n(h)), await i.rename(h, t);
803
+ await s(m, p, St(r), n(h)), await i.rename(h, t);
790
804
  } catch (e) {
791
805
  throw await i.rm(h, { force: !0 }).catch(() => {}), e;
792
806
  }
@@ -795,27 +809,27 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
795
809
  checksum: d.digest("hex")
796
810
  };
797
811
  },
798
- catch: (e) => new G({
799
- reason: `write table failed: ${Y(e)}`,
812
+ catch: (e) => new H({
813
+ reason: `write table failed: ${q(e)}`,
800
814
  path: t
801
815
  })
802
- }), fn = (e, t) => n.tryPromise({
816
+ }), mn = (e, t) => n.tryPromise({
803
817
  try: async () => {
804
818
  await (await import("node:fs/promises")).appendFile(e, `${t}\n`);
805
819
  },
806
- catch: (t) => new G({
807
- reason: `append failed: ${Y(t)}`,
820
+ catch: (t) => new H({
821
+ reason: `append failed: ${q(t)}`,
808
822
  path: e
809
823
  })
810
- }), pn = (e, t) => n.gen(function* () {
824
+ }), hn = (e, t) => n.gen(function* () {
811
825
  let r = [], i = t.ordered.length;
812
826
  for (let a = 0; a < t.ordered.length; a++) {
813
- let o = t.ordered[a], s = sn(t.snapshot, o), c = un(t.snapshot, o);
814
- if ("refusal" in c) return yield* n.fail(new Xe({ reason: `export: ${c.refusal}` }));
815
- let u = c.column, d = `${jt}/${o}.ndjson${yt(t.compression)}`;
816
- if (Ut(t.ledger, o)) {
827
+ let o = t.ordered[a], s = ln(t.snapshot, o), c = fn(t.snapshot, o);
828
+ if ("refusal" in c) return yield* n.fail(new U({ reason: `export: ${c.refusal}` }));
829
+ let u = c.column, d = `${Nt}/${o}.ndjson${xt(t.compression)}`;
830
+ if (Gt(t.ledger, o)) {
817
831
  let e = t.ledger.tables[o];
818
- q(t.onProgress, {
832
+ G(t.onProgress, {
819
833
  phase: "export",
820
834
  table: o,
821
835
  index: a,
@@ -833,7 +847,7 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
833
847
  });
834
848
  continue;
835
849
  }
836
- q(t.onProgress, {
850
+ G(t.onProgress, {
837
851
  phase: "export",
838
852
  table: o,
839
853
  index: a,
@@ -841,17 +855,17 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
841
855
  event: "start",
842
856
  rowsDone: 0
843
857
  });
844
- let f = t.resolved.predicateFor(o), p = w(e, {
858
+ let f = t.resolved.predicateFor(o), p = C(e, {
845
859
  table: o,
846
860
  pk: u,
847
861
  chunkSize: t.chunkSize,
848
862
  retry: t.retry,
849
863
  ...f === void 0 ? {} : { where: f }
850
- }), m = cn(t.snapshot, o), h = m.length === 0 ? p : p.pipe(l.map((e) => ln(e, m))), g = t.mask ? h.pipe(l.map((e) => He(e, o, t.mask.actions, t.mask.seed, s))) : h, { rowCount: _, checksum: v } = yield* Bt("export", o, a, i, (e) => e.rowCount, dn(nn(g, s), t.bundleFile(d), t.compression));
864
+ }), m = un(t.snapshot, o), h = m.length === 0 ? p : p.pipe(l.map((e) => dn(e, m))), g = t.mask ? h.pipe(l.map((e) => Ge(e, o, t.mask.actions, t.mask.seed, s))) : h, { rowCount: _, checksum: v } = yield* Ht("export", o, a, i, (e) => e.rowCount, pn(an(g, s), t.bundleFile(d), t.compression));
851
865
  t.ledger.tables[o] = {
852
866
  rowCount: _,
853
867
  checksum: v
854
- }, yield* J(t.ledgerPath, t.ledger), q(t.onProgress, {
868
+ }, yield* K(t.ledgerPath, t.ledger), G(t.onProgress, {
855
869
  phase: "export",
856
870
  table: o,
857
871
  index: a,
@@ -869,43 +883,43 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
869
883
  });
870
884
  }
871
885
  return r;
872
- }), mn = (e) => ({
886
+ }), gn = (e) => ({
873
887
  _tag: "RawSqlFragment",
874
888
  strings: [e],
875
889
  values: []
876
- }), hn = (t, i, a) => n.tryPromise({
890
+ }), _n = (t, i, a) => n.tryPromise({
877
891
  try: () => t.transactional(async (t) => {
878
- if (t.raw) for (let e of Ce(i)) await t.raw(mn(e));
892
+ if (t.raw) for (let e of Ee(i)) await t.raw(gn(e));
879
893
  let o = await n.runPromiseExit(a(t));
880
894
  if (r.isFailure(o)) throw Error(e.pretty(o.cause));
881
895
  return o.value;
882
896
  }),
883
- catch: (e) => e instanceof G ? e : new G({ reason: `snapshot export failed: ${Y(e)}` })
884
- }), gn = (e) => n.gen(function* () {
885
- let t = e.scope ?? { kind: "all" }, r = vt(e.compression), i = e.chunkSize ?? 1e3, a = e.retryTimes ?? 5, o = s.exponential("50 millis").pipe(s.jittered, s.intersect(s.recurs(a))), c = yield* n.promise(() => import("node:path")), l = (t) => c.join(e.outDir, t);
897
+ catch: (e) => e instanceof H ? e : new H({ reason: `snapshot export failed: ${q(e)}` })
898
+ }), vn = (e) => n.gen(function* () {
899
+ let t = e.scope ?? { kind: "all" }, r = bt(e.compression), i = e.chunkSize ?? 1e3, a = e.retryTimes ?? 5, o = s.exponential("50 millis").pipe(s.jittered, s.intersect(s.recurs(a))), c = yield* n.promise(() => import("node:path")), l = (t) => c.join(e.outDir, t);
886
900
  yield* n.tryPromise({
887
901
  try: async () => {
888
902
  let t = await import("node:fs/promises");
889
- await t.mkdir(l(jt), { recursive: !0 }), e.assets && await t.mkdir(l(Mt), { recursive: !0 });
903
+ await t.mkdir(l(Nt), { recursive: !0 }), e.assets && await t.mkdir(l(Pt), { recursive: !0 });
890
904
  },
891
- catch: (t) => new G({
892
- reason: `mkdir failed: ${Y(t)}`,
905
+ catch: (t) => new H({
906
+ reason: `mkdir failed: ${q(t)}`,
893
907
  path: e.outDir
894
908
  })
895
909
  });
896
- let u = l(Pt), d = yield* Ht(u), f = e.subset ? at(yield* it(e.store, e.snapshot, e.subset), e.snapshot) : yield* st(t, e.snapshot, {
910
+ let u = l(It), d = yield* Wt(u), f = e.subset ? st(yield* ot(e.store, e.snapshot, e.subset), e.snapshot) : yield* lt(t, e.snapshot, {
897
911
  store: e.store,
898
912
  ...e.tenantTables ? { tenantTables: e.tenantTables } : {}
899
- }), p = an(f.tables, e.snapshot), m = e.consistency ?? "live", h, g;
913
+ }), p = sn(f.tables, e.snapshot), m = e.consistency ?? "live", h, g;
900
914
  if (e.masking) {
901
- let t = e.classification ?? Te(e.snapshot), r = ze(p.map((t) => ({
915
+ let t = e.classification ?? Oe(e.snapshot), r = He(p.map((t) => ({
902
916
  name: t,
903
917
  columns: (e.snapshot.tables.find((e) => e.name === t)?.columns ?? []).map((e) => ({
904
918
  name: e.name,
905
919
  type: e.type
906
920
  }))
907
921
  })), t, e.masking);
908
- if (r.unclassified.length > 0 || r.invalid.length > 0) return yield* n.fail(new $e({
922
+ if (r.unclassified.length > 0 || r.invalid.length > 0) return yield* n.fail(new tt({
909
923
  unclassified: r.unclassified,
910
924
  ...r.invalid.length > 0 ? { invalidActions: r.invalid.map((e) => `${e.column}: ${JSON.stringify(e.action)}`) } : {}
911
925
  }));
@@ -931,14 +945,14 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
931
945
  bundleFile: l,
932
946
  ...g ? { mask: g } : {},
933
947
  ...e.onProgress ? { onProgress: e.onProgress } : {}
934
- }, v = m === "snapshot" ? yield* hn(e.store, e.dialect, (e) => pn(e, _)) : yield* pn(e.store, _), y = 0, b = 0;
948
+ }, v = m === "snapshot" ? yield* _n(e.store, e.dialect, (e) => hn(e, _)) : yield* hn(e.store, _), y = 0, b = 0;
935
949
  if (e.assets) {
936
- let t = l(Nt), r = yield* mt({
950
+ let t = l(Ft), r = yield* gt({
937
951
  source: e.assets,
938
- assetsDir: l(Mt),
952
+ assetsDir: l(Pt),
939
953
  progress: {
940
954
  done: (e) => e in d.assets,
941
- mark: (e, r) => (d.assets[e] = !0, fn(t, JSON.stringify(r)).pipe(n.andThen(J(u, d))))
955
+ mark: (e, r) => (d.assets[e] = !0, mn(t, JSON.stringify(r)).pipe(n.andThen(K(u, d))))
942
956
  }
943
957
  });
944
958
  y = r.count, b = r.totalBytes, r.missing.length > 0 && (yield* n.logWarning(`${r.missing.length} of ${r.missing.length + r.count} blob reference(s) point at objects the storage provider does not have; they are NOT in this bundle and no import can bring them back. e.g. ${r.missing.slice(0, 3).map((e) => `'${e}'`).join(", ")}` + (r.missing.length > 3 ? `, and ${r.missing.length - 3} more` : "")));
@@ -948,7 +962,7 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
948
962
  createdAt: e.createdAt ?? (/* @__PURE__ */ new Date()).toISOString(),
949
963
  source: {
950
964
  dialect: e.dialect,
951
- schemaFingerprint: T(e.snapshot)
965
+ schemaFingerprint: w(e.snapshot)
952
966
  },
953
967
  scope: t,
954
968
  consistency: m,
@@ -957,7 +971,7 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
957
971
  assets: y > 0 ? {
958
972
  count: y,
959
973
  totalBytes: b,
960
- index: Nt
974
+ index: Ft
961
975
  } : {
962
976
  count: 0,
963
977
  totalBytes: 0
@@ -966,23 +980,23 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
966
980
  };
967
981
  return yield* n.tryPromise({
968
982
  try: async () => {
969
- await (await import("node:fs/promises")).writeFile(l(kt), Dt(x));
983
+ await (await import("node:fs/promises")).writeFile(l(jt), kt(x));
970
984
  },
971
- catch: (e) => new G({
972
- reason: `manifest write failed: ${Y(e)}`,
973
- path: kt
985
+ catch: (e) => new H({
986
+ reason: `manifest write failed: ${q(e)}`,
987
+ path: jt
974
988
  })
975
989
  }), yield* n.tryPromise({
976
990
  try: async () => {
977
991
  let e = await import("node:fs/promises"), t = await import("node:os");
978
- await e.writeFile(l(At), It(x, { hostname: t.hostname() }));
992
+ await e.writeFile(l(Mt), Rt(x, { hostname: t.hostname() }));
979
993
  },
980
- catch: (e) => new G({
981
- reason: `readme write failed: ${Y(e)}`,
982
- path: At
994
+ catch: (e) => new H({
995
+ reason: `readme write failed: ${q(e)}`,
996
+ path: Mt
983
997
  })
984
998
  }), x;
985
- }), _n = (e, t) => {
999
+ }), yn = (e, t) => {
986
1000
  let n = new Set(t), r = [];
987
1001
  for (let t of e.tables) if (!n.has(t.name)) for (let e of t.columns) {
988
1002
  let i = e.references?.table;
@@ -993,7 +1007,7 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
993
1007
  });
994
1008
  }
995
1009
  return r;
996
- }, vn = (e) => {
1010
+ }, bn = (e) => {
997
1011
  let t = /* @__PURE__ */ new Map();
998
1012
  for (let n of e) t.set(n.from, [...t.get(n.from) ?? [], n]);
999
1013
  let n = [...t.entries()].map(([e, t]) => {
@@ -1001,7 +1015,7 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
1001
1015
  return ` ${e} (${n} row${n === 1 ? "" : "s"}): ${r}`;
1002
1016
  });
1003
1017
  return `replace cannot empty this target: ${t.size} table(s) OUTSIDE the bundle hold rows that reference tables INSIDE it. Emptying the bundle's tables would leave those rows pointing at nothing, and the bundle cannot restore them.\n${n.join("\n")}\nNothing has been deleted. Either re-export with a scope that includes those tables, or use --mode upsert if those rows are meant to survive.`;
1004
- }, yn = (e) => {
1018
+ }, xn = (e) => {
1005
1019
  switch (e) {
1006
1020
  case "id":
1007
1021
  case "text":
@@ -1020,12 +1034,12 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
1020
1034
  case "raw": return "raw";
1021
1035
  default: return "string";
1022
1036
  }
1023
- }, bn = {
1037
+ }, Sn = {
1024
1038
  vector: /* @__PURE__ */ new Set(["postgres"]),
1025
1039
  array: /* @__PURE__ */ new Set(["postgres"]),
1026
1040
  interval: /* @__PURE__ */ new Set(["postgres"])
1027
- }, xn = (e, t, n, r) => {
1028
- let i = yn(n);
1041
+ }, Cn = (e, t, n, r) => {
1042
+ let i = xn(n);
1029
1043
  if (i === "raw") return {
1030
1044
  table: e,
1031
1045
  column: t,
@@ -1033,7 +1047,7 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
1033
1047
  severity: "block",
1034
1048
  reason: `raw() is verbatim source-dialect SQL — it cannot be assumed valid on ${r}`
1035
1049
  };
1036
- let a = bn[i];
1050
+ let a = Sn[i];
1037
1051
  return !a || a.has(r) ? null : i === "array" || i === "interval" ? {
1038
1052
  table: e,
1039
1053
  column: t,
@@ -1047,15 +1061,15 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
1047
1061
  severity: "block",
1048
1062
  reason: `${i} columns require a ${[...a].join("/")} target; ${r} has no compatible column type`
1049
1063
  };
1050
- }, Sn = (e, t, n) => {
1064
+ }, wn = (e, t, n) => {
1051
1065
  if (t === n) return [];
1052
1066
  let r = [];
1053
1067
  for (let t of e) for (let [e, i] of Object.entries(t.columnTypes)) {
1054
- let a = xn(t.name, e, i, n);
1068
+ let a = Cn(t.name, e, i, n);
1055
1069
  a && r.push(a);
1056
1070
  }
1057
1071
  return r;
1058
- }, Cn = (e) => `[${e.severity}] ${e.table}.${e.column} (${e.type}): ${e.reason}`, wn = (e) => {
1072
+ }, Tn = (e) => `[${e.severity}] ${e.table}.${e.column} (${e.type}): ${e.reason}`, En = (e) => {
1059
1073
  let t = e.constraint ?? e.column, n = t === void 0 ? "" : ` ${t}`;
1060
1074
  switch (e.kind) {
1061
1075
  case "foreignKey": return `foreign key${n}: the referenced row does not exist (import it first, or check the bundle's table order)`;
@@ -1064,36 +1078,36 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
1064
1078
  case "notNull": return `not-null constraint${n}: the column requires a value`;
1065
1079
  case "check": return `check constraint${n}: the row does not satisfy it`;
1066
1080
  }
1067
- }, Tn = (e) => {
1081
+ }, Dn = (e) => {
1068
1082
  let t = [e.dbCode, e.dbErrno ?? e.dbNumber].filter((e) => e !== void 0).map(String);
1069
1083
  return t.length > 0 ? t.join("/") : void 0;
1070
- }, En = "Failed to execute statement", Dn = (e) => {
1084
+ }, On = "Failed to execute statement", kn = (e) => {
1071
1085
  let t = (e.split("\n", 1)[0] ?? "").trim();
1072
1086
  for (; t.startsWith("(FiberFailure)");) t = t.slice(14).trim();
1073
- return t === `SqlError: ${En}` ? En : t;
1074
- }, On = (e) => {
1087
+ return t === `SqlError: ${On}` ? On : t;
1088
+ }, An = (e) => {
1075
1089
  let t = String(e?.stack ?? e), n = t.length <= 1200 ? t : `${t.slice(0, 1200)}…`, r = (e, t) => ({
1076
1090
  reason: e.length <= 300 ? e : `${e.slice(0, 300)}…`,
1077
1091
  unclassified: t,
1078
1092
  raw: n
1079
- }), i = v(e), a = m(i), o = Tn(i), s = o === void 0 ? "" : ` [${o}]`;
1080
- if (a !== void 0) return r(`${wn(a)}${s}`, !1);
1081
- let c = typeof i.dbMessage == "string" ? i.dbMessage : void 0, l = e?.message, u = Dn(typeof l == "string" && l.length > 0 ? l : String(e)), d = c !== void 0 && c !== u && !c.startsWith("SqlError:") ? c : u, f = typeof i.dbCauseChain == "string" ? i.dbCauseChain : void 0, p = f !== void 0 && /[←‖]/.test(f) ? ` (via ${f})` : "";
1082
- return r(d === En || d.length === 0 ? `the database refused the write and the driver gave no detail${s}${p}` : `${d}${s}`, d === En || d.length === 0);
1083
- }, kn = (e) => On(e).reason, An = (e) => {
1093
+ }), i = v(e), a = m(i), o = Dn(i), s = o === void 0 ? "" : ` [${o}]`;
1094
+ if (a !== void 0) return r(`${En(a)}${s}`, !1);
1095
+ let c = typeof i.dbMessage == "string" ? i.dbMessage : void 0, l = e?.message, u = kn(typeof l == "string" && l.length > 0 ? l : String(e)), d = c !== void 0 && c !== u && !c.startsWith("SqlError:") ? c : u, f = typeof i.dbCauseChain == "string" ? i.dbCauseChain : void 0, p = f !== void 0 && /[←‖]/.test(f) ? ` (via ${f})` : "";
1096
+ return r(d === On || d.length === 0 ? `the database refused the write and the driver gave no detail${s}${p}` : `${d}${s}`, d === On || d.length === 0);
1097
+ }, jn = (e) => An(e).reason, Mn = (e) => {
1084
1098
  let t = v(e), n = m(t);
1085
1099
  if (n?.kind === "foreignKeyInUse") {
1086
- let e = n.constraint ?? n.column, r = e === void 0 ? "" : ` ${e}`, i = Tn(t);
1100
+ let e = n.constraint ?? n.column, r = e === void 0 ? "" : ` ${e}`, i = Dn(t);
1087
1101
  return `foreign key${r}: rows elsewhere still reference this table${i === void 0 ? "" : ` [${i}]`}`;
1088
1102
  }
1089
- return kn(e);
1090
- }, jn = f, X = (e) => `${jn}${e}`, Mn = (e) => typeof e.run == "function", Nn = (e) => `staging is not available for this run — loading directly into the target instead: ${e}\n The load therefore holds the destructive transaction open for its whole duration, so a
1103
+ return jn(e);
1104
+ }, Nn = f, J = (e) => `${Nn}${e}`, Pn = (e) => typeof e.run == "function", Fn = (e) => `staging is not available for this run — loading directly into the target instead: ${e}\n The load therefore holds the destructive transaction open for its whole duration, so a
1091
1105
  process that dies mid-load depends on the database rolling it back. The rollback capture
1092
- written before the first delete is what covers that case.`, Pn = /^[a-zA-Z_][a-zA-Z0-9_]*$/, Z = (e, t) => {
1093
- if (!Pn.test(e)) throw Error(`refusing to build SQL for the table name ${JSON.stringify(e)}: it is outside the identifier class the framework allows. A name from a bundle manifest reaches this concatenation, so it is checked here rather than assumed to still be what the declaration validated.`);
1106
+ written before the first delete is what covers that case.`, In = /^[a-zA-Z_][a-zA-Z0-9_]*$/, Y = (e, t) => {
1107
+ if (!In.test(e)) throw Error(`refusing to build SQL for the table name ${JSON.stringify(e)}: it is outside the identifier class the framework allows. A name from a bundle manifest reaches this concatenation, so it is checked here rather than assumed to still be what the declaration validated.`);
1094
1108
  return t === "mysql" || t === "mariadb" ? `\`${e}\`` : t === "mssql" ? `[${e}]` : `"${e}"`;
1095
- }, Fn = (e, t) => {
1096
- let n = Z(e, t), r = Z(X(e), t);
1109
+ }, Ln = (e, t) => {
1110
+ let n = Y(e, t), r = Y(J(e), t);
1097
1111
  switch (t) {
1098
1112
  case "postgres": return `CREATE TABLE ${r} (LIKE ${n})`;
1099
1113
  case "mysql":
@@ -1101,20 +1115,20 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
1101
1115
  case "sqlite": return `CREATE TABLE ${r} AS SELECT * FROM ${n} WHERE 0`;
1102
1116
  case "mssql": return `SELECT * INTO ${r} FROM ${n} WHERE 1 = 0`;
1103
1117
  }
1104
- }, In = (e, t) => {
1105
- let n = Z(X(e), t);
1106
- return t === "mssql" ? `IF OBJECT_ID('${X(e)}', 'U') IS NOT NULL DROP TABLE ${n}` : `DROP TABLE IF EXISTS ${n}`;
1107
- }, Ln = (e, t) => {
1118
+ }, Rn = (e, t) => {
1119
+ let n = Y(J(e), t);
1120
+ return t === "mssql" ? `IF OBJECT_ID('${J(e)}', 'U') IS NOT NULL DROP TABLE ${n}` : `DROP TABLE IF EXISTS ${n}`;
1121
+ }, zn = (e, t) => {
1108
1122
  let n = t === "mysql" || t === "mariadb", r = [];
1109
1123
  n && r.push("SET FOREIGN_KEY_CHECKS = 0");
1110
- for (let n of [...e].reverse()) r.push(`DELETE FROM ${Z(n.name, t)}`);
1124
+ for (let n of [...e].reverse()) r.push(`DELETE FROM ${Y(n.name, t)}`);
1111
1125
  for (let n of e) {
1112
1126
  if (n.columns.length === 0) throw Error(`refusing to build a swap for '${n.name}' with no columns: an empty list would have to mean \`SELECT *\`, which is the shape that fails on a generated column.`);
1113
- let e = n.columns.map((e) => Z(e, t)).join(", ");
1114
- r.push(`INSERT INTO ${Z(n.name, t)} (${e}) SELECT ${e} FROM ${Z(X(n.name), t)}`);
1127
+ let e = n.columns.map((e) => Y(e, t)).join(", ");
1128
+ r.push(`INSERT INTO ${Y(n.name, t)} (${e}) SELECT ${e} FROM ${Y(J(n.name), t)}`);
1115
1129
  }
1116
1130
  return n && r.push("SET FOREIGN_KEY_CHECKS = 1"), r;
1117
- }, Rn = (e, t) => {
1131
+ }, Bn = (e, t) => {
1118
1132
  let n = [], r = () => {
1119
1133
  for (let e of n) t.unregisterTable(e);
1120
1134
  };
@@ -1122,7 +1136,7 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
1122
1136
  for (let r of e) {
1123
1137
  let e = t.getTable(r);
1124
1138
  if (e === void 0) continue;
1125
- let i = X(r);
1139
+ let i = J(r);
1126
1140
  t.registerTable({
1127
1141
  ...e,
1128
1142
  tableName: i,
@@ -1136,7 +1150,7 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
1136
1150
  staged: n,
1137
1151
  undo: r
1138
1152
  };
1139
- }, zn = (e, t) => {
1153
+ }, Vn = (e, t) => {
1140
1154
  let n = new Set(t), r = [];
1141
1155
  for (let t of e.tables) {
1142
1156
  if (!n.has(t.name)) continue;
@@ -1153,22 +1167,22 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
1153
1167
  }
1154
1168
  }
1155
1169
  return r;
1156
- }, Bn = (e, t) => {
1157
- let n = Z(X(e.from), t), r = Z(X(e.to), t), i = Z(e.column, t), a = Z(e.toColumn, t);
1158
- return `SELECT ${Z(e.primaryKey, t)} AS pk, ${i} AS value FROM ${n} c WHERE ${i} IS NOT NULL AND NOT EXISTS (SELECT 1 FROM ${r} p WHERE p.${a} = c.${i})`;
1159
- }, Vn = (e) => {
1170
+ }, Hn = (e, t) => {
1171
+ let n = Y(J(e.from), t), r = Y(J(e.to), t), i = Y(e.column, t), a = Y(e.toColumn, t);
1172
+ return `SELECT ${Y(e.primaryKey, t)} AS pk, ${i} AS value FROM ${n} c WHERE ${i} IS NOT NULL AND NOT EXISTS (SELECT 1 FROM ${r} p WHERE p.${a} = c.${i})`;
1173
+ }, Un = (e) => {
1160
1174
  if (e.length === 0) return;
1161
1175
  let t = e.slice(0, 20), n = t.map((e) => ` ${e.table}.${e.primaryKey}: ${e.column} = ${JSON.stringify(e.value)} — no such row in ${e.references}`);
1162
1176
  return `the swap could not run: ${e.length} row(s) in the bundle reference a row the bundle does not carry.\n${n.join("\n")}\n` + (e.length > t.length ? ` … and ${e.length - t.length} more\n` : "") + " The target is UNCHANGED — the swap runs in one transaction and none of it committed.\n Every offending row is listed above rather than only the first, so this can be fixed in one pass.";
1163
- }, Hn = async (e, t) => {
1164
- t.length !== 0 && await e.run(F.SqlClient.pipe(n.flatMap((e) => n.forEach(t, (t) => e.unsafe(t), { discard: !0 }))));
1165
- }, Un = async (e, t, r) => {
1166
- let i = Ln(t, r);
1167
- i.length !== 0 && await e.run(F.SqlClient.pipe(n.flatMap((e) => e.withTransaction(n.forEach(i, (t) => e.unsafe(t), { discard: !0 })))));
1168
- }, Wn = async (e, t, r) => {
1177
+ }, Wn = async (e, t) => {
1178
+ t.length !== 0 && await e.run(N.SqlClient.pipe(n.flatMap((e) => n.forEach(t, (t) => e.unsafe(t), { discard: !0 }))));
1179
+ }, Gn = async (e, t, r) => {
1180
+ let i = zn(t, r);
1181
+ i.length !== 0 && await e.run(N.SqlClient.pipe(n.flatMap((e) => e.withTransaction(n.forEach(i, (t) => e.unsafe(t), { discard: !0 })))));
1182
+ }, Kn = async (e, t, r) => {
1169
1183
  let i = [];
1170
1184
  for (let a of t) {
1171
- let t = await e.run(F.SqlClient.pipe(n.flatMap((e) => e.unsafe(Bn(a, r)))));
1185
+ let t = await e.run(N.SqlClient.pipe(n.flatMap((e) => e.unsafe(Hn(a, r)))));
1172
1186
  for (let e of t) i.push({
1173
1187
  table: a.from,
1174
1188
  primaryKey: String(e.pk ?? ""),
@@ -1178,14 +1192,14 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
1178
1192
  });
1179
1193
  }
1180
1194
  return i;
1181
- }, Gn = (e, t) => {
1195
+ }, qn = (e, t) => {
1182
1196
  let n = new Map(t.map((e, t) => [e, t]));
1183
1197
  return e.filter((e) => {
1184
1198
  if (e.from === e.to) return !1;
1185
1199
  let t = n.get(e.from), r = n.get(e.to);
1186
1200
  return t === void 0 || r === void 0 ? !1 : r > t;
1187
1201
  });
1188
- }, Kn = (e) => e === "mysql" || e === "mariadb", qn = (e) => {
1202
+ }, Jn = (e) => e === "mysql" || e === "mariadb", Yn = (e) => {
1189
1203
  if (e.mode !== "replace") return {
1190
1204
  active: !1,
1191
1205
  tables: [],
@@ -1235,7 +1249,7 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
1235
1249
  tables: [],
1236
1250
  blocker: "every table in the bundle is one that describes a deployment, so there is nothing for a staged swap to move."
1237
1251
  };
1238
- let s = o.map((e) => e.name), c = Kn(t) ? [] : Gn(zn(n, s), s);
1252
+ let s = o.map((e) => e.name), c = Jn(t) ? [] : qn(Vn(n, s), s);
1239
1253
  return c.length > 0 ? {
1240
1254
  active: !1,
1241
1255
  tables: [],
@@ -1244,9 +1258,9 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
1244
1258
  active: !0,
1245
1259
  tables: o
1246
1260
  };
1247
- }, Jn = (e) => n.gen(function* () {
1261
+ }, Xn = (e) => n.gen(function* () {
1248
1262
  if (e.mode !== "replace" || e.dir === void 0 || e.tables.length === 0) return;
1249
- if (e.snapshot === void 0) return yield* n.fail(new G({
1263
+ if (e.snapshot === void 0) return yield* n.fail(new H({
1250
1264
  reason: "rollback capture needs the TARGET's schema, and this run has none.\n `--mode replace` empties the target first, so a run without a capture can leave it\n emptied and unfilled if the process does not survive to roll back. Pass the target\n snapshot, or `--no-rollback` to accept that risk deliberately.",
1251
1265
  path: e.dir
1252
1266
  }));
@@ -1257,14 +1271,14 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
1257
1271
  if (t.tables.length === 0) return;
1258
1272
  e.onWarn?.(`capturing the target's current rows before emptying it → ${e.dir}\n This is what a failed replace is restored FROM. It is written before the first delete,
1259
1273
  so it survives a run whose process does not.`);
1260
- let r = yield* gn({
1274
+ let r = yield* vn({
1261
1275
  store: e.store,
1262
1276
  snapshot: t,
1263
1277
  dialect: e.dialect ?? "unknown",
1264
1278
  outDir: e.dir,
1265
1279
  scope: { kind: "all" },
1266
1280
  compression: "none"
1267
- }).pipe(n.mapError((t) => new G({
1281
+ }).pipe(n.mapError((t) => new H({
1268
1282
  reason: `rollback capture failed, so the import did not start and the target is untouched: ${t.reason ?? String(t)}\n Fix the capture, or re-run with \`--no-rollback\` to proceed without one.`,
1269
1283
  path: e.dir
1270
1284
  })));
@@ -1273,18 +1287,18 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
1273
1287
  rows: r.tables.reduce((e, t) => e + t.rowCount, 0),
1274
1288
  tables: r.tables.length
1275
1289
  };
1276
- }), Yn = (e) => `rollback capture: ${e.rows} row(s) across ${e.tables} table(s) → ${e.dir}\n If this run does not finish, restore with: voltro data import ${e.dir} --mode replace`, Xn = (e, t) => e.tables.find((e) => e.name === t), Zn = (e, t) => new Map((Xn(e, t)?.columns ?? []).map((e) => [e.name, e])), Qn = /__dropped_\d+$/, $n = (e, t) => {
1290
+ }), Zn = (e) => `rollback capture: ${e.rows} row(s) across ${e.tables} table(s) → ${e.dir}\n If this run does not finish, restore with: voltro data import ${e.dir} --mode replace`, Qn = (e, t) => e.tables.find((e) => e.name === t), $n = (e, t) => new Map((Qn(e, t)?.columns ?? []).map((e) => [e.name, e])), er = /__dropped_\d+$/, tr = (e, t) => {
1277
1291
  let n = [];
1278
1292
  for (let r of [...e.tables].sort((e, t) => e.name.localeCompare(t.name))) {
1279
- if (Xn(t, r.name) === void 0) {
1293
+ if (Qn(t, r.name) === void 0) {
1280
1294
  n.push(`table '${r.name}' is in the bundle but MISSING from the target — its rows have nowhere to go`);
1281
1295
  continue;
1282
1296
  }
1283
- let e = Zn(t, r.name), i = new Map(r.columns.map((e) => [e.name, e]));
1297
+ let e = $n(t, r.name), i = new Map(r.columns.map((e) => [e.name, e]));
1284
1298
  for (let [t, a] of i) {
1285
1299
  let i = e.get(t);
1286
1300
  if (i === void 0) {
1287
- n.push(Qn.test(t) ? `${r.name}.${t}: a soft-dropped column, present only in the SOURCE — reclaim it there (voltro db gc-snapshots --before <date>) or re-export without it; the target is not missing anything` : `${r.name}.${t}: in the bundle, MISSING from the target — the value has nowhere to go`);
1301
+ n.push(er.test(t) ? `${r.name}.${t}: a soft-dropped column, present only in the SOURCE — reclaim it there (voltro db gc-snapshots --before <date>) or re-export without it; the target is not missing anything` : `${r.name}.${t}: in the bundle, MISSING from the target — the value has nowhere to go`);
1288
1302
  continue;
1289
1303
  }
1290
1304
  i.type !== a.type && n.push(`${r.name}.${t}: type '${a.type}' (bundle) vs '${i.type}' (target)`);
@@ -1292,22 +1306,22 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
1292
1306
  for (let [t, a] of e) i.has(t) || !a.nullable && !a.hasDefault && n.push(`${r.name}.${t}: the target requires it (NOT NULL, no default) and the bundle carries no value — every row of this table would fail`);
1293
1307
  }
1294
1308
  return n.length > 30 ? [...n.slice(0, 30), `… and ${n.length - 30} more difference(s)`] : n;
1295
- }, er = (e, t, n) => {
1296
- let r = T(t);
1309
+ }, nr = (e, t, n) => {
1310
+ let r = w(t);
1297
1311
  if (r === e || n === void 0) return {
1298
1312
  drifted: !1,
1299
1313
  bundleFingerprint: e,
1300
1314
  targetFingerprint: r,
1301
1315
  diff: []
1302
1316
  };
1303
- let i = $n(n, t);
1317
+ let i = tr(n, t);
1304
1318
  return {
1305
1319
  drifted: i.length > 0,
1306
1320
  bundleFingerprint: e,
1307
1321
  targetFingerprint: r,
1308
1322
  diff: i
1309
1323
  };
1310
- }, tr = 2e3, nr = 2e3, rr = 200, ir = /* @__PURE__ */ new Set([
1324
+ }, rr = 2e3, ir = 2e3, ar = 200, or = /* @__PURE__ */ new Set([
1311
1325
  "BundleError",
1312
1326
  "CodecError",
1313
1327
  "IntegrityError",
@@ -1316,33 +1330,33 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
1316
1330
  "RowsRefusedError",
1317
1331
  "SchemaDriftError",
1318
1332
  "StorageError"
1319
- ]), ar = (t) => {
1333
+ ]), sr = (t) => {
1320
1334
  let n = o.isFiberFailure(t) ? [...e.failures(t[o.FiberFailureCauseId]), ...e.defects(t[o.FiberFailureCauseId])] : [t];
1321
1335
  for (let e of n) {
1322
1336
  let t = e?._tag;
1323
- if (typeof t == "string" && ir.has(t)) return e;
1337
+ if (typeof t == "string" && or.has(t)) return e;
1324
1338
  if (o.isFiberFailure(e)) {
1325
- let t = ar(e);
1339
+ let t = sr(e);
1326
1340
  if (t) return t;
1327
1341
  }
1328
1342
  }
1329
- }, or = (t) => [...e.failures(t)][0] ?? Error(e.pretty(t)), sr = (e) => n.tryPromise({
1343
+ }, cr = (t) => [...e.failures(t)][0] ?? Error(e.pretty(t)), lr = (e) => n.tryPromise({
1330
1344
  try: async () => {
1331
1345
  let t = await import("node:fs/promises"), n = await import("node:path");
1332
- return Ot(await t.readFile(n.join(e, kt), "utf8"));
1346
+ return At(await t.readFile(n.join(e, jt), "utf8"));
1333
1347
  },
1334
- catch: (e) => new G({
1348
+ catch: (e) => new H({
1335
1349
  reason: `manifest read/parse failed: ${String(e?.message ?? e)}`,
1336
- path: kt
1350
+ path: jt
1337
1351
  })
1338
- }), cr = (e) => {
1352
+ }), ur = (e) => {
1339
1353
  let t;
1340
1354
  return n.gen(function* () {
1341
- let i = yield* n.promise(() => import("node:path")), a = yield* sr(e.bundleDir);
1342
- if (a.formatVersion !== 1) return yield* n.fail(new G({ reason: `unsupported bundle formatVersion ${a.formatVersion} (expected 1)` }));
1355
+ let i = yield* n.promise(() => import("node:path")), a = yield* lr(e.bundleDir);
1356
+ if (a.formatVersion !== 1) return yield* n.fail(new H({ reason: `unsupported bundle formatVersion ${a.formatVersion} (expected 1)` }));
1343
1357
  if (e.tables !== void 0) {
1344
1358
  let t = new Set(a.tables.map((e) => e.name)), r = e.tables.filter((e) => !t.has(e));
1345
- if (r.length > 0) return yield* n.fail(new G({ reason: `--tables names ${r.length} table(s) this bundle does not carry: ${r.join(", ")}. The bundle carries: ${[...t].sort().join(", ")}.` }));
1359
+ if (r.length > 0) return yield* n.fail(new H({ reason: `--tables names ${r.length} table(s) this bundle does not carry: ${r.join(", ")}. The bundle carries: ${[...t].sort().join(", ")}.` }));
1346
1360
  }
1347
1361
  let o = e.tables === void 0 ? void 0 : new Set(e.tables), s = o === void 0 ? a : {
1348
1362
  ...a,
@@ -1359,9 +1373,9 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
1359
1373
  unique: !1,
1360
1374
  hasDefault: !1
1361
1375
  }))
1362
- })) }, r = er(s.source.schemaFingerprint, e.targetSnapshot, t);
1376
+ })) }, r = nr(s.source.schemaFingerprint, e.targetSnapshot, t);
1363
1377
  if (r.drifted) {
1364
- if (!e.force) return yield* n.fail(new Qe({
1378
+ if (!e.force) return yield* n.fail(new et({
1365
1379
  bundleFingerprint: r.bundleFingerprint,
1366
1380
  targetFingerprint: r.targetFingerprint,
1367
1381
  diff: r.diff
@@ -1370,15 +1384,15 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
1370
1384
  }
1371
1385
  }
1372
1386
  if (e.targetDialect && e.targetDialect !== s.source.dialect) {
1373
- let t = Sn(s.tables, s.source.dialect, e.targetDialect).filter((e) => e.severity === "block");
1374
- if (t.length > 0 && !e.allowIncompatible) return yield* n.fail(new tt({
1387
+ let t = wn(s.tables, s.source.dialect, e.targetDialect).filter((e) => e.severity === "block");
1388
+ if (t.length > 0 && !e.allowIncompatible) return yield* n.fail(new rt({
1375
1389
  sourceDialect: s.source.dialect,
1376
1390
  targetDialect: e.targetDialect,
1377
- blocking: t.map(Cn)
1391
+ blocking: t.map(Tn)
1378
1392
  }));
1379
1393
  }
1380
- let c = e.verify ?? !0, f = e.mode ?? "upsert", m = e.atomic ?? f === "replace", _ = e.onConflict ?? "skip", v = e.ledgerPath ?? i.join(e.bundleDir, ".import..ledger.json"), b = yield* Ht(v);
1381
- if (f === "replace" && s.scope.kind !== "all") return yield* n.fail(new et({
1394
+ let c = e.verify ?? !0, f = e.mode ?? "upsert", m = e.atomic ?? f === "replace", _ = e.onConflict ?? "skip", v = e.ledgerPath ?? i.join(e.bundleDir, ".import..ledger.json"), b = yield* Wt(v);
1395
+ if (f === "replace" && s.scope.kind !== "all") return yield* n.fail(new nt({
1382
1396
  mode: f,
1383
1397
  reason: `replace refuses a partial bundle (scope='${s.scope.kind}') — truncating would delete rows not in the bundle. Use --mode upsert, or re-export with full scope. To leave specific tables out of a FULL export, use \`--exclude a,b\`: it keeps the scope \`all\` and records what it left out.`
1384
1398
  }));
@@ -1390,8 +1404,8 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
1390
1404
  if (f === "replace") {
1391
1405
  let t = s.tables.map((e) => e.name), r = e.store.incomingForeignKeys ? yield* n.tryPromise({
1392
1406
  try: () => e.store.incomingForeignKeys(t),
1393
- catch: (e) => new G({ reason: `foreign-key pre-flight failed: ${An(e)}` })
1394
- }) : e.targetSnapshot === void 0 ? [] : _n(e.targetSnapshot, t), i = [], a = /* @__PURE__ */ new Map();
1407
+ catch: (e) => new H({ reason: `foreign-key pre-flight failed: ${Mn(e)}` })
1408
+ }) : e.targetSnapshot === void 0 ? [] : yn(e.targetSnapshot, t), i = [], a = /* @__PURE__ */ new Map();
1395
1409
  for (let t of r) {
1396
1410
  if (!a.has(t.from)) {
1397
1411
  let r = yield* n.tryPromise({
@@ -1403,7 +1417,7 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
1403
1417
  skip: void 0,
1404
1418
  projection: []
1405
1419
  }),
1406
- catch: () => new G({ reason: `unreadable: ${t.from}` })
1420
+ catch: () => new H({ reason: `unreadable: ${t.from}` })
1407
1421
  }).pipe(n.map((e) => e.length), n.orElseSucceed(() => 0));
1408
1422
  a.set(t.from, r);
1409
1423
  }
@@ -1413,9 +1427,9 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
1413
1427
  rowCount: r
1414
1428
  });
1415
1429
  }
1416
- if (i.length > 0) return yield* n.fail(new et({
1430
+ if (i.length > 0) return yield* n.fail(new nt({
1417
1431
  mode: f,
1418
- reason: vn(i)
1432
+ reason: bn(i)
1419
1433
  }));
1420
1434
  }
1421
1435
  if (e.dryRun === !0) return e.traceId !== void 0 && (yield* n.promise(() => e.store.update(u, e.traceId, {
@@ -1436,27 +1450,35 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
1436
1450
  let e = t.columns.filter((e) => e.generatedAs !== void 0).map((e) => e.name);
1437
1451
  e.length > 0 && S.set(t.name, e);
1438
1452
  }
1439
- let w = (e, t) => {
1453
+ let C = (e, t) => {
1440
1454
  let n = S.get(e);
1441
1455
  if (n === void 0) return t;
1442
1456
  let r;
1443
1457
  for (let e of n) e in t && (r ??= { ...t }, delete r[e]);
1444
1458
  return r ?? t;
1445
- }, T = (e, t, n, r = !1) => {
1446
- let i = O ? X(t.name) : t.name, a = t.primaryKey, o = w(t.name, n);
1459
+ }, w = (e, t, n, r = !1) => {
1460
+ let i = O ? J(t.name) : t.name, a = t.primaryKey, o = oe(t.name, C(t.name, n), t.columnTypes);
1447
1461
  return f === "append" ? _ === "fail" ? e.insert(i, o) : e.insertIgnore(i, o, { conflictColumns: [a] }) : f === "replace" ? r ? e.upsert(i, o, { conflictColumns: [a] }) : e.insert(i, o) : e.upsert(i, o, { conflictColumns: [a] });
1448
- }, ie = (e, t) => e.savepoint ? e.savepoint(t) : t(), ae = 0, oe = (t, n, r) => {
1449
- r.unclassified && (ae++, !(ae > 3) && e.onWarn?.(`row refused with no driver detail — table '${t.name}', row '${String(n.id ?? "?")}'. The full rendering follows so the LAYER that refused is on the record; it is logged, never returned. ${r.raw}` + (ae === 3 ? " (further unclassified refusals are counted, not logged)" : "")));
1450
- }, se = (e, t, r = !0) => n.tryPromise({
1462
+ }, ae = e.targetDialect !== void 0 && e.targetDialect !== "memory", oe = (e, t, n) => {
1463
+ if (!ae || n === void 0 || y(e) !== void 0) return t;
1464
+ let r = null;
1465
+ for (let [e, i] of Object.entries(n)) {
1466
+ let n = t[e];
1467
+ i === "json" && n != null && (r === null && (r = { ...t }), r[e] = JSON.stringify(n));
1468
+ }
1469
+ return r ?? t;
1470
+ }, T = (e, t) => e.savepoint ? e.savepoint(t) : t(), se = 0, ce = (t, n, r) => {
1471
+ r.unclassified && (se++, !(se > 3) && e.onWarn?.(`row refused with no driver detail — table '${t.name}', row '${String(n.id ?? "?")}'. The full rendering follows so the LAYER that refused is on the record; it is logged, never returned. ${r.raw}` + (se === 3 ? " (further unclassified refusals are counted, not logged)" : "")));
1472
+ }, le = (e, t, r = !0) => n.tryPromise({
1451
1473
  try: e,
1452
- catch: (e) => On(e)
1453
- }).pipe(n.map(() => !0), n.catchAll((e) => n.sync(() => (r && (t.reason = e.reason, oe(t.entry, t.row, e)), !1)))), ce = (e) => {
1474
+ catch: (e) => An(e)
1475
+ }).pipe(n.map(() => !0), n.catchAll((e) => n.sync(() => (r && (t.reason = e.reason, ce(t.entry, t.row, e)), !1)))), ue = (e) => {
1454
1476
  let t = Object.entries(e.entry.columnTypes).filter(([t, n]) => n === "reference" && e.row[t] !== null && e.row[t] !== void 0).map(([e]) => e);
1455
1477
  if (t.length !== 0) return {
1456
1478
  ...e.row,
1457
1479
  ...Object.fromEntries(t.map((e) => [e, null]))
1458
1480
  };
1459
- }, le = (e) => {
1481
+ }, de = (e) => {
1460
1482
  let t = new Set(e.map((e) => String(e.row[e.entry.primaryKey]))), n = (e) => Object.entries(e.entry.columnTypes).some(([n, r]) => {
1461
1483
  if (r !== "reference") return !1;
1462
1484
  let i = e.row[n];
@@ -1474,7 +1496,7 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
1474
1496
  };
1475
1497
  t.refused++, e.derived || t.primary++, a.set(e.table, t);
1476
1498
  }
1477
- return new Ze({
1499
+ return new $e({
1478
1500
  rows: i.slice(0, 20),
1479
1501
  primaryCount: r.filter((e) => !e.derived).length,
1480
1502
  totalCount: e.length,
@@ -1484,62 +1506,62 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
1484
1506
  primary: t.primary
1485
1507
  })).sort((e, t) => t.refused - e.refused || e.table.localeCompare(t.table)).slice(0, 100)
1486
1508
  });
1487
- }, ue = (e, t) => n.gen(function* () {
1509
+ }, pe = (e, t) => n.gen(function* () {
1488
1510
  let r = t, i = [], a = !0;
1489
1511
  for (; r.length > 0 && a;) {
1490
1512
  a = !1;
1491
1513
  let t = [];
1492
- for (let n of r) (yield* se(() => ie(e, () => T(e, n.entry, n.row, !0)), n)) ? a = !0 : t.push(n);
1514
+ for (let n of r) (yield* le(() => T(e, () => w(e, n.entry, n.row, !0)), n)) ? a = !0 : t.push(n);
1493
1515
  if (!a && t.length > 0) for (let n = t.length - 1; n >= 0; n--) {
1494
- let r = t[n], o = ce(r);
1495
- o !== void 0 && (yield* se(() => ie(e, () => T(e, r.entry, o, !0)), r, !1)) && (i.push(r), t.splice(n, 1), a = !0);
1516
+ let r = t[n], o = ue(r);
1517
+ o !== void 0 && (yield* le(() => T(e, () => w(e, r.entry, o, !0)), r, !1)) && (i.push(r), t.splice(n, 1), a = !0);
1496
1518
  }
1497
1519
  r = t;
1498
1520
  }
1499
- for (let t of i) (yield* se(() => ie(e, () => e.upsert(t.entry.name, t.row, { conflictColumns: [t.entry.primaryKey] })), t)) || (r = [...r, t]);
1500
- if (r.length > 0) return yield* n.fail(le(r));
1521
+ for (let t of i) (yield* le(() => T(e, () => e.upsert(t.entry.name, oe(t.entry.name, t.row, t.entry.columnTypes), { conflictColumns: [t.entry.primaryKey] })), t)) || (r = [...r, t]);
1522
+ if (r.length > 0) return yield* n.fail(de(r));
1501
1523
  }), E = (() => {
1502
1524
  let t = e.targetDialect;
1503
1525
  return t === "postgres" || t === "mysql" || t === "mariadb" || t === "sqlite" || t === "mssql" ? t : void 0;
1504
- })(), D = qn({
1526
+ })(), D = Yn({
1505
1527
  mode: f,
1506
1528
  ...e.targetDialect === void 0 ? {} : { targetDialect: e.targetDialect },
1507
1529
  ...e.targetSnapshot === void 0 ? {} : { targetSnapshot: e.targetSnapshot },
1508
1530
  bundleTables: s.tables.map((e) => e.name),
1509
- isSkipped: W,
1510
- canRunSql: Mn(e.store)
1511
- }), fe = D.tables, pe = s.tables.filter((e) => !W(e.name) && C(e.name)).map((e) => e.name), O = D.active, k = !1, A = 0, j = 0, he, M, N = 0, P = 0, ge = (t, r) => n.gen(function* () {
1531
+ isSkipped: V,
1532
+ canRunSql: Pn(e.store)
1533
+ }), me = D.tables, he = s.tables.filter((e) => !V(e.name) && ee(e.name)).map((e) => e.name), O = D.active, _e = !1, k = 0, A = 0, j, M, ve = 0, N = 0, P = (t, r) => n.gen(function* () {
1512
1534
  if (f === "replace" && !O && !(r && b.truncated)) {
1513
1535
  e.recordInterruption === !0 && (yield* n.tryPromise({
1514
1536
  try: () => t.insert(d, {
1515
- id: h("repl", F),
1516
- startedAt: I,
1537
+ id: h("repl", ye),
1538
+ startedAt: be,
1517
1539
  tables: String(s.tables.length),
1518
- capture: L?.dir ?? null,
1540
+ capture: F?.dir ?? null,
1519
1541
  via: e.via ?? "direct"
1520
1542
  }),
1521
- catch: (e) => new G({ reason: `could not record that this replace started: ${String(e?.message ?? e)}\n The marker is what makes an interrupted run visible instead of silent, so the run does
1543
+ catch: (e) => new H({ reason: `could not record that this replace started: ${String(e?.message ?? e)}\n The marker is what makes an interrupted run visible instead of silent, so the run does
1522
1544
  not proceed without it.` })
1523
1545
  }));
1524
- let i = [...s.tables].reverse().map((e) => e.name).filter((e) => !W(e)), a = !r, o = t.emptyTables ? () => t.emptyTables(i) : a ? async () => {
1546
+ let i = [...s.tables].reverse().map((e) => e.name).filter((e) => !V(e)), a = !r, o = t.emptyTables ? () => t.emptyTables(i) : a ? async () => {
1525
1547
  for (let e of [...s.tables].reverse()) await t.deleteMany(e.name, { where: x(e.primaryKey) });
1526
1548
  } : () => t.transactional(async (e) => {
1527
1549
  for (let t of [...s.tables].reverse()) await e.deleteMany(t.name, { where: x(t.primaryKey) });
1528
1550
  });
1529
1551
  yield* n.tryPromise({
1530
1552
  try: o,
1531
- catch: (e) => new G({ reason: `emptying the target for --mode replace failed (nothing was deleted): ${An(e)}` })
1532
- }), r && (b.truncated = !0, yield* J(v, b));
1553
+ catch: (e) => new H({ reason: `emptying the target for --mode replace failed (nothing was deleted): ${Mn(e)}` })
1554
+ }), r && (b.truncated = !0, yield* K(v, b));
1533
1555
  }
1534
1556
  let a = [], o = [], u = [], p = [], g = s.tables.length;
1535
1557
  for (let d = 0; d < s.tables.length; d++) {
1536
1558
  let h = s.tables[d];
1537
- if (W(h.name)) {
1559
+ if (V(h.name)) {
1538
1560
  p.push(h.name);
1539
1561
  continue;
1540
1562
  }
1541
1563
  if (r && h.name in b.tables) {
1542
- u.push(h.name), P++, N += b.tables[h.name].rowCount, q(e.onProgress, {
1564
+ u.push(h.name), N++, ve += b.tables[h.name].rowCount, G(e.onProgress, {
1543
1565
  phase: "import",
1544
1566
  table: h.name,
1545
1567
  index: d,
@@ -1551,7 +1573,7 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
1551
1573
  continue;
1552
1574
  }
1553
1575
  let _ = i.join(e.bundleDir, h.file);
1554
- q(e.onProgress, {
1576
+ G(e.onProgress, {
1555
1577
  phase: "import",
1556
1578
  table: h.name,
1557
1579
  index: d,
@@ -1561,22 +1583,22 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
1561
1583
  total: h.rowCount
1562
1584
  });
1563
1585
  let y = a.length, x = n.gen(function* () {
1564
- let { createHash: r } = yield* n.promise(() => import("node:crypto")), i = r("sha256"), o = 0, c = me("bundle", () => de(_).pipe(xt(s.compression))).pipe(l.tap((e) => n.sync(() => i.update(e)))), u = async (e) => {
1586
+ let { createHash: r } = yield* n.promise(() => import("node:crypto")), i = r("sha256"), o = 0, c = ge("bundle", () => fe(_).pipe(Ct(s.compression))).pipe(l.tap((e) => n.sync(() => i.update(e)))), u = async (e) => {
1565
1587
  let n = {
1566
1588
  entry: h,
1567
1589
  row: e,
1568
1590
  reason: ""
1569
1591
  };
1570
1592
  try {
1571
- await ie(t, () => T(t, h, e));
1593
+ await T(t, () => w(t, h, e));
1572
1594
  } catch (t) {
1573
- let r = On(t);
1574
- n.reason = r.reason, oe(h, e, r), a.push(n);
1595
+ let r = An(t);
1596
+ n.reason = r.reason, ce(h, e, r), a.push(n);
1575
1597
  }
1576
1598
  }, d = yield* n.promise(async () => {
1577
1599
  let n = e.copyLoader;
1578
1600
  if (!n || n.dialect !== "postgres") return !1;
1579
- if (m) return k || (k = !0, e.onWarn?.("bulk COPY is off for this run: it needs its own connection and this import runs in ONE transaction (the default for --mode replace, so a failure mid-load cannot leave the target emptied and unfilled). Pass --no-atomic to trade that guarantee back for COPY.")), !1;
1601
+ if (m) return _e || (_e = !0, e.onWarn?.("bulk COPY is off for this run: it needs its own connection and this import runs in ONE transaction (the default for --mode replace, so a failure mid-load cannot leave the target emptied and unfilled). Pass --no-atomic to trade that guarantee back for COPY.")), !1;
1580
1602
  if (f === "replace") return !0;
1581
1603
  if (f !== "upsert") return !1;
1582
1604
  try {
@@ -1606,46 +1628,46 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
1606
1628
  d = !1, e.onWarn?.(`bulk COPY into ${h.name} failed (${String(n?.message ?? n)}); falling back to per-row writes for this table`);
1607
1629
  for (let e of t) await u(e);
1608
1630
  }
1609
- }, b = Math.max(1, e.savepointBatchSize ?? 200), x = typeof t.savepoint == "function", S = [], C = async () => {
1631
+ }, b = Math.max(1, e.savepointBatchSize ?? 200), x = typeof t.savepoint == "function", S = [], ee = async () => {
1610
1632
  if (S.length === 0) return;
1611
1633
  let e = S;
1612
1634
  S = [];
1613
1635
  try {
1614
1636
  await t.savepoint(async () => {
1615
- for (let n of e) await T(t, h, n);
1637
+ for (let n of e) await w(t, h, n);
1616
1638
  });
1617
1639
  } catch {
1618
1640
  for (let t of e) await u(t);
1619
1641
  }
1620
1642
  };
1621
- return yield* l.runForEach(rn(c, h.name, h.columnTypes), (e) => n.promise(async () => {
1643
+ return yield* l.runForEach(on(c, h.name, h.columnTypes), (e) => n.promise(async () => {
1622
1644
  if (o++, M?.(), d) {
1623
1645
  v.push(e), v.length >= g && await y();
1624
1646
  return;
1625
1647
  }
1626
1648
  if (x) {
1627
- S.push(e), S.length >= b && await C();
1649
+ S.push(e), S.length >= b && await ee();
1628
1650
  return;
1629
1651
  }
1630
1652
  await u(e);
1631
- })), yield* n.promise(C), yield* n.promise(y), {
1653
+ })), yield* n.promise(ee), yield* n.promise(y), {
1632
1654
  rowCount: o,
1633
1655
  checksum: i.digest("hex")
1634
1656
  };
1635
- }), { rowCount: S, checksum: C } = yield* Bt("import", h.name, d, g, (e) => e.rowCount, x);
1657
+ }), { rowCount: S, checksum: ee } = yield* Ht("import", h.name, d, g, (e) => e.rowCount, x);
1636
1658
  if (c) {
1637
- if (C !== h.checksum) return yield* n.fail(new Je({
1659
+ if (ee !== h.checksum) return yield* n.fail(new Ze({
1638
1660
  what: `table ${h.name} checksum`,
1639
1661
  expected: h.checksum,
1640
- actual: C
1662
+ actual: ee
1641
1663
  }));
1642
- if (S !== h.rowCount) return yield* n.fail(new Je({
1664
+ if (S !== h.rowCount) return yield* n.fail(new Ze({
1643
1665
  what: `table ${h.name} rowCount`,
1644
1666
  expected: String(h.rowCount),
1645
1667
  actual: String(S)
1646
1668
  }));
1647
1669
  }
1648
- q(e.onProgress, {
1670
+ G(e.onProgress, {
1649
1671
  phase: "import",
1650
1672
  table: h.name,
1651
1673
  index: d,
@@ -1653,18 +1675,18 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
1653
1675
  event: "done",
1654
1676
  rowsDone: S,
1655
1677
  total: h.rowCount
1656
- }), j++, A += S, he?.(), M?.(), r && (a.length > y ? o.push({
1678
+ }), A++, k += S, j?.(), M?.(), r && (a.length > y ? o.push({
1657
1679
  name: h.name,
1658
1680
  rowCount: S
1659
1681
  }) : (b.tables[h.name] = {
1660
1682
  rowCount: S,
1661
1683
  checksum: h.checksum
1662
- }, yield* J(v, b)));
1684
+ }, yield* K(v, b)));
1663
1685
  }
1664
- if (a.length > 0 && (yield* ue(t, a)), f === "replace" && (yield* n.promise(() => t.deleteMany(d, { where: {
1686
+ if (a.length > 0 && (yield* pe(t, a)), f === "replace" && (yield* n.promise(() => t.deleteMany(d, { where: {
1665
1687
  column: "startedAt",
1666
1688
  op: "lte",
1667
- value: I
1689
+ value: be
1668
1690
  } }).then(() => void 0, () => void 0))), r && o.length > 0) {
1669
1691
  for (let e of o) {
1670
1692
  let t = s.tables.find((t) => t.name === e.name);
@@ -1673,35 +1695,35 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
1673
1695
  checksum: t.checksum
1674
1696
  };
1675
1697
  }
1676
- yield* J(v, b);
1698
+ yield* K(v, b);
1677
1699
  }
1678
1700
  {
1679
- let t = Ke(p, "skipped");
1701
+ let t = Ye(p, "skipped");
1680
1702
  t !== void 0 && e.onWarn?.(t);
1681
1703
  }
1682
1704
  if (u.length > 0) {
1683
1705
  let t = u.length === s.tables.length;
1684
1706
  e.onWarn?.(`resume: ${u.length} of ${s.tables.length} table(s) were already applied by an earlier run of THIS bundle directory, so this run wrote NO rows for them${t ? " — that is every table in the bundle, so nothing was written at all" : ""}. Tables: ${u.join(", ")}. Delete ${v} to force a full re-import.`);
1685
1707
  }
1686
- }), F = `${Date.now().toString(36)}${Math.random().toString(36).slice(2, 8)}`, I = /* @__PURE__ */ new Date(), L = yield* Jn({
1708
+ }), ye = `${Date.now().toString(36)}${Math.random().toString(36).slice(2, 8)}`, be = /* @__PURE__ */ new Date(), F = yield* Xn({
1687
1709
  store: e.store,
1688
1710
  mode: f,
1689
1711
  dir: e.rollbackDir,
1690
1712
  snapshot: e.targetSnapshot,
1691
1713
  dialect: e.targetDialect,
1692
- tables: s.tables.map((e) => e.name).filter((e) => !W(e)),
1714
+ tables: s.tables.map((e) => e.name).filter((e) => !V(e)),
1693
1715
  onWarn: e.onWarn
1694
1716
  });
1695
- L !== void 0 && (e.onRollbackCaptured !== void 0 && (yield* n.tryPromise({
1696
- try: () => e.onRollbackCaptured(L),
1697
- catch: (e) => new G({
1717
+ F !== void 0 && (e.onRollbackCaptured !== void 0 && (yield* n.tryPromise({
1718
+ try: () => e.onRollbackCaptured(F),
1719
+ catch: (e) => new H({
1698
1720
  reason: `the rollback capture could not be stored durably, so the import did not start and the target is untouched: ${String(e?.message ?? e)}\n The capture only helps if it outlives this process — that is the failure it exists for.`,
1699
- path: L.dir
1721
+ path: F.dir
1700
1722
  })
1701
- })), e.onWarn?.(Yn(L)));
1702
- let _e = (e) => f === "replace" ? te(e) : e(), R = (e) => f === "replace" ? ne(e) : e, z = e.traceId ?? h("dimp", `${Date.now()}-${s.source.schemaFingerprint ?? ""}`), ve = e.traceId !== void 0, B = (e.targetSnapshot?.tables.some((e) => e.name === u) ?? !1) || y(u) !== void 0;
1703
- B && g(p), B && e.traceId === void 0 && (yield* n.promise(() => e.store.insert(u, {
1704
- id: z,
1723
+ })), e.onWarn?.(Zn(F)));
1724
+ let xe = (e) => f === "replace" ? ne(e) : e(), Se = (e) => f === "replace" ? re(e) : e, I = e.traceId ?? h("dimp", `${Date.now()}-${s.source.schemaFingerprint ?? ""}`), L = e.traceId !== void 0, Ce = (e.targetSnapshot?.tables.some((e) => e.name === u) ?? !1) || y(u) !== void 0;
1725
+ Ce && g(p), Ce && e.traceId === void 0 && (yield* n.promise(() => e.store.insert(u, {
1726
+ id: I,
1705
1727
  mode: f,
1706
1728
  via: e.via ?? "direct",
1707
1729
  direction: "import",
@@ -1711,45 +1733,45 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
1711
1733
  rowsWritten: 0,
1712
1734
  staged: f === "replace" ? O : null
1713
1735
  }).then(() => {
1714
- ve = !0;
1736
+ L = !0;
1715
1737
  }, (t) => {
1716
1738
  e.onWarn?.(`the import trace could not be written (${String(t?.message ?? t)}).\n The import continues — this is a record of what happened, not a safety check. Run
1717
1739
  \`voltro db apply\` so the next one is recorded.`);
1718
- }))), e.traceId !== void 0 && B && (yield* n.promise(() => e.store.update(u, z, {
1740
+ }))), e.traceId !== void 0 && Ce && (yield* n.promise(() => e.store.update(u, I, {
1719
1741
  staged: f === "replace" ? O : null,
1720
1742
  sourceFingerprint: s.source.schemaFingerprint ?? null
1721
1743
  }).then(() => void 0, () => void 0)));
1722
- let ye = 0, be = !1;
1723
- he = () => {
1724
- if (!ve || be) return;
1744
+ let we = 0, Te = !1;
1745
+ j = () => {
1746
+ if (!L || Te) return;
1725
1747
  let t = Date.now();
1726
- t - ye < tr || (ye = t, e.store.update(u, z, {
1727
- tablesWritten: j,
1728
- rowsWritten: A
1748
+ t - we < rr || (we = t, e.store.update(u, I, {
1749
+ tablesWritten: A,
1750
+ rowsWritten: k
1729
1751
  }).then(() => void 0, () => {
1730
- be = !0;
1752
+ Te = !0;
1731
1753
  }));
1732
1754
  };
1733
- let xe = (t) => ve ? e.store.update(u, z, {
1755
+ let Ee = (t) => L ? e.store.update(u, I, {
1734
1756
  finishedAt: t === null ? /* @__PURE__ */ new Date() : null,
1735
- tablesWritten: j,
1736
- rowsWritten: A,
1757
+ tablesWritten: A,
1758
+ rowsWritten: k,
1737
1759
  failure: t
1738
1760
  }).then(() => void 0, () => void 0) : Promise.resolve();
1739
- if (t = (e) => xe(e), f === "replace" && !O && D.blocker !== void 0 && e.onWarn?.(Nn(D.blocker)), f === "replace" && pe.length > 0 && e.onWarn?.(`write recorders are SUSPENDED for this replace (${pe.length} table(s) have one).\n A replace sets a state rather than changing rows, so a per-row history entry would describe
1761
+ if (t = (e) => Ee(e), f === "replace" && !O && D.blocker !== void 0 && e.onWarn?.(Fn(D.blocker)), f === "replace" && he.length > 0 && e.onWarn?.(`write recorders are SUSPENDED for this replace (${he.length} table(s) have one).\n A replace sets a state rather than changing rows, so a per-row history entry would describe
1740
1762
  something that did not happen — and this path already writes through the raw store, without
1741
1763
  tenant scoping or \`audit()\` stamping, for the same reason.`), O) {
1742
- e.onWarn?.(`staging ${fe.length} table(s) before the swap — the target keeps its rows until the load stands.\n The destructive step is one server-side transaction at the end, not the whole load.`);
1743
- let t = e.store, r = fe.map((e) => e.name), i = h("repl", `staging-${F}`), a = !1;
1764
+ e.onWarn?.(`staging ${me.length} table(s) before the swap — the target keeps its rows until the load stands.\n The destructive step is one server-side transaction at the end, not the whole load.`);
1765
+ let t = e.store, r = me.map((e) => e.name), i = h("repl", `staging-${ye}`), a = !1;
1744
1766
  if (e.recordInterruption === !0) {
1745
1767
  yield* n.promise(() => e.store.insert(d, {
1746
1768
  id: i,
1747
- startedAt: I,
1769
+ startedAt: be,
1748
1770
  kind: "staging",
1749
- tables: String(fe.length),
1750
- capture: L?.dir ?? null,
1771
+ tables: String(me.length),
1772
+ capture: F?.dir ?? null,
1751
1773
  via: e.via ?? "direct",
1752
- staging: r.map(X).join(","),
1774
+ staging: r.map(J).join(","),
1753
1775
  heartbeatAt: /* @__PURE__ */ new Date(),
1754
1776
  resumable: !m
1755
1777
  }).then(() => {
@@ -1763,76 +1785,76 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
1763
1785
  M = () => {
1764
1786
  if (!a) return;
1765
1787
  let n = Date.now();
1766
- n - t < nr || (t = n, e.store.update(d, i, { heartbeatAt: /* @__PURE__ */ new Date() }).then(() => void 0, () => void 0));
1788
+ n - t < ir || (t = n, e.store.update(d, i, { heartbeatAt: /* @__PURE__ */ new Date() }).then(() => void 0, () => void 0));
1767
1789
  };
1768
1790
  }
1769
- let o = () => a ? e.store.delete(d, i).then(() => void 0, () => void 0) : Promise.resolve(), s = Rn(r, {
1791
+ let o = () => a ? e.store.delete(d, i).then(() => void 0, () => void 0) : Promise.resolve(), s = Bn(r, {
1770
1792
  getTable: (e) => y(e),
1771
1793
  registerTable: (e) => {
1772
- ee(e);
1794
+ te(e);
1773
1795
  },
1774
- unregisterTable: re
1796
+ unregisterTable: ie
1775
1797
  }), c = !1;
1776
1798
  try {
1777
- let i = m ? r : r.filter((e) => !Ut(b, e));
1799
+ let i = m ? r : r.filter((e) => !Gt(b, e));
1778
1800
  yield* n.tryPromise({
1779
1801
  try: async () => {
1780
- await Hn(t, i.map((e) => In(e, E))), await Hn(t, i.map((e) => Fn(e, E)));
1802
+ await Wn(t, i.map((e) => Rn(e, E))), await Wn(t, i.map((e) => Ln(e, E)));
1781
1803
  },
1782
- catch: (e) => new G({ reason: `could not prepare the staging tables, so the import did not start and the target is untouched: ${String(e?.message ?? e)}` })
1783
- }), yield* R(ge(e.store, !m)), !m && b.truncated === !0 ? c = !0 : yield* n.tryPromise({
1784
- try: () => Un(t, fe, E).then(() => {
1804
+ catch: (e) => new H({ reason: `could not prepare the staging tables, so the import did not start and the target is untouched: ${String(e?.message ?? e)}` })
1805
+ }), yield* Se(P(e.store, !m)), !m && b.truncated === !0 ? c = !0 : yield* n.tryPromise({
1806
+ try: () => Gn(t, me, E).then(() => {
1785
1807
  c = !0;
1786
1808
  }),
1787
- catch: (e) => new G({ reason: String(e?.message ?? e) })
1809
+ catch: (e) => new H({ reason: String(e?.message ?? e) })
1788
1810
  }).pipe(n.catchAll((i) => n.gen(function* () {
1789
- let a = Vn(yield* n.promise(() => Wn(t, zn(e.targetSnapshot, r), E).then((e) => e, () => [])));
1790
- return yield* n.fail(new G({ reason: a ?? `the swap failed and the target is UNCHANGED: ${i.reason}` }));
1791
- }))), !m && c && b.truncated !== !0 && (b.truncated = !0, yield* J(v, b));
1811
+ let a = Un(yield* n.promise(() => Kn(t, Vn(e.targetSnapshot, r), E).then((e) => e, () => [])));
1812
+ return yield* n.fail(new H({ reason: a ?? `the swap failed and the target is UNCHANGED: ${i.reason}` }));
1813
+ }))), !m && c && b.truncated !== !0 && (b.truncated = !0, yield* K(v, b));
1792
1814
  } finally {
1793
- s.undo(), c || m ? (M = void 0, yield* n.promise(() => Hn(t, r.map((e) => In(e, E))).then(() => void 0, () => void 0)), yield* n.promise(o)) : e.onWarn?.("the staged rows are KEPT so a re-run can continue from them rather than reload.\n If you are not going to re-run this bundle, drop them: voltro data clear-staging --yes");
1815
+ s.undo(), c || m ? (M = void 0, yield* n.promise(() => Wn(t, r.map((e) => Rn(e, E))).then(() => void 0, () => void 0)), yield* n.promise(o)) : e.onWarn?.("the staged rows are KEPT so a re-run can continue from them rather than reload.\n If you are not going to re-run this bundle, drop them: voltro data clear-staging --yes");
1794
1816
  }
1795
1817
  } else m ? yield* n.tryPromise({
1796
1818
  try: () => e.store.transactional(async (e) => {
1797
- let t = await _e(() => n.runPromiseExit(ge(e, !1)));
1798
- if (r.isFailure(t)) throw or(t.cause);
1819
+ let t = await xe(() => n.runPromiseExit(P(e, !1)));
1820
+ if (r.isFailure(t)) throw cr(t.cause);
1799
1821
  }),
1800
- catch: (e) => ar(e) ?? new G({ reason: `atomic import failed (rolled back): ${String(e?.message ?? e)}` })
1801
- }) : yield* R(ge(e.store, !0));
1822
+ catch: (e) => sr(e) ?? new H({ reason: `atomic import failed (rolled back): ${String(e?.message ?? e)}` })
1823
+ }) : yield* Se(P(e.store, !0));
1802
1824
  if (e.assets && s.assets.index && !e.assetsAlreadyRestored) {
1803
1825
  let t = e.assets;
1804
- yield* gt({
1826
+ yield* vt({
1805
1827
  sink: t,
1806
- assetsDir: i.join(e.bundleDir, Mt),
1828
+ assetsDir: i.join(e.bundleDir, Pt),
1807
1829
  indexPath: i.join(e.bundleDir, s.assets.index ?? "assets/index.ndjson"),
1808
1830
  progress: {
1809
1831
  done: (e) => e in b.assets,
1810
- mark: (e) => (b.assets[e] = !0, J(v, b))
1832
+ mark: (e) => (b.assets[e] = !0, K(v, b))
1811
1833
  }
1812
1834
  });
1813
1835
  }
1814
- return yield* n.promise(() => xe(null)), {
1836
+ return yield* n.promise(() => Ee(null)), {
1815
1837
  manifest: s,
1816
- tablesWritten: j,
1817
- rowsWritten: A,
1818
- tablesSkipped: P,
1819
- rowsSkipped: N,
1820
- fullyResumed: j === 0 && P > 0,
1821
- ...L === void 0 ? {} : { rollback: L }
1838
+ tablesWritten: A,
1839
+ rowsWritten: k,
1840
+ tablesSkipped: N,
1841
+ rowsSkipped: ve,
1842
+ fullyResumed: A === 0 && N > 0,
1843
+ ...F === void 0 ? {} : { rollback: F }
1822
1844
  };
1823
1845
  }).pipe(n.tapError((e) => n.promise(() => t?.(e?.reason ?? e?._tag ?? "the import did not finish") ?? Promise.resolve())));
1824
- }, lr = (e) => e, ur = (e) => {
1846
+ }, dr = (e) => e, fr = (e) => {
1825
1847
  if (e.allowLive || e.liveInstance === null || e.sameTarget === "different") return { refuse: !1 };
1826
1848
  let t = e.targetLabel === void 0 ? "" : ` Target: ${e.targetLabel}.`, n = e.sameTarget === "same" ? " That instance is connected to the SAME database." : " We could not confirm which database that instance is connected to, so this is refused on the conservative reading — an older instance, or one whose connection could not be parsed, reports nothing to compare.";
1827
1849
  return {
1828
1850
  refuse: !0,
1829
1851
  message: `refusing to write into a target with a LIVE instance (${e.liveInstance}).${t}${n} A direct import is an uncoordinated concurrent writer — readers see partial state, the reactive layer either storms or goes stale, and rows race with live writes. Re-run with --allow-live to override, or use a live-safe strategy (shadow-swap for replace, or the api target).`
1830
1852
  };
1831
- }, Q = Buffer.from("VBUNDLE2"), dr = 0, fr = 1, pr = 2, mr = 32, hr = async (e) => {
1853
+ }, X = Buffer.from("VBUNDLE2"), pr = 0, mr = 1, hr = 2, gr = 32, _r = async (e) => {
1832
1854
  let t = [], n = async (r) => {
1833
1855
  let i;
1834
1856
  try {
1835
- i = await L(B(e, r), { withFileTypes: !0 });
1857
+ i = await ye(I(e, r), { withFileTypes: !0 });
1836
1858
  } catch {
1837
1859
  return;
1838
1860
  }
@@ -1842,22 +1864,22 @@ voltro data import <this-directory> --target api --api-url <url> --token <secret
1842
1864
  }
1843
1865
  };
1844
1866
  return await n(""), t.sort();
1845
- }, gr = (e, t) => {
1867
+ }, vr = (e, t) => {
1846
1868
  let n = Buffer.from(e, "utf8"), r = Buffer.alloc(5 + n.length + 8);
1847
- return r.writeUInt8(fr, 0), r.writeUInt32BE(n.length, 1), n.copy(r, 5), r.writeBigUInt64BE(BigInt(t), 5 + n.length), r;
1848
- }, _r = (e, t, n) => {
1869
+ return r.writeUInt8(mr, 0), r.writeUInt32BE(n.length, 1), n.copy(r, 5), r.writeBigUInt64BE(BigInt(t), 5 + n.length), r;
1870
+ }, yr = (e, t, n) => {
1849
1871
  let r = Buffer.from(e, "utf8"), i = Buffer.from(t, "utf8"), a = Buffer.alloc(5 + r.length + 2 + i.length + 8), o = 0;
1850
- return a.writeUInt8(pr, o), o += 1, a.writeUInt32BE(r.length, o), o += 4, r.copy(a, o), o += r.length, a.writeUInt16BE(i.length, o), o += 2, i.copy(a, o), o += i.length, a.writeBigUInt64BE(BigInt(n), o), a;
1872
+ return a.writeUInt8(hr, o), o += 1, a.writeUInt32BE(r.length, o), o += 4, r.copy(a, o), o += r.length, a.writeUInt16BE(i.length, o), o += 2, i.copy(a, o), o += i.length, a.writeBigUInt64BE(BigInt(n), o), a;
1851
1873
  };
1852
- async function* vr(e) {
1853
- yield new Uint8Array(Q);
1854
- for (let t of await hr(e.dir)) {
1855
- let n = B(e.dir, t), r = await _e(n);
1856
- if (yield new Uint8Array(gr(t, r.size)), r.size > 0) for await (let e of de(n)) yield new Uint8Array(e);
1874
+ async function* br(e) {
1875
+ yield new Uint8Array(X);
1876
+ for (let t of await _r(e.dir)) {
1877
+ let n = I(e.dir, t), r = await be(n);
1878
+ if (yield new Uint8Array(vr(t, r.size)), r.size > 0) for await (let e of fe(n)) yield new Uint8Array(e);
1857
1879
  }
1858
1880
  if (e.blobs) for await (let t of e.blobs.list()) {
1859
- yield new Uint8Array(_r(t.key, t.contentType, t.size));
1860
- let n = oe("sha256"), r = 0;
1881
+ yield new Uint8Array(yr(t.key, t.contentType, t.size));
1882
+ let n = T("sha256"), r = 0;
1861
1883
  for await (let i of e.blobs.open(t.key)) {
1862
1884
  let e = Buffer.from(i);
1863
1885
  n.update(e), r += e.length, yield new Uint8Array(e);
@@ -1865,11 +1887,11 @@ async function* vr(e) {
1865
1887
  if (r !== t.size) throw Error(`blob '${t.key}' size mismatch: header ${t.size}, streamed ${r}`);
1866
1888
  yield new Uint8Array(n.digest());
1867
1889
  }
1868
- yield new Uint8Array(Buffer.from([dr]));
1890
+ yield new Uint8Array(Buffer.from([pr]));
1869
1891
  }
1870
- var yr = (e, t) => new Promise((n, r) => e.write(t, (e) => e ? r(e) : n())), br = (e) => new Promise((t) => e.end(t)), xr = async (e, t) => {
1871
- let n = ye(t.dir);
1872
- await I(n, { recursive: !0 });
1892
+ var xr = (e, t) => new Promise((n, r) => e.write(t, (e) => e ? r(e) : n())), Sr = (e) => new Promise((t) => e.end(t)), Cr = async (e, t) => {
1893
+ let n = L(t.dir);
1894
+ await P(n, { recursive: !0 });
1873
1895
  let r = Buffer.alloc(0), i = e[Symbol.asyncIterator](), a = !1, o = async () => {
1874
1896
  let { value: e, done: t } = await i.next();
1875
1897
  return t ? (a = !0, !1) : (r = r.length === 0 ? Buffer.from(e) : Buffer.concat([r, Buffer.from(e)]), !0);
@@ -1880,28 +1902,28 @@ var yr = (e, t) => new Promise((n, r) => e.write(t, (e) => e ? r(e) : n())), br
1880
1902
  return r = r.subarray(e), t;
1881
1903
  };
1882
1904
  try {
1883
- if (await s(Q.length), !c(Q.length).equals(Q)) throw Error("not a bundle archive (bad magic)");
1905
+ if (await s(X.length), !c(X.length).equals(X)) throw Error("not a bundle archive (bad magic)");
1884
1906
  for (;;) {
1885
1907
  await s(1);
1886
1908
  let e = c(1).readUInt8(0);
1887
- if (e === dr) return;
1888
- if (e === fr) {
1909
+ if (e === pr) return;
1910
+ if (e === mr) {
1889
1911
  await s(4);
1890
1912
  let e = c(4).readUInt32BE(0);
1891
1913
  await s(e);
1892
1914
  let t = c(e).toString("utf8");
1893
1915
  await s(8);
1894
- let i = c(8).readBigUInt64BE(0), a = ye(n, t);
1895
- if (a !== n && !a.startsWith(n + be)) throw Error(`archive path '${t}' escapes the destination`);
1896
- await I(ve(a), { recursive: !0 });
1897
- let o = D(a);
1916
+ let i = c(8).readBigUInt64BE(0), a = L(n, t);
1917
+ if (a !== n && !a.startsWith(n + Ce)) throw Error(`archive path '${t}' escapes the destination`);
1918
+ await P(Se(a), { recursive: !0 });
1919
+ let o = pe(a);
1898
1920
  for (; i > 0n;) {
1899
1921
  r.length === 0 && await s(1);
1900
1922
  let e = i < BigInt(r.length) ? Number(i) : r.length;
1901
- await yr(o, c(e)), i -= BigInt(e);
1923
+ await xr(o, c(e)), i -= BigInt(e);
1902
1924
  }
1903
- await br(o);
1904
- } else if (e === pr) {
1925
+ await Sr(o);
1926
+ } else if (e === hr) {
1905
1927
  await s(4);
1906
1928
  let e = c(4).readUInt32BE(0);
1907
1929
  await s(e);
@@ -1911,24 +1933,24 @@ var yr = (e, t) => new Promise((n, r) => e.write(t, (e) => e ? r(e) : n())), br
1911
1933
  await s(i);
1912
1934
  let a = c(i).toString("utf8");
1913
1935
  await s(8);
1914
- let o = c(8).readBigUInt64BE(0), l = await t.blobs.has(n), u = oe("sha256"), d = new P(), f = l ? Promise.resolve() : t.blobs.write(n, d, {
1936
+ let o = c(8).readBigUInt64BE(0), l = await t.blobs.has(n), u = T("sha256"), d = new M(), f = l ? Promise.resolve() : t.blobs.write(n, d, {
1915
1937
  contentType: a,
1916
1938
  size: Number(o)
1917
1939
  }), p = o;
1918
1940
  for (; p > 0n;) {
1919
1941
  r.length === 0 && await s(1);
1920
1942
  let e = p < BigInt(r.length) ? Number(p) : r.length, t = c(e);
1921
- u.update(t), l || await yr(d, t), p -= BigInt(e);
1943
+ u.update(t), l || await xr(d, t), p -= BigInt(e);
1922
1944
  }
1923
- l ? d.destroy() : await br(d), await f, await s(mr);
1924
- let m = c(mr);
1945
+ l ? d.destroy() : await Sr(d), await f, await s(gr);
1946
+ let m = c(gr);
1925
1947
  if (!u.digest().equals(m)) throw Error(`blob '${n}' failed integrity (sha mismatch)`);
1926
1948
  } else throw Error(`unknown bundle entry kind ${e}`);
1927
1949
  }
1928
1950
  } finally {
1929
1951
  a || await Promise.resolve(i.return?.()).catch(() => void 0);
1930
1952
  }
1931
- }, Sr = async (e, t) => {
1953
+ }, wr = async (e, t) => {
1932
1954
  let n = new Set(t), r = /* @__PURE__ */ new Map(), i = Buffer.alloc(0), a = e[Symbol.asyncIterator](), o = async () => {
1933
1955
  let { value: e, done: t } = await a.next();
1934
1956
  return !t && (i = i.length === 0 ? Buffer.from(e) : Buffer.concat([i, Buffer.from(e)]), !0);
@@ -1947,11 +1969,11 @@ var yr = (e, t) => new Promise((n, r) => e.write(t, (e) => e ? r(e) : n())), br
1947
1969
  }
1948
1970
  return Buffer.concat(t);
1949
1971
  };
1950
- if (!await s(Q.length) || !c(Q.length).equals(Q)) throw Error("not a bundle archive (bad magic)");
1972
+ if (!await s(X.length) || !c(X.length).equals(X)) throw Error("not a bundle archive (bad magic)");
1951
1973
  for (; await s(1);) {
1952
1974
  let e = c(1).readUInt8(0);
1953
- if (e === dr || e === pr) break;
1954
- if (e !== fr) throw Error(`unknown bundle entry kind ${e}`);
1975
+ if (e === pr || e === hr) break;
1976
+ if (e !== mr) throw Error(`unknown bundle entry kind ${e}`);
1955
1977
  if (!await s(4)) break;
1956
1978
  let t = c(4).readUInt32BE(0);
1957
1979
  if (!await s(t)) break;
@@ -1961,22 +1983,22 @@ var yr = (e, t) => new Promise((n, r) => e.write(t, (e) => e ? r(e) : n())), br
1961
1983
  if (a === null || n.has(i) && (r.set(i, a), n.delete(i), n.size === 0)) break;
1962
1984
  }
1963
1985
  return r;
1964
- }, Cr = (e, t) => xr(e, {
1986
+ }, Tr = (e, t) => Cr(e, {
1965
1987
  dir: t,
1966
- blobs: wr(t)
1967
- }), wr = (e) => {
1988
+ blobs: Er(t)
1989
+ }), Er = (e) => {
1968
1990
  let t = /* @__PURE__ */ new Set();
1969
1991
  return {
1970
1992
  has: async (e) => t.has(e),
1971
1993
  write: async (n, r, i) => {
1972
- let a = await import("node:fs/promises"), { pipeline: o } = await import("node:stream/promises"), { Transform: s } = await import("node:stream"), c = B(e, "assets");
1973
- await I(c, { recursive: !0 });
1974
- let l = oe("sha256"), u = 0, d = new s({ transform(e, t, n) {
1994
+ let a = await import("node:fs/promises"), { pipeline: o } = await import("node:stream/promises"), { Transform: s } = await import("node:stream"), c = I(e, "assets");
1995
+ await P(c, { recursive: !0 });
1996
+ let l = T("sha256"), u = 0, d = new s({ transform(e, t, n) {
1975
1997
  l.update(e), u += e.length, n(null, e);
1976
- } }), f = B(c, `.tmp-${Date.now()}-${t.size}`);
1977
- await o(r, d, D(f));
1998
+ } }), f = I(c, `.tmp-${Date.now()}-${t.size}`);
1999
+ await o(r, d, pe(f));
1978
2000
  let p = l.digest("hex");
1979
- await a.rename(f, B(c, p)), await a.appendFile(B(c, "index.ndjson"), `${JSON.stringify({
2001
+ await a.rename(f, I(c, p)), await a.appendFile(I(c, "index.ndjson"), `${JSON.stringify({
1980
2002
  key: n,
1981
2003
  sha256: p,
1982
2004
  size: u,
@@ -1984,33 +2006,33 @@ var yr = (e, t) => new Promise((n, r) => e.write(t, (e) => e ? r(e) : n())), br
1984
2006
  })}\n`), t.add(n);
1985
2007
  }
1986
2008
  };
1987
- }, Tr = xe(ue), Er = Buffer.from("VENC1\0\0\0"), Dr = 32, Or = 16, kr = 7, Ar = 16, jr = 262144, Mr = {
2009
+ }, Dr = we(ue), Or = Buffer.from("VENC1\0\0\0"), kr = 32, Ar = 16, jr = 7, Mr = 16, Nr = 262144, Pr = {
1988
2010
  N: 32768,
1989
2011
  r: 8,
1990
2012
  p: 1
1991
- }, Nr = 134217728, Pr = 43, Fr = (e, t, n) => {
2013
+ }, Fr = 134217728, Ir = 43, Lr = (e, t, n) => {
1992
2014
  let r = Buffer.alloc(12);
1993
- return e.copy(r, 0, 0, kr), r.writeUInt32BE(t >>> 0, kr), r.writeUInt8(+!!n, 11), r;
2015
+ return e.copy(r, 0, 0, jr), r.writeUInt32BE(t >>> 0, jr), r.writeUInt8(+!!n, 11), r;
1994
2016
  };
1995
- async function* Ir(e, t) {
2017
+ async function* Rr(e, t) {
1996
2018
  if (!t) throw Error("encryptStream: a non-empty passphrase is required");
1997
- let n = ce(Or), r = ce(kr), i = await Tr(t, n, Dr, {
1998
- ...Mr,
1999
- maxmem: Nr
2000
- }), a = Buffer.alloc(Pr);
2001
- Er.copy(a, 0), a.writeUInt32BE(Mr.N, 8), a.writeUInt32BE(Mr.r, 12), a.writeUInt32BE(Mr.p, 16), n.copy(a, 20), r.copy(a, 36), yield new Uint8Array(a);
2019
+ let n = ce(Ar), r = ce(jr), i = await Dr(t, n, kr, {
2020
+ ...Pr,
2021
+ maxmem: Fr
2022
+ }), a = Buffer.alloc(Ir);
2023
+ Or.copy(a, 0), a.writeUInt32BE(Pr.N, 8), a.writeUInt32BE(Pr.r, 12), a.writeUInt32BE(Pr.p, 16), n.copy(a, 20), r.copy(a, 36), yield new Uint8Array(a);
2002
2024
  let o = 0, s = (e, t) => {
2003
- let n = ie("aes-256-gcm", i, Fr(r, o, t));
2025
+ let n = ae("aes-256-gcm", i, Lr(r, o, t));
2004
2026
  o === 0 && n.setAAD(a);
2005
2027
  let s = Buffer.concat([n.update(e), n.final()]), c = n.getAuthTag();
2006
2028
  o++;
2007
- let l = Buffer.alloc(5 + s.length + Ar);
2008
- return l.writeUInt8(+!!t, 0), l.writeUInt32BE(s.length + Ar, 1), s.copy(l, 5), c.copy(l, 5 + s.length), new Uint8Array(l);
2029
+ let l = Buffer.alloc(5 + s.length + Mr);
2030
+ return l.writeUInt8(+!!t, 0), l.writeUInt32BE(s.length + Mr, 1), s.copy(l, 5), c.copy(l, 5 + s.length), new Uint8Array(l);
2009
2031
  }, c = Buffer.alloc(0);
2010
- for await (let t of e) for (c = c.length === 0 ? Buffer.from(t) : Buffer.concat([c, Buffer.from(t)]); c.length > jr;) yield s(c.subarray(0, jr), !1), c = c.subarray(jr);
2032
+ for await (let t of e) for (c = c.length === 0 ? Buffer.from(t) : Buffer.concat([c, Buffer.from(t)]); c.length > Nr;) yield s(c.subarray(0, Nr), !1), c = c.subarray(Nr);
2011
2033
  yield s(c, !0);
2012
2034
  }
2013
- async function* Lr(e, t) {
2035
+ async function* zr(e, t) {
2014
2036
  if (!t) throw Error("decryptStream: a non-empty passphrase is required");
2015
2037
  let n = e[Symbol.asyncIterator](), r = Buffer.alloc(0), i = !1, a = async () => {
2016
2038
  let { value: e, done: t } = await n.next();
@@ -2019,16 +2041,16 @@ async function* Lr(e, t) {
2019
2041
  for (; r.length < e && !i && await a(););
2020
2042
  return r.length >= e;
2021
2043
  };
2022
- if (!await o(Pr)) throw Error("encrypted bundle truncated (no header)");
2023
- let s = r.subarray(0, Pr);
2024
- if (!s.subarray(0, 8).equals(Er)) throw Error("not an encrypted bundle (bad magic / wrong passphrase target)");
2025
- let c = s.readUInt32BE(8), l = s.readUInt32BE(12), u = s.readUInt32BE(16), d = Buffer.from(s.subarray(20, 36)), f = Buffer.from(s.subarray(36, Pr)), p = await Tr(t, d, Dr, {
2044
+ if (!await o(Ir)) throw Error("encrypted bundle truncated (no header)");
2045
+ let s = r.subarray(0, Ir);
2046
+ if (!s.subarray(0, 8).equals(Or)) throw Error("not an encrypted bundle (bad magic / wrong passphrase target)");
2047
+ let c = s.readUInt32BE(8), l = s.readUInt32BE(12), u = s.readUInt32BE(16), d = Buffer.from(s.subarray(20, 36)), f = Buffer.from(s.subarray(36, Ir)), p = await Dr(t, d, kr, {
2026
2048
  N: c,
2027
2049
  r: l,
2028
2050
  p: u,
2029
- maxmem: Nr
2051
+ maxmem: Fr
2030
2052
  });
2031
- r = r.subarray(Pr);
2053
+ r = r.subarray(Ir);
2032
2054
  let m = 0, h = !1;
2033
2055
  for (;;) {
2034
2056
  if (!await o(5)) {
@@ -2037,11 +2059,11 @@ async function* Lr(e, t) {
2037
2059
  }
2038
2060
  if (h) throw Error("encrypted bundle has trailing data after the final frame");
2039
2061
  let e = r.readUInt8(0) === 1, t = r.readUInt32BE(1);
2040
- if (t < Ar) throw Error("encrypted bundle corrupt (short frame)");
2062
+ if (t < Mr) throw Error("encrypted bundle corrupt (short frame)");
2041
2063
  if (!await o(5 + t)) throw Error("encrypted bundle truncated (frame body)");
2042
- let n = r.subarray(5, 5 + t - Ar), i = r.subarray(5 + t - Ar, 5 + t);
2064
+ let n = r.subarray(5, 5 + t - Mr), i = r.subarray(5 + t - Mr, 5 + t);
2043
2065
  r = r.subarray(5 + t);
2044
- let a = ae("aes-256-gcm", p, Fr(f, m, e));
2066
+ let a = oe("aes-256-gcm", p, Lr(f, m, e));
2045
2067
  m === 0 && a.setAAD(s), a.setAuthTag(i);
2046
2068
  let c = Buffer.concat([a.update(n), a.final()]);
2047
2069
  m++, e && (h = !0), c.length > 0 && (yield new Uint8Array(c));
@@ -2049,7 +2071,7 @@ async function* Lr(e, t) {
2049
2071
  }
2050
2072
  //#endregion
2051
2073
  //#region src/blobStorage.ts
2052
- var Rr = (e, t) => ({
2074
+ var Br = (e, t) => ({
2053
2075
  list: () => {
2054
2076
  let e = t();
2055
2077
  return { async *[Symbol.asyncIterator]() {
@@ -2062,32 +2084,32 @@ var Rr = (e, t) => ({
2062
2084
  } };
2063
2085
  },
2064
2086
  open: (t) => ({ async *[Symbol.asyncIterator]() {
2065
- let r = await n.runPromise(j(e, t)), i = await M(r.stream);
2087
+ let r = await n.runPromise(_e(e, t)), i = await A(r.stream);
2066
2088
  for await (let e of i) yield e instanceof Uint8Array ? e : new Uint8Array(e);
2067
2089
  } })
2068
- }), zr = (e, t) => Rr(e, () => w(t, {
2069
- table: A,
2090
+ }), Vr = (e, t) => Br(e, () => C(t, {
2091
+ table: O,
2070
2092
  chunkSize: 500
2071
2093
  }).pipe(l.map((e) => ({
2072
2094
  key: String(e.key),
2073
2095
  contentType: String(e.contentType ?? "application/octet-stream"),
2074
2096
  size: Number(e.size ?? 0)
2075
- })))), Br = (e) => ({
2097
+ })))), Hr = (e) => ({
2076
2098
  has: (t) => n.runPromise(e.head(t).pipe(n.map((e) => e !== null))),
2077
2099
  write: async (t, r, i) => {
2078
- let a = me("storage", () => ge.from(r));
2079
- await n.runPromise(he(e, t, a, {
2100
+ let a = ge("storage", () => ve.from(r));
2101
+ await n.runPromise(k(e, t, a, {
2080
2102
  contentType: i.contentType,
2081
2103
  totalSize: i.size
2082
2104
  }));
2083
2105
  }
2084
- }), Vr = (e, t) => {
2106
+ }), Ur = (e, t) => {
2085
2107
  let n = t === "dump" ? "mariadb-dump" : "mariadb", r = t === "dump" ? "mysqldump" : "mysql";
2086
- return e === "mariadb" ? Hr(n) ? { tool: n } : {
2108
+ return e === "mariadb" ? Wr(n) ? { tool: n } : {
2087
2109
  tool: r,
2088
2110
  hint: `'${n}' is not on PATH, so this ran '${r}' instead. If that binary came from Oracle's MySQL client it queries information_schema.COLUMN_STATISTICS, which MariaDB does not have, and the run dies with error 1109 after the first table. Install the MariaDB client package (which ships '${n}') and re-run. Do NOT reach for --column-statistics=0: that flag does not exist on '${n}', so it fixes the wrong client and breaks the right one. Note: a MariaDB 12.x client requires TLS by default, so running '${n}' BY HAND against a server without it fails with "TLS/SSL error: SSL is required" (2026) and needs --skip-ssl. This command is not affected.`
2089
2111
  } : { tool: r };
2090
- }, Hr = (e) => (process.env.PATH ?? "").split(z).filter((e) => e !== "").some((t) => fe(B(t, e))), Ur = (e) => {
2112
+ }, Wr = (e) => (process.env.PATH ?? "").split(xe).filter((e) => e !== "").some((t) => E(I(t, e))), Gr = (e) => {
2091
2113
  switch (e) {
2092
2114
  case "postgres": return "db.dump";
2093
2115
  case "mysql":
@@ -2097,23 +2119,23 @@ var Rr = (e, t) => ({
2097
2119
  case "mssql": return "db.bacpac";
2098
2120
  default: return "db.dump";
2099
2121
  }
2100
- }, Wr = (e) => e.filename ?? e.database ?? ((e.url ?? "").replace(/^file:/, "") || "app.sqlite"), $ = (e) => {
2122
+ }, Kr = (e) => e.filename ?? e.database ?? ((e.url ?? "").replace(/^file:/, "") || "app.sqlite"), Z = (e, t = 3306) => {
2101
2123
  if (e.host || e.database) return {
2102
2124
  host: e.host ?? "localhost",
2103
- port: e.port ?? 3306,
2125
+ port: e.port ?? t,
2104
2126
  username: e.username ?? "root",
2105
2127
  password: e.password ?? "",
2106
2128
  database: e.database ?? ""
2107
2129
  };
2108
- let t = new URL(e.url ?? "");
2130
+ let n = new URL(e.url ?? "");
2109
2131
  return {
2110
- host: t.hostname || "localhost",
2111
- port: t.port ? Number(t.port) : 3306,
2112
- username: decodeURIComponent(t.username) || "root",
2113
- password: decodeURIComponent(t.password) || "",
2114
- database: t.pathname.replace(/^\//, "") || ""
2132
+ host: n.hostname || "localhost",
2133
+ port: e.port ?? (n.port ? Number(n.port) : t),
2134
+ username: decodeURIComponent(n.username) || "root",
2135
+ password: decodeURIComponent(n.password) || "",
2136
+ database: n.pathname.replace(/^\//, "") || ""
2115
2137
  };
2116
- }, Gr = (e) => `Server=${e.host},${e.port};Database=${e.database};User ID=${e.username};Password=${e.password};TrustServerCertificate=True`, Kr = (e, t, n) => {
2138
+ }, qr = (e) => `Server=${e.host},${e.port};Database=${e.database};User ID=${e.username};Password=${e.password};TrustServerCertificate=True`, Jr = (e, t, n) => {
2117
2139
  switch (e) {
2118
2140
  case "postgres": {
2119
2141
  if (t.url) return {
@@ -2123,7 +2145,7 @@ var Rr = (e, t) => ({
2123
2145
  "--format=custom",
2124
2146
  "--no-owner",
2125
2147
  "--no-privileges",
2126
- ...Jr,
2148
+ ...Xr,
2127
2149
  "--dbname",
2128
2150
  t.url,
2129
2151
  "--file",
@@ -2131,10 +2153,7 @@ var Rr = (e, t) => ({
2131
2153
  ],
2132
2154
  env: {}
2133
2155
  };
2134
- let e = $({
2135
- ...t,
2136
- port: t.port ?? 5432
2137
- });
2156
+ let e = Z(t, 5432);
2138
2157
  return {
2139
2158
  kind: "spawn",
2140
2159
  tool: "pg_dump",
@@ -2142,7 +2161,7 @@ var Rr = (e, t) => ({
2142
2161
  "--format=custom",
2143
2162
  "--no-owner",
2144
2163
  "--no-privileges",
2145
- ...Jr,
2164
+ ...Xr,
2146
2165
  "-h",
2147
2166
  e.host,
2148
2167
  "-p",
@@ -2159,17 +2178,17 @@ var Rr = (e, t) => ({
2159
2178
  }
2160
2179
  case "mysql":
2161
2180
  case "mariadb": {
2162
- let r = $(t);
2181
+ let r = Z(t);
2163
2182
  return {
2164
2183
  kind: "spawn",
2165
- ...Vr(e, "dump"),
2184
+ ...Ur(e, "dump"),
2166
2185
  args: [
2167
2186
  "--single-transaction",
2168
2187
  "--routines",
2169
2188
  "--triggers",
2170
2189
  "--no-tablespaces",
2171
2190
  "--protocol=TCP",
2172
- ...qr.map((e) => `--ignore-table=${r.database}.${e}`),
2191
+ ...Yr.map((e) => `--ignore-table=${r.database}.${e}`),
2173
2192
  "-h",
2174
2193
  r.host,
2175
2194
  "-P",
@@ -2185,7 +2204,7 @@ var Rr = (e, t) => ({
2185
2204
  case "sqlite":
2186
2205
  case "turso": return {
2187
2206
  kind: "copy",
2188
- from: Wr(t),
2207
+ from: Kr(t),
2189
2208
  to: n
2190
2209
  };
2191
2210
  case "mssql": return {
@@ -2193,20 +2212,17 @@ var Rr = (e, t) => ({
2193
2212
  tool: "sqlpackage",
2194
2213
  args: [
2195
2214
  "/Action:Export",
2196
- `/SourceConnectionString:${Gr($({
2197
- ...t,
2198
- port: t.port ?? 1433
2199
- }))}`,
2215
+ `/SourceConnectionString:${qr(Z(t, 1433))}`,
2200
2216
  `/TargetFile:${n}`
2201
2217
  ],
2202
2218
  env: {}
2203
2219
  };
2204
- default: throw new K({
2220
+ default: throw new W({
2205
2221
  tool: "backup",
2206
2222
  reason: `no native backup for dialect '${e}'`
2207
2223
  });
2208
2224
  }
2209
- }, qr = [d, u], Jr = qr.flatMap((e) => ["--exclude-table", e]), Yr = (e) => e === "postgres" || e === "mysql" || e === "mariadb" ? qr : [], Xr = (e, t, n) => {
2225
+ }, Yr = [d, u], Xr = Yr.flatMap((e) => ["--exclude-table", e]), Zr = (e) => e === "postgres" || e === "mysql" || e === "mariadb" ? Yr : [], Qr = (e, t, n) => {
2210
2226
  switch (e) {
2211
2227
  case "postgres": {
2212
2228
  if (t.url) return {
@@ -2222,10 +2238,7 @@ var Rr = (e, t) => ({
2222
2238
  ],
2223
2239
  env: {}
2224
2240
  };
2225
- let e = $({
2226
- ...t,
2227
- port: t.port ?? 5432
2228
- });
2241
+ let e = Z(t, 5432);
2229
2242
  return {
2230
2243
  kind: "spawn",
2231
2244
  tool: "pg_restore",
@@ -2248,10 +2261,10 @@ var Rr = (e, t) => ({
2248
2261
  }
2249
2262
  case "mysql":
2250
2263
  case "mariadb": {
2251
- let r = $(t);
2264
+ let r = Z(t);
2252
2265
  return {
2253
2266
  kind: "spawn",
2254
- ...Vr(e, "client"),
2267
+ ...Ur(e, "client"),
2255
2268
  args: [
2256
2269
  "--protocol=TCP",
2257
2270
  "-h",
@@ -2270,37 +2283,104 @@ var Rr = (e, t) => ({
2270
2283
  case "turso": return {
2271
2284
  kind: "copy",
2272
2285
  from: n,
2273
- to: Wr(t)
2274
- };
2275
- case "mssql": return {
2276
- kind: "spawn",
2277
- tool: "sqlpackage",
2278
- args: [
2279
- "/Action:Import",
2280
- `/TargetConnectionString:${Gr($({
2281
- ...t,
2282
- port: t.port ?? 1433
2283
- }))}`,
2284
- `/SourceFile:${n}`
2285
- ],
2286
- env: {}
2286
+ to: Kr(t)
2287
2287
  };
2288
- default: throw new K({
2288
+ case "mssql": {
2289
+ let e = Z(t, 1433), r = ei(e.database);
2290
+ return {
2291
+ kind: "mssql-replace",
2292
+ load: {
2293
+ kind: "spawn",
2294
+ tool: "sqlpackage",
2295
+ args: [
2296
+ "/Action:Import",
2297
+ `/TargetConnectionString:${qr({
2298
+ ...e,
2299
+ database: r
2300
+ })}`,
2301
+ `/SourceFile:${n}`
2302
+ ],
2303
+ env: {}
2304
+ },
2305
+ server: {
2306
+ host: e.host,
2307
+ port: e.port,
2308
+ username: e.username,
2309
+ password: e.password,
2310
+ database: "master"
2311
+ },
2312
+ live: e.database,
2313
+ scratch: r,
2314
+ carry: Yr
2315
+ };
2316
+ }
2317
+ default: throw new W({
2289
2318
  tool: "restore",
2290
2319
  reason: `no native restore for dialect '${e}'`
2291
2320
  });
2292
2321
  }
2293
- }, Zr = (e) => e.kind === "copy" ? n.async((t) => {
2322
+ }, Q = (e) => `[${e.replaceAll("]", "]]")}]`, $ = (e) => `N'${e.replaceAll("'", "''")}'`, $r = "__voltro_restore_", ei = (e, t = le().slice(0, 8)) => `${e}${$r}${t}`, ti = (e) => e.replace($r, "__voltro_replaced_"), ni = (e) => `IF DB_ID(${$(e)}) IS NOT NULL BEGIN ALTER DATABASE ${Q(e)} SET SINGLE_USER WITH ROLLBACK IMMEDIATE; DROP DATABASE ${Q(e)} END`, ri = (e) => `DECLARE @leftover sysname, @drop nvarchar(max);
2323
+ DECLARE leftovers CURSOR LOCAL FAST_FORWARD FOR SELECT name FROM sys.databases WHERE name LIKE ${$(`${`${e}${$r}`.replace(/[\\%_[]/g, (e) => `\\${e}`)}%`)} ESCAPE N'\\';
2324
+ OPEN leftovers; FETCH NEXT FROM leftovers INTO @leftover;
2325
+ WHILE @@FETCH_STATUS = 0 BEGIN
2326
+ SET @drop = N'ALTER DATABASE ' + QUOTENAME(@leftover) + N' SET SINGLE_USER WITH ROLLBACK IMMEDIATE; DROP DATABASE ' + QUOTENAME(@leftover);
2327
+ EXEC(@drop);
2328
+ FETCH NEXT FROM leftovers INTO @leftover;
2329
+ END`, ii = (e) => {
2330
+ let t = Q(e.live), n = Q(e.scratch), r = ti(e.scratch);
2331
+ return {
2332
+ prepare: [ri(e.live)],
2333
+ carry: e.carry.map((e) => {
2334
+ let r = $(`${n}.dbo.${Q(e)}`), i = $(`${t}.dbo.${Q(e)}`);
2335
+ return `IF OBJECT_ID(${r}) IS NOT NULL BEGIN
2336
+ DELETE FROM ${n}.dbo.${Q(e)};
2337
+ IF OBJECT_ID(${i}) IS NOT NULL BEGIN
2338
+ DECLARE @columns nvarchar(max) = (SELECT STRING_AGG(QUOTENAME(s.name), ',') FROM ${n}.sys.columns s
2339
+ JOIN ${t}.sys.columns l ON l.name = s.name AND l.object_id = OBJECT_ID(${i})
2340
+ WHERE s.object_id = OBJECT_ID(${r}) AND s.is_computed = 0);
2341
+ EXEC(N'INSERT INTO ${n.replaceAll("'", "''")}.dbo.${Q(e).replaceAll("'", "''")} (' + @columns + N') SELECT ' + @columns + N' FROM ${t.replaceAll("'", "''")}.dbo.${Q(e).replaceAll("'", "''")}');
2342
+ END
2343
+ END`;
2344
+ }),
2345
+ swap: [
2346
+ `ALTER DATABASE ${t} SET SINGLE_USER WITH ROLLBACK IMMEDIATE`,
2347
+ `ALTER DATABASE ${t} MODIFY NAME = ${Q(r)}`,
2348
+ `ALTER DATABASE ${n} MODIFY NAME = ${t}`,
2349
+ ni(r)
2350
+ ],
2351
+ undoSwap: [`IF DB_ID(${$(e.live)}) IS NULL AND DB_ID(${$(r)}) IS NOT NULL ALTER DATABASE ${Q(r)} MODIFY NAME = ${t}`, `IF DB_ID(${$(e.live)}) IS NOT NULL ALTER DATABASE ${t} SET MULTI_USER`],
2352
+ cleanup: [ni(e.scratch)]
2353
+ };
2354
+ }, ai = (e) => {
2355
+ let t = [];
2356
+ for (let n = e, r = 0; n != null && r < 4; r++) {
2357
+ let e = n instanceof Error ? n.message : typeof n == "object" && "message" in n ? String(n.message) : String(n);
2358
+ e && !t.includes(e) && t.push(e), n = typeof n == "object" && "cause" in n ? n.cause : void 0;
2359
+ }
2360
+ return t.join(": ");
2361
+ }, oi = (e, t) => {
2362
+ if (t === void 0) return n.fail(new W({
2363
+ tool: "sqlpackage",
2364
+ reason: "an mssql restore swaps databases and needs a SQL connection to the server; none was provided"
2365
+ }));
2366
+ let r = ii(e), i = (r, i) => t(e.server, i).pipe(n.mapError((e) => new W({
2367
+ tool: "sqlpackage",
2368
+ reason: `${r}: ${ai(e)}`
2369
+ }))), a = i("dropping the scratch database", r.cleanup).pipe(n.ignore);
2370
+ return n.gen(function* () {
2371
+ yield* i(`preparing ${e.scratch}`, r.prepare), yield* si(e.load).pipe(n.tapError(() => a)), yield* i(`carrying ${e.carry.join(", ")} into the imported copy`, r.carry).pipe(n.tapError(() => a)), yield* i(`swapping ${e.scratch} in as ${e.live}`, r.swap).pipe(n.tapError(() => i("putting the original database back", r.undoSwap).pipe(n.ignore)));
2372
+ });
2373
+ }, si = (e, t) => e.kind === "mssql-replace" ? oi(e, t) : e.kind === "copy" ? n.async((t) => {
2294
2374
  let r = `${e.to}.restoring-${le()}`, i = (e) => {
2295
2375
  try {
2296
- k(r);
2376
+ he(r);
2297
2377
  } catch {}
2298
- t(n.fail(new K({
2378
+ t(n.fail(new W({
2299
2379
  tool: "copy",
2300
2380
  reason: e
2301
2381
  })));
2302
2382
  };
2303
- E(e.from, r, (a) => {
2383
+ de(e.from, r, (a) => {
2304
2384
  if (a) {
2305
2385
  i(`copy ${e.from} → ${e.to}: ${a.message}`);
2306
2386
  return;
@@ -2310,9 +2390,9 @@ var Rr = (e, t) => ({
2310
2390
  `${e.to}-shm`,
2311
2391
  `${e.to}-journal`
2312
2392
  ]) try {
2313
- k(t);
2393
+ he(t);
2314
2394
  } catch {}
2315
- pe(r, e.to, (r) => {
2395
+ D(r, e.to, (r) => {
2316
2396
  if (r) {
2317
2397
  i(`copy ${e.from} → ${e.to}: ${r.message}`);
2318
2398
  return;
@@ -2321,7 +2401,7 @@ var Rr = (e, t) => ({
2321
2401
  });
2322
2402
  });
2323
2403
  }) : n.async((t) => {
2324
- let r = Se(e.tool, [...e.args], {
2404
+ let r = Te(e.tool, [...e.args], {
2325
2405
  env: {
2326
2406
  ...process.env,
2327
2407
  ...e.env
@@ -2341,27 +2421,27 @@ var Rr = (e, t) => ({
2341
2421
  s ??= e;
2342
2422
  };
2343
2423
  if (e.stdoutFile && r.stdout) {
2344
- let t = D(e.stdoutFile);
2345
- t.on("error", (t) => c(`writing ${R(e.stdoutFile)}: ${t.message}`)), r.stdout.on("error", (e) => c(`reading the tool's output: ${e.message}`)), r.stdout.pipe(t);
2424
+ let t = pe(e.stdoutFile);
2425
+ t.on("error", (t) => c(`writing ${F(e.stdoutFile)}: ${t.message}`)), r.stdout.on("error", (e) => c(`reading the tool's output: ${e.message}`)), r.stdout.pipe(t);
2346
2426
  }
2347
2427
  let l = 0;
2348
2428
  if (e.stdinFile && r.stdin) {
2349
- let t = de(e.stdinFile);
2429
+ let t = fe(e.stdinFile);
2350
2430
  t.on("data", (e) => {
2351
2431
  l += e.length;
2352
2432
  }), t.on("error", (t) => {
2353
- c(`reading ${R(e.stdinFile)}: ${t.message}`), r.stdin?.end();
2433
+ c(`reading ${F(e.stdinFile)}: ${t.message}`), r.stdin?.end();
2354
2434
  }), r.stdin.on("error", (t) => {
2355
- t.code !== "EPIPE" && c(`feeding ${R(e.stdinFile)} to ${e.tool}: ${t.message}`);
2435
+ t.code !== "EPIPE" && c(`feeding ${F(e.stdinFile)} to ${e.tool}: ${t.message}`);
2356
2436
  }), t.pipe(r.stdin);
2357
2437
  }
2358
2438
  let u = () => {
2359
2439
  if (e.stdoutFile !== void 0) try {
2360
- k(e.stdoutFile);
2440
+ he(e.stdoutFile);
2361
2441
  } catch {}
2362
2442
  };
2363
2443
  r.on("error", (t) => {
2364
- u(), o(n.fail(new K({
2444
+ u(), o(n.fail(new W({
2365
2445
  tool: e.tool,
2366
2446
  reason: `failed to launch (is '${e.tool}' installed + on PATH?): ${t.message}`,
2367
2447
  ...e.hint === void 0 ? {} : { hint: e.hint }
@@ -2372,25 +2452,25 @@ var Rr = (e, t) => ({
2372
2452
  return;
2373
2453
  }
2374
2454
  u();
2375
- let r = e.stdinFile === void 0 ? "" : ` — ${l} of ${Qr(e.stdinFile)} byte(s) of ${R(e.stdinFile)} had been fed to it`;
2376
- o(n.fail(new K({
2455
+ let r = e.stdinFile === void 0 ? "" : ` — ${l} of ${ci(e.stdinFile)} byte(s) of ${F(e.stdinFile)} had been fed to it`;
2456
+ o(n.fail(new W({
2377
2457
  tool: e.tool,
2378
- reason: (t === 0 ? `exited cleanly, but ${s}` : `exited with code ${t}${s === void 0 ? "" : ` (${s})`}`) + r + (e.stdoutFile === void 0 ? "" : ` — the partial ${R(e.stdoutFile)} was removed, so it cannot be mistaken for a backup`),
2458
+ reason: (t === 0 ? `exited cleanly, but ${s}` : `exited with code ${t}${s === void 0 ? "" : ` (${s})`}`) + r + (e.stdoutFile === void 0 ? "" : ` — the partial ${F(e.stdoutFile)} was removed, so it cannot be mistaken for a backup`),
2379
2459
  stderr: i.trim() === "" ? `(${e.tool} printed nothing to stderr)` : i.slice(-2e3),
2380
2460
  ...e.hint === void 0 ? {} : { hint: e.hint }
2381
2461
  })));
2382
2462
  });
2383
- }), Qr = (e) => {
2463
+ }), ci = (e) => {
2384
2464
  try {
2385
- return String(O(e).size);
2465
+ return String(me(e).size);
2386
2466
  } catch {
2387
2467
  return "?";
2388
2468
  }
2389
- }, $r = (e) => typeof e == "object" && e ? "fake" in e ? `fake:${e.fake}` : "custom" : String(e), ei = (e) => n.gen(function* () {
2390
- let t = yield* st(e.scope ?? { kind: "all" }, e.snapshot, {
2469
+ }, li = (e) => typeof e == "object" && e ? "fake" in e ? `fake:${e.fake}` : "custom" : String(e), ui = (e) => n.gen(function* () {
2470
+ let t = yield* lt(e.scope ?? { kind: "all" }, e.snapshot, {
2391
2471
  store: e.store,
2392
2472
  ...e.tenantTables ? { tenantTables: e.tenantTables } : {}
2393
- }), r = an(t.tables, e.snapshot), i = e.classification ?? Te(e.snapshot), a = e.sampleSize ?? 20, o = ze(r.map((t) => ({
2473
+ }), r = sn(t.tables, e.snapshot), i = e.classification ?? Oe(e.snapshot), a = e.sampleSize ?? 20, o = He(r.map((t) => ({
2394
2474
  name: t,
2395
2475
  columns: (e.snapshot.tables.find((e) => e.name === t)?.columns ?? []).map((e) => ({
2396
2476
  name: e.name,
@@ -2398,19 +2478,19 @@ var Rr = (e, t) => ({
2398
2478
  }))
2399
2479
  })), i, e.masking), s = [], c = [];
2400
2480
  for (let i of r) {
2401
- let r = t.predicateFor(i), u = yield* w(e.store, {
2481
+ let r = t.predicateFor(i), u = yield* C(e.store, {
2402
2482
  table: i,
2403
2483
  chunkSize: a,
2404
2484
  ...r === void 0 ? {} : { where: r }
2405
- }).pipe(l.take(a), l.runCollect, n.map((e) => [...e])), d = u.map((t) => He(t, i, o.actions, e.masking.seed));
2406
- c.push(...Ve(d, i, o.actions));
2485
+ }).pipe(l.take(a), l.runCollect, n.map((e) => [...e])), d = u.map((t) => Ge(t, i, o.actions, e.masking.seed));
2486
+ c.push(...We(d, i, o.actions));
2407
2487
  let f = u[0], p = d[0], m = [];
2408
2488
  if (f && p) for (let [e, t] of Object.entries(o.actions)) {
2409
2489
  if (!e.startsWith(`${i}.`) || t === "keep") continue;
2410
2490
  let n = e.slice(i.length + 1);
2411
2491
  m.push({
2412
2492
  column: n,
2413
- action: $r(t),
2493
+ action: li(t),
2414
2494
  before: f[n],
2415
2495
  after: p[n]
2416
2496
  });
@@ -2425,7 +2505,7 @@ var Rr = (e, t) => ({
2425
2505
  leaks: c,
2426
2506
  unclassified: o.unclassified
2427
2507
  };
2428
- }), ti = (e, t) => {
2508
+ }), di = (e, t) => {
2429
2509
  let n = new Map(t.map((e) => [e.name, e])), r = [], i = {};
2430
2510
  for (let t of e) {
2431
2511
  let e = n.get(t.name);
@@ -2480,7 +2560,7 @@ var Rr = (e, t) => ({
2480
2560
  skipColumns: i,
2481
2561
  refuse: r.some((e) => e.verdict === "refuse")
2482
2562
  };
2483
- }, ni = (e) => {
2563
+ }, fi = (e) => {
2484
2564
  if (e.findings.length === 0) return [" schema matches the bundle"];
2485
2565
  let t = {
2486
2566
  safe: "✓",
@@ -2491,4 +2571,4 @@ var Rr = (e, t) => ({
2491
2571
  return n.push(""), n.push(` discarded: ${r("value-dropped")} defaulted: ${r("filled-by-default")} refused: ${r("refuse")}`), e.refuse && (n.push(""), n.push(" REFUSED — no row was written. These are the differences that would make"), n.push(" imported rows WRONG rather than merely incomplete.")), n;
2492
2572
  };
2493
2573
  //#endregion
2494
- export { Mt as ASSETS_DIR, Nt as ASSET_INDEX_FILE, G as BundleError, qe as CodecError, Ye as CompressionError, tt as CrossDialectError, jt as DATA_DIR, we as DEFAULT_CLASS_ACTIONS, Ue as ENVIRONMENT_LOCAL_TABLES, We as ENVIRONMENT_PORTABLE_TABLES, qr as EXCLUDED_FROM_DUMP, St as FORMAT_VERSION, et as ImportModeError, Je as IntegrityError, Pt as LEDGER_FILE, kt as MANIFEST_FILE, $e as MaskingError, K as NativeToolError, Ze as RowsRefusedError, rr as SAVEPOINT_BATCH_SIZE, jn as STAGING_PREFIX, Qe as SchemaDriftError, Xe as ScopeError, U as applyAction, ar as asImportError, ur as assessLiveImport, Wt as assetDone, Ur as backupArtifactName, Kr as backupCommand, Mn as canStage, yn as canonicalType, mt as captureAssetsToCas, Sn as checkPortability, er as checkSchemaDrift, Te as classificationFromSnapshot, ti as classifyImportDrift, yt as compressionExt, it as computeSubsetIds, qn as decideStaging, Ot as decodeManifest, en as decodeRow, Qt as decodeValue, Lr as decryptStream, lr as defineDataProfile, $n as diffSnapshots, wr as dirBlobSink, In as dropStagingSql, Yr as dumpExcludedTables, Vt as emptyLedger, Dt as encodeManifest, $t as encodeRow, Xt as encodeValue, Ir as encryptStream, Ke as environmentLocalNotice, Ge as environmentLocalReason, Hn as execStatements, ni as formatImportDrift, Cn as formatIssue, _t as hasZstd, W as isEnvironmentLocal, bt as makeCompressor, xt as makeDecompressor, He as maskRow, rn as ndjsonToRows, ft as noAssetProgress, vn as outsideReferenceRefusal, _n as outsideReferencesInto, vr as packBundle, Sr as peekBundle, vt as pickCompression, ze as planMasking, ei as previewMasking, ht as readAssetIndex, Ht as readLedger, Ee as resolveAction, st as resolveScope, dt as restoreAssetFromCas, gt as restoreAssetsFromCas, Xr as restoreCommand, nn as rowsToNdjson, gn as runExport, cr as runImport, Zr as runNativeStep, Ve as scanForLeaks, X as stagingNameFor, lt as storageAssetSink, ct as storageAssetSource, Br as storageBlobSink, Rr as storageBlobSource, zr as storageRefsBlobSource, at as subsetToScope, Ut as tableDone, an as topoSortTables, xr as unpackBundle, Cr as unpackBundleToDir, ut as writeAssetToCas, J as writeLedger };
2574
+ export { Pt as ASSETS_DIR, Ft as ASSET_INDEX_FILE, H as BundleError, Xe as CodecError, Qe as CompressionError, rt as CrossDialectError, Nt as DATA_DIR, De as DEFAULT_CLASS_ACTIONS, Ke as ENVIRONMENT_LOCAL_TABLES, qe as ENVIRONMENT_PORTABLE_TABLES, Yr as EXCLUDED_FROM_DUMP, wt as FORMAT_VERSION, nt as ImportModeError, Ze as IntegrityError, It as LEDGER_FILE, jt as MANIFEST_FILE, tt as MaskingError, W as NativeToolError, $e as RowsRefusedError, ar as SAVEPOINT_BATCH_SIZE, Nn as STAGING_PREFIX, et as SchemaDriftError, U as ScopeError, B as applyAction, sr as asImportError, fr as assessLiveImport, Kt as assetDone, Gr as backupArtifactName, Jr as backupCommand, Pn as canStage, xn as canonicalType, gt as captureAssetsToCas, wn as checkPortability, nr as checkSchemaDrift, Oe as classificationFromSnapshot, di as classifyImportDrift, xt as compressionExt, ot as computeSubsetIds, Yn as decideStaging, At as decodeManifest, nn as decodeRow, en as decodeValue, zr as decryptStream, dr as defineDataProfile, tr as diffSnapshots, Er as dirBlobSink, Rn as dropStagingSql, Zr as dumpExcludedTables, Ut as emptyLedger, kt as encodeManifest, tn as encodeRow, Qt as encodeValue, Rr as encryptStream, Ye as environmentLocalNotice, Je as environmentLocalReason, Wn as execStatements, fi as formatImportDrift, Tn as formatIssue, yt as hasZstd, V as isEnvironmentLocal, St as makeCompressor, Ct as makeDecompressor, Ge as maskRow, ii as mssqlReplaceStatements, ei as mssqlScratchName, on as ndjsonToRows, mt as noAssetProgress, bn as outsideReferenceRefusal, yn as outsideReferencesInto, br as packBundle, wr as peekBundle, bt as pickCompression, He as planMasking, ui as previewMasking, _t as readAssetIndex, Wt as readLedger, ke as resolveAction, lt as resolveScope, pt as restoreAssetFromCas, vt as restoreAssetsFromCas, Qr as restoreCommand, an as rowsToNdjson, vn as runExport, ur as runImport, si as runNativeStep, We as scanForLeaks, J as stagingNameFor, dt as storageAssetSink, ut as storageAssetSource, Hr as storageBlobSink, Br as storageBlobSource, Vr as storageRefsBlobSource, st as subsetToScope, Gt as tableDone, sn as topoSortTables, Cr as unpackBundle, Tr as unpackBundleToDir, ft as writeAssetToCas, K as writeLedger };