@voltro/database 0.24.0 → 0.25.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/CHANGELOG.md +426 -0
- package/dist/{frameworkLiveTables-BvPIm2cD.js → frameworkLiveTables-BQwB8K6R.js} +9 -0
- package/dist/index.d.ts +153 -0
- package/dist/index.js +457 -426
- package/dist/sql.d.ts +45 -0
- package/dist/sql.js +20 -4
- package/package.json +2 -2
package/dist/sql.d.ts
CHANGED
|
@@ -143,6 +143,25 @@ export declare const applySchema: (tables: ReadonlyArray<AnyTable>, dialect?: Di
|
|
|
143
143
|
* raised nothing. */
|
|
144
144
|
cdcChannel?: string) => Effect.Effect<void, never, SqlClient.SqlClient>;
|
|
145
145
|
|
|
146
|
+
/**
|
|
147
|
+
* The OPT-IN refuse gate over the advisory. By default (`VOLTRO_ROLLING_DEPLOY`
|
|
148
|
+
* unset) this never fires — the classifier stays a `db plan` advisory, because
|
|
149
|
+
* the framework can't know the deploy strategy and a maintenance-window /
|
|
150
|
+
* scale-to-zero deploy has no overlap window. An operator who DOES rolling
|
|
151
|
+
* deploys opts in with `VOLTRO_ROLLING_DEPLOY=1`, turning an unsafe `db apply`
|
|
152
|
+
* into a hard refusal they must split (expand/contract) or explicitly `--force`.
|
|
153
|
+
*
|
|
154
|
+
* Pure — the caller supplies the resolved flags + the unsafe-op count (the ⚠
|
|
155
|
+
* detail is already printed by the plan renderer), so the decision is testable
|
|
156
|
+
* without a CLI or a DB, and the cloud managed-hosting migration wall can reuse
|
|
157
|
+
* exactly this verdict.
|
|
158
|
+
*/
|
|
159
|
+
export declare const assessRollingDeployGate: (input: {
|
|
160
|
+
readonly enabled: boolean;
|
|
161
|
+
readonly forced: boolean;
|
|
162
|
+
readonly unsafeCount: number;
|
|
163
|
+
}) => RollingDeployGateVerdict;
|
|
164
|
+
|
|
146
165
|
/** Per-row backfill body executed by the migration runner. */
|
|
147
166
|
declare type BackfillFunction<TsType = unknown> = (row: Readonly<Record<string, unknown>>) => TsType | Promise<TsType>;
|
|
148
167
|
|
|
@@ -380,6 +399,23 @@ declare interface ColumnDefinition<TsType, Type extends ColumnType = ColumnType,
|
|
|
380
399
|
* COSTS is per command — see `serverOnly()` below for the matrix.
|
|
381
400
|
*/
|
|
382
401
|
readonly serverOnly?: boolean;
|
|
402
|
+
/**
|
|
403
|
+
* Optimistic-concurrency marker, set by `.version()`.
|
|
404
|
+
*
|
|
405
|
+
* The column the store INCREMENTS on every update, and the one an update may
|
|
406
|
+
* carry an expectation of. Two clients that read the same row and both write
|
|
407
|
+
* it are the normal case, not an exotic one — and without this the second
|
|
408
|
+
* write silently wins, which is the shape of every "my change disappeared"
|
|
409
|
+
* report ever filed.
|
|
410
|
+
*
|
|
411
|
+
* A TIMESTAMP cannot do this job. Two writes in the same millisecond are
|
|
412
|
+
* indistinguishable, and across replicas the clocks disagree; this repo has
|
|
413
|
+
* already lost rows to exactly that (an analytics sink dropped 7 of 40 events
|
|
414
|
+
* written in the same millisecond as the query bounding them). A monotonic
|
|
415
|
+
* integer has neither problem, and it also answers the other half of the
|
|
416
|
+
* question — which of two copies is NEWER — without consulting a clock.
|
|
417
|
+
*/
|
|
418
|
+
readonly versionColumn?: boolean;
|
|
383
419
|
/**
|
|
384
420
|
* Data-sensitivity classification, set by `.sensitive(class)`. Declares that
|
|
385
421
|
* this column holds personal / sensitive data of a given CLASS (`'email'`,
|
|
@@ -1671,6 +1707,15 @@ export declare const rollbackFileBasedMigration: (sql: SqlClient.SqlClient, ctx:
|
|
|
1671
1707
|
durationMs: number;
|
|
1672
1708
|
}, unknown>;
|
|
1673
1709
|
|
|
1710
|
+
export declare interface RollingDeployGateVerdict {
|
|
1711
|
+
/** The apply MUST NOT proceed (opt-in gate tripped, not forced). */
|
|
1712
|
+
readonly refuse: boolean;
|
|
1713
|
+
/** The gate tripped but `--force` waved it through — surface a warning. */
|
|
1714
|
+
readonly warnForced: boolean;
|
|
1715
|
+
/** Empty unless refuse or warnForced. */
|
|
1716
|
+
readonly message: string;
|
|
1717
|
+
}
|
|
1718
|
+
|
|
1674
1719
|
/** Verdict for one operation under a rolling deploy. */
|
|
1675
1720
|
export declare type RollingDeploySafety = {
|
|
1676
1721
|
readonly safe: true;
|
package/dist/sql.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { H as e, U as t, a as n, c as r, d as i, ft as a, i as o, n as s, o as c, ot as l, q as u, r as d, s as f } from "./frameworkLiveTables-
|
|
1
|
+
import { H as e, U as t, a as n, c as r, d as i, ft as a, i as o, n as s, o as c, ot as l, q as u, r as d, s as f } from "./frameworkLiveTables-BQwB8K6R.js";
|
|
2
2
|
import { Effect as p } from "effect";
|
|
3
3
|
import { createLogger as m } from "@voltro/logger";
|
|
4
4
|
import { SqlClient as h } from "@effect/sql";
|
|
@@ -3008,10 +3008,26 @@ BEGIN
|
|
|
3008
3008
|
});
|
|
3009
3009
|
}
|
|
3010
3010
|
return t;
|
|
3011
|
-
}, ni = (e
|
|
3011
|
+
}, ni = (e) => {
|
|
3012
|
+
if (!e.enabled || e.unsafeCount === 0) return {
|
|
3013
|
+
refuse: !1,
|
|
3014
|
+
warnForced: !1,
|
|
3015
|
+
message: ""
|
|
3016
|
+
};
|
|
3017
|
+
let t = `${e.unsafeCount} operation(s) are UNSAFE under a rolling deploy (VOLTRO_ROLLING_DEPLOY=1)`;
|
|
3018
|
+
return e.forced ? {
|
|
3019
|
+
refuse: !1,
|
|
3020
|
+
warnForced: !0,
|
|
3021
|
+
message: `${t} — proceeding anyway (--force). Old instances may error mid-rollout.`
|
|
3022
|
+
} : {
|
|
3023
|
+
refuse: !0,
|
|
3024
|
+
warnForced: !1,
|
|
3025
|
+
message: `${t}. Old instances would break against the new schema mid-rollout. Split into expand → deploy → contract (see the ⚠ list above), deploy with no overlap (maintenance window / scale-to-zero), or pass --force to override.`
|
|
3026
|
+
};
|
|
3027
|
+
}, ri = (e, ...t) => ({
|
|
3012
3028
|
_tag: "RawSqlFragment",
|
|
3013
3029
|
strings: [...e],
|
|
3014
3030
|
values: [...t]
|
|
3015
|
-
}),
|
|
3031
|
+
}), ii = (e) => typeof e == "object" && !!e && e._tag === "RawSqlFragment";
|
|
3016
3032
|
//#endregion
|
|
3017
|
-
export { O as DEFAULT_CDC_CHANNEL, o as FILE_MIGRATION_PATTERN, Gr as FileMigrationLedgerError, k as REACTIVE_TRIGGER_PREFIX, re as VOLTRO_MIGRATION_LOCK_KEY, T as acquireMigrationLock, et as applyNamespacedSchema, Tr as applyPlan, Je as applySchema, $t as chunkTables, ei as classifyRollingDeploySafety, I as declaredSnapshot, xe as defaultArrayClause, be as defaultClause, M as defaultJsonClause, Br as describeOutcome, Pr as destructiveScope, ft as detectReactiveTriggerDrift, gn as emitDropColumnDdl, _n as emitDropColumnDdlMysql, qe as emitFrameworkBootstrapSql, Ge as emitNamespaceProvisionDdl, Ke as emitNamespacedSchemaSql, We as emitSchemaSql, P as fingerprintSchema, pt as formatReactiveTriggerDrift, Nr as ignoreTablesFromEnv, U as introspectSchema, n as isFileMigration,
|
|
3033
|
+
export { O as DEFAULT_CDC_CHANNEL, o as FILE_MIGRATION_PATTERN, Gr as FileMigrationLedgerError, k as REACTIVE_TRIGGER_PREFIX, re as VOLTRO_MIGRATION_LOCK_KEY, T as acquireMigrationLock, et as applyNamespacedSchema, Tr as applyPlan, Je as applySchema, ni as assessRollingDeployGate, $t as chunkTables, ei as classifyRollingDeploySafety, I as declaredSnapshot, xe as defaultArrayClause, be as defaultClause, M as defaultJsonClause, Br as describeOutcome, Pr as destructiveScope, ft as detectReactiveTriggerDrift, gn as emitDropColumnDdl, _n as emitDropColumnDdlMysql, qe as emitFrameworkBootstrapSql, Ge as emitNamespaceProvisionDdl, Ke as emitNamespacedSchemaSql, We as emitSchemaSql, P as fingerprintSchema, pt as formatReactiveTriggerDrift, Nr as ignoreTablesFromEnv, U as introspectSchema, n as isFileMigration, ii as isRawSqlFragment, Jt as mapPgType, c as migration, N as numericIdSql, qt as parseEnumCheck, Jr as pendingFileMigrationIds, Kt as planMigrations, tt as provisionTenantNamespace, Fe as reactiveTriggerRepairSql, E as releaseMigrationLock, Mn as renderColumnMysql, Dn as renderColumnPg, Zr as rollbackFileBasedMigration, ti as rollingDeployUnsafeOps, Yr as runFileBasedMigrations, nt as runFrameworkBootstrap, $e as runMigrate, zr as runPlannedMigrations, F as shortFingerprint, ct as snapshotColumn, ri as sql, j as sqlType, Qr as squashMigrationPlans, Ir as unblockLossy, D as withMigrationLock };
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@voltro/database",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.25.0",
|
|
4
4
|
"description": "Browser-safe schema DSL, query builder, and cross-dialect migration planner for Voltro — one schema, every SQL backend.",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"voltro",
|
|
@@ -43,7 +43,7 @@
|
|
|
43
43
|
},
|
|
44
44
|
"dependencies": {
|
|
45
45
|
"@effect/sql": "^0.52.0",
|
|
46
|
-
"@voltro/logger": "0.
|
|
46
|
+
"@voltro/logger": "0.25.0",
|
|
47
47
|
"typeid-js": "^1.2.0",
|
|
48
48
|
"ulidx": "^2.4.1"
|
|
49
49
|
},
|