kysely 0.10.1 → 0.11.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 (134) hide show
  1. package/README.md +7 -3
  2. package/dist/cjs/dialect/dialect-adapter.d.ts +3 -2
  3. package/dist/cjs/dialect/mysql/mysql-adapter.js +1 -1
  4. package/dist/cjs/dialect/mysql/mysql-dialect.d.ts +3 -3
  5. package/dist/cjs/dialect/mysql/mysql-driver.js +25 -32
  6. package/dist/cjs/dialect/postgres/postgres-dialect.d.ts +2 -2
  7. package/dist/cjs/dialect/postgres/postgres-driver.js +8 -19
  8. package/dist/cjs/dialect/sqlite/sqlite-adapter.d.ts +7 -0
  9. package/dist/cjs/dialect/sqlite/sqlite-adapter.js +18 -0
  10. package/dist/cjs/dialect/sqlite/sqlite-dialect.d.ts +64 -0
  11. package/dist/cjs/dialect/sqlite/sqlite-dialect.js +33 -0
  12. package/dist/cjs/dialect/sqlite/sqlite-driver.d.ts +14 -0
  13. package/dist/cjs/dialect/sqlite/sqlite-driver.js +116 -0
  14. package/dist/cjs/dialect/sqlite/sqlite-introspector.d.ts +7 -0
  15. package/dist/cjs/dialect/sqlite/sqlite-introspector.js +31 -0
  16. package/dist/cjs/dialect/sqlite/sqlite-query-compiler.d.ts +7 -0
  17. package/dist/cjs/dialect/sqlite/sqlite-query-compiler.js +19 -0
  18. package/dist/cjs/driver/database-connection.d.ts +2 -2
  19. package/dist/cjs/index.d.ts +8 -0
  20. package/dist/cjs/index.js +8 -0
  21. package/dist/cjs/kysely.d.ts +6 -4
  22. package/dist/cjs/kysely.js +6 -4
  23. package/dist/cjs/migration/migration.d.ts +1 -1
  24. package/dist/cjs/migration/migration.js +3 -3
  25. package/dist/cjs/operation-node/create-view-node.d.ts +1 -0
  26. package/dist/cjs/operation-node/having-node.d.ts +4 -8
  27. package/dist/cjs/operation-node/having-node.js +3 -3
  28. package/dist/cjs/operation-node/join-node.d.ts +6 -9
  29. package/dist/cjs/operation-node/join-node.js +10 -7
  30. package/dist/cjs/operation-node/on-node.d.ts +14 -0
  31. package/dist/cjs/operation-node/on-node.js +28 -0
  32. package/dist/cjs/operation-node/operation-node-transformer.d.ts +2 -0
  33. package/dist/cjs/operation-node/operation-node-transformer.js +8 -0
  34. package/dist/cjs/operation-node/operation-node-visitor.d.ts +3 -0
  35. package/dist/cjs/operation-node/operation-node-visitor.js +4 -0
  36. package/dist/cjs/operation-node/operation-node.d.ts +1 -1
  37. package/dist/cjs/operation-node/query-node.d.ts +3 -3
  38. package/dist/cjs/operation-node/select-query-node.d.ts +4 -4
  39. package/dist/cjs/operation-node/where-node.d.ts +4 -8
  40. package/dist/cjs/operation-node/where-node.js +3 -3
  41. package/dist/cjs/parser/filter-parser.js +1 -1
  42. package/dist/cjs/parser/returning-parser.d.ts +4 -2
  43. package/dist/cjs/parser/select-parser.d.ts +2 -2
  44. package/dist/cjs/plugin/immediate-value.ts/immediate-value-plugin.d.ts +1 -1
  45. package/dist/cjs/query-builder/delete-result.d.ts +5 -0
  46. package/dist/cjs/query-builder/delete-result.js +13 -0
  47. package/dist/cjs/query-builder/expression-builder.d.ts +2 -2
  48. package/dist/cjs/query-builder/expression-builder.js +1 -1
  49. package/dist/cjs/query-builder/function-builder.d.ts +5 -5
  50. package/dist/cjs/query-builder/function-builder.js +3 -3
  51. package/dist/cjs/query-builder/insert-result.d.ts +27 -0
  52. package/dist/cjs/query-builder/insert-result.js +35 -0
  53. package/dist/cjs/query-builder/query-builder.d.ts +91 -81
  54. package/dist/cjs/query-builder/query-builder.js +38 -41
  55. package/dist/cjs/query-builder/update-result.d.ts +5 -0
  56. package/dist/cjs/query-builder/update-result.js +13 -0
  57. package/dist/cjs/query-compiler/compiled-query.d.ts +5 -0
  58. package/dist/cjs/query-compiler/compiled-query.js +12 -0
  59. package/dist/cjs/query-compiler/default-query-compiler.d.ts +2 -0
  60. package/dist/cjs/query-compiler/default-query-compiler.js +24 -13
  61. package/dist/cjs/query-creator.d.ts +36 -26
  62. package/dist/cjs/query-creator.js +25 -17
  63. package/dist/cjs/schema/create-view-builder.d.ts +4 -0
  64. package/dist/cjs/schema/create-view-builder.js +11 -0
  65. package/dist/cjs/util/dynamic-import.d.ts +2 -0
  66. package/dist/cjs/util/dynamic-import.js +32 -0
  67. package/dist/cjs/util/type-utils.d.ts +4 -15
  68. package/dist/esm/dialect/dialect-adapter.d.ts +3 -2
  69. package/dist/esm/dialect/mysql/mysql-adapter.js +1 -1
  70. package/dist/esm/dialect/mysql/mysql-dialect.d.ts +3 -3
  71. package/dist/esm/dialect/mysql/mysql-driver.js +26 -33
  72. package/dist/esm/dialect/postgres/postgres-dialect.d.ts +2 -2
  73. package/dist/esm/dialect/postgres/postgres-driver.js +8 -19
  74. package/dist/esm/dialect/sqlite/sqlite-adapter.d.ts +7 -0
  75. package/dist/esm/dialect/sqlite/sqlite-adapter.js +14 -0
  76. package/dist/esm/dialect/sqlite/sqlite-dialect.d.ts +64 -0
  77. package/dist/esm/dialect/sqlite/sqlite-dialect.js +29 -0
  78. package/dist/esm/dialect/sqlite/sqlite-driver.d.ts +14 -0
  79. package/dist/esm/dialect/sqlite/sqlite-driver.js +112 -0
  80. package/dist/esm/dialect/sqlite/sqlite-introspector.d.ts +7 -0
  81. package/dist/esm/dialect/sqlite/sqlite-introspector.js +27 -0
  82. package/dist/esm/dialect/sqlite/sqlite-query-compiler.d.ts +7 -0
  83. package/dist/esm/dialect/sqlite/sqlite-query-compiler.js +15 -0
  84. package/dist/esm/driver/database-connection.d.ts +2 -2
  85. package/dist/esm/index.d.ts +8 -0
  86. package/dist/esm/index.js +8 -0
  87. package/dist/esm/kysely.d.ts +6 -4
  88. package/dist/esm/kysely.js +6 -4
  89. package/dist/esm/migration/migration.d.ts +1 -1
  90. package/dist/esm/migration/migration.js +3 -3
  91. package/dist/esm/operation-node/create-view-node.d.ts +1 -0
  92. package/dist/esm/operation-node/having-node.d.ts +4 -8
  93. package/dist/esm/operation-node/having-node.js +3 -3
  94. package/dist/esm/operation-node/join-node.d.ts +6 -9
  95. package/dist/esm/operation-node/join-node.js +10 -7
  96. package/dist/esm/operation-node/on-node.d.ts +14 -0
  97. package/dist/esm/operation-node/on-node.js +25 -0
  98. package/dist/esm/operation-node/operation-node-transformer.d.ts +2 -0
  99. package/dist/esm/operation-node/operation-node-transformer.js +8 -0
  100. package/dist/esm/operation-node/operation-node-visitor.d.ts +3 -0
  101. package/dist/esm/operation-node/operation-node-visitor.js +4 -0
  102. package/dist/esm/operation-node/operation-node.d.ts +1 -1
  103. package/dist/esm/operation-node/query-node.d.ts +3 -3
  104. package/dist/esm/operation-node/select-query-node.d.ts +4 -4
  105. package/dist/esm/operation-node/where-node.d.ts +4 -8
  106. package/dist/esm/operation-node/where-node.js +3 -3
  107. package/dist/esm/parser/filter-parser.js +1 -1
  108. package/dist/esm/parser/returning-parser.d.ts +4 -2
  109. package/dist/esm/parser/select-parser.d.ts +2 -2
  110. package/dist/esm/plugin/immediate-value.ts/immediate-value-plugin.d.ts +1 -1
  111. package/dist/esm/query-builder/delete-result.d.ts +5 -0
  112. package/dist/esm/query-builder/delete-result.js +9 -0
  113. package/dist/esm/query-builder/expression-builder.d.ts +2 -2
  114. package/dist/esm/query-builder/expression-builder.js +1 -1
  115. package/dist/esm/query-builder/function-builder.d.ts +5 -5
  116. package/dist/esm/query-builder/function-builder.js +3 -3
  117. package/dist/esm/query-builder/insert-result.d.ts +27 -0
  118. package/dist/esm/query-builder/insert-result.js +31 -0
  119. package/dist/esm/query-builder/query-builder.d.ts +91 -81
  120. package/dist/esm/query-builder/query-builder.js +38 -41
  121. package/dist/esm/query-builder/update-result.d.ts +5 -0
  122. package/dist/esm/query-builder/update-result.js +9 -0
  123. package/dist/esm/query-compiler/compiled-query.d.ts +5 -0
  124. package/dist/esm/query-compiler/compiled-query.js +11 -1
  125. package/dist/esm/query-compiler/default-query-compiler.d.ts +2 -0
  126. package/dist/esm/query-compiler/default-query-compiler.js +24 -13
  127. package/dist/esm/query-creator.d.ts +36 -26
  128. package/dist/esm/query-creator.js +25 -17
  129. package/dist/esm/schema/create-view-builder.d.ts +4 -0
  130. package/dist/esm/schema/create-view-builder.js +11 -0
  131. package/dist/esm/util/dynamic-import.d.ts +2 -0
  132. package/dist/esm/util/dynamic-import.js +27 -0
  133. package/dist/esm/util/type-utils.d.ts +4 -15
  134. package/package.json +3 -1
@@ -0,0 +1,112 @@
1
+ import { CompiledQuery } from '../../query-compiler/compiled-query.js';
2
+ import { importFunction } from '../../util/dynamic-import.js';
3
+ export class SqliteDriver {
4
+ #config;
5
+ #connectionMutex = new ConnectionMutex();
6
+ #db;
7
+ #connection;
8
+ constructor(config) {
9
+ this.#config = config;
10
+ }
11
+ async init() {
12
+ // Import the `better-sqlite3` module here instead at the top of the file
13
+ // so that this file can be loaded by node without `better-sqlite3` driver
14
+ // installed. As you can see, there IS an import from `better-sqlite3` at
15
+ // the top level too, but that's only for types. It doesn't get compiled
16
+ // into javascript. You can check the built javascript code.
17
+ const DatabaseConstructor = await importBetterSqlite3Database();
18
+ const options = {};
19
+ if (typeof this.#config.readonly === 'boolean') {
20
+ options.readonly = this.#config.readonly;
21
+ }
22
+ if (typeof this.#config.fileMustExist === 'boolean') {
23
+ options.fileMustExist = this.#config.fileMustExist;
24
+ }
25
+ if (typeof this.#config.timeout === 'number') {
26
+ options.timeout = this.#config.timeout;
27
+ }
28
+ if (typeof this.#config.verbose === 'function') {
29
+ options.verbose = this.#config.verbose;
30
+ }
31
+ this.#db = new DatabaseConstructor(this.#config.databasePath, options);
32
+ this.#connection = new SqliteConnection(this.#db);
33
+ if (this.#config.onCreateConnection) {
34
+ await this.#config.onCreateConnection(this.#connection);
35
+ }
36
+ }
37
+ async acquireConnection() {
38
+ // sqlite effectively only has one single connection. We use a mutex
39
+ // here to wait until the single connection has been released.
40
+ await this.#connectionMutex.lock();
41
+ return this.#connection;
42
+ }
43
+ async beginTransaction(connection) {
44
+ await connection.executeQuery(CompiledQuery.raw('begin'));
45
+ }
46
+ async commitTransaction(connection) {
47
+ await connection.executeQuery(CompiledQuery.raw('commit'));
48
+ }
49
+ async rollbackTransaction(connection) {
50
+ await connection.executeQuery(CompiledQuery.raw('rollback'));
51
+ }
52
+ async releaseConnection() {
53
+ this.#connectionMutex.unlock();
54
+ }
55
+ async destroy() {
56
+ this.#db?.close();
57
+ }
58
+ }
59
+ async function importBetterSqlite3Database() {
60
+ try {
61
+ return await importFunction('better-sqlite3');
62
+ }
63
+ catch (error) {
64
+ console.error(error);
65
+ throw new Error('SQLite client not installed. Please run `npm install better-sqlite3`');
66
+ }
67
+ }
68
+ class SqliteConnection {
69
+ #db;
70
+ constructor(db) {
71
+ this.#db = db;
72
+ }
73
+ executeQuery(compiledQuery) {
74
+ const { sql, parameters } = compiledQuery;
75
+ const stmt = this.#db.prepare(sql);
76
+ if (stmt.reader) {
77
+ return Promise.resolve({
78
+ rows: stmt.all(parameters),
79
+ });
80
+ }
81
+ else {
82
+ const { changes, lastInsertRowid } = stmt.run(parameters);
83
+ return Promise.resolve({
84
+ numUpdatedOrDeletedRows: changes !== undefined && changes !== null
85
+ ? BigInt(changes)
86
+ : undefined,
87
+ insertId: lastInsertRowid !== undefined && lastInsertRowid !== null
88
+ ? BigInt(lastInsertRowid)
89
+ : undefined,
90
+ rows: [],
91
+ });
92
+ }
93
+ }
94
+ }
95
+ class ConnectionMutex {
96
+ #promise;
97
+ #resolve;
98
+ async lock() {
99
+ while (this.#promise) {
100
+ await this.#promise;
101
+ }
102
+ this.#promise = new Promise((resolve) => {
103
+ this.#resolve = resolve;
104
+ });
105
+ }
106
+ unlock() {
107
+ const resolve = this.#resolve;
108
+ this.#promise = undefined;
109
+ this.#resolve = undefined;
110
+ resolve?.();
111
+ }
112
+ }
@@ -0,0 +1,7 @@
1
+ import { DatabaseIntrospector, DatabaseMetadata, DatabaseMetadataOptions } from '../../introspection/database-introspector.js';
2
+ import { Kysely } from '../../kysely.js';
3
+ export declare class SqliteIntrospector implements DatabaseIntrospector {
4
+ #private;
5
+ constructor(db: Kysely<any>);
6
+ getMetadata(options?: DatabaseMetadataOptions): Promise<DatabaseMetadata>;
7
+ }
@@ -0,0 +1,27 @@
1
+ import { MIGRATION_LOCK_TABLE, MIGRATION_TABLE, } from '../../migration/migration.js';
2
+ export class SqliteIntrospector {
3
+ #db;
4
+ constructor(db) {
5
+ this.#db = db;
6
+ }
7
+ async getMetadata(options = { withInternalKyselyTables: false }) {
8
+ let query = this.#db
9
+ .selectFrom('sqlite_schema')
10
+ .where('type', '=', 'table')
11
+ .where('name', 'not like', 'sqlite_%')
12
+ .select('name');
13
+ if (!options.withInternalKyselyTables) {
14
+ query = query
15
+ .where('name', '!=', MIGRATION_TABLE)
16
+ .where('name', '!=', MIGRATION_LOCK_TABLE);
17
+ }
18
+ const result = await query.execute();
19
+ return {
20
+ tables: result.map((it) => ({
21
+ name: it.name,
22
+ // TODO: Get columns somehow.
23
+ columns: [],
24
+ })),
25
+ };
26
+ }
27
+ }
@@ -0,0 +1,7 @@
1
+ import { DefaultQueryCompiler } from '../../query-compiler/default-query-compiler.js';
2
+ export declare class SqliteQueryCompiler extends DefaultQueryCompiler {
3
+ protected visitReturning(): void;
4
+ protected getSql(): string;
5
+ protected getCurrentParameterPlaceholder(): string;
6
+ protected getAutoIncrement(): string;
7
+ }
@@ -0,0 +1,15 @@
1
+ import { DefaultQueryCompiler } from '../../query-compiler/default-query-compiler.js';
2
+ export class SqliteQueryCompiler extends DefaultQueryCompiler {
3
+ visitReturning() {
4
+ // Do nothing.
5
+ }
6
+ getSql() {
7
+ return super.getSql().trimEnd();
8
+ }
9
+ getCurrentParameterPlaceholder() {
10
+ return '?';
11
+ }
12
+ getAutoIncrement() {
13
+ return 'autoincrement';
14
+ }
15
+ }
@@ -12,12 +12,12 @@ export interface QueryResult<O> {
12
12
  * This is defined for update and delete queries and contains
13
13
  * the number of rows the query updated/deleted.
14
14
  */
15
- readonly numUpdatedOrDeletedRows?: number;
15
+ readonly numUpdatedOrDeletedRows?: bigint;
16
16
  /**
17
17
  * This is defined for insert queries on dialects that return
18
18
  * the auto incrementing primary key from an insert.
19
19
  */
20
- readonly insertedPrimaryKey?: number;
20
+ readonly insertId?: bigint;
21
21
  /**
22
22
  * The rows returned by the query. This is always defined and is
23
23
  * empty if the query returned no rows.
@@ -3,6 +3,9 @@ export * from './query-creator.js';
3
3
  export * from './query-builder/query-builder.js';
4
4
  export * from './query-builder/join-builder.js';
5
5
  export * from './query-builder/expression-builder.js';
6
+ export * from './query-builder/insert-result.js';
7
+ export * from './query-builder/delete-result.js';
8
+ export * from './query-builder/update-result.js';
6
9
  export * from './raw-builder/raw-builder.js';
7
10
  export * from './query-executor/query-executor.js';
8
11
  export * from './query-executor/default-query-executor.js';
@@ -37,6 +40,11 @@ export * from './dialect/mysql/mysql-query-compiler.js';
37
40
  export * from './dialect/mysql/mysql-driver.js';
38
41
  export * from './dialect/mysql/mysql-introspector.js';
39
42
  export * from './dialect/mysql/mysql-adapter.js';
43
+ export * from './dialect/sqlite/sqlite-dialect.js';
44
+ export * from './dialect/sqlite/sqlite-query-compiler.js';
45
+ export * from './dialect/sqlite/sqlite-driver.js';
46
+ export * from './dialect/sqlite/sqlite-introspector.js';
47
+ export * from './dialect/sqlite/sqlite-adapter.js';
40
48
  export * from './query-compiler/default-query-compiler.js';
41
49
  export * from './query-compiler/query-compiler.js';
42
50
  export * from './migration/migration.js';
package/dist/esm/index.js CHANGED
@@ -3,6 +3,9 @@ export * from './query-creator.js';
3
3
  export * from './query-builder/query-builder.js';
4
4
  export * from './query-builder/join-builder.js';
5
5
  export * from './query-builder/expression-builder.js';
6
+ export * from './query-builder/insert-result.js';
7
+ export * from './query-builder/delete-result.js';
8
+ export * from './query-builder/update-result.js';
6
9
  export * from './raw-builder/raw-builder.js';
7
10
  export * from './query-executor/query-executor.js';
8
11
  export * from './query-executor/default-query-executor.js';
@@ -37,6 +40,11 @@ export * from './dialect/mysql/mysql-query-compiler.js';
37
40
  export * from './dialect/mysql/mysql-driver.js';
38
41
  export * from './dialect/mysql/mysql-introspector.js';
39
42
  export * from './dialect/mysql/mysql-adapter.js';
43
+ export * from './dialect/sqlite/sqlite-dialect.js';
44
+ export * from './dialect/sqlite/sqlite-query-compiler.js';
45
+ export * from './dialect/sqlite/sqlite-driver.js';
46
+ export * from './dialect/sqlite/sqlite-introspector.js';
47
+ export * from './dialect/sqlite/sqlite-adapter.js';
40
48
  export * from './query-compiler/default-query-compiler.js';
41
49
  export * from './query-compiler/query-compiler.js';
42
50
  export * from './migration/migration.js';
@@ -116,7 +116,7 @@ export declare class Kysely<DB> extends QueryCreator<DB> {
116
116
  * .execute()
117
117
  * ```
118
118
  *
119
- * The generated SQL (postgresql):
119
+ * The generated SQL (PostgreSQL):
120
120
  *
121
121
  * ```sql
122
122
  * select "person"."id", count("pet"."id") as "pet_count"
@@ -146,17 +146,19 @@ export declare class Kysely<DB> extends QueryCreator<DB> {
146
146
  * const catto = await db.transaction().execute(async (trx) => {
147
147
  * const jennifer = await trx.insertInto('person')
148
148
  * .values({
149
+ * id: db.generated,
149
150
  * first_name: 'Jennifer',
150
- * last_name: 'Aniston',
151
+ * last_name: 'Aniston',
151
152
  * })
152
153
  * .returning('id')
153
- * .executeTakeFirst()
154
+ * .executeTakeFirstOrThrow()
154
155
  *
155
156
  * await someFunction(trx, jennifer)
156
157
  *
157
158
  * return await trx.insertInto('pet')
158
159
  * .values({
159
- * user_id: jennifer!.id,
160
+ * id: db.generated,
161
+ * user_id: jennifer.id,
160
162
  * name: 'Catto',
161
163
  * species: 'cat'
162
164
  * })
@@ -151,7 +151,7 @@ export class Kysely extends QueryCreator {
151
151
  * .execute()
152
152
  * ```
153
153
  *
154
- * The generated SQL (postgresql):
154
+ * The generated SQL (PostgreSQL):
155
155
  *
156
156
  * ```sql
157
157
  * select "person"."id", count("pet"."id") as "pet_count"
@@ -183,17 +183,19 @@ export class Kysely extends QueryCreator {
183
183
  * const catto = await db.transaction().execute(async (trx) => {
184
184
  * const jennifer = await trx.insertInto('person')
185
185
  * .values({
186
+ * id: db.generated,
186
187
  * first_name: 'Jennifer',
187
- * last_name: 'Aniston',
188
+ * last_name: 'Aniston',
188
189
  * })
189
190
  * .returning('id')
190
- * .executeTakeFirst()
191
+ * .executeTakeFirstOrThrow()
191
192
  *
192
193
  * await someFunction(trx, jennifer)
193
194
  *
194
195
  * return await trx.insertInto('pet')
195
196
  * .values({
196
- * user_id: jennifer!.id,
197
+ * id: db.generated,
198
+ * user_id: jennifer.id,
197
199
  * name: 'Catto',
198
200
  * species: 'cat'
199
201
  * })
@@ -62,5 +62,5 @@ export declare class MigrationModule {
62
62
  }
63
63
  export interface Migration {
64
64
  up(db: Kysely<any>): Promise<void>;
65
- down(db: Kysely<any>): Promise<void>;
65
+ down?(db: Kysely<any>): Promise<void>;
66
66
  }
@@ -57,7 +57,7 @@ async function ensureMigrationTableExists(db) {
57
57
  .execute();
58
58
  }
59
59
  catch (error) {
60
- // At least on postgres, `if not exists` doesn't guarantee the `create table`
60
+ // At least on PostgreSQL, `if not exists` doesn't guarantee the `create table`
61
61
  // query doesn't throw if the table already exits. That's why we check if
62
62
  // the table exist here and ignore the error if it does.
63
63
  if (!(await doesTableExists(db, MIGRATION_TABLE))) {
@@ -77,7 +77,7 @@ async function ensureMigrationLockTableExists(db) {
77
77
  .execute();
78
78
  }
79
79
  catch (error) {
80
- // At least on postgres, `if not exists` doesn't guarantee the `create table`
80
+ // At least on PostgreSQL, `if not exists` doesn't guarantee the `create table`
81
81
  // query doesn't throw if the table already exits. That's why we check if
82
82
  // the table exist here and ignore the error if it does.
83
83
  if (!(await doesTableExists(db, MIGRATION_LOCK_TABLE))) {
@@ -179,5 +179,5 @@ function ensureMigrationsAreNotCorrupted(executedMigrationNames, oldMigrationNam
179
179
  }
180
180
  }
181
181
  function isMigration(obj) {
182
- return isObject(obj) && isFunction(obj.up) && isFunction(obj.down);
182
+ return isObject(obj) && isFunction(obj.up);
183
183
  }
@@ -9,6 +9,7 @@ export interface CreateViewNode extends OperationNode {
9
9
  readonly name: IdentifierNode;
10
10
  readonly materialized?: boolean;
11
11
  readonly orReplace?: boolean;
12
+ readonly ifNotExists?: boolean;
12
13
  readonly columns?: ReadonlyArray<ColumnNode>;
13
14
  readonly as?: SelectQueryNode | RawNode;
14
15
  }
@@ -1,18 +1,14 @@
1
- import { AndNode } from './and-node.js';
2
- import { FilterNode } from './filter-node.js';
1
+ import { FilterExpressionNode } from './operation-node-utils.js';
3
2
  import { OperationNode } from './operation-node.js';
4
- import { OrNode } from './or-node.js';
5
- import { ParensNode } from './parens-node.js';
6
- export declare type HavingNodeChild = FilterNode | AndNode | OrNode | ParensNode;
7
3
  export interface HavingNode extends OperationNode {
8
4
  readonly kind: 'HavingNode';
9
- readonly having: HavingNodeChild;
5
+ readonly having: FilterExpressionNode;
10
6
  }
11
7
  /**
12
8
  * @internal
13
9
  */
14
10
  export declare const HavingNode: Readonly<{
15
11
  is(node: OperationNode): node is HavingNode;
16
- create(filter: HavingNodeChild): HavingNode;
17
- cloneWithFilter(havingNode: HavingNode, op: 'And' | 'Or', having: HavingNodeChild): HavingNode;
12
+ create(filter: FilterExpressionNode): HavingNode;
13
+ cloneWithFilter(havingNode: HavingNode, op: 'And' | 'Or', filter: FilterExpressionNode): HavingNode;
18
14
  }>;
@@ -14,12 +14,12 @@ export const HavingNode = freeze({
14
14
  having: filter,
15
15
  });
16
16
  },
17
- cloneWithFilter(havingNode, op, having) {
17
+ cloneWithFilter(havingNode, op, filter) {
18
18
  return freeze({
19
19
  ...havingNode,
20
20
  having: op === 'And'
21
- ? AndNode.create(havingNode.having, having)
22
- : OrNode.create(havingNode.having, having),
21
+ ? AndNode.create(havingNode.having, filter)
22
+ : OrNode.create(havingNode.having, filter),
23
23
  });
24
24
  },
25
25
  });
@@ -1,18 +1,15 @@
1
1
  import { AliasNode } from './alias-node.js';
2
- import { AndNode } from './and-node.js';
3
- import { FilterNode } from './filter-node.js';
2
+ import { OnNode } from './on-node.js';
3
+ import { FilterExpressionNode } from './operation-node-utils.js';
4
4
  import { OperationNode } from './operation-node.js';
5
- import { OrNode } from './or-node.js';
6
- import { ParensNode } from './parens-node.js';
7
5
  import { TableNode } from './table-node.js';
8
6
  export declare type JoinTableNode = TableNode | AliasNode;
9
7
  export declare type JoinType = 'InnerJoin' | 'LeftJoin' | 'RightJoin' | 'FullJoin';
10
- export declare type JoinNodeOnNode = FilterNode | AndNode | OrNode | ParensNode;
11
8
  export interface JoinNode extends OperationNode {
12
9
  readonly kind: 'JoinNode';
13
10
  readonly joinType: JoinType;
14
11
  readonly table: JoinTableNode;
15
- readonly on?: JoinNodeOnNode;
12
+ readonly on?: OnNode;
16
13
  }
17
14
  /**
18
15
  * @internal
@@ -20,7 +17,7 @@ export interface JoinNode extends OperationNode {
20
17
  export declare const JoinNode: Readonly<{
21
18
  is(node: OperationNode): node is JoinNode;
22
19
  create(joinType: JoinType, table: JoinTableNode): JoinNode;
23
- createWithOn(joinType: JoinType, table: JoinTableNode, on: JoinNodeOnNode): JoinNode;
24
- cloneWithOn(joinNode: JoinNode, on: JoinNodeOnNode): JoinNode;
25
- cloneWithOrOn(joinNode: JoinNode, on: JoinNodeOnNode): JoinNode;
20
+ createWithOn(joinType: JoinType, table: JoinTableNode, on: FilterExpressionNode): JoinNode;
21
+ cloneWithOn(joinNode: JoinNode, filter: FilterExpressionNode): JoinNode;
22
+ cloneWithOrOn(joinNode: JoinNode, filter: FilterExpressionNode): JoinNode;
26
23
  }>;
@@ -1,6 +1,5 @@
1
1
  import { freeze } from '../util/object-utils.js';
2
- import { AndNode } from './and-node.js';
3
- import { OrNode } from './or-node.js';
2
+ import { OnNode } from './on-node.js';
4
3
  /**
5
4
  * @internal
6
5
  */
@@ -21,19 +20,23 @@ export const JoinNode = freeze({
21
20
  kind: 'JoinNode',
22
21
  joinType,
23
22
  table,
24
- on,
23
+ on: OnNode.create(on),
25
24
  });
26
25
  },
27
- cloneWithOn(joinNode, on) {
26
+ cloneWithOn(joinNode, filter) {
28
27
  return freeze({
29
28
  ...joinNode,
30
- on: joinNode.on ? AndNode.create(joinNode.on, on) : on,
29
+ on: joinNode.on
30
+ ? OnNode.cloneWithFilter(joinNode.on, 'And', filter)
31
+ : OnNode.create(filter),
31
32
  });
32
33
  },
33
- cloneWithOrOn(joinNode, on) {
34
+ cloneWithOrOn(joinNode, filter) {
34
35
  return freeze({
35
36
  ...joinNode,
36
- on: joinNode.on ? OrNode.create(joinNode.on, on) : on,
37
+ on: joinNode.on
38
+ ? OnNode.cloneWithFilter(joinNode.on, 'Or', filter)
39
+ : OnNode.create(filter),
37
40
  });
38
41
  },
39
42
  });
@@ -0,0 +1,14 @@
1
+ import { FilterExpressionNode } from './operation-node-utils.js';
2
+ import { OperationNode } from './operation-node.js';
3
+ export interface OnNode extends OperationNode {
4
+ readonly kind: 'OnNode';
5
+ readonly on: FilterExpressionNode;
6
+ }
7
+ /**
8
+ * @internal
9
+ */
10
+ export declare const OnNode: Readonly<{
11
+ is(node: OperationNode): node is OnNode;
12
+ create(filter: FilterExpressionNode): OnNode;
13
+ cloneWithFilter(onNode: OnNode, op: 'And' | 'Or', filter: FilterExpressionNode): OnNode;
14
+ }>;
@@ -0,0 +1,25 @@
1
+ import { freeze } from '../util/object-utils.js';
2
+ import { AndNode } from './and-node.js';
3
+ import { OrNode } from './or-node.js';
4
+ /**
5
+ * @internal
6
+ */
7
+ export const OnNode = freeze({
8
+ is(node) {
9
+ return node.kind === 'OnNode';
10
+ },
11
+ create(filter) {
12
+ return freeze({
13
+ kind: 'OnNode',
14
+ on: filter,
15
+ });
16
+ },
17
+ cloneWithFilter(onNode, op, filter) {
18
+ return freeze({
19
+ ...onNode,
20
+ on: op === 'And'
21
+ ? AndNode.create(onNode.on, filter)
22
+ : OrNode.create(onNode.on, filter),
23
+ });
24
+ },
25
+ });
@@ -62,6 +62,7 @@ import { CreateViewNode } from './create-view-node.js';
62
62
  import { DropViewNode } from './drop-view-node.js';
63
63
  import { GeneratedAlwaysAsNode } from './generated-always-as-node.js';
64
64
  import { DefaultValueNode } from './default-value-node.js';
65
+ import { OnNode } from './on-node.js';
65
66
  /**
66
67
  * Transforms an operation node tree into another one.
67
68
  *
@@ -153,6 +154,7 @@ export declare class OperationNodeTransformer {
153
154
  protected transformDropView(node: DropViewNode): DropViewNode;
154
155
  protected transformGeneratedAlwaysAs(node: GeneratedAlwaysAsNode): GeneratedAlwaysAsNode;
155
156
  protected transformDefaultValue(node: DefaultValueNode): DefaultValueNode;
157
+ protected transformOn(node: OnNode): OnNode;
156
158
  protected transformDataType(node: DataTypeNode): DataTypeNode;
157
159
  protected transformSelectAll(node: SelectAllNode): SelectAllNode;
158
160
  protected transformIdentifier(node: IdentifierNode): IdentifierNode;
@@ -94,6 +94,7 @@ export class OperationNodeTransformer {
94
94
  DropViewNode: this.transformDropView.bind(this),
95
95
  GeneratedAlwaysAsNode: this.transformGeneratedAlwaysAs.bind(this),
96
96
  DefaultValueNode: this.transformDefaultValue.bind(this),
97
+ OnNode: this.transformOn.bind(this),
97
98
  });
98
99
  transformNode = (node) => {
99
100
  if (!node) {
@@ -525,6 +526,7 @@ export class OperationNodeTransformer {
525
526
  kind: 'CreateViewNode',
526
527
  name: this.transformNode(node.name),
527
528
  orReplace: node.orReplace,
529
+ ifNotExists: node.ifNotExists,
528
530
  materialized: node.materialized,
529
531
  columns: this.transformNodeList(node.columns),
530
532
  as: this.transformNode(node.as),
@@ -551,6 +553,12 @@ export class OperationNodeTransformer {
551
553
  defaultValue: this.transformNode(node.defaultValue),
552
554
  };
553
555
  }
556
+ transformOn(node) {
557
+ return {
558
+ kind: 'OnNode',
559
+ on: this.transformNode(node.on),
560
+ };
561
+ }
554
562
  transformDataType(node) {
555
563
  // An Object.freezed leaf node. No need to clone.
556
564
  return node;
@@ -62,9 +62,11 @@ import { CreateViewNode } from './create-view-node.js';
62
62
  import { DropViewNode } from './drop-view-node.js';
63
63
  import { GeneratedAlwaysAsNode } from './generated-always-as-node.js';
64
64
  import { DefaultValueNode } from './default-value-node.js';
65
+ import { OnNode } from './on-node.js';
65
66
  export declare abstract class OperationNodeVisitor {
66
67
  #private;
67
68
  protected readonly nodeStack: OperationNode[];
69
+ protected get parentNode(): OperationNode | undefined;
68
70
  protected readonly visitNode: (node: OperationNode) => void;
69
71
  protected abstract visitSelectQuery(node: SelectQueryNode): void;
70
72
  protected abstract visitSelection(node: SelectionNode): void;
@@ -129,4 +131,5 @@ export declare abstract class OperationNodeVisitor {
129
131
  protected abstract visitDropView(node: DropViewNode): void;
130
132
  protected abstract visitGeneratedAlwaysAs(node: GeneratedAlwaysAsNode): void;
131
133
  protected abstract visitDefaultValue(node: DefaultValueNode): void;
134
+ protected abstract visitOn(node: OnNode): void;
132
135
  }
@@ -1,6 +1,9 @@
1
1
  import { freeze } from '../util/object-utils.js';
2
2
  export class OperationNodeVisitor {
3
3
  nodeStack = [];
4
+ get parentNode() {
5
+ return this.nodeStack[this.nodeStack.length - 2];
6
+ }
4
7
  #visitors = freeze({
5
8
  AliasNode: this.visitAlias.bind(this),
6
9
  ColumnNode: this.visitColumn.bind(this),
@@ -65,6 +68,7 @@ export class OperationNodeVisitor {
65
68
  DropViewNode: this.visitDropView.bind(this),
66
69
  GeneratedAlwaysAsNode: this.visitGeneratedAlwaysAs.bind(this),
67
70
  DefaultValueNode: this.visitDefaultValue.bind(this),
71
+ OnNode: this.visitOn.bind(this),
68
72
  });
69
73
  visitNode = (node) => {
70
74
  this.nodeStack.push(node);
@@ -1,4 +1,4 @@
1
- export declare type OperationNodeKind = 'IdentifierNode' | 'RawNode' | 'SelectQueryNode' | 'SelectionNode' | 'ReferenceNode' | 'ColumnNode' | 'TableNode' | 'AliasNode' | 'FromNode' | 'SelectAllNode' | 'FilterNode' | 'AndNode' | 'OrNode' | 'ParensNode' | 'ValueNode' | 'ValueListNode' | 'PrimitiveValueListNode' | 'JoinNode' | 'OperatorNode' | 'WhereNode' | 'InsertQueryNode' | 'DeleteQueryNode' | 'ReturningNode' | 'CreateTableNode' | 'ColumnDefinitionNode' | 'AddColumnNode' | 'DropTableNode' | 'DataTypeNode' | 'OrderByNode' | 'OrderByItemNode' | 'GroupByNode' | 'GroupByItemNode' | 'UpdateQueryNode' | 'ColumnUpdateNode' | 'LimitNode' | 'OffsetNode' | 'OnConflictNode' | 'OnDuplicateKeyNode' | 'CreateIndexNode' | 'DropIndexNode' | 'ListNode' | 'ReferencesNode' | 'PrimaryKeyConstraintNode' | 'UniqueConstraintNode' | 'CheckConstraintNode' | 'ForeignKeyConstraintNode' | 'WithNode' | 'CommonTableExpressionNode' | 'HavingNode' | 'CreateSchemaNode' | 'DropSchemaNode' | 'AlterTableNode' | 'ModifyColumnNode' | 'DropColumnNode' | 'RenameColumnNode' | 'AlterColumnNode' | 'AddConstraintNode' | 'DropConstraintNode' | 'UnionNode' | 'CreateViewNode' | 'DropViewNode' | 'GeneratedAlwaysAsNode' | 'DefaultValueNode';
1
+ export declare type OperationNodeKind = 'IdentifierNode' | 'RawNode' | 'SelectQueryNode' | 'SelectionNode' | 'ReferenceNode' | 'ColumnNode' | 'TableNode' | 'AliasNode' | 'FromNode' | 'SelectAllNode' | 'FilterNode' | 'AndNode' | 'OrNode' | 'ParensNode' | 'ValueNode' | 'ValueListNode' | 'PrimitiveValueListNode' | 'JoinNode' | 'OperatorNode' | 'WhereNode' | 'InsertQueryNode' | 'DeleteQueryNode' | 'ReturningNode' | 'CreateTableNode' | 'ColumnDefinitionNode' | 'AddColumnNode' | 'DropTableNode' | 'DataTypeNode' | 'OrderByNode' | 'OrderByItemNode' | 'GroupByNode' | 'GroupByItemNode' | 'UpdateQueryNode' | 'ColumnUpdateNode' | 'LimitNode' | 'OffsetNode' | 'OnConflictNode' | 'OnDuplicateKeyNode' | 'CreateIndexNode' | 'DropIndexNode' | 'ListNode' | 'ReferencesNode' | 'PrimaryKeyConstraintNode' | 'UniqueConstraintNode' | 'CheckConstraintNode' | 'ForeignKeyConstraintNode' | 'WithNode' | 'CommonTableExpressionNode' | 'HavingNode' | 'CreateSchemaNode' | 'DropSchemaNode' | 'AlterTableNode' | 'ModifyColumnNode' | 'DropColumnNode' | 'RenameColumnNode' | 'AlterColumnNode' | 'AddConstraintNode' | 'DropConstraintNode' | 'UnionNode' | 'CreateViewNode' | 'DropViewNode' | 'GeneratedAlwaysAsNode' | 'DefaultValueNode' | 'OnNode';
2
2
  export interface OperationNode {
3
3
  readonly kind: OperationNodeKind;
4
4
  }
@@ -2,10 +2,10 @@ import { InsertQueryNode } from './insert-query-node.js';
2
2
  import { SelectQueryNode } from './select-query-node.js';
3
3
  import { UpdateQueryNode } from './update-query-node.js';
4
4
  import { DeleteQueryNode } from './delete-query-node.js';
5
- import { WhereChildNode } from './where-node.js';
6
5
  import { JoinNode } from './join-node.js';
7
6
  import { SelectionNode } from './selection-node.js';
8
7
  import { OperationNode } from './operation-node.js';
8
+ import { FilterExpressionNode } from './operation-node-utils.js';
9
9
  export declare type QueryNode = SelectQueryNode | DeleteQueryNode | InsertQueryNode | UpdateQueryNode;
10
10
  export declare type MutatingQueryNode = DeleteQueryNode | InsertQueryNode | UpdateQueryNode;
11
11
  export declare type FilterableQueryNode = SelectQueryNode | DeleteQueryNode | UpdateQueryNode;
@@ -16,8 +16,8 @@ export declare const QueryNode: Readonly<{
16
16
  is(node: OperationNode): node is QueryNode;
17
17
  isMutating(node: OperationNode): node is MutatingQueryNode;
18
18
  isFilterable(node: OperationNode): node is FilterableQueryNode;
19
- cloneWithWhere<T extends FilterableQueryNode>(node: T, filter: WhereChildNode): T;
20
- cloneWithOrWhere<T_1 extends FilterableQueryNode>(node: T_1, filter: WhereChildNode): T_1;
19
+ cloneWithWhere<T extends FilterableQueryNode>(node: T, filter: FilterExpressionNode): T;
20
+ cloneWithOrWhere<T_1 extends FilterableQueryNode>(node: T_1, filter: FilterExpressionNode): T_1;
21
21
  cloneWithJoin<T_2 extends FilterableQueryNode>(node: T_2, join: JoinNode): T_2;
22
22
  cloneWithReturning<T_3 extends MutatingQueryNode>(node: T_3, selections: ReadonlyArray<SelectionNode>): T_3;
23
23
  }>;
@@ -1,12 +1,12 @@
1
1
  import { FromNode } from './from-node.js';
2
2
  import { GroupByItemNode } from './group-by-item-node.js';
3
3
  import { GroupByNode } from './group-by-node.js';
4
- import { HavingNode, HavingNodeChild } from './having-node.js';
4
+ import { HavingNode } from './having-node.js';
5
5
  import { JoinNode } from './join-node.js';
6
6
  import { LimitNode } from './limit-node.js';
7
7
  import { OffsetNode } from './offset-node.js';
8
8
  import { OperationNode } from './operation-node.js';
9
- import { TableExpressionNode } from './operation-node-utils.js';
9
+ import { FilterExpressionNode, TableExpressionNode } from './operation-node-utils.js';
10
10
  import { OrderByItemNode } from './order-by-item-node.js';
11
11
  import { OrderByNode } from './order-by-node.js';
12
12
  import { SelectionNode } from './selection-node.js';
@@ -44,8 +44,8 @@ export declare const SelectQueryNode: Readonly<{
44
44
  cloneWithGroupByItems(selectNode: SelectQueryNode, items: ReadonlyArray<GroupByItemNode>): SelectQueryNode;
45
45
  cloneWithLimit(selectNode: SelectQueryNode, limit: LimitNode): SelectQueryNode;
46
46
  cloneWithOffset(selectNode: SelectQueryNode, offset: OffsetNode): SelectQueryNode;
47
- cloneWithHaving(selectNode: SelectQueryNode, filter: HavingNodeChild): SelectQueryNode;
48
- cloneWithOrHaving(selectNode: SelectQueryNode, filter: HavingNodeChild): SelectQueryNode;
47
+ cloneWithHaving(selectNode: SelectQueryNode, filter: FilterExpressionNode): SelectQueryNode;
48
+ cloneWithOrHaving(selectNode: SelectQueryNode, filter: FilterExpressionNode): SelectQueryNode;
49
49
  cloneWithDistinct(selectNode: SelectQueryNode): SelectQueryNode;
50
50
  cloneWithUnion(selectNode: SelectQueryNode, union: UnionNode): SelectQueryNode;
51
51
  }>;