kysely 0.12.2 → 0.15.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (156) hide show
  1. package/README.md +115 -31
  2. package/dist/cjs/{introspection → dialect}/database-introspector.d.ts +0 -0
  3. package/dist/cjs/{introspection → dialect}/database-introspector.js +0 -0
  4. package/dist/cjs/dialect/dialect.d.ts +1 -1
  5. package/dist/cjs/dialect/mysql/mysql-adapter.d.ts +2 -2
  6. package/dist/cjs/dialect/mysql/mysql-adapter.js +2 -1
  7. package/dist/cjs/dialect/mysql/mysql-dialect.d.ts +1 -1
  8. package/dist/cjs/dialect/mysql/mysql-introspector.d.ts +1 -1
  9. package/dist/cjs/dialect/mysql/mysql-introspector.js +3 -3
  10. package/dist/cjs/dialect/postgres/postgres-adapter.d.ts +2 -2
  11. package/dist/cjs/dialect/postgres/postgres-adapter.js +2 -1
  12. package/dist/cjs/dialect/postgres/postgres-dialect.d.ts +1 -1
  13. package/dist/cjs/dialect/postgres/postgres-introspector.d.ts +1 -1
  14. package/dist/cjs/dialect/postgres/postgres-introspector.js +3 -3
  15. package/dist/cjs/dialect/sqlite/sqlite-adapter.d.ts +2 -2
  16. package/dist/cjs/dialect/sqlite/sqlite-dialect.d.ts +1 -1
  17. package/dist/cjs/dialect/sqlite/sqlite-introspector.d.ts +1 -1
  18. package/dist/cjs/dialect/sqlite/sqlite-introspector.js +3 -3
  19. package/dist/cjs/index.d.ts +7 -4
  20. package/dist/cjs/index.js +6 -3
  21. package/dist/cjs/kysely.d.ts +8 -40
  22. package/dist/cjs/kysely.js +8 -40
  23. package/dist/cjs/migration/file-migration-provider.d.ts +52 -0
  24. package/dist/cjs/migration/file-migration-provider.js +52 -0
  25. package/dist/cjs/migration/migrator.d.ts +234 -0
  26. package/dist/cjs/migration/migrator.js +417 -0
  27. package/dist/cjs/operation-node/check-constraint-node.d.ts +1 -1
  28. package/dist/cjs/operation-node/check-constraint-node.js +2 -3
  29. package/dist/cjs/operation-node/column-definition-node.d.ts +8 -7
  30. package/dist/cjs/operation-node/column-definition-node.js +0 -4
  31. package/dist/cjs/operation-node/data-type-node.d.ts +1 -1
  32. package/dist/cjs/operation-node/generated-node.d.ts +20 -0
  33. package/dist/cjs/operation-node/generated-node.js +31 -0
  34. package/dist/cjs/operation-node/on-conflict-node.d.ts +13 -2
  35. package/dist/cjs/operation-node/on-conflict-node.js +39 -1
  36. package/dist/cjs/operation-node/operation-node-transformer.d.ts +2 -2
  37. package/dist/cjs/operation-node/operation-node-transformer.js +13 -6
  38. package/dist/cjs/operation-node/operation-node-visitor.d.ts +2 -2
  39. package/dist/cjs/operation-node/operation-node-visitor.js +1 -1
  40. package/dist/cjs/operation-node/operation-node.d.ts +1 -1
  41. package/dist/cjs/parser/insert-values-parser.d.ts +4 -4
  42. package/dist/cjs/parser/insert-values-parser.js +2 -3
  43. package/dist/cjs/parser/reference-parser.d.ts +4 -3
  44. package/dist/cjs/parser/select-parser.d.ts +10 -4
  45. package/dist/cjs/parser/update-set-parser.d.ts +2 -1
  46. package/dist/cjs/plugin/camel-case/camel-case-plugin.d.ts +2 -2
  47. package/dist/cjs/query-builder/delete-query-builder.d.ts +0 -3
  48. package/dist/cjs/query-builder/insert-query-builder.d.ts +78 -94
  49. package/dist/cjs/query-builder/insert-query-builder.js +145 -15
  50. package/dist/cjs/query-builder/on-conflict-builder.d.ts +686 -0
  51. package/dist/cjs/query-builder/on-conflict-builder.js +323 -0
  52. package/dist/cjs/query-builder/returning-interface.d.ts +0 -3
  53. package/dist/cjs/query-builder/update-query-builder.d.ts +0 -3
  54. package/dist/cjs/query-compiler/default-query-compiler.d.ts +2 -2
  55. package/dist/cjs/query-compiler/default-query-compiler.js +37 -8
  56. package/dist/cjs/query-creator.d.ts +0 -2
  57. package/dist/cjs/query-creator.js +0 -2
  58. package/dist/cjs/schema/alter-table-builder.d.ts +41 -9
  59. package/dist/cjs/schema/alter-table-builder.js +45 -9
  60. package/dist/cjs/schema/column-definition-builder.d.ts +40 -8
  61. package/dist/cjs/schema/column-definition-builder.js +21 -8
  62. package/dist/cjs/schema/create-index-builder.d.ts +3 -2
  63. package/dist/cjs/schema/create-index-builder.js +2 -2
  64. package/dist/cjs/schema/create-table-builder.d.ts +3 -2
  65. package/dist/cjs/schema/create-table-builder.js +2 -2
  66. package/dist/cjs/util/column-type.d.ts +165 -0
  67. package/dist/cjs/util/column-type.js +2 -0
  68. package/dist/cjs/util/private-symbols.d.ts +5 -0
  69. package/dist/cjs/util/private-symbols.js +8 -0
  70. package/dist/cjs/util/type-utils.d.ts +6 -42
  71. package/dist/esm/{introspection → dialect}/database-introspector.d.ts +0 -0
  72. package/dist/esm/{introspection → dialect}/database-introspector.js +0 -0
  73. package/dist/esm/dialect/dialect.d.ts +1 -1
  74. package/dist/esm/dialect/mysql/mysql-adapter.d.ts +2 -2
  75. package/dist/esm/dialect/mysql/mysql-adapter.js +2 -1
  76. package/dist/esm/dialect/mysql/mysql-dialect.d.ts +1 -1
  77. package/dist/esm/dialect/mysql/mysql-introspector.d.ts +1 -1
  78. package/dist/esm/dialect/mysql/mysql-introspector.js +1 -1
  79. package/dist/esm/dialect/postgres/postgres-adapter.d.ts +2 -2
  80. package/dist/esm/dialect/postgres/postgres-adapter.js +2 -1
  81. package/dist/esm/dialect/postgres/postgres-dialect.d.ts +1 -1
  82. package/dist/esm/dialect/postgres/postgres-introspector.d.ts +1 -1
  83. package/dist/esm/dialect/postgres/postgres-introspector.js +1 -1
  84. package/dist/esm/dialect/sqlite/sqlite-adapter.d.ts +2 -2
  85. package/dist/esm/dialect/sqlite/sqlite-dialect.d.ts +1 -1
  86. package/dist/esm/dialect/sqlite/sqlite-introspector.d.ts +1 -1
  87. package/dist/esm/dialect/sqlite/sqlite-introspector.js +1 -1
  88. package/dist/esm/index.d.ts +7 -4
  89. package/dist/esm/index.js +6 -3
  90. package/dist/esm/kysely.d.ts +8 -40
  91. package/dist/esm/kysely.js +8 -40
  92. package/dist/esm/migration/file-migration-provider.d.ts +52 -0
  93. package/dist/esm/migration/file-migration-provider.js +48 -0
  94. package/dist/esm/migration/migrator.d.ts +234 -0
  95. package/dist/esm/migration/migrator.js +413 -0
  96. package/dist/esm/operation-node/check-constraint-node.d.ts +1 -1
  97. package/dist/esm/operation-node/check-constraint-node.js +2 -3
  98. package/dist/esm/operation-node/column-definition-node.d.ts +8 -7
  99. package/dist/esm/operation-node/column-definition-node.js +0 -4
  100. package/dist/esm/operation-node/data-type-node.d.ts +1 -1
  101. package/dist/esm/operation-node/generated-node.d.ts +20 -0
  102. package/dist/esm/operation-node/generated-node.js +28 -0
  103. package/dist/esm/operation-node/on-conflict-node.d.ts +13 -2
  104. package/dist/esm/operation-node/on-conflict-node.js +39 -1
  105. package/dist/esm/operation-node/operation-node-transformer.d.ts +2 -2
  106. package/dist/esm/operation-node/operation-node-transformer.js +13 -6
  107. package/dist/esm/operation-node/operation-node-visitor.d.ts +2 -2
  108. package/dist/esm/operation-node/operation-node-visitor.js +1 -1
  109. package/dist/esm/operation-node/operation-node.d.ts +1 -1
  110. package/dist/esm/parser/insert-values-parser.d.ts +4 -4
  111. package/dist/esm/parser/insert-values-parser.js +2 -3
  112. package/dist/esm/parser/reference-parser.d.ts +4 -3
  113. package/dist/esm/parser/select-parser.d.ts +10 -4
  114. package/dist/esm/parser/update-set-parser.d.ts +2 -1
  115. package/dist/esm/plugin/camel-case/camel-case-plugin.d.ts +2 -2
  116. package/dist/esm/query-builder/delete-query-builder.d.ts +0 -3
  117. package/dist/esm/query-builder/insert-query-builder.d.ts +78 -94
  118. package/dist/esm/query-builder/insert-query-builder.js +145 -15
  119. package/dist/esm/query-builder/on-conflict-builder.d.ts +686 -0
  120. package/dist/esm/query-builder/on-conflict-builder.js +317 -0
  121. package/dist/esm/query-builder/returning-interface.d.ts +0 -3
  122. package/dist/esm/query-builder/update-query-builder.d.ts +0 -3
  123. package/dist/esm/query-compiler/default-query-compiler.d.ts +2 -2
  124. package/dist/esm/query-compiler/default-query-compiler.js +37 -8
  125. package/dist/esm/query-creator.d.ts +0 -2
  126. package/dist/esm/query-creator.js +0 -2
  127. package/dist/esm/schema/alter-table-builder.d.ts +41 -9
  128. package/dist/esm/schema/alter-table-builder.js +45 -9
  129. package/dist/esm/schema/column-definition-builder.d.ts +40 -8
  130. package/dist/esm/schema/column-definition-builder.js +21 -8
  131. package/dist/esm/schema/create-index-builder.d.ts +3 -2
  132. package/dist/esm/schema/create-index-builder.js +2 -2
  133. package/dist/esm/schema/create-table-builder.d.ts +3 -2
  134. package/dist/esm/schema/create-table-builder.js +2 -2
  135. package/dist/esm/util/column-type.d.ts +165 -0
  136. package/dist/esm/util/column-type.js +1 -0
  137. package/dist/esm/util/private-symbols.d.ts +5 -0
  138. package/dist/esm/util/private-symbols.js +5 -0
  139. package/dist/esm/util/type-utils.d.ts +6 -42
  140. package/package.json +1 -1
  141. package/dist/cjs/migration/migration.d.ts +0 -66
  142. package/dist/cjs/migration/migration.js +0 -187
  143. package/dist/cjs/operation-node/generated-always-as-node.d.ts +0 -16
  144. package/dist/cjs/operation-node/generated-always-as-node.js +0 -25
  145. package/dist/cjs/parser/on-conflict-parser.d.ts +0 -10
  146. package/dist/cjs/parser/on-conflict-parser.js +0 -35
  147. package/dist/cjs/util/generated-placeholder.d.ts +0 -3
  148. package/dist/cjs/util/generated-placeholder.js +0 -11
  149. package/dist/esm/migration/migration.d.ts +0 -66
  150. package/dist/esm/migration/migration.js +0 -183
  151. package/dist/esm/operation-node/generated-always-as-node.d.ts +0 -16
  152. package/dist/esm/operation-node/generated-always-as-node.js +0 -22
  153. package/dist/esm/parser/on-conflict-parser.d.ts +0 -10
  154. package/dist/esm/parser/on-conflict-parser.js +0 -30
  155. package/dist/esm/util/generated-placeholder.d.ts +0 -3
  156. package/dist/esm/util/generated-placeholder.js +0 -7
@@ -0,0 +1,417 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.Migrator = exports.NO_MIGRATIONS = exports.MIGRATION_LOCK_ID = exports.MIGRATION_LOCK_TABLE = exports.MIGRATION_TABLE = void 0;
4
+ const object_utils_js_1 = require("../util/object-utils.js");
5
+ const private_symbols_js_1 = require("../util/private-symbols.js");
6
+ exports.MIGRATION_TABLE = 'kysely_migration';
7
+ exports.MIGRATION_LOCK_TABLE = 'kysely_migration_lock';
8
+ exports.MIGRATION_LOCK_ID = 'migration_lock';
9
+ exports.NO_MIGRATIONS = (0, object_utils_js_1.freeze)({ __noMigrations__: true });
10
+ /**
11
+ * A class for running migrations.
12
+ *
13
+ * ### Example
14
+ *
15
+ * This example uses the {@link FileMigrationProvider} that reads migrations
16
+ * files from a single folder. You can easily implement your own
17
+ * {@link MigrationProvider} if you want to provide migrations some
18
+ * other way.
19
+ *
20
+ * ```ts
21
+ * const migrator = new Migrator({
22
+ * db,
23
+ * // The constructor signature of FileMigrationProvider is a
24
+ * // bit weird to keep Kysely independent of node.js or any
25
+ * // other environment.
26
+ * provider: new FileMigrationProvider(
27
+ * fs.readdir,
28
+ * path.join,
29
+ * // Path to the folder that contains all your migrations.
30
+ * 'migrations'
31
+ * )
32
+ * })
33
+ * ```
34
+ */
35
+ class Migrator {
36
+ #props;
37
+ constructor(props) {
38
+ this.#props = (0, object_utils_js_1.freeze)(props);
39
+ }
40
+ /**
41
+ * Runs all migrations that have not yet been run.
42
+ *
43
+ * This method returns a {@link MigrationResultSet} instance and _never_ throws.
44
+ * {@link MigrationResultSet.error} holds the error if something went wrong.
45
+ * {@link MigrationResultSet.results} contains information about which migrations
46
+ * were executed and which failed. See the examples below.
47
+ *
48
+ * This method goes through all possible migrations provided by the provider and runs the
49
+ * ones whose names come alphabetically after the last migration that has been run. If the
50
+ * list of executed migrations doesn't match the beginning of the list of possible migrations
51
+ * an error is thrown.
52
+ *
53
+ * ### Examples
54
+ *
55
+ * ```ts
56
+ * import * as path from 'path'
57
+ * import * as fs from 'fs/promises'
58
+ *
59
+ * const db = new Kysely<Database>({
60
+ * dialect: new PostgresDialect({
61
+ * host: 'localhost',
62
+ * database: 'kysely_test',
63
+ * }),
64
+ * })
65
+ *
66
+ * const migrator = new Migrator({
67
+ * db,
68
+ * // The constructor signature of FileMigrationProvider is a
69
+ * // bit weird to keep Kysely independent of node.js or any
70
+ * // other environment.
71
+ * provider: new FileMigrationProvider(
72
+ * fs.readdir,
73
+ * path.join,
74
+ * // Path to the folder that contains all your migrations.
75
+ * 'migrations'
76
+ * )
77
+ * })
78
+ *
79
+ * const { error, results } = await migrator.migrateToLatest()
80
+ *
81
+ * results?.forEach((it) => {
82
+ * if (it.status === 'Success') {
83
+ * console.log(`migration "${it.migrationName}" was executed successfully`)
84
+ * } else if (it.status === 'Error') {
85
+ * console.error(`failed to execute migration "${it.migrationName}"`)
86
+ * }
87
+ * })
88
+ *
89
+ * if (error) {
90
+ * console.error('failed to run `migrateToLatest`')
91
+ * console.error(error)
92
+ * }
93
+ * ```
94
+ */
95
+ async migrateToLatest() {
96
+ return this.#migrate(({ migrations }) => migrations.length - 1);
97
+ }
98
+ /**
99
+ * Migrate up/down to a specific migration.
100
+ *
101
+ * This method returns a {@link MigrationResultSet} instance and _never_ throws.
102
+ * {@link MigrationResultSet.error} holds the error if something went wrong.
103
+ * {@link MigrationResultSet.results} contains information about which migrations
104
+ * were executed and which failed.
105
+ *
106
+ * ### Examples
107
+ *
108
+ * ```ts
109
+ * await migrator.migrateTo('some_migration')
110
+ * ```
111
+ *
112
+ * If you specify the name of the first migration, this method migrates
113
+ * down to the first migration, but doesn't run the `down` method of
114
+ * the first migration. In case you want to migrate all the way down,
115
+ * you can use a special constant `NO_MIGRATIONS`:
116
+ *
117
+ * ```ts
118
+ * await migrator.migrateTo(NO_MIGRATIONS)
119
+ * ```
120
+ */
121
+ async migrateTo(targetMigrationName) {
122
+ return this.#migrate(({ migrations }) => {
123
+ if (targetMigrationName === exports.NO_MIGRATIONS) {
124
+ return -1;
125
+ }
126
+ const index = migrations.findIndex((it) => it.name === targetMigrationName);
127
+ if (index === -1) {
128
+ throw new Error(`migration "${targetMigrationName}" doesn't exist`);
129
+ }
130
+ return index;
131
+ });
132
+ }
133
+ /**
134
+ * Migrate one step up.
135
+ *
136
+ * This method returns a {@link MigrationResultSet} instance and _never_ throws.
137
+ * {@link MigrationResultSet.error} holds the error if something went wrong.
138
+ * {@link MigrationResultSet.results} contains information about which migrations
139
+ * were executed and which failed.
140
+ *
141
+ * ### Examples
142
+ *
143
+ * ```ts
144
+ * await migrator.migrateUp()
145
+ * ```
146
+ */
147
+ async migrateUp() {
148
+ return this.#migrate(({ currentIndex, migrations }) => Math.min(currentIndex + 1, migrations.length - 1));
149
+ }
150
+ /**
151
+ * Migrate one step down.
152
+ *
153
+ * This method returns a {@link MigrationResultSet} instance and _never_ throws.
154
+ * {@link MigrationResultSet.error} holds the error if something went wrong.
155
+ * {@link MigrationResultSet.results} contains information about which migrations
156
+ * were executed and which failed.
157
+ *
158
+ * ### Examples
159
+ *
160
+ * ```ts
161
+ * await migrator.migrateDown()
162
+ * ```
163
+ */
164
+ async migrateDown() {
165
+ return this.#migrate(({ currentIndex }) => Math.max(currentIndex - 1, -1));
166
+ }
167
+ async #migrate(getTargetMigrationIndex) {
168
+ try {
169
+ await this.#ensureMigrationTablesExists();
170
+ return await this.#runMigrations(getTargetMigrationIndex);
171
+ }
172
+ catch (error) {
173
+ if (error instanceof MigrationResultSetError) {
174
+ return error.resultSet;
175
+ }
176
+ return { error };
177
+ }
178
+ }
179
+ async #ensureMigrationTablesExists() {
180
+ await this.#ensureMigrationTableExists();
181
+ await this.#ensureMigrationLockTableExists();
182
+ await this.#ensureLockRowExists();
183
+ }
184
+ async #ensureMigrationTableExists() {
185
+ if (!(await this.#doesTableExists(exports.MIGRATION_TABLE))) {
186
+ try {
187
+ await this.#props.db.schema
188
+ .createTable(exports.MIGRATION_TABLE)
189
+ .ifNotExists()
190
+ .addColumn('name', 'varchar(255)', (col) => col.notNull().primaryKey())
191
+ // The migration run time as ISO string. This is not a real date type as we
192
+ // can't know which data type is supported by all future dialects.
193
+ .addColumn('timestamp', 'varchar(255)', (col) => col.notNull())
194
+ .execute();
195
+ }
196
+ catch (error) {
197
+ // At least on PostgreSQL, `if not exists` doesn't guarantee the `create table`
198
+ // query doesn't throw if the table already exits. That's why we check if
199
+ // the table exist here and ignore the error if it does.
200
+ if (!(await this.#doesTableExists(exports.MIGRATION_TABLE))) {
201
+ throw error;
202
+ }
203
+ }
204
+ }
205
+ }
206
+ async #ensureMigrationLockTableExists() {
207
+ if (!(await this.#doesTableExists(exports.MIGRATION_LOCK_TABLE))) {
208
+ try {
209
+ await this.#props.db.schema
210
+ .createTable(exports.MIGRATION_LOCK_TABLE)
211
+ .ifNotExists()
212
+ .addColumn('id', 'varchar(255)', (col) => col.notNull().primaryKey())
213
+ .addColumn('is_locked', 'integer', (col) => col.notNull().defaultTo(0))
214
+ .execute();
215
+ }
216
+ catch (error) {
217
+ // At least on PostgreSQL, `if not exists` doesn't guarantee the `create table`
218
+ // query doesn't throw if the table already exits. That's why we check if
219
+ // the table exist here and ignore the error if it does.
220
+ if (!(await this.#doesTableExists(exports.MIGRATION_LOCK_TABLE))) {
221
+ throw error;
222
+ }
223
+ }
224
+ }
225
+ }
226
+ async #ensureLockRowExists() {
227
+ if (!(await this.#doesLockRowExists())) {
228
+ try {
229
+ await this.#props.db
230
+ .insertInto(exports.MIGRATION_LOCK_TABLE)
231
+ .values({ id: exports.MIGRATION_LOCK_ID })
232
+ .execute();
233
+ }
234
+ catch (error) {
235
+ if (!(await this.#doesLockRowExists())) {
236
+ throw error;
237
+ }
238
+ }
239
+ }
240
+ }
241
+ async #doesTableExists(tableName) {
242
+ const metadata = await this.#props.db.introspection.getMetadata({
243
+ withInternalKyselyTables: true,
244
+ });
245
+ return !!metadata.tables.find((it) => it.name === tableName);
246
+ }
247
+ async #doesLockRowExists() {
248
+ const lockRow = await this.#props.db
249
+ .selectFrom(exports.MIGRATION_LOCK_TABLE)
250
+ .where('id', '=', exports.MIGRATION_LOCK_ID)
251
+ .select('id')
252
+ .executeTakeFirst();
253
+ return !!lockRow;
254
+ }
255
+ async #runMigrations(getTargetMigrationIndex) {
256
+ const run = async (db) => {
257
+ try {
258
+ await this.#props.db[private_symbols_js_1.PRIVATE_ADAPTER].acquireMigrationLock(db);
259
+ const state = await this.#getState(db);
260
+ if (state.migrations.length === 0) {
261
+ return { results: [] };
262
+ }
263
+ const targetIndex = getTargetMigrationIndex(state);
264
+ if (targetIndex === undefined) {
265
+ return { results: [] };
266
+ }
267
+ if (targetIndex < state.currentIndex) {
268
+ return await this.#migrateDown(db, state, targetIndex);
269
+ }
270
+ else if (targetIndex > state.currentIndex) {
271
+ return await this.#migrateUp(db, state, targetIndex);
272
+ }
273
+ return { results: [] };
274
+ }
275
+ finally {
276
+ await this.#props.db[private_symbols_js_1.PRIVATE_ADAPTER].releaseMigrationLock(db);
277
+ }
278
+ };
279
+ if (this.#props.db[private_symbols_js_1.PRIVATE_ADAPTER].supportsTransactionalDdl) {
280
+ return this.#props.db.transaction().execute(run);
281
+ }
282
+ else {
283
+ return this.#props.db.connection().execute(run);
284
+ }
285
+ }
286
+ async #getState(db) {
287
+ const migrations = await this.#resolveMigrations();
288
+ const executedMigrations = await this.#getExecutedMigrations(db);
289
+ this.#ensureMigrationsNotCorrupted(migrations, executedMigrations);
290
+ return (0, object_utils_js_1.freeze)({
291
+ migrations,
292
+ currentIndex: migrations.findIndex((it) => it.name === (0, object_utils_js_1.getLast)(executedMigrations)),
293
+ });
294
+ }
295
+ async #resolveMigrations() {
296
+ const allMigrations = await this.#props.provider.getMigrations();
297
+ return Object.keys(allMigrations)
298
+ .sort()
299
+ .map((name) => ({
300
+ ...allMigrations[name],
301
+ name,
302
+ }));
303
+ }
304
+ async #getExecutedMigrations(db) {
305
+ const executedMigrations = await db
306
+ .selectFrom(exports.MIGRATION_TABLE)
307
+ .select('name')
308
+ .orderBy('name')
309
+ .execute();
310
+ return executedMigrations.map((it) => it.name);
311
+ }
312
+ #ensureMigrationsNotCorrupted(migrations, executedMigrations) {
313
+ for (const executed of executedMigrations) {
314
+ if (!migrations.some((it) => it.name === executed)) {
315
+ throw new Error(`corrupted migrations: previously executed migration ${executed} is missing`);
316
+ }
317
+ }
318
+ // Now we know all executed migrations exist in the `migrations` list.
319
+ // Next we need to make sure that the executed migratiosns are the first
320
+ // ones in the migration list.
321
+ for (let i = 0; i < executedMigrations.length; ++i) {
322
+ if (migrations[i].name !== executedMigrations[i]) {
323
+ throw new Error(`corrupted migrations: expected previously executed migration ${executedMigrations[i]} to be at index ${i} but ${migrations[i].name} was found in its place. New migrations must always have a name that comes alphabetically after the last executed migration.`);
324
+ }
325
+ }
326
+ }
327
+ async #migrateDown(db, state, targetIndex) {
328
+ const results = [];
329
+ for (let i = state.currentIndex; i > targetIndex; --i) {
330
+ results.push({
331
+ migrationName: state.migrations[i].name,
332
+ direction: 'Down',
333
+ status: 'NotExecuted',
334
+ });
335
+ }
336
+ for (let i = 0; i < results.length; ++i) {
337
+ const migration = state.migrations.find((it) => it.name === results[i].migrationName);
338
+ try {
339
+ if (migration.down) {
340
+ await migration.down(db);
341
+ await db
342
+ .deleteFrom(exports.MIGRATION_TABLE)
343
+ .where('name', '=', migration.name)
344
+ .execute();
345
+ results[i] = {
346
+ migrationName: migration.name,
347
+ direction: 'Down',
348
+ status: 'Success',
349
+ };
350
+ }
351
+ }
352
+ catch (error) {
353
+ results[i] = {
354
+ migrationName: migration.name,
355
+ direction: 'Down',
356
+ status: 'Error',
357
+ };
358
+ throw new MigrationResultSetError({
359
+ error,
360
+ results,
361
+ });
362
+ }
363
+ }
364
+ return { results };
365
+ }
366
+ async #migrateUp(db, state, targetIndex) {
367
+ const results = [];
368
+ for (let i = state.currentIndex + 1; i <= targetIndex; ++i) {
369
+ results.push({
370
+ migrationName: state.migrations[i].name,
371
+ direction: 'Up',
372
+ status: 'NotExecuted',
373
+ });
374
+ }
375
+ for (let i = 0; i < results.length; ++i) {
376
+ const migration = state.migrations.find((it) => it.name === results[i].migrationName);
377
+ try {
378
+ await migration.up(db);
379
+ await db
380
+ .insertInto(exports.MIGRATION_TABLE)
381
+ .values({
382
+ name: migration.name,
383
+ timestamp: new Date().toISOString(),
384
+ })
385
+ .execute();
386
+ results[i] = {
387
+ migrationName: migration.name,
388
+ direction: 'Up',
389
+ status: 'Success',
390
+ };
391
+ }
392
+ catch (error) {
393
+ results[i] = {
394
+ migrationName: migration.name,
395
+ direction: 'Up',
396
+ status: 'Error',
397
+ };
398
+ throw new MigrationResultSetError({
399
+ error,
400
+ results,
401
+ });
402
+ }
403
+ }
404
+ return { results };
405
+ }
406
+ }
407
+ exports.Migrator = Migrator;
408
+ class MigrationResultSetError extends Error {
409
+ #resultSet;
410
+ constructor(result) {
411
+ super();
412
+ this.#resultSet = result;
413
+ }
414
+ get resultSet() {
415
+ return this.#resultSet;
416
+ }
417
+ }
@@ -11,5 +11,5 @@ export interface CheckConstraintNode extends OperationNode {
11
11
  */
12
12
  export declare const CheckConstraintNode: Readonly<{
13
13
  is(node: OperationNode): node is CheckConstraintNode;
14
- create(expressionSql: string, constraintName?: string | undefined): CheckConstraintNode;
14
+ create(expression: RawNode, constraintName?: string | undefined): CheckConstraintNode;
15
15
  }>;
@@ -2,7 +2,6 @@
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.CheckConstraintNode = void 0;
4
4
  const object_utils_js_1 = require("../util/object-utils.js");
5
- const raw_node_js_1 = require("./raw-node.js");
6
5
  const identifier_node_js_1 = require("./identifier-node.js");
7
6
  /**
8
7
  * @internal
@@ -11,10 +10,10 @@ exports.CheckConstraintNode = (0, object_utils_js_1.freeze)({
11
10
  is(node) {
12
11
  return node.kind === 'CheckConstraintNode';
13
12
  },
14
- create(expressionSql, constraintName) {
13
+ create(expression, constraintName) {
15
14
  return (0, object_utils_js_1.freeze)({
16
15
  kind: 'CheckConstraintNode',
17
- expression: raw_node_js_1.RawNode.createWithSql(expressionSql),
16
+ expression,
18
17
  name: constraintName ? identifier_node_js_1.IdentifierNode.create(constraintName) : undefined,
19
18
  });
20
19
  },
@@ -2,24 +2,25 @@ import { CheckConstraintNode } from './check-constraint-node.js';
2
2
  import { ColumnNode } from './column-node.js';
3
3
  import { DataTypeNode } from './data-type-node.js';
4
4
  import { DefaultValueNode } from './default-value-node.js';
5
- import { GeneratedAlwaysAsNode } from './generated-always-as-node.js';
5
+ import { GeneratedNode } from './generated-node.js';
6
6
  import { OperationNode } from './operation-node.js';
7
7
  import { RawNode } from './raw-node.js';
8
8
  import { ReferencesNode } from './references-node.js';
9
- export declare type ColumnDefinitionNodeProps = Omit<Partial<ColumnDefinitionNode>, 'kind'>;
9
+ export declare type ColumnDefinitionNodeProps = Omit<Partial<ColumnDefinitionNode>, 'kind' | 'dataType'>;
10
10
  export declare type ColumnDataTypeNode = DataTypeNode | RawNode;
11
11
  export interface ColumnDefinitionNode extends OperationNode {
12
12
  readonly kind: 'ColumnDefinitionNode';
13
13
  readonly column: ColumnNode;
14
14
  readonly dataType: ColumnDataTypeNode;
15
15
  readonly references?: ReferencesNode;
16
- readonly primaryKey: boolean;
17
- readonly autoIncrement: boolean;
18
- readonly unique: boolean;
19
- readonly nullable: boolean;
16
+ readonly primaryKey?: boolean;
17
+ readonly autoIncrement?: boolean;
18
+ readonly unique?: boolean;
19
+ readonly notNull?: boolean;
20
20
  readonly defaultTo?: DefaultValueNode;
21
21
  readonly check?: CheckConstraintNode;
22
- readonly generatedAlwaysAs?: GeneratedAlwaysAsNode;
22
+ readonly generated?: GeneratedNode;
23
+ readonly unsigned?: boolean;
23
24
  }
24
25
  /**
25
26
  * @internal
@@ -15,10 +15,6 @@ exports.ColumnDefinitionNode = (0, object_utils_js_1.freeze)({
15
15
  kind: 'ColumnDefinitionNode',
16
16
  column: column_node_js_1.ColumnNode.create(column),
17
17
  dataType,
18
- primaryKey: false,
19
- autoIncrement: false,
20
- unique: false,
21
- nullable: true,
22
18
  });
23
19
  },
24
20
  cloneWith(node, props) {
@@ -1,5 +1,5 @@
1
1
  import { OperationNode } from './operation-node.js';
2
- export declare type ColumnDataType = 'varchar' | `varchar(${number})` | 'text' | 'integer' | 'int2' | 'int4' | 'int8' | 'bigint' | 'boolean' | 'real' | 'double precision' | 'float4' | 'float8' | 'decimal' | `decimal(${number}, ${number})` | 'numeric' | `numeric(${number}, ${number})` | 'binary' | 'date' | 'datetime' | 'time' | 'timetz' | 'timestamp' | 'timestamptz' | 'serial' | 'bigserial' | 'uuid' | 'json' | 'jsonb';
2
+ export declare type ColumnDataType = 'varchar' | `varchar(${number})` | 'text' | 'integer' | 'int2' | 'int4' | 'int8' | 'bigint' | 'boolean' | 'real' | 'double precision' | 'float4' | 'float8' | 'decimal' | `decimal(${number}, ${number})` | 'numeric' | `numeric(${number}, ${number})` | 'binary' | 'date' | 'datetime' | 'time' | 'timetz' | 'timestamp' | 'timestamptz' | 'serial' | 'bigserial' | 'uuid' | 'json' | 'jsonb' | 'blob';
3
3
  export declare type DataTypeParams = Omit<DataTypeNode, 'kind' | 'dataType'>;
4
4
  export interface DataTypeNode extends OperationNode {
5
5
  readonly kind: 'DataTypeNode';
@@ -0,0 +1,20 @@
1
+ import { OperationNode } from './operation-node.js';
2
+ import { RawNode } from './raw-node.js';
3
+ export declare type GeneratedNodeParams = Omit<GeneratedNode, 'kind' | 'expression'>;
4
+ export interface GeneratedNode extends OperationNode {
5
+ readonly kind: 'GeneratedNode';
6
+ readonly byDefault?: boolean;
7
+ readonly always?: boolean;
8
+ readonly identity?: boolean;
9
+ readonly stored?: boolean;
10
+ readonly expression?: RawNode;
11
+ }
12
+ /**
13
+ * @internal
14
+ */
15
+ export declare const GeneratedNode: Readonly<{
16
+ is(node: OperationNode): node is GeneratedNode;
17
+ create(params: GeneratedNodeParams): GeneratedNode;
18
+ createWithExpression(expression: RawNode): GeneratedNode;
19
+ cloneWith(node: GeneratedNode, params: GeneratedNodeParams): GeneratedNode;
20
+ }>;
@@ -0,0 +1,31 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.GeneratedNode = void 0;
4
+ const object_utils_js_1 = require("../util/object-utils.js");
5
+ /**
6
+ * @internal
7
+ */
8
+ exports.GeneratedNode = (0, object_utils_js_1.freeze)({
9
+ is(node) {
10
+ return node.kind === 'GeneratedNode';
11
+ },
12
+ create(params) {
13
+ return (0, object_utils_js_1.freeze)({
14
+ kind: 'GeneratedNode',
15
+ ...params,
16
+ });
17
+ },
18
+ createWithExpression(expression) {
19
+ return (0, object_utils_js_1.freeze)({
20
+ kind: 'GeneratedNode',
21
+ always: true,
22
+ expression,
23
+ });
24
+ },
25
+ cloneWith(node, params) {
26
+ return (0, object_utils_js_1.freeze)({
27
+ ...node,
28
+ ...params,
29
+ });
30
+ },
31
+ });
@@ -1,13 +1,19 @@
1
1
  import { ColumnNode } from './column-node.js';
2
2
  import { ColumnUpdateNode } from './column-update-node.js';
3
3
  import { IdentifierNode } from './identifier-node.js';
4
+ import { FilterExpressionNode } from './operation-node-utils.js';
4
5
  import { OperationNode } from './operation-node.js';
5
- export declare type OnConflictNodeProps = Omit<OnConflictNode, 'kind'>;
6
+ import { RawNode } from './raw-node.js';
7
+ import { WhereNode } from './where-node.js';
8
+ export declare type OnConflictNodeProps = Omit<OnConflictNode, 'kind' | 'indexWhere' | 'updateWhere'>;
6
9
  export interface OnConflictNode extends OperationNode {
7
10
  readonly kind: 'OnConflictNode';
8
11
  readonly columns?: ReadonlyArray<ColumnNode>;
9
12
  readonly constraint?: IdentifierNode;
13
+ readonly indexExpression?: RawNode;
14
+ readonly indexWhere?: WhereNode;
10
15
  readonly updates?: ReadonlyArray<ColumnUpdateNode>;
16
+ readonly updateWhere?: WhereNode;
11
17
  readonly doNothing?: boolean;
12
18
  }
13
19
  /**
@@ -15,5 +21,10 @@ export interface OnConflictNode extends OperationNode {
15
21
  */
16
22
  export declare const OnConflictNode: Readonly<{
17
23
  is(node: OperationNode): node is OnConflictNode;
18
- create(props: OnConflictNodeProps): OnConflictNode;
24
+ create(): OnConflictNode;
25
+ cloneWith(node: OnConflictNode, props: OnConflictNodeProps): OnConflictNode;
26
+ cloneWithIndexWhere(node: OnConflictNode, filter: FilterExpressionNode): OnConflictNode;
27
+ cloneWithIndexOrWhere(node: OnConflictNode, filter: FilterExpressionNode): OnConflictNode;
28
+ cloneWithUpdateWhere(node: OnConflictNode, filter: FilterExpressionNode): OnConflictNode;
29
+ cloneWithUpdateOrWhere(node: OnConflictNode, filter: FilterExpressionNode): OnConflictNode;
19
30
  }>;
@@ -2,6 +2,7 @@
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.OnConflictNode = void 0;
4
4
  const object_utils_js_1 = require("../util/object-utils.js");
5
+ const where_node_js_1 = require("./where-node.js");
5
6
  /**
6
7
  * @internal
7
8
  */
@@ -9,10 +10,47 @@ exports.OnConflictNode = (0, object_utils_js_1.freeze)({
9
10
  is(node) {
10
11
  return node.kind === 'OnConflictNode';
11
12
  },
12
- create(props) {
13
+ create() {
13
14
  return (0, object_utils_js_1.freeze)({
14
15
  kind: 'OnConflictNode',
16
+ });
17
+ },
18
+ cloneWith(node, props) {
19
+ return (0, object_utils_js_1.freeze)({
20
+ ...node,
15
21
  ...props,
16
22
  });
17
23
  },
24
+ cloneWithIndexWhere(node, filter) {
25
+ return (0, object_utils_js_1.freeze)({
26
+ ...node,
27
+ indexWhere: node.indexWhere
28
+ ? where_node_js_1.WhereNode.cloneWithFilter(node.indexWhere, 'And', filter)
29
+ : where_node_js_1.WhereNode.create(filter),
30
+ });
31
+ },
32
+ cloneWithIndexOrWhere(node, filter) {
33
+ return (0, object_utils_js_1.freeze)({
34
+ ...node,
35
+ indexWhere: node.indexWhere
36
+ ? where_node_js_1.WhereNode.cloneWithFilter(node.indexWhere, 'Or', filter)
37
+ : where_node_js_1.WhereNode.create(filter),
38
+ });
39
+ },
40
+ cloneWithUpdateWhere(node, filter) {
41
+ return (0, object_utils_js_1.freeze)({
42
+ ...node,
43
+ updateWhere: node.updateWhere
44
+ ? where_node_js_1.WhereNode.cloneWithFilter(node.updateWhere, 'And', filter)
45
+ : where_node_js_1.WhereNode.create(filter),
46
+ });
47
+ },
48
+ cloneWithUpdateOrWhere(node, filter) {
49
+ return (0, object_utils_js_1.freeze)({
50
+ ...node,
51
+ updateWhere: node.updateWhere
52
+ ? where_node_js_1.WhereNode.cloneWithFilter(node.updateWhere, 'Or', filter)
53
+ : where_node_js_1.WhereNode.create(filter),
54
+ });
55
+ },
18
56
  });
@@ -61,7 +61,7 @@ import { OnDuplicateKeyNode } from './on-duplicate-key-node.js';
61
61
  import { UnionNode } from './union-node.js';
62
62
  import { CreateViewNode } from './create-view-node.js';
63
63
  import { DropViewNode } from './drop-view-node.js';
64
- import { GeneratedAlwaysAsNode } from './generated-always-as-node.js';
64
+ import { GeneratedNode } from './generated-node.js';
65
65
  import { DefaultValueNode } from './default-value-node.js';
66
66
  import { OnNode } from './on-node.js';
67
67
  import { ValuesNode } from './values-node.js';
@@ -156,7 +156,7 @@ export declare class OperationNodeTransformer {
156
156
  protected transformDropConstraint(node: DropConstraintNode): DropConstraintNode;
157
157
  protected transformCreateView(node: CreateViewNode): CreateViewNode;
158
158
  protected transformDropView(node: DropViewNode): DropViewNode;
159
- protected transformGeneratedAlwaysAs(node: GeneratedAlwaysAsNode): GeneratedAlwaysAsNode;
159
+ protected transformGenerated(node: GeneratedNode): GeneratedNode;
160
160
  protected transformDefaultValue(node: DefaultValueNode): DefaultValueNode;
161
161
  protected transformOn(node: OnNode): OnNode;
162
162
  protected transformDataType(node: DataTypeNode): DataTypeNode;