@adminiumjs/meta 0.2.1 → 0.2.2
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/bootstrap.d.ts +10 -2
- package/dist/bootstrap.d.ts.map +1 -1
- package/dist/bootstrap.js +12 -3
- package/dist/bootstrap.js.map +1 -1
- package/dist/columns.d.ts.map +1 -1
- package/dist/columns.js +1 -0
- package/dist/columns.js.map +1 -1
- package/dist/connect.d.ts.map +1 -1
- package/dist/connect.js +1 -0
- package/dist/connect.js.map +1 -1
- package/dist/ids.d.ts +4 -0
- package/dist/ids.d.ts.map +1 -1
- package/dist/ids.js +8 -0
- package/dist/ids.js.map +1 -1
- package/dist/index.d.ts +2 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +3 -0
- package/dist/index.js.map +1 -1
- package/dist/migrate-lock.d.ts +104 -0
- package/dist/migrate-lock.d.ts.map +1 -0
- package/dist/migrate-lock.js +197 -0
- package/dist/migrate-lock.js.map +1 -0
- package/dist/migrations/0001_core_auth.d.ts.map +1 -1
- package/dist/migrations/0001_core_auth.js +1 -0
- package/dist/migrations/0001_core_auth.js.map +1 -1
- package/dist/migrations/0002_rbac.d.ts.map +1 -1
- package/dist/migrations/0002_rbac.js +1 -0
- package/dist/migrations/0002_rbac.js.map +1 -1
- package/dist/migrations/0003_connections_schema.d.ts.map +1 -1
- package/dist/migrations/0003_connections_schema.js +1 -0
- package/dist/migrations/0003_connections_schema.js.map +1 -1
- package/dist/migrations/0004_pages_views.d.ts.map +1 -1
- package/dist/migrations/0004_pages_views.js +1 -0
- package/dist/migrations/0004_pages_views.js.map +1 -1
- package/dist/migrations/0005_ops.d.ts.map +1 -1
- package/dist/migrations/0005_ops.js +1 -0
- package/dist/migrations/0005_ops.js.map +1 -1
- package/dist/migrations/0006_platform.d.ts.map +1 -1
- package/dist/migrations/0006_platform.js +1 -0
- package/dist/migrations/0006_platform.js.map +1 -1
- package/dist/migrations/0007_llm_runs.d.ts.map +1 -1
- package/dist/migrations/0007_llm_runs.js +1 -0
- package/dist/migrations/0007_llm_runs.js.map +1 -1
- package/dist/migrations/0008_llm_overrides.d.ts.map +1 -1
- package/dist/migrations/0008_llm_overrides.js +1 -0
- package/dist/migrations/0008_llm_overrides.js.map +1 -1
- package/dist/migrations/0009_views_kind.d.ts.map +1 -1
- package/dist/migrations/0009_views_kind.js +1 -0
- package/dist/migrations/0009_views_kind.js.map +1 -1
- package/dist/migrations/0010_llm_prompt_version_width.d.ts.map +1 -1
- package/dist/migrations/0010_llm_prompt_version_width.js +1 -0
- package/dist/migrations/0010_llm_prompt_version_width.js.map +1 -1
- package/dist/migrations/0011_i18n_runtime.d.ts.map +1 -1
- package/dist/migrations/0011_i18n_runtime.js +1 -0
- package/dist/migrations/0011_i18n_runtime.js.map +1 -1
- package/dist/migrations/0012_locale_width.d.ts.map +1 -1
- package/dist/migrations/0012_locale_width.js +1 -0
- package/dist/migrations/0012_locale_width.js.map +1 -1
- package/dist/migrations/0013_connection_last_error_hint.d.ts +17 -0
- package/dist/migrations/0013_connection_last_error_hint.d.ts.map +1 -0
- package/dist/migrations/0013_connection_last_error_hint.js +22 -0
- package/dist/migrations/0013_connection_last_error_hint.js.map +1 -0
- package/dist/migrations/0014_public_surface.d.ts +40 -0
- package/dist/migrations/0014_public_surface.d.ts.map +1 -0
- package/dist/migrations/0014_public_surface.js +186 -0
- package/dist/migrations/0014_public_surface.js.map +1 -0
- package/dist/migrations/index.d.ts.map +1 -1
- package/dist/migrations/index.js +5 -0
- package/dist/migrations/index.js.map +1 -1
- package/dist/migrator.d.ts +22 -3
- package/dist/migrator.d.ts.map +1 -1
- package/dist/migrator.js +27 -6
- package/dist/migrator.js.map +1 -1
- package/dist/prefix.d.ts.map +1 -1
- package/dist/prefix.js +1 -0
- package/dist/prefix.js.map +1 -1
- package/dist/relocate.d.ts +118 -0
- package/dist/relocate.d.ts.map +1 -0
- package/dist/relocate.js +376 -0
- package/dist/relocate.js.map +1 -0
- package/dist/repos/api-keys.d.ts.map +1 -1
- package/dist/repos/api-keys.js +1 -0
- package/dist/repos/api-keys.js.map +1 -1
- package/dist/repos/audit.d.ts.map +1 -1
- package/dist/repos/audit.js +1 -0
- package/dist/repos/audit.js.map +1 -1
- package/dist/repos/connections.d.ts +5 -0
- package/dist/repos/connections.d.ts.map +1 -1
- package/dist/repos/connections.js +8 -0
- package/dist/repos/connections.js.map +1 -1
- package/dist/repos/email-templates.d.ts.map +1 -1
- package/dist/repos/email-templates.js +1 -0
- package/dist/repos/email-templates.js.map +1 -1
- package/dist/repos/exports.d.ts.map +1 -1
- package/dist/repos/exports.js +1 -0
- package/dist/repos/exports.js.map +1 -1
- package/dist/repos/files.d.ts.map +1 -1
- package/dist/repos/files.js +1 -0
- package/dist/repos/files.js.map +1 -1
- package/dist/repos/i18n-version.d.ts.map +1 -1
- package/dist/repos/i18n-version.js +1 -0
- package/dist/repos/i18n-version.js.map +1 -1
- package/dist/repos/imports.d.ts.map +1 -1
- package/dist/repos/imports.js +1 -0
- package/dist/repos/imports.js.map +1 -1
- package/dist/repos/index.d.ts +1 -0
- package/dist/repos/index.d.ts.map +1 -1
- package/dist/repos/index.js +2 -0
- package/dist/repos/index.js.map +1 -1
- package/dist/repos/jobs.d.ts.map +1 -1
- package/dist/repos/jobs.js +1 -0
- package/dist/repos/jobs.js.map +1 -1
- package/dist/repos/llm-overrides.d.ts.map +1 -1
- package/dist/repos/llm-overrides.js +1 -0
- package/dist/repos/llm-overrides.js.map +1 -1
- package/dist/repos/llm-runs.d.ts.map +1 -1
- package/dist/repos/llm-runs.js +1 -0
- package/dist/repos/llm-runs.js.map +1 -1
- package/dist/repos/locales.d.ts.map +1 -1
- package/dist/repos/locales.js +1 -0
- package/dist/repos/locales.js.map +1 -1
- package/dist/repos/notification-prefs.d.ts.map +1 -1
- package/dist/repos/notification-prefs.js +1 -0
- package/dist/repos/notification-prefs.js.map +1 -1
- package/dist/repos/notifications.d.ts.map +1 -1
- package/dist/repos/notifications.js +1 -0
- package/dist/repos/notifications.js.map +1 -1
- package/dist/repos/overrides.d.ts.map +1 -1
- package/dist/repos/overrides.js +1 -0
- package/dist/repos/overrides.js.map +1 -1
- package/dist/repos/pages.d.ts +147 -1
- package/dist/repos/pages.d.ts.map +1 -1
- package/dist/repos/pages.js +318 -23
- package/dist/repos/pages.js.map +1 -1
- package/dist/repos/password-resets.d.ts.map +1 -1
- package/dist/repos/password-resets.js +1 -0
- package/dist/repos/password-resets.js.map +1 -1
- package/dist/repos/permissions.d.ts +15 -0
- package/dist/repos/permissions.d.ts.map +1 -1
- package/dist/repos/permissions.js +39 -0
- package/dist/repos/permissions.js.map +1 -1
- package/dist/repos/public-api.d.ts +116 -0
- package/dist/repos/public-api.d.ts.map +1 -0
- package/dist/repos/public-api.js +249 -0
- package/dist/repos/public-api.js.map +1 -0
- package/dist/repos/roles.d.ts.map +1 -1
- package/dist/repos/roles.js +1 -0
- package/dist/repos/roles.js.map +1 -1
- package/dist/repos/scheduled-reports.d.ts.map +1 -1
- package/dist/repos/scheduled-reports.js +1 -0
- package/dist/repos/scheduled-reports.js.map +1 -1
- package/dist/repos/sessions.d.ts +9 -0
- package/dist/repos/sessions.d.ts.map +1 -1
- package/dist/repos/sessions.js +26 -0
- package/dist/repos/sessions.js.map +1 -1
- package/dist/repos/settings.d.ts.map +1 -1
- package/dist/repos/settings.js +1 -0
- package/dist/repos/settings.js.map +1 -1
- package/dist/repos/snapshots.d.ts.map +1 -1
- package/dist/repos/snapshots.js +1 -0
- package/dist/repos/snapshots.js.map +1 -1
- package/dist/repos/translations.d.ts.map +1 -1
- package/dist/repos/translations.js +1 -0
- package/dist/repos/translations.js.map +1 -1
- package/dist/repos/user-prefs.d.ts.map +1 -1
- package/dist/repos/user-prefs.js +1 -0
- package/dist/repos/user-prefs.js.map +1 -1
- package/dist/repos/users.d.ts +31 -0
- package/dist/repos/users.d.ts.map +1 -1
- package/dist/repos/users.js +80 -4
- package/dist/repos/users.js.map +1 -1
- package/dist/repos/util.d.ts.map +1 -1
- package/dist/repos/util.js +1 -0
- package/dist/repos/util.js.map +1 -1
- package/dist/repos/views.d.ts.map +1 -1
- package/dist/repos/views.js +1 -0
- package/dist/repos/views.js.map +1 -1
- package/dist/schema/index.d.ts.map +1 -1
- package/dist/schema/index.js +1 -0
- package/dist/schema/index.js.map +1 -1
- package/dist/schema/json-payloads.d.ts +2 -1
- package/dist/schema/json-payloads.d.ts.map +1 -1
- package/dist/schema/json-payloads.js +7 -0
- package/dist/schema/json-payloads.js.map +1 -1
- package/dist/schema/settings-registry.d.ts +45 -0
- package/dist/schema/settings-registry.d.ts.map +1 -1
- package/dist/schema/settings-registry.js +60 -0
- package/dist/schema/settings-registry.js.map +1 -1
- package/dist/schema/tables.d.ts +91 -1
- package/dist/schema/tables.d.ts.map +1 -1
- package/dist/schema/tables.js +5 -0
- package/dist/schema/tables.js.map +1 -1
- package/package.json +2 -2
|
@@ -0,0 +1,186 @@
|
|
|
1
|
+
// SPDX-License-Identifier: AGPL-3.0-only
|
|
2
|
+
/**
|
|
3
|
+
* Wave 0014 — the public surface (28-public-surface.md §3).
|
|
4
|
+
*
|
|
5
|
+
* Four tables behind the scoped, off-by-default `/api/v1/public` namespace:
|
|
6
|
+
* the browser-safe key kind, the scope document that says what a key may reach,
|
|
7
|
+
* the end-customer session a `claim` mints, and the one-time challenge the
|
|
8
|
+
* `email-code` claim tier needs.
|
|
9
|
+
*
|
|
10
|
+
* WHY THESE ARE NOT `adminium_api_keys` ROWS WITH A `kind` COLUMN (28 §3.3).
|
|
11
|
+
* Two properties diverge and both are load-bearing:
|
|
12
|
+
*
|
|
13
|
+
* 1. The secret is RE-READABLE by an admin. `adminium_api_keys` reveals once
|
|
14
|
+
* and never again, which is right for a server-side credential a human
|
|
15
|
+
* copies into a deployment. An `adm_pub_` secret lives in a public bundle
|
|
16
|
+
* and has to survive a rebuild months later, so the row keeps a reversible
|
|
17
|
+
* copy alongside the hash.
|
|
18
|
+
* 2. A publishable key is NEVER an `RbacPrincipal` (28 D3). `parseBearerApiKey`
|
|
19
|
+
* gates on the `adm_sk_` prefix, so a token from this table cannot resolve
|
|
20
|
+
* through the rbac plugin at all — which is what makes it inert on every
|
|
21
|
+
* other route BY CONSTRUCTION rather than by an allow-list somebody has to
|
|
22
|
+
* maintain. Sharing a table would invite exactly the `kind`-check-per-route
|
|
23
|
+
* that property exists to avoid.
|
|
24
|
+
*
|
|
25
|
+
* NO SETTINGS TABLE HERE, deliberately (28 D20). Tenant configuration is
|
|
26
|
+
* hybrid: the only key Adminium must own is the `timezone` it needs to
|
|
27
|
+
* interpret its own `timestamptz` values, and that rides on the SCOPE document
|
|
28
|
+
* below — already per-connection, already operator-authored, already served on
|
|
29
|
+
* `/public/config`. A global settings key would be one line cheaper and wrong
|
|
30
|
+
* the moment an instance holds two connections for businesses in different
|
|
31
|
+
* zones. Everything else an app needs (tax rates, tip presets, opening hours)
|
|
32
|
+
* stays in the app's own tables, where the generated dashboard edits it for
|
|
33
|
+
* free.
|
|
34
|
+
*
|
|
35
|
+
* `0013_connection_last_error_hint` is the latest applied migration; never edit
|
|
36
|
+
* a shipped one (the one-time checksum exception in `index.ts` was pre-release).
|
|
37
|
+
*/
|
|
38
|
+
import { metaTable } from '../prefix.js';
|
|
39
|
+
export async function up(db, c) {
|
|
40
|
+
/*
|
|
41
|
+
* The scope document. One row per (connection, side) the operator publishes.
|
|
42
|
+
*
|
|
43
|
+
* `document` is the compiled-from JSON: resources, their logical refs, the
|
|
44
|
+
* `expose` column allow-list, `filterable`/`searchable`/`orderable`, the
|
|
45
|
+
* mandatory `where` predicate, and the claim strategy. It is validated by
|
|
46
|
+
* `compileScope` on every write and on every boot — never trusted from disk.
|
|
47
|
+
*
|
|
48
|
+
* `timezone` is a COLUMN rather than a field inside `document` because it is
|
|
49
|
+
* the one datum the SERIALIZER needs, not the caller: a reader has to reach it
|
|
50
|
+
* without parsing and validating the whole document first.
|
|
51
|
+
*
|
|
52
|
+
* `proposed_from_manifest` records whether this row was seeded from a
|
|
53
|
+
* manifest's `publicApi.propose` block (O2 option b) or authored from scratch
|
|
54
|
+
* in Studio (option c). It exists so widening past a publisher's proposal can
|
|
55
|
+
* be audited, and it is nullable because option (c) is unblocked today and
|
|
56
|
+
* option (b) is not yet ruled.
|
|
57
|
+
*/
|
|
58
|
+
await db.schema
|
|
59
|
+
.createTable(metaTable('public_scopes'))
|
|
60
|
+
.ifNotExists()
|
|
61
|
+
.addColumn('id', c.id, (col) => col.primaryKey())
|
|
62
|
+
.addColumn('connection_id', c.id, (col) => col.notNull())
|
|
63
|
+
.addColumn('side', c.str(16), (col) => col.notNull())
|
|
64
|
+
.addColumn('name', c.str(80), (col) => col.notNull())
|
|
65
|
+
/** IANA zone, e.g. `Europe/London`. Required — see 28 D20. */
|
|
66
|
+
.addColumn('timezone', c.str(64), (col) => col.notNull())
|
|
67
|
+
.addColumn('document', c.json, (col) => col.notNull())
|
|
68
|
+
.addColumn('proposed_from_manifest', c.str(80))
|
|
69
|
+
.addColumn('created_by', c.id)
|
|
70
|
+
.addColumn('created_at', c.ts, (col) => col.notNull())
|
|
71
|
+
.addColumn('updated_at', c.ts, (col) => col.notNull())
|
|
72
|
+
.addForeignKeyConstraint('fk_adminium_public_scopes_connection', ['connection_id'], metaTable('connections'), ['id'], (cb) => cb.onDelete('cascade'))
|
|
73
|
+
.addForeignKeyConstraint('fk_adminium_public_scopes_created_by', ['created_by'], metaTable('users'), ['id'], (cb) => cb.onDelete('set null'))
|
|
74
|
+
.execute();
|
|
75
|
+
await db.schema
|
|
76
|
+
.createIndex('ix_adminium_public_scopes_connection')
|
|
77
|
+
.on(metaTable('public_scopes'))
|
|
78
|
+
.columns(['connection_id'])
|
|
79
|
+
.execute();
|
|
80
|
+
/*
|
|
81
|
+
* The publishable key.
|
|
82
|
+
*
|
|
83
|
+
* `token_hash` is what a request is verified against. `token_encrypted` is the
|
|
84
|
+
* reversible copy that makes the secret re-readable (see the header) — it uses
|
|
85
|
+
* the same `dsnCryptoFromSecret` envelope as connection DSNs, so it is
|
|
86
|
+
* unreadable without `ADMINIUM_SECRET` and it never leaves the server except
|
|
87
|
+
* through an authenticated reveal.
|
|
88
|
+
*
|
|
89
|
+
* `origins` is a JSON array narrowing the instance-wide
|
|
90
|
+
* `ADMINIUM_PUBLIC_API_ORIGINS` allow-list for this one key. Empty array means
|
|
91
|
+
* "no narrowing" — it does NOT mean "any origin", because the env var is
|
|
92
|
+
* always the outer bound.
|
|
93
|
+
*
|
|
94
|
+
* `scope_id` is `restrict` on delete, not `cascade`: deleting a scope out from
|
|
95
|
+
* under a live key would silently turn a working public surface into a 500,
|
|
96
|
+
* so the operator has to revoke the key first and see what they are breaking.
|
|
97
|
+
*/
|
|
98
|
+
await db.schema
|
|
99
|
+
.createTable(metaTable('public_keys'))
|
|
100
|
+
.ifNotExists()
|
|
101
|
+
.addColumn('id', c.id, (col) => col.primaryKey())
|
|
102
|
+
.addColumn('name', c.str(80), (col) => col.notNull())
|
|
103
|
+
/** Display fragment, e.g. `adm_pub_4f2a91cd`. */
|
|
104
|
+
.addColumn('prefix', c.str(32), (col) => col.notNull())
|
|
105
|
+
.addColumn('token_hash', c.str(128), (col) => col.notNull())
|
|
106
|
+
.addColumn('token_encrypted', c.text, (col) => col.notNull())
|
|
107
|
+
.addColumn('scope_id', c.id, (col) => col.notNull())
|
|
108
|
+
.addColumn('side', c.str(16), (col) => col.notNull())
|
|
109
|
+
.addColumn('origins', c.json, (col) => col.notNull())
|
|
110
|
+
.addColumn('expires_at', c.ts)
|
|
111
|
+
.addColumn('revoked_at', c.ts)
|
|
112
|
+
.addColumn('last_used_at', c.ts)
|
|
113
|
+
.addColumn('created_by', c.id)
|
|
114
|
+
.addColumn('created_at', c.ts, (col) => col.notNull())
|
|
115
|
+
.addColumn('updated_at', c.ts, (col) => col.notNull())
|
|
116
|
+
.addForeignKeyConstraint('fk_adminium_public_keys_scope', ['scope_id'], metaTable('public_scopes'), ['id'], (cb) => cb.onDelete('restrict'))
|
|
117
|
+
.addForeignKeyConstraint('fk_adminium_public_keys_created_by', ['created_by'], metaTable('users'), ['id'], (cb) => cb.onDelete('set null'))
|
|
118
|
+
.execute();
|
|
119
|
+
/* Lookup is by prefix on every public request — the hot path of this wave. */
|
|
120
|
+
await db.schema
|
|
121
|
+
.createIndex('ix_adminium_public_keys_prefix')
|
|
122
|
+
.on(metaTable('public_keys'))
|
|
123
|
+
.columns(['prefix'])
|
|
124
|
+
.execute();
|
|
125
|
+
/*
|
|
126
|
+
* The end-customer session minted by `POST /public/claim` (28 §3.4).
|
|
127
|
+
*
|
|
128
|
+
* `grants` is the resolved claim — the mandatory predicate later requests are
|
|
129
|
+
* filtered by, e.g. "patient_id = 41". It is stored RESOLVED rather than
|
|
130
|
+
* re-derived per request so that editing a scope cannot retroactively widen a
|
|
131
|
+
* session that is already in someone's browser.
|
|
132
|
+
*
|
|
133
|
+
* There is no `user_id`. An end customer is deliberately NOT an
|
|
134
|
+
* `adminium_users` row (28 §3.4) — Adminium grows no second identity system,
|
|
135
|
+
* and this table is the whole of what a claimed customer is.
|
|
136
|
+
*/
|
|
137
|
+
await db.schema
|
|
138
|
+
.createTable(metaTable('public_sessions'))
|
|
139
|
+
.ifNotExists()
|
|
140
|
+
.addColumn('id', c.id, (col) => col.primaryKey())
|
|
141
|
+
.addColumn('key_id', c.id, (col) => col.notNull())
|
|
142
|
+
.addColumn('token_hash', c.str(128), (col) => col.notNull())
|
|
143
|
+
.addColumn('grants', c.json, (col) => col.notNull())
|
|
144
|
+
.addColumn('expires_at', c.ts, (col) => col.notNull())
|
|
145
|
+
.addColumn('created_at', c.ts, (col) => col.notNull())
|
|
146
|
+
.addColumn('last_seen_at', c.ts)
|
|
147
|
+
.addForeignKeyConstraint('fk_adminium_public_sessions_key', ['key_id'], metaTable('public_keys'), ['id'], (cb) => cb.onDelete('cascade'))
|
|
148
|
+
.execute();
|
|
149
|
+
await db.schema
|
|
150
|
+
.createIndex('ix_adminium_public_sessions_token_hash')
|
|
151
|
+
.on(metaTable('public_sessions'))
|
|
152
|
+
.columns(['token_hash'])
|
|
153
|
+
.execute();
|
|
154
|
+
/*
|
|
155
|
+
* One-time challenges for the `email-code` claim tier (28 D11/D17).
|
|
156
|
+
*
|
|
157
|
+
* `attempts` is on the row rather than in a counter elsewhere because the
|
|
158
|
+
* containment property this tier is bought for — a low-entropy code is only
|
|
159
|
+
* safe if guesses are bounded — has to survive a process restart, and the
|
|
160
|
+
* rate limiter is an in-process `Map` that does not.
|
|
161
|
+
*
|
|
162
|
+
* `destination_hash` rather than the address itself: a challenge table is a
|
|
163
|
+
* list of customer email addresses otherwise, which is a needless standing
|
|
164
|
+
* disclosure for a row whose whole life is five minutes.
|
|
165
|
+
*/
|
|
166
|
+
await db.schema
|
|
167
|
+
.createTable(metaTable('public_challenges'))
|
|
168
|
+
.ifNotExists()
|
|
169
|
+
.addColumn('id', c.id, (col) => col.primaryKey())
|
|
170
|
+
.addColumn('key_id', c.id, (col) => col.notNull())
|
|
171
|
+
.addColumn('ref', c.str(64), (col) => col.notNull())
|
|
172
|
+
.addColumn('destination_hash', c.str(128), (col) => col.notNull())
|
|
173
|
+
.addColumn('code_hash', c.str(128), (col) => col.notNull())
|
|
174
|
+
.addColumn('attempts', c.int, (col) => col.notNull().defaultTo(0))
|
|
175
|
+
.addColumn('consumed_at', c.ts)
|
|
176
|
+
.addColumn('expires_at', c.ts, (col) => col.notNull())
|
|
177
|
+
.addColumn('created_at', c.ts, (col) => col.notNull())
|
|
178
|
+
.addForeignKeyConstraint('fk_adminium_public_challenges_key', ['key_id'], metaTable('public_keys'), ['id'], (cb) => cb.onDelete('cascade'))
|
|
179
|
+
.execute();
|
|
180
|
+
await db.schema
|
|
181
|
+
.createIndex('ix_adminium_public_challenges_key_ref')
|
|
182
|
+
.on(metaTable('public_challenges'))
|
|
183
|
+
.columns(['key_id', 'ref'])
|
|
184
|
+
.execute();
|
|
185
|
+
}
|
|
186
|
+
//# sourceMappingURL=0014_public_surface.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"0014_public_surface.js","sourceRoot":"","sources":["../../src/migrations/0014_public_surface.ts"],"names":[],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/migrations/index.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/migrations/index.ts"],"names":[],"mappings":"AACA;;;;;;;;;;;;;;;;;;;GAmBG;AAEH,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,QAAQ,CAAC;AAErC,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,eAAe,CAAC;AAgBnD,MAAM,WAAW,aAAa;IAC5B,uDAAuD;IACvD,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,EAAE,EAAE,CAAC,EAAE,EAAE,MAAM,CAAC,OAAO,CAAC,EAAE,CAAC,EAAE,aAAa,KAAK,OAAO,CAAC,IAAI,CAAC,CAAC;CACvE;AAED,eAAO,MAAM,cAAc,EAAE,SAAS,aAAa,EAelD,CAAC"}
|
package/dist/migrations/index.js
CHANGED
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
// SPDX-License-Identifier: AGPL-3.0-only
|
|
1
2
|
/**
|
|
2
3
|
* Ordered, append-only migration list (07-meta-store.md §4). Up-only: a
|
|
3
4
|
* mistake ships as a new compensating migration; an applied migration is never
|
|
@@ -30,6 +31,8 @@ import { up as up0009 } from './0009_views_kind.js';
|
|
|
30
31
|
import { up as up0010 } from './0010_llm_prompt_version_width.js';
|
|
31
32
|
import { up as up0011 } from './0011_i18n_runtime.js';
|
|
32
33
|
import { up as up0012 } from './0012_locale_width.js';
|
|
34
|
+
import { up as up0013 } from './0013_connection_last_error_hint.js';
|
|
35
|
+
import { up as up0014 } from './0014_public_surface.js';
|
|
33
36
|
export const ALL_MIGRATIONS = [
|
|
34
37
|
{ name: '0001_core_auth', up: up0001 },
|
|
35
38
|
{ name: '0002_rbac', up: up0002 },
|
|
@@ -43,5 +46,7 @@ export const ALL_MIGRATIONS = [
|
|
|
43
46
|
{ name: '0010_llm_prompt_version_width', up: up0010 },
|
|
44
47
|
{ name: '0011_i18n_runtime', up: up0011 },
|
|
45
48
|
{ name: '0012_locale_width', up: up0012 },
|
|
49
|
+
{ name: '0013_connection_last_error_hint', up: up0013 },
|
|
50
|
+
{ name: '0014_public_surface', up: up0014 },
|
|
46
51
|
];
|
|
47
52
|
//# sourceMappingURL=index.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/migrations/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;GAmBG;AAKH,OAAO,EAAE,EAAE,IAAI,MAAM,EAAE,MAAM,qBAAqB,CAAC;AACnD,OAAO,EAAE,EAAE,IAAI,MAAM,EAAE,MAAM,gBAAgB,CAAC;AAC9C,OAAO,EAAE,EAAE,IAAI,MAAM,EAAE,MAAM,8BAA8B,CAAC;AAC5D,OAAO,EAAE,EAAE,IAAI,MAAM,EAAE,MAAM,uBAAuB,CAAC;AACrD,OAAO,EAAE,EAAE,IAAI,MAAM,EAAE,MAAM,eAAe,CAAC;AAC7C,OAAO,EAAE,EAAE,IAAI,MAAM,EAAE,MAAM,oBAAoB,CAAC;AAClD,OAAO,EAAE,EAAE,IAAI,MAAM,EAAE,MAAM,oBAAoB,CAAC;AAClD,OAAO,EAAE,EAAE,IAAI,MAAM,EAAE,MAAM,yBAAyB,CAAC;AACvD,OAAO,EAAE,EAAE,IAAI,MAAM,EAAE,MAAM,sBAAsB,CAAC;AACpD,OAAO,EAAE,EAAE,IAAI,MAAM,EAAE,MAAM,oCAAoC,CAAC;AAClE,OAAO,EAAE,EAAE,IAAI,MAAM,EAAE,MAAM,wBAAwB,CAAC;AACtD,OAAO,EAAE,EAAE,IAAI,MAAM,EAAE,MAAM,wBAAwB,CAAC;
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/migrations/index.ts"],"names":[],"mappings":"AAAA,yCAAyC;AACzC;;;;;;;;;;;;;;;;;;;GAmBG;AAKH,OAAO,EAAE,EAAE,IAAI,MAAM,EAAE,MAAM,qBAAqB,CAAC;AACnD,OAAO,EAAE,EAAE,IAAI,MAAM,EAAE,MAAM,gBAAgB,CAAC;AAC9C,OAAO,EAAE,EAAE,IAAI,MAAM,EAAE,MAAM,8BAA8B,CAAC;AAC5D,OAAO,EAAE,EAAE,IAAI,MAAM,EAAE,MAAM,uBAAuB,CAAC;AACrD,OAAO,EAAE,EAAE,IAAI,MAAM,EAAE,MAAM,eAAe,CAAC;AAC7C,OAAO,EAAE,EAAE,IAAI,MAAM,EAAE,MAAM,oBAAoB,CAAC;AAClD,OAAO,EAAE,EAAE,IAAI,MAAM,EAAE,MAAM,oBAAoB,CAAC;AAClD,OAAO,EAAE,EAAE,IAAI,MAAM,EAAE,MAAM,yBAAyB,CAAC;AACvD,OAAO,EAAE,EAAE,IAAI,MAAM,EAAE,MAAM,sBAAsB,CAAC;AACpD,OAAO,EAAE,EAAE,IAAI,MAAM,EAAE,MAAM,oCAAoC,CAAC;AAClE,OAAO,EAAE,EAAE,IAAI,MAAM,EAAE,MAAM,wBAAwB,CAAC;AACtD,OAAO,EAAE,EAAE,IAAI,MAAM,EAAE,MAAM,wBAAwB,CAAC;AACtD,OAAO,EAAE,EAAE,IAAI,MAAM,EAAE,MAAM,sCAAsC,CAAC;AACpE,OAAO,EAAE,EAAE,IAAI,MAAM,EAAE,MAAM,0BAA0B,CAAC;AAQxD,MAAM,CAAC,MAAM,cAAc,GAA6B;IACtD,EAAE,IAAI,EAAE,gBAAgB,EAAE,EAAE,EAAE,MAAM,EAAE;IACtC,EAAE,IAAI,EAAE,WAAW,EAAE,EAAE,EAAE,MAAM,EAAE;IACjC,EAAE,IAAI,EAAE,yBAAyB,EAAE,EAAE,EAAE,MAAM,EAAE;IAC/C,EAAE,IAAI,EAAE,kBAAkB,EAAE,EAAE,EAAE,MAAM,EAAE;IACxC,EAAE,IAAI,EAAE,UAAU,EAAE,EAAE,EAAE,MAAM,EAAE;IAChC,EAAE,IAAI,EAAE,eAAe,EAAE,EAAE,EAAE,MAAM,EAAE;IACrC,EAAE,IAAI,EAAE,eAAe,EAAE,EAAE,EAAE,MAAM,EAAE;IACrC,EAAE,IAAI,EAAE,oBAAoB,EAAE,EAAE,EAAE,MAAM,EAAE;IAC1C,EAAE,IAAI,EAAE,iBAAiB,EAAE,EAAE,EAAE,MAAM,EAAE;IACvC,EAAE,IAAI,EAAE,+BAA+B,EAAE,EAAE,EAAE,MAAM,EAAE;IACrD,EAAE,IAAI,EAAE,mBAAmB,EAAE,EAAE,EAAE,MAAM,EAAE;IACzC,EAAE,IAAI,EAAE,mBAAmB,EAAE,EAAE,EAAE,MAAM,EAAE;IACzC,EAAE,IAAI,EAAE,iCAAiC,EAAE,EAAE,EAAE,MAAM,EAAE;IACvD,EAAE,IAAI,EAAE,qBAAqB,EAAE,EAAE,EAAE,MAAM,EAAE;CAC5C,CAAC"}
|
package/dist/migrator.d.ts
CHANGED
|
@@ -12,9 +12,12 @@
|
|
|
12
12
|
* - Transactional per migration on PostgreSQL/SQLite (transactional DDL); on
|
|
13
13
|
* MySQL the ledger row is written immediately after the last statement and
|
|
14
14
|
* every DDL statement is individually re-runnable (ifNotExists guards).
|
|
15
|
+
* - Serialized across processes by a per-dialect advisory lock (migrate-lock.ts)
|
|
16
|
+
* so two replicas booting together cannot both enter the pending set.
|
|
15
17
|
*/
|
|
16
18
|
import { type Kysely } from 'kysely';
|
|
17
19
|
import { type MetaDialect } from './columns.js';
|
|
20
|
+
import { type MigrationLockOptions } from './migrate-lock.js';
|
|
18
21
|
import { type MetaMigration } from './migrations/index.js';
|
|
19
22
|
import type { MetaDB } from './schema/tables.js';
|
|
20
23
|
/**
|
|
@@ -55,6 +58,17 @@ export interface MigratorOptions {
|
|
|
55
58
|
version?: string;
|
|
56
59
|
/** Clock override — tests only. */
|
|
57
60
|
now?: () => number;
|
|
61
|
+
/**
|
|
62
|
+
* Advisory-lock settings for the pass, or `false` to run unlocked — for a
|
|
63
|
+
* caller that already holds the lock, or a test that wants the raw runner.
|
|
64
|
+
*/
|
|
65
|
+
lock?: Omit<MigrationLockOptions, 'dialect'> | false;
|
|
66
|
+
/**
|
|
67
|
+
* Set when `db` is already inside a transaction the caller opened (the
|
|
68
|
+
* SQLite lock is). Suppresses the per-migration transaction: SQLite has no
|
|
69
|
+
* nested `BEGIN`, and the pass is already atomic as a whole.
|
|
70
|
+
*/
|
|
71
|
+
inTransaction?: boolean;
|
|
58
72
|
}
|
|
59
73
|
export interface ApplyResult {
|
|
60
74
|
/** Names applied by this call, in order (empty ⇒ already up to date). */
|
|
@@ -73,9 +87,14 @@ export interface MigrationStatusEntry {
|
|
|
73
87
|
export declare function enableSqliteForeignKeys(db: Kysely<MetaDB>): Promise<void>;
|
|
74
88
|
/**
|
|
75
89
|
* Apply all pending migrations, in order. Idempotent: already-applied
|
|
76
|
-
* migrations are skipped via the ledger
|
|
77
|
-
*
|
|
78
|
-
*
|
|
90
|
+
* migrations are skipped via the ledger.
|
|
91
|
+
*
|
|
92
|
+
* Concurrent runners are serialized by the advisory lock (migrate-lock.ts),
|
|
93
|
+
* held on one pinned connection for the whole pass — the ledger PK alone only
|
|
94
|
+
* defends PostgreSQL/SQLite, where it shares a transaction with the DDL, and
|
|
95
|
+
* MySQL is exactly the dialect where it does not. Pass `lock: false` to opt
|
|
96
|
+
* out; a lock wait is bounded and fails with {@link MigrationLockTimeoutError}
|
|
97
|
+
* rather than hanging a container boot.
|
|
79
98
|
*/
|
|
80
99
|
export declare function applyMigrations(db: Kysely<MetaDB>, options: MigratorOptions): Promise<ApplyResult>;
|
|
81
100
|
/** Ledger vs file status for `adminium migrate --status`. */
|
package/dist/migrator.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"migrator.d.ts","sourceRoot":"","sources":["../src/migrator.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"migrator.d.ts","sourceRoot":"","sources":["../src/migrator.ts"],"names":[],"mappings":"AACA;;;;;;;;;;;;;;;;GAgBG;AAKH,OAAO,EAAO,KAAK,MAAM,EAAE,MAAM,QAAQ,CAAC;AAE1C,OAAO,EAAiB,KAAK,WAAW,EAAE,MAAM,cAAc,CAAC;AAC/D,OAAO,EAAqB,KAAK,oBAAoB,EAAE,MAAM,mBAAmB,CAAC;AACjF,OAAO,EAAkB,KAAK,aAAa,EAAE,MAAM,uBAAuB,CAAC;AAC3E,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,oBAAoB,CAAC;AAEjD;;;;;;;;;;GAUG;AACH,eAAO,MAAM,oBAAoB,EAAE,MAI1B,CAAC;AAIV,qBAAa,2BAA4B,SAAQ,KAAK;IAExC,QAAQ,CAAC,aAAa,EAAE,MAAM;IADjC,IAAI,SAAiC;gBACzB,aAAa,EAAE,MAAM;CAM3C;AAED,qBAAa,qBAAsB,SAAQ,KAAK;IAElC,QAAQ,CAAC,aAAa,EAAE,MAAM;IADjC,IAAI,SAA2B;gBACnB,aAAa,EAAE,MAAM;CAM3C;AAED,qBAAa,mBAAoB,SAAQ,KAAK;IACnC,IAAI,SAAyB;CACvC;AAED;;;GAGG;AACH,wBAAgB,iBAAiB,CAAC,SAAS,EAAE,aAAa,GAAG,MAAM,CAElE;AAED,MAAM,WAAW,eAAe;IAC9B,OAAO,EAAE,WAAW,CAAC;IACrB,+CAA+C;IAC/C,UAAU,CAAC,EAAE,SAAS,aAAa,EAAE,CAAC;IACtC,iFAAiF;IACjF,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,mCAAmC;IACnC,GAAG,CAAC,EAAE,MAAM,MAAM,CAAC;IACnB;;;OAGG;IACH,IAAI,CAAC,EAAE,IAAI,CAAC,oBAAoB,EAAE,SAAS,CAAC,GAAG,KAAK,CAAC;IACrD;;;;OAIG;IACH,aAAa,CAAC,EAAE,OAAO,CAAC;CACzB;AAED,MAAM,WAAW,WAAW;IAC1B,yEAAyE;IACzE,OAAO,EAAE,MAAM,EAAE,CAAC;CACnB;AAED,MAAM,WAAW,oBAAoB;IACnC,IAAI,EAAE,MAAM,CAAC;IACb,OAAO,EAAE,OAAO,CAAC;IACjB,SAAS,EAAE,MAAM,GAAG,IAAI,CAAC;IACzB,gEAAgE;IAChE,KAAK,EAAE,OAAO,CAAC;IACf,iEAAiE;IACjE,KAAK,EAAE,OAAO,CAAC;CAChB;AA6BD,wFAAwF;AACxF,wBAAsB,uBAAuB,CAAC,EAAE,EAAE,MAAM,CAAC,MAAM,CAAC,GAAG,OAAO,CAAC,IAAI,CAAC,CAE/E;AAsBD;;;;;;;;;;GAUG;AACH,wBAAsB,eAAe,CAAC,EAAE,EAAE,MAAM,CAAC,MAAM,CAAC,EAAE,OAAO,EAAE,eAAe,GAAG,OAAO,CAAC,WAAW,CAAC,CASxG;AAkDD,6DAA6D;AAC7D,wBAAsB,eAAe,CACnC,EAAE,EAAE,MAAM,CAAC,MAAM,CAAC,EAClB,OAAO,EAAE,eAAe,GACvB,OAAO,CAAC,oBAAoB,EAAE,CAAC,CAuBjC"}
|
package/dist/migrator.js
CHANGED
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
// SPDX-License-Identifier: AGPL-3.0-only
|
|
1
2
|
/**
|
|
2
3
|
* Adminium-owned migration runner (07-meta-store.md §4).
|
|
3
4
|
*
|
|
@@ -12,11 +13,14 @@
|
|
|
12
13
|
* - Transactional per migration on PostgreSQL/SQLite (transactional DDL); on
|
|
13
14
|
* MySQL the ledger row is written immediately after the last statement and
|
|
14
15
|
* every DDL statement is individually re-runnable (ifNotExists guards).
|
|
16
|
+
* - Serialized across processes by a per-dialect advisory lock (migrate-lock.ts)
|
|
17
|
+
* so two replicas booting together cannot both enter the pending set.
|
|
15
18
|
*/
|
|
16
19
|
import { createHash } from 'node:crypto';
|
|
17
20
|
import { readFileSync } from 'node:fs';
|
|
18
21
|
import { sql } from 'kysely';
|
|
19
22
|
import { columnHelpers } from './columns.js';
|
|
23
|
+
import { withMigrationLock } from './migrate-lock.js';
|
|
20
24
|
import { ALL_MIGRATIONS } from './migrations/index.js';
|
|
21
25
|
/**
|
|
22
26
|
* Package version recorded in the ledger, read from package.json at module
|
|
@@ -104,15 +108,30 @@ async function readAndValidateLedger(db, migrations) {
|
|
|
104
108
|
}
|
|
105
109
|
/**
|
|
106
110
|
* Apply all pending migrations, in order. Idempotent: already-applied
|
|
107
|
-
* migrations are skipped via the ledger
|
|
108
|
-
*
|
|
109
|
-
*
|
|
111
|
+
* migrations are skipped via the ledger.
|
|
112
|
+
*
|
|
113
|
+
* Concurrent runners are serialized by the advisory lock (migrate-lock.ts),
|
|
114
|
+
* held on one pinned connection for the whole pass — the ledger PK alone only
|
|
115
|
+
* defends PostgreSQL/SQLite, where it shares a transaction with the DDL, and
|
|
116
|
+
* MySQL is exactly the dialect where it does not. Pass `lock: false` to opt
|
|
117
|
+
* out; a lock wait is bounded and fails with {@link MigrationLockTimeoutError}
|
|
118
|
+
* rather than hanging a container boot.
|
|
110
119
|
*/
|
|
111
120
|
export async function applyMigrations(db, options) {
|
|
121
|
+
// `db.connection()` cannot pin anything on a handle that is already a
|
|
122
|
+
// transaction, and an outer transaction is itself a serialization point.
|
|
123
|
+
if (options.lock === false || options.inTransaction === true || db.isTransaction) {
|
|
124
|
+
return applyMigrationsUnlocked(db, options);
|
|
125
|
+
}
|
|
126
|
+
return withMigrationLock(db, { dialect: options.dialect, ...options.lock }, (locked, ctx) => applyMigrationsUnlocked(locked, { ...options, lock: false, inTransaction: ctx.inTransaction }));
|
|
127
|
+
}
|
|
128
|
+
async function applyMigrationsUnlocked(db, options) {
|
|
112
129
|
const migrations = orderedMigrations(options.migrations ?? ALL_MIGRATIONS);
|
|
113
130
|
const now = options.now ?? Date.now;
|
|
114
131
|
const version = options.version ?? META_PACKAGE_VERSION;
|
|
115
132
|
const dialect = options.dialect;
|
|
133
|
+
// Kept for unlocked callers: inside the SQLite lock's transaction the pragma
|
|
134
|
+
// is a no-op, which is why the lock runs it before its BEGIN (migrate-lock.ts).
|
|
116
135
|
if (dialect === 'sqlite')
|
|
117
136
|
await enableSqliteForeignKeys(db);
|
|
118
137
|
await ensureLedger(db, dialect);
|
|
@@ -130,9 +149,11 @@ export async function applyMigrations(db, options) {
|
|
|
130
149
|
durationMs: Math.max(0, now() - startedAt),
|
|
131
150
|
adminiumVersion: version,
|
|
132
151
|
});
|
|
133
|
-
if (dialect === 'mysql') {
|
|
134
|
-
//
|
|
135
|
-
// (ifNotExists)
|
|
152
|
+
if (dialect === 'mysql' || options.inTransaction === true) {
|
|
153
|
+
// MySQL: no transactional DDL, so statements are individually re-runnable
|
|
154
|
+
// (ifNotExists) and the ledger row lands right after the last one.
|
|
155
|
+
// `inTransaction`: the caller already opened one (the SQLite lock does),
|
|
156
|
+
// and SQLite has no nested BEGIN.
|
|
136
157
|
await migration.up(db, c);
|
|
137
158
|
await db.insertInto(LEDGER).values(ledgerRow()).execute();
|
|
138
159
|
}
|
package/dist/migrator.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"migrator.js","sourceRoot":"","sources":["../src/migrator.ts"],"names":[],"mappings":"AAAA
|
|
1
|
+
{"version":3,"file":"migrator.js","sourceRoot":"","sources":["../src/migrator.ts"],"names":[],"mappings":"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"}
|
package/dist/prefix.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"prefix.d.ts","sourceRoot":"","sources":["../src/prefix.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"prefix.d.ts","sourceRoot":"","sources":["../src/prefix.ts"],"names":[],"mappings":"AACA;;;;;GAKG;AAEH,eAAO,MAAM,WAAW,cAAc,CAAC;AAEvC,qBAAa,eAAgB,SAAQ,KAAK;IAC/B,IAAI,SAAqB;CACnC;AAED;;;;GAIG;AACH,wBAAgB,SAAS,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,CAU9C;AAED,kFAAkF;AAClF,wBAAgB,eAAe,CAAC,IAAI,EAAE,MAAM,GAAG,IAAI,CAIlD"}
|
package/dist/prefix.js
CHANGED
package/dist/prefix.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"prefix.js","sourceRoot":"","sources":["../src/prefix.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH,MAAM,CAAC,MAAM,WAAW,GAAG,WAAW,CAAC;AAEvC,MAAM,OAAO,eAAgB,SAAQ,KAAK;IAC/B,IAAI,GAAG,iBAAiB,CAAC;CACnC;AAED;;;;GAIG;AACH,MAAM,UAAU,SAAS,CAAC,IAAY;IACpC,IAAI,CAAC,mBAAmB,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC;QACpC,MAAM,IAAI,eAAe,CAAC,4BAA4B,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;IAChF,CAAC;IACD,IAAI,IAAI,CAAC,UAAU,CAAC,WAAW,CAAC,EAAE,CAAC;QACjC,MAAM,IAAI,eAAe,CAAC,gCAAgC,IAAI,EAAE,CAAC,CAAC;IACpE,CAAC;IACD,MAAM,IAAI,GAAG,GAAG,WAAW,GAAG,IAAI,EAAE,CAAC;IACrC,eAAe,CAAC,IAAI,CAAC,CAAC;IACtB,OAAO,IAAI,CAAC;AACd,CAAC;AAED,kFAAkF;AAClF,MAAM,UAAU,eAAe,CAAC,IAAY;IAC1C,IAAI,CAAC,IAAI,CAAC,UAAU,CAAC,WAAW,CAAC,EAAE,CAAC;QAClC,MAAM,IAAI,eAAe,CAAC,yCAAyC,IAAI,EAAE,CAAC,CAAC;IAC7E,CAAC;AACH,CAAC"}
|
|
1
|
+
{"version":3,"file":"prefix.js","sourceRoot":"","sources":["../src/prefix.ts"],"names":[],"mappings":"AAAA,yCAAyC;AACzC;;;;;GAKG;AAEH,MAAM,CAAC,MAAM,WAAW,GAAG,WAAW,CAAC;AAEvC,MAAM,OAAO,eAAgB,SAAQ,KAAK;IAC/B,IAAI,GAAG,iBAAiB,CAAC;CACnC;AAED;;;;GAIG;AACH,MAAM,UAAU,SAAS,CAAC,IAAY;IACpC,IAAI,CAAC,mBAAmB,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC;QACpC,MAAM,IAAI,eAAe,CAAC,4BAA4B,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;IAChF,CAAC;IACD,IAAI,IAAI,CAAC,UAAU,CAAC,WAAW,CAAC,EAAE,CAAC;QACjC,MAAM,IAAI,eAAe,CAAC,gCAAgC,IAAI,EAAE,CAAC,CAAC;IACpE,CAAC;IACD,MAAM,IAAI,GAAG,GAAG,WAAW,GAAG,IAAI,EAAE,CAAC;IACrC,eAAe,CAAC,IAAI,CAAC,CAAC;IACtB,OAAO,IAAI,CAAC;AACd,CAAC;AAED,kFAAkF;AAClF,MAAM,UAAU,eAAe,CAAC,IAAY;IAC1C,IAAI,CAAC,IAAI,CAAC,UAAU,CAAC,WAAW,CAAC,EAAE,CAAC;QAClC,MAAM,IAAI,eAAe,CAAC,yCAAyC,IAAI,EAAE,CAAC,CAAC;IAC7E,CAAC;AACH,CAAC"}
|
|
@@ -0,0 +1,118 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Whole-store copy, for moving a meta store from one database to another
|
|
3
|
+
* (07-meta-store.md §1; 01-architecture.md §3.1 meta placement).
|
|
4
|
+
*
|
|
5
|
+
* ── WHY THIS IS NOT `export-zip` / `import-zip` ─────────────────────────────
|
|
6
|
+
* The export bundle carries CONFIGURATION — settings, roles, rolePermissions,
|
|
7
|
+
* connections, snapshots, overrides, pages, views. Eight resources out of the
|
|
8
|
+
* tables in {@link META_TABLE_NAMES}. That is the right content for
|
|
9
|
+
* "replay this instance's setup somewhere else", and exactly the wrong content
|
|
10
|
+
* for "this instance is now living in a different database": it carries no
|
|
11
|
+
* users, no sessions and no user_roles, so a relocation built on it would log
|
|
12
|
+
* the operator out of the wizard they are standing in and strand the instance
|
|
13
|
+
* with no accounts at all. Relocation is a MOVE, not a replay, and a move has
|
|
14
|
+
* to be total.
|
|
15
|
+
*
|
|
16
|
+
* ── DIALECT PORTABILITY, AND WHY COERCION IS DRIVEN BY THE TARGET ───────────
|
|
17
|
+
* `columns.ts` maps one logical type onto three physical ones — `bool` is a
|
|
18
|
+
* postgres `boolean`, a mysql `tinyint(1)` and a sqlite `integer`; `json` is
|
|
19
|
+
* `jsonb`, `json` and `text`. So a value read from one dialect is not always a
|
|
20
|
+
* value the next dialect's driver will accept. SQLite hands back `0`/`1` where
|
|
21
|
+
* postgres wants a boolean, and `pg` hands back a parsed object where
|
|
22
|
+
* better-sqlite3 accepts only numbers, strings, bigints, buffers and null.
|
|
23
|
+
*
|
|
24
|
+
* Some of those mismatches happen to survive on their own — postgres will cast
|
|
25
|
+
* the text `'1'` to `boolean`, so sqlite → postgres appears to work untouched.
|
|
26
|
+
* Relying on that is how a copy engine ends up correct in exactly the direction
|
|
27
|
+
* it was first tested in. The coercion below is therefore driven by what the
|
|
28
|
+
* TARGET's columns actually are, read back with Kysely's introspection, so
|
|
29
|
+
* every direction is handled by the same rule rather than by luck.
|
|
30
|
+
*
|
|
31
|
+
* `ts` columns need no handling at all, which removes the worst class of
|
|
32
|
+
* cross-dialect bug before it starts: §2.1 pins every timestamp to epoch
|
|
33
|
+
* milliseconds in an integer column, so nothing here ever touches a native
|
|
34
|
+
* date.
|
|
35
|
+
*
|
|
36
|
+
* ── ATOMICITY ───────────────────────────────────────────────────────────────
|
|
37
|
+
* The whole copy runs in ONE transaction on the target. A relocation that
|
|
38
|
+
* failed halfway would otherwise leave a half-populated store that the next
|
|
39
|
+
* boot cannot tell from a real one; rolling back means the target is either
|
|
40
|
+
* fully written or untouched, and the caller can keep pointing at the source.
|
|
41
|
+
*/
|
|
42
|
+
import type { MetaDb } from './connect.js';
|
|
43
|
+
/**
|
|
44
|
+
* The migration ledger is never copied. The target builds its own by running
|
|
45
|
+
* the migrations, and that ledger — not the source's — is the honest record of
|
|
46
|
+
* what has been applied to THIS database. Copying the source's on top would at
|
|
47
|
+
* best be a no-op and at worst re-assert checksums for DDL the target reached
|
|
48
|
+
* by a different route.
|
|
49
|
+
*/
|
|
50
|
+
export declare const RELOCATE_SKIP_TABLES: readonly string[];
|
|
51
|
+
/**
|
|
52
|
+
* `name` is typed `string`, not narrowed to the literal, precisely so the
|
|
53
|
+
* subclasses below (and the server's, which extend this across the package
|
|
54
|
+
* boundary) can each declare their own — a literal here makes every `override
|
|
55
|
+
* readonly name` in a subclass a type error.
|
|
56
|
+
*/
|
|
57
|
+
export declare class MetaRelocateError extends Error {
|
|
58
|
+
readonly name: string;
|
|
59
|
+
}
|
|
60
|
+
/** The target already holds Adminium data — refuse rather than merge into it. */
|
|
61
|
+
export declare class MetaStoreNotEmptyError extends MetaRelocateError {
|
|
62
|
+
readonly tables: readonly string[];
|
|
63
|
+
readonly name = "MetaStoreNotEmptyError";
|
|
64
|
+
constructor(tables: readonly string[]);
|
|
65
|
+
}
|
|
66
|
+
/** A table came out the other side with a different number of rows. */
|
|
67
|
+
export declare class MetaCopyVerificationError extends MetaRelocateError {
|
|
68
|
+
readonly table: string;
|
|
69
|
+
readonly expected: number;
|
|
70
|
+
readonly actual: number;
|
|
71
|
+
readonly name = "MetaCopyVerificationError";
|
|
72
|
+
constructor(table: string, expected: number, actual: number);
|
|
73
|
+
}
|
|
74
|
+
/** The tables this copies, in FK-safe insert order. */
|
|
75
|
+
export declare function relocatableTables(): readonly string[];
|
|
76
|
+
/**
|
|
77
|
+
* Kysely's `CamelCasePlugin` maps COLUMN names, so every row this module reads
|
|
78
|
+
* and writes is camelCase — but `introspection.getTables()` reports the
|
|
79
|
+
* PHYSICAL names, which are snake_case. This is that bridge, and it matches the
|
|
80
|
+
* plugin's own default transform: split on underscores, capitalize each
|
|
81
|
+
* subsequent segment.
|
|
82
|
+
*/
|
|
83
|
+
export declare function snakeToCamel(name: string): string;
|
|
84
|
+
/**
|
|
85
|
+
* Row counts for every relocatable table. Used both to size the copy up front
|
|
86
|
+
* and to verify it afterwards.
|
|
87
|
+
*/
|
|
88
|
+
export declare function countMetaRows(meta: MetaDb): Promise<Map<string, number>>;
|
|
89
|
+
/**
|
|
90
|
+
* Throw unless the store holds no Adminium data. Called against the TARGET
|
|
91
|
+
* before anything is written, so "already in use" is a refusal rather than a
|
|
92
|
+
* primary-key collision halfway through the copy.
|
|
93
|
+
*/
|
|
94
|
+
export declare function assertMetaStoreEmpty(meta: MetaDb): Promise<void>;
|
|
95
|
+
export interface CopyMetaStoreOptions {
|
|
96
|
+
from: MetaDb;
|
|
97
|
+
/** Must already be migrated — run `applyMigrations` before calling. */
|
|
98
|
+
to: MetaDb;
|
|
99
|
+
/** Per-table progress, for a CLI spinner or a wizard's status line. */
|
|
100
|
+
onProgress?: ((table: string, rows: number) => void) | undefined;
|
|
101
|
+
}
|
|
102
|
+
export interface CopyMetaStoreResult {
|
|
103
|
+
tables: {
|
|
104
|
+
table: string;
|
|
105
|
+
rows: number;
|
|
106
|
+
}[];
|
|
107
|
+
totalRows: number;
|
|
108
|
+
}
|
|
109
|
+
/**
|
|
110
|
+
* Copy every `adminium_*` table from `from` to `to`, in one transaction.
|
|
111
|
+
*
|
|
112
|
+
* The target must be migrated and empty ({@link assertMetaStoreEmpty}). Insert
|
|
113
|
+
* order is {@link META_TABLE_NAMES}, which is declared in dependency-safe
|
|
114
|
+
* creation order and is therefore also FK-safe for inserts — so this needs no
|
|
115
|
+
* constraint juggling on any of the three dialects.
|
|
116
|
+
*/
|
|
117
|
+
export declare function copyMetaStore(opts: CopyMetaStoreOptions): Promise<CopyMetaStoreResult>;
|
|
118
|
+
//# sourceMappingURL=relocate.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"relocate.d.ts","sourceRoot":"","sources":["../src/relocate.ts"],"names":[],"mappings":"AACA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAwCG;AAIH,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,cAAc,CAAC;AAK3C;;;;;;GAMG;AACH,eAAO,MAAM,oBAAoB,EAAE,SAAS,MAAM,EAA4B,CAAC;AAmB/E;;;;;GAKG;AACH,qBAAa,iBAAkB,SAAQ,KAAK;IAC1C,SAAkB,IAAI,EAAE,MAAM,CAAuB;CACtD;AAED,iFAAiF;AACjF,qBAAa,sBAAuB,SAAQ,iBAAiB;IAE/C,QAAQ,CAAC,MAAM,EAAE,SAAS,MAAM,EAAE;IAD9C,SAAkB,IAAI,4BAA4B;gBAC7B,MAAM,EAAE,SAAS,MAAM,EAAE;CAO/C;AAED,uEAAuE;AACvE,qBAAa,yBAA0B,SAAQ,iBAAiB;IAElD,QAAQ,CAAC,KAAK,EAAE,MAAM;IAAE,QAAQ,CAAC,QAAQ,EAAE,MAAM;IAAE,QAAQ,CAAC,MAAM,EAAE,MAAM;IADtF,SAAkB,IAAI,+BAA+B;gBAChC,KAAK,EAAE,MAAM,EAAW,QAAQ,EAAE,MAAM,EAAW,MAAM,EAAE,MAAM;CAMvF;AAED,uDAAuD;AACvD,wBAAgB,iBAAiB,IAAI,SAAS,MAAM,EAAE,CAErD;AAED;;;;;;GAMG;AACH,wBAAgB,YAAY,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,CAEjD;AA4JD;;;GAGG;AACH,wBAAsB,aAAa,CAAC,IAAI,EAAE,MAAM,GAAG,OAAO,CAAC,GAAG,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC,CAM9E;AAED;;;;GAIG;AACH,wBAAsB,oBAAoB,CAAC,IAAI,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAItE;AAED,MAAM,WAAW,oBAAoB;IACnC,IAAI,EAAE,MAAM,CAAC;IACb,uEAAuE;IACvE,EAAE,EAAE,MAAM,CAAC;IACX,uEAAuE;IACvE,UAAU,CAAC,EAAE,CAAC,CAAC,KAAK,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,KAAK,IAAI,CAAC,GAAG,SAAS,CAAC;CAClE;AAED,MAAM,WAAW,mBAAmB;IAClC,MAAM,EAAE;QAAE,KAAK,EAAE,MAAM,CAAC;QAAC,IAAI,EAAE,MAAM,CAAA;KAAE,EAAE,CAAC;IAC1C,SAAS,EAAE,MAAM,CAAC;CACnB;AAED;;;;;;;GAOG;AACH,wBAAsB,aAAa,CAAC,IAAI,EAAE,oBAAoB,GAAG,OAAO,CAAC,mBAAmB,CAAC,CAyC5F"}
|