drizzle-orm 0.25.2 → 0.25.3-4cc2d87
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/aws-data-api/pg/index.cjs +234 -1
- package/aws-data-api/pg/index.cjs.map +1 -1
- package/aws-data-api/pg/index.d.ts +5 -6
- package/aws-data-api/pg/index.mjs +228 -1
- package/aws-data-api/pg/index.mjs.map +1 -1
- package/aws-data-api/pg/migrator.cjs +13 -1
- package/aws-data-api/pg/migrator.cjs.map +1 -1
- package/aws-data-api/pg/migrator.d.ts +5 -6
- package/aws-data-api/pg/migrator.mjs +11 -1
- package/aws-data-api/pg/migrator.mjs.map +1 -1
- package/better-sqlite3/index.cjs +119 -1
- package/better-sqlite3/index.cjs.map +1 -1
- package/better-sqlite3/index.d.ts +14 -12
- package/better-sqlite3/index.mjs +114 -1
- package/better-sqlite3/index.mjs.map +1 -1
- package/better-sqlite3/migrator.cjs +13 -1
- package/better-sqlite3/migrator.cjs.map +1 -1
- package/better-sqlite3/migrator.d.ts +5 -5
- package/better-sqlite3/migrator.mjs +11 -1
- package/better-sqlite3/migrator.mjs.map +1 -1
- package/bun-sqlite/index.cjs +126 -1
- package/bun-sqlite/index.cjs.map +1 -1
- package/bun-sqlite/index.d.ts +14 -12
- package/bun-sqlite/index.mjs +121 -1
- package/bun-sqlite/index.mjs.map +1 -1
- package/bun-sqlite/migrator.cjs +13 -1
- package/bun-sqlite/migrator.cjs.map +1 -1
- package/bun-sqlite/migrator.d.ts +5 -5
- package/bun-sqlite/migrator.mjs +11 -1
- package/bun-sqlite/migrator.mjs.map +1 -1
- package/{column.d-8b137277.d.ts → column.d-c31e7ad3.d.ts} +77 -6
- package/d1/index.cjs +116 -1
- package/d1/index.cjs.map +1 -1
- package/d1/index.d.ts +15 -12
- package/d1/index.mjs +111 -1
- package/d1/index.mjs.map +1 -1
- package/d1/migrator.cjs +13 -1
- package/d1/migrator.cjs.map +1 -1
- package/d1/migrator.d.ts +5 -5
- package/d1/migrator.mjs +11 -1
- package/d1/migrator.mjs.map +1 -1
- package/{db.d-ae495c35.d.ts → db.d-a2311092.d.ts} +121 -44
- package/{db.d-66553b9e.d.ts → db.d-bc9a1d6c.d.ts} +193 -16
- package/driver.d-17ca4c15.d.ts +8 -0
- package/driver.d-300ddb0e.d.ts +64 -0
- package/driver.d-45e56643.d.ts +60 -0
- package/driver.d-64f2125c.d.ts +8 -0
- package/driver.d-7fde2e9d.d.ts +55 -0
- package/driver.d-9d703b84.d.ts +8 -0
- package/driver.d-b2b94bf9.d.ts +46 -0
- package/driver.d-b70ee7ee.d.ts +55 -0
- package/driver.d-dea23ee6.d.ts +8 -0
- package/driver.d-e54af17b.d.ts +52 -0
- package/driver.d-eb490c91.d.ts +9 -0
- package/driver.d-ef6fa2df.d.ts +14 -0
- package/errors-bb636d84.mjs +19 -0
- package/errors-bb636d84.mjs.map +1 -0
- package/errors-d0192d62.cjs +22 -0
- package/errors-d0192d62.cjs.map +1 -0
- package/index.cjs +105 -1
- package/index.cjs.map +1 -1
- package/index.d.ts +16 -432
- package/index.mjs +3 -1
- package/index.mjs.map +1 -1
- package/knex/index.cjs +2 -1
- package/knex/index.cjs.map +1 -1
- package/knex/index.d.ts +1 -1
- package/kysely/index.cjs +2 -1
- package/kysely/index.cjs.map +1 -1
- package/kysely/index.d.ts +1 -1
- package/libsql/index.cjs +155 -1
- package/libsql/index.cjs.map +1 -1
- package/libsql/index.d.ts +14 -12
- package/libsql/index.mjs +150 -1
- package/libsql/index.mjs.map +1 -1
- package/libsql/migrator.cjs +13 -1
- package/libsql/migrator.cjs.map +1 -1
- package/libsql/migrator.d.ts +5 -5
- package/libsql/migrator.mjs +11 -1
- package/libsql/migrator.mjs.map +1 -1
- package/logger-caa1ca6e.cjs +34 -0
- package/logger-caa1ca6e.cjs.map +1 -0
- package/logger-caf75bde.mjs +30 -0
- package/logger-caf75bde.mjs.map +1 -0
- package/migrator.cjs +48 -1
- package/migrator.cjs.map +1 -1
- package/migrator.mjs +46 -1
- package/migrator.mjs.map +1 -1
- package/mysql-core/index.cjs +1004 -1
- package/mysql-core/index.cjs.map +1 -1
- package/mysql-core/index.d.ts +347 -347
- package/mysql-core/index.mjs +869 -1
- package/mysql-core/index.mjs.map +1 -1
- package/mysql2/index.cjs +230 -1
- package/mysql2/index.cjs.map +1 -1
- package/mysql2/index.d.ts +5 -6
- package/mysql2/index.mjs +223 -1
- package/mysql2/index.mjs.map +1 -1
- package/mysql2/migrator.cjs +13 -1
- package/mysql2/migrator.cjs.map +1 -1
- package/mysql2/migrator.d.ts +5 -6
- package/mysql2/migrator.mjs +11 -1
- package/mysql2/migrator.mjs.map +1 -1
- package/neon-serverless/index.cjs +155 -1
- package/neon-serverless/index.cjs.map +1 -1
- package/neon-serverless/index.d.ts +5 -6
- package/neon-serverless/index.mjs +149 -1
- package/neon-serverless/index.mjs.map +1 -1
- package/neon-serverless/migrator.cjs +13 -1
- package/neon-serverless/migrator.cjs.map +1 -1
- package/neon-serverless/migrator.d.ts +5 -6
- package/neon-serverless/migrator.mjs +11 -1
- package/neon-serverless/migrator.mjs.map +1 -1
- package/node-postgres/index.cjs +157 -1
- package/node-postgres/index.cjs.map +1 -1
- package/node-postgres/index.d.ts +5 -6
- package/node-postgres/index.mjs +151 -1
- package/node-postgres/index.mjs.map +1 -1
- package/node-postgres/migrator.cjs +13 -1
- package/node-postgres/migrator.cjs.map +1 -1
- package/node-postgres/migrator.d.ts +5 -6
- package/node-postgres/migrator.mjs +11 -1
- package/node-postgres/migrator.mjs.map +1 -1
- package/package.json +97 -34
- package/pg-core/index.cjs +652 -1
- package/pg-core/index.cjs.map +1 -1
- package/pg-core/index.d.ts +13 -7
- package/pg-core/index.mjs +501 -1
- package/pg-core/index.mjs.map +1 -1
- package/planetscale-serverless/index.cjs +111 -1
- package/planetscale-serverless/index.cjs.map +1 -1
- package/planetscale-serverless/index.d.ts +5 -6
- package/planetscale-serverless/index.mjs +106 -1
- package/planetscale-serverless/index.mjs.map +1 -1
- package/planetscale-serverless/migrator.cjs +13 -1
- package/planetscale-serverless/migrator.cjs.map +1 -1
- package/planetscale-serverless/migrator.d.ts +5 -6
- package/planetscale-serverless/migrator.mjs +11 -1
- package/planetscale-serverless/migrator.mjs.map +1 -1
- package/postgres-js/index.cjs +113 -1
- package/postgres-js/index.cjs.map +1 -1
- package/postgres-js/index.d.ts +5 -6
- package/postgres-js/index.mjs +108 -1
- package/postgres-js/index.mjs.map +1 -1
- package/postgres-js/migrator.cjs +13 -1
- package/postgres-js/migrator.cjs.map +1 -1
- package/postgres-js/migrator.d.ts +5 -6
- package/postgres-js/migrator.mjs +11 -1
- package/postgres-js/migrator.mjs.map +1 -1
- package/query-promise.d-e370e0a9.d.ts +617 -0
- package/relations-47eb5c5f.mjs +2954 -0
- package/relations-47eb5c5f.mjs.map +1 -0
- package/relations-5e2d30dd.cjs +3117 -0
- package/relations-5e2d30dd.cjs.map +1 -0
- package/{select.types.d-c3e86d45.d.ts → select.types.d-34d7f74e.d.ts} +1 -1
- package/{select.types.d-adb82002.d.ts → select.types.d-ae2f8e44.d.ts} +58 -14
- package/session-483ed08d.mjs +1263 -0
- package/session-483ed08d.mjs.map +1 -0
- package/session-6bd76405.cjs +362 -0
- package/session-6bd76405.cjs.map +1 -0
- package/session-a90df8a2.cjs +1252 -0
- package/session-a90df8a2.cjs.map +1 -0
- package/session-b99382a2.mjs +1223 -0
- package/session-b99382a2.mjs.map +1 -0
- package/session-c62f6348.cjs +1298 -0
- package/session-c62f6348.cjs.map +1 -0
- package/session-e8745392.mjs +351 -0
- package/session-e8745392.mjs.map +1 -0
- package/sql-js/index.cjs +175 -1
- package/sql-js/index.cjs.map +1 -1
- package/sql-js/index.d.ts +14 -12
- package/sql-js/index.mjs +170 -1
- package/sql-js/index.mjs.map +1 -1
- package/sql-js/migrator.cjs +13 -1
- package/sql-js/migrator.cjs.map +1 -1
- package/sql-js/migrator.d.ts +5 -5
- package/sql-js/migrator.mjs +11 -1
- package/sql-js/migrator.mjs.map +1 -1
- package/sqlite-core/index.cjs +516 -1
- package/sqlite-core/index.cjs.map +1 -1
- package/sqlite-core/index.d.ts +6 -5
- package/sqlite-core/index.mjs +441 -1
- package/sqlite-core/index.mjs.map +1 -1
- package/sqlite-proxy/index.cjs +118 -1
- package/sqlite-proxy/index.cjs.map +1 -1
- package/sqlite-proxy/index.d.ts +12 -11
- package/sqlite-proxy/index.mjs +113 -1
- package/sqlite-proxy/index.mjs.map +1 -1
- package/sqlite-proxy/migrator.cjs +25 -2
- package/sqlite-proxy/migrator.cjs.map +1 -1
- package/sqlite-proxy/migrator.d.ts +5 -5
- package/sqlite-proxy/migrator.mjs +23 -2
- package/sqlite-proxy/migrator.mjs.map +1 -1
- package/version.cjs +9 -1
- package/version.cjs.map +1 -1
- package/version.d.ts +1 -1
- package/version.mjs +6 -1
- package/version.mjs.map +1 -1
- package/README.md +0 -150
- package/column-builder-592f0191.mjs +0 -2
- package/column-builder-592f0191.mjs.map +0 -1
- package/column-builder-b48639f3.cjs +0 -2
- package/column-builder-b48639f3.cjs.map +0 -1
- package/driver.d-0158cd93.d.ts +0 -11
- package/driver.d-1f73a4a9.d.ts +0 -70
- package/driver.d-2e907d12.d.ts +0 -17
- package/driver.d-3781598a.d.ts +0 -11
- package/driver.d-3a8adf2a.d.ts +0 -61
- package/driver.d-59580d08.d.ts +0 -11
- package/driver.d-5f3fc125.d.ts +0 -12
- package/driver.d-693f7f9f.d.ts +0 -56
- package/driver.d-6c43e393.d.ts +0 -60
- package/driver.d-b00fc6ec.d.ts +0 -57
- package/driver.d-e4bd120b.d.ts +0 -47
- package/driver.d-f4b5b390.d.ts +0 -11
- package/index-59b7992d.cjs +0 -2
- package/index-59b7992d.cjs.map +0 -1
- package/index-b71998f1.mjs +0 -2
- package/index-b71998f1.mjs.map +0 -1
- package/logger-04bad527.cjs +0 -2
- package/logger-04bad527.cjs.map +0 -1
- package/logger-2598bf05.mjs +0 -2
- package/logger-2598bf05.mjs.map +0 -1
- package/logger.d-37185354.d.ts +0 -21
- package/query-builder-2f2e8229.cjs +0 -2
- package/query-builder-2f2e8229.cjs.map +0 -1
- package/query-builder-2fcde2f0.mjs +0 -2
- package/query-builder-2fcde2f0.mjs.map +0 -1
- package/query-promise-2c5b43ab.cjs +0 -2
- package/query-promise-2c5b43ab.cjs.map +0 -1
- package/query-promise-a65edd44.mjs +0 -2
- package/query-promise-a65edd44.mjs.map +0 -1
- package/query-promise.d-a8af8583.d.ts +0 -9
- package/session-8a621f09.mjs +0 -8
- package/session-8a621f09.mjs.map +0 -1
- package/session-b6939bab.cjs +0 -14
- package/session-b6939bab.cjs.map +0 -1
- package/session-b977ce56.mjs +0 -14
- package/session-b977ce56.mjs.map +0 -1
- package/session-c891400d.mjs +0 -8
- package/session-c891400d.mjs.map +0 -1
- package/session-e6db6732.cjs +0 -8
- package/session-e6db6732.cjs.map +0 -1
- package/session-ef1ef979.cjs +0 -8
- package/session-ef1ef979.cjs.map +0 -1
- package/utils-9d882195.cjs +0 -2
- package/utils-9d882195.cjs.map +0 -1
- package/utils-e6870670.mjs +0 -2
- package/utils-e6870670.mjs.map +0 -1
|
@@ -0,0 +1,1298 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
var errors = require('./errors-d0192d62.cjs');
|
|
4
|
+
var relations = require('./relations-5e2d30dd.cjs');
|
|
5
|
+
|
|
6
|
+
var _a, _b;
|
|
7
|
+
/** @internal */
|
|
8
|
+
const InlineForeignKeys = Symbol('InlineForeignKeys');
|
|
9
|
+
class MySqlTable extends relations.Table {
|
|
10
|
+
constructor() {
|
|
11
|
+
super(...arguments);
|
|
12
|
+
/** @internal */
|
|
13
|
+
this[_a] = [];
|
|
14
|
+
/** @internal */
|
|
15
|
+
this[_b] = undefined;
|
|
16
|
+
}
|
|
17
|
+
}
|
|
18
|
+
relations.Table.Symbol.Columns, _a = InlineForeignKeys, _b = relations.Table.Symbol.ExtraConfigBuilder;
|
|
19
|
+
/** @internal */
|
|
20
|
+
MySqlTable.Symbol = Object.assign({}, relations.Table.Symbol, {
|
|
21
|
+
InlineForeignKeys: InlineForeignKeys,
|
|
22
|
+
});
|
|
23
|
+
function mysqlTableWithSchema(name, columns, extraConfig, schema, baseName = name) {
|
|
24
|
+
const rawTable = new MySqlTable(name, schema, baseName);
|
|
25
|
+
const builtColumns = Object.fromEntries(Object.entries(columns).map(([name, colBuilder]) => {
|
|
26
|
+
const column = colBuilder.build(rawTable);
|
|
27
|
+
rawTable[InlineForeignKeys].push(...colBuilder.buildForeignKeys(column, rawTable));
|
|
28
|
+
return [name, column];
|
|
29
|
+
}));
|
|
30
|
+
const table = Object.assign(rawTable, builtColumns);
|
|
31
|
+
table[relations.Table.Symbol.Columns] = builtColumns;
|
|
32
|
+
if (extraConfig) {
|
|
33
|
+
table[MySqlTable.Symbol.ExtraConfigBuilder] = extraConfig;
|
|
34
|
+
}
|
|
35
|
+
return table;
|
|
36
|
+
}
|
|
37
|
+
const mysqlTable = (name, columns, extraConfig) => {
|
|
38
|
+
return mysqlTableWithSchema(name, columns, extraConfig, undefined, name);
|
|
39
|
+
};
|
|
40
|
+
function mysqlTableCreator(customizeTableName) {
|
|
41
|
+
return (name, columns, extraConfig) => {
|
|
42
|
+
return mysqlTableWithSchema(customizeTableName(name), columns, extraConfig, undefined, name);
|
|
43
|
+
};
|
|
44
|
+
}
|
|
45
|
+
|
|
46
|
+
class ForeignKeyBuilder {
|
|
47
|
+
constructor(config, actions) {
|
|
48
|
+
this.reference = () => {
|
|
49
|
+
const { columns, foreignColumns } = config();
|
|
50
|
+
return { columns, foreignTable: foreignColumns[0].table, foreignColumns };
|
|
51
|
+
};
|
|
52
|
+
if (actions) {
|
|
53
|
+
this._onUpdate = actions.onUpdate;
|
|
54
|
+
this._onDelete = actions.onDelete;
|
|
55
|
+
}
|
|
56
|
+
}
|
|
57
|
+
onUpdate(action) {
|
|
58
|
+
this._onUpdate = action;
|
|
59
|
+
return this;
|
|
60
|
+
}
|
|
61
|
+
onDelete(action) {
|
|
62
|
+
this._onDelete = action;
|
|
63
|
+
return this;
|
|
64
|
+
}
|
|
65
|
+
/** @internal */
|
|
66
|
+
build(table) {
|
|
67
|
+
return new ForeignKey(table, this);
|
|
68
|
+
}
|
|
69
|
+
}
|
|
70
|
+
class ForeignKey {
|
|
71
|
+
constructor(table, builder) {
|
|
72
|
+
this.table = table;
|
|
73
|
+
this.reference = builder.reference;
|
|
74
|
+
this.onUpdate = builder._onUpdate;
|
|
75
|
+
this.onDelete = builder._onDelete;
|
|
76
|
+
}
|
|
77
|
+
getName() {
|
|
78
|
+
const { columns, foreignColumns } = this.reference();
|
|
79
|
+
const columnNames = columns.map((column) => column.name);
|
|
80
|
+
const foreignColumnNames = foreignColumns.map((column) => column.name);
|
|
81
|
+
const chunks = [
|
|
82
|
+
this.table[MySqlTable.Symbol.Name],
|
|
83
|
+
...columnNames,
|
|
84
|
+
foreignColumns[0].table[MySqlTable.Symbol.Name],
|
|
85
|
+
...foreignColumnNames,
|
|
86
|
+
];
|
|
87
|
+
return `${chunks.join('_')}_fk`;
|
|
88
|
+
}
|
|
89
|
+
}
|
|
90
|
+
function foreignKey(config) {
|
|
91
|
+
function mappedConfig() {
|
|
92
|
+
const { columns, foreignColumns } = config;
|
|
93
|
+
return {
|
|
94
|
+
columns,
|
|
95
|
+
foreignColumns,
|
|
96
|
+
};
|
|
97
|
+
}
|
|
98
|
+
return new ForeignKeyBuilder(mappedConfig);
|
|
99
|
+
}
|
|
100
|
+
|
|
101
|
+
class MySqlColumnBuilder extends relations.ColumnBuilder {
|
|
102
|
+
constructor() {
|
|
103
|
+
super(...arguments);
|
|
104
|
+
this.foreignKeyConfigs = [];
|
|
105
|
+
}
|
|
106
|
+
references(ref, actions = {}) {
|
|
107
|
+
this.foreignKeyConfigs.push({ ref, actions });
|
|
108
|
+
return this;
|
|
109
|
+
}
|
|
110
|
+
/** @internal */
|
|
111
|
+
buildForeignKeys(column, table) {
|
|
112
|
+
return this.foreignKeyConfigs.map(({ ref, actions }) => {
|
|
113
|
+
return ((ref, actions) => {
|
|
114
|
+
const builder = new ForeignKeyBuilder(() => {
|
|
115
|
+
const foreignColumn = ref();
|
|
116
|
+
return { columns: [column], foreignColumns: [foreignColumn] };
|
|
117
|
+
});
|
|
118
|
+
if (actions.onUpdate) {
|
|
119
|
+
builder.onUpdate(actions.onUpdate);
|
|
120
|
+
}
|
|
121
|
+
if (actions.onDelete) {
|
|
122
|
+
builder.onDelete(actions.onDelete);
|
|
123
|
+
}
|
|
124
|
+
return builder.build(table);
|
|
125
|
+
})(ref, actions);
|
|
126
|
+
});
|
|
127
|
+
}
|
|
128
|
+
}
|
|
129
|
+
// To understand how to use `MySqlColumn` and `AnyMySqlColumn`, see `Column` and `AnyColumn` documentation.
|
|
130
|
+
class MySqlColumn extends relations.Column {
|
|
131
|
+
}
|
|
132
|
+
class MySqlColumnBuilderWithAutoIncrement extends MySqlColumnBuilder {
|
|
133
|
+
constructor(name) {
|
|
134
|
+
super(name);
|
|
135
|
+
this.config.autoIncrement = false;
|
|
136
|
+
}
|
|
137
|
+
autoincrement() {
|
|
138
|
+
this.config.autoIncrement = true;
|
|
139
|
+
return this;
|
|
140
|
+
}
|
|
141
|
+
}
|
|
142
|
+
class MySqlColumnWithAutoIncrement extends MySqlColumn {
|
|
143
|
+
constructor() {
|
|
144
|
+
super(...arguments);
|
|
145
|
+
this.autoIncrement = this.config.autoIncrement;
|
|
146
|
+
}
|
|
147
|
+
}
|
|
148
|
+
|
|
149
|
+
class MySqlDelete extends relations.QueryPromise {
|
|
150
|
+
constructor(table, session, dialect) {
|
|
151
|
+
super();
|
|
152
|
+
this.table = table;
|
|
153
|
+
this.session = session;
|
|
154
|
+
this.dialect = dialect;
|
|
155
|
+
this.execute = (placeholderValues) => {
|
|
156
|
+
return this.prepare().execute(placeholderValues);
|
|
157
|
+
};
|
|
158
|
+
this.createIterator = () => {
|
|
159
|
+
const self = this;
|
|
160
|
+
return async function* (placeholderValues) {
|
|
161
|
+
yield* self.prepare().iterator(placeholderValues);
|
|
162
|
+
};
|
|
163
|
+
};
|
|
164
|
+
this.iterator = this.createIterator();
|
|
165
|
+
this.config = { table };
|
|
166
|
+
}
|
|
167
|
+
where(where) {
|
|
168
|
+
this.config.where = where;
|
|
169
|
+
return this;
|
|
170
|
+
}
|
|
171
|
+
/** @internal */
|
|
172
|
+
getSQL() {
|
|
173
|
+
return this.dialect.buildDeleteQuery(this.config);
|
|
174
|
+
}
|
|
175
|
+
toSQL() {
|
|
176
|
+
const { typings: _typings, ...rest } = this.dialect.sqlToQuery(this.getSQL());
|
|
177
|
+
return rest;
|
|
178
|
+
}
|
|
179
|
+
prepare() {
|
|
180
|
+
return this.session.prepareQuery(this.dialect.sqlToQuery(this.getSQL()), this.config.returning);
|
|
181
|
+
}
|
|
182
|
+
}
|
|
183
|
+
|
|
184
|
+
class MySqlInsertBuilder {
|
|
185
|
+
constructor(table, session, dialect) {
|
|
186
|
+
this.table = table;
|
|
187
|
+
this.session = session;
|
|
188
|
+
this.dialect = dialect;
|
|
189
|
+
this.shouldIgnore = false;
|
|
190
|
+
}
|
|
191
|
+
ignore() {
|
|
192
|
+
this.shouldIgnore = true;
|
|
193
|
+
return this;
|
|
194
|
+
}
|
|
195
|
+
values(values) {
|
|
196
|
+
values = Array.isArray(values) ? values : [values];
|
|
197
|
+
if (values.length === 0) {
|
|
198
|
+
throw new Error('values() must be called with at least one value');
|
|
199
|
+
}
|
|
200
|
+
const mappedValues = values.map((entry) => {
|
|
201
|
+
const result = {};
|
|
202
|
+
const cols = this.table[relations.Table.Symbol.Columns];
|
|
203
|
+
for (const colKey of Object.keys(entry)) {
|
|
204
|
+
const colValue = entry[colKey];
|
|
205
|
+
result[colKey] = colValue instanceof relations.SQL ? colValue : new relations.Param(colValue, cols[colKey]);
|
|
206
|
+
}
|
|
207
|
+
return result;
|
|
208
|
+
});
|
|
209
|
+
return new MySqlInsert(this.table, mappedValues, this.shouldIgnore, this.session, this.dialect);
|
|
210
|
+
}
|
|
211
|
+
}
|
|
212
|
+
class MySqlInsert extends relations.QueryPromise {
|
|
213
|
+
constructor(table, values, ignore, session, dialect) {
|
|
214
|
+
super();
|
|
215
|
+
this.session = session;
|
|
216
|
+
this.dialect = dialect;
|
|
217
|
+
this.execute = (placeholderValues) => {
|
|
218
|
+
return this.prepare().execute(placeholderValues);
|
|
219
|
+
};
|
|
220
|
+
this.createIterator = () => {
|
|
221
|
+
const self = this;
|
|
222
|
+
return async function* (placeholderValues) {
|
|
223
|
+
yield* self.prepare().iterator(placeholderValues);
|
|
224
|
+
};
|
|
225
|
+
};
|
|
226
|
+
this.iterator = this.createIterator();
|
|
227
|
+
this.config = { table, values, ignore };
|
|
228
|
+
}
|
|
229
|
+
onDuplicateKeyUpdate(config) {
|
|
230
|
+
const setSql = this.dialect.buildUpdateSet(this.config.table, relations.mapUpdateSet(this.config.table, config.set));
|
|
231
|
+
this.config.onConflict = relations.sql `update ${setSql}`;
|
|
232
|
+
return this;
|
|
233
|
+
}
|
|
234
|
+
/** @internal */
|
|
235
|
+
getSQL() {
|
|
236
|
+
return this.dialect.buildInsertQuery(this.config);
|
|
237
|
+
}
|
|
238
|
+
toSQL() {
|
|
239
|
+
const { typings: _typings, ...rest } = this.dialect.sqlToQuery(this.getSQL());
|
|
240
|
+
return rest;
|
|
241
|
+
}
|
|
242
|
+
prepare() {
|
|
243
|
+
return this.session.prepareQuery(this.dialect.sqlToQuery(this.getSQL()), undefined);
|
|
244
|
+
}
|
|
245
|
+
}
|
|
246
|
+
|
|
247
|
+
class ViewBuilderCore {
|
|
248
|
+
constructor(name, schema) {
|
|
249
|
+
this.name = name;
|
|
250
|
+
this.schema = schema;
|
|
251
|
+
this.config = {};
|
|
252
|
+
}
|
|
253
|
+
algorithm(algorithm) {
|
|
254
|
+
this.config.algorithm = algorithm;
|
|
255
|
+
return this;
|
|
256
|
+
}
|
|
257
|
+
definer(definer) {
|
|
258
|
+
this.config.definer = definer;
|
|
259
|
+
return this;
|
|
260
|
+
}
|
|
261
|
+
sqlSecurity(sqlSecurity) {
|
|
262
|
+
this.config.sqlSecurity = sqlSecurity;
|
|
263
|
+
return this;
|
|
264
|
+
}
|
|
265
|
+
withCheckOption(withCheckOption) {
|
|
266
|
+
this.config.withCheckOption = withCheckOption ?? 'cascaded';
|
|
267
|
+
return this;
|
|
268
|
+
}
|
|
269
|
+
}
|
|
270
|
+
class ViewBuilder extends ViewBuilderCore {
|
|
271
|
+
as(qb) {
|
|
272
|
+
if (typeof qb === 'function') {
|
|
273
|
+
qb = qb(new QueryBuilder());
|
|
274
|
+
}
|
|
275
|
+
const selectionProxy = new relations.SelectionProxyHandler({
|
|
276
|
+
alias: this.name,
|
|
277
|
+
sqlBehavior: 'error',
|
|
278
|
+
sqlAliasedBehavior: 'alias',
|
|
279
|
+
replaceOriginalName: true,
|
|
280
|
+
});
|
|
281
|
+
const aliasedSelection = new Proxy(qb.getSelectedFields(), selectionProxy);
|
|
282
|
+
return new Proxy(new MySqlView({
|
|
283
|
+
mysqlConfig: this.config,
|
|
284
|
+
config: {
|
|
285
|
+
name: this.name,
|
|
286
|
+
schema: this.schema,
|
|
287
|
+
selectedFields: aliasedSelection,
|
|
288
|
+
query: qb.getSQL().inlineParams(),
|
|
289
|
+
},
|
|
290
|
+
}), selectionProxy);
|
|
291
|
+
}
|
|
292
|
+
}
|
|
293
|
+
class ManualViewBuilder extends ViewBuilderCore {
|
|
294
|
+
constructor(name, columns, schema) {
|
|
295
|
+
super(name, schema);
|
|
296
|
+
this.columns = relations.getTableColumns(mysqlTable(name, columns));
|
|
297
|
+
}
|
|
298
|
+
existing() {
|
|
299
|
+
return new Proxy(new MySqlView({
|
|
300
|
+
mysqlConfig: undefined,
|
|
301
|
+
config: {
|
|
302
|
+
name: this.name,
|
|
303
|
+
schema: this.schema,
|
|
304
|
+
selectedFields: this.columns,
|
|
305
|
+
query: undefined,
|
|
306
|
+
},
|
|
307
|
+
}), new relations.SelectionProxyHandler({
|
|
308
|
+
alias: this.name,
|
|
309
|
+
sqlBehavior: 'error',
|
|
310
|
+
sqlAliasedBehavior: 'alias',
|
|
311
|
+
replaceOriginalName: true,
|
|
312
|
+
}));
|
|
313
|
+
}
|
|
314
|
+
as(query) {
|
|
315
|
+
return new Proxy(new MySqlView({
|
|
316
|
+
mysqlConfig: this.config,
|
|
317
|
+
config: {
|
|
318
|
+
name: this.name,
|
|
319
|
+
schema: this.schema,
|
|
320
|
+
selectedFields: this.columns,
|
|
321
|
+
query: query.inlineParams(),
|
|
322
|
+
},
|
|
323
|
+
}), new relations.SelectionProxyHandler({
|
|
324
|
+
alias: this.name,
|
|
325
|
+
sqlBehavior: 'error',
|
|
326
|
+
sqlAliasedBehavior: 'alias',
|
|
327
|
+
replaceOriginalName: true,
|
|
328
|
+
}));
|
|
329
|
+
}
|
|
330
|
+
}
|
|
331
|
+
class MySqlViewBase extends relations.View {
|
|
332
|
+
}
|
|
333
|
+
const MySqlViewConfig = Symbol('MySqlViewConfig');
|
|
334
|
+
class MySqlView extends MySqlViewBase {
|
|
335
|
+
constructor({ mysqlConfig, config }) {
|
|
336
|
+
super(config);
|
|
337
|
+
this[MySqlViewConfig] = mysqlConfig;
|
|
338
|
+
}
|
|
339
|
+
}
|
|
340
|
+
/** @internal */
|
|
341
|
+
function mysqlViewWithSchema(name, selection, schema) {
|
|
342
|
+
if (selection) {
|
|
343
|
+
return new ManualViewBuilder(name, selection, schema);
|
|
344
|
+
}
|
|
345
|
+
return new ViewBuilder(name, schema);
|
|
346
|
+
}
|
|
347
|
+
function mysqlView(name, selection) {
|
|
348
|
+
return mysqlViewWithSchema(name, selection, undefined);
|
|
349
|
+
}
|
|
350
|
+
|
|
351
|
+
// TODO find out how to use all/values. Seems like I need those functions
|
|
352
|
+
// Build project
|
|
353
|
+
// copy runtime tests to be sure it's working
|
|
354
|
+
// Add mysql to drizzle-kit
|
|
355
|
+
// Add Planetscale Driver and create example repo
|
|
356
|
+
class MySqlDialect {
|
|
357
|
+
async migrate(migrations, session, config) {
|
|
358
|
+
const migrationsTable = config.migrationsTable ?? '__drizzle_migrations';
|
|
359
|
+
const migrationTableCreate = relations.sql `
|
|
360
|
+
create table if not exists ${relations.name(migrationsTable)} (
|
|
361
|
+
id serial primary key,
|
|
362
|
+
hash text not null,
|
|
363
|
+
created_at bigint
|
|
364
|
+
)
|
|
365
|
+
`;
|
|
366
|
+
await session.execute(migrationTableCreate);
|
|
367
|
+
const dbMigrations = await session.all(relations.sql `select id, hash, created_at from ${relations.name(migrationsTable)} order by created_at desc limit 1`);
|
|
368
|
+
const lastDbMigration = dbMigrations[0];
|
|
369
|
+
await session.transaction(async (tx) => {
|
|
370
|
+
for (const migration of migrations) {
|
|
371
|
+
if (!lastDbMigration
|
|
372
|
+
|| Number(lastDbMigration.created_at) < migration.folderMillis) {
|
|
373
|
+
for (const stmt of migration.sql) {
|
|
374
|
+
await tx.execute(relations.sql.raw(stmt));
|
|
375
|
+
}
|
|
376
|
+
await tx.execute(relations.sql `insert into ${relations.name(migrationsTable)} (\`hash\`, \`created_at\`) values(${migration.hash}, ${migration.folderMillis})`);
|
|
377
|
+
}
|
|
378
|
+
}
|
|
379
|
+
});
|
|
380
|
+
}
|
|
381
|
+
escapeName(name) {
|
|
382
|
+
return `\`${name}\``;
|
|
383
|
+
}
|
|
384
|
+
escapeParam(_num) {
|
|
385
|
+
return `?`;
|
|
386
|
+
}
|
|
387
|
+
escapeString(str) {
|
|
388
|
+
return `'${str.replace(/'/g, "''")}'`;
|
|
389
|
+
}
|
|
390
|
+
buildDeleteQuery({ table, where, returning }) {
|
|
391
|
+
const returningSql = returning
|
|
392
|
+
? relations.sql ` returning ${this.buildSelection(returning, { isSingleTable: true })}`
|
|
393
|
+
: undefined;
|
|
394
|
+
const whereSql = where ? relations.sql ` where ${where}` : undefined;
|
|
395
|
+
return relations.sql `delete from ${table}${whereSql}${returningSql}`;
|
|
396
|
+
}
|
|
397
|
+
buildUpdateSet(table, set) {
|
|
398
|
+
const setEntries = Object.entries(set);
|
|
399
|
+
const setSize = setEntries.length;
|
|
400
|
+
return relations.sql.fromList(setEntries
|
|
401
|
+
.flatMap(([colName, value], i) => {
|
|
402
|
+
const col = table[relations.Table.Symbol.Columns][colName];
|
|
403
|
+
const res = relations.sql `${relations.name(col.name)} = ${value}`;
|
|
404
|
+
if (i < setSize - 1) {
|
|
405
|
+
return [res, relations.sql.raw(', ')];
|
|
406
|
+
}
|
|
407
|
+
return [res];
|
|
408
|
+
}));
|
|
409
|
+
}
|
|
410
|
+
buildUpdateQuery({ table, set, where, returning }) {
|
|
411
|
+
const setSql = this.buildUpdateSet(table, set);
|
|
412
|
+
const returningSql = returning
|
|
413
|
+
? relations.sql ` returning ${this.buildSelection(returning, { isSingleTable: true })}`
|
|
414
|
+
: undefined;
|
|
415
|
+
const whereSql = where ? relations.sql ` where ${where}` : undefined;
|
|
416
|
+
return relations.sql `update ${table} set ${setSql}${whereSql}${returningSql}`;
|
|
417
|
+
}
|
|
418
|
+
/**
|
|
419
|
+
* Builds selection SQL with provided fields/expressions
|
|
420
|
+
*
|
|
421
|
+
* Examples:
|
|
422
|
+
*
|
|
423
|
+
* `select <selection> from`
|
|
424
|
+
*
|
|
425
|
+
* `insert ... returning <selection>`
|
|
426
|
+
*
|
|
427
|
+
* If `isSingleTable` is true, then columns won't be prefixed with table name
|
|
428
|
+
*/
|
|
429
|
+
buildSelection(fields, { isSingleTable = false } = {}) {
|
|
430
|
+
const columnsLen = fields.length;
|
|
431
|
+
const chunks = fields
|
|
432
|
+
.flatMap(({ field }, i) => {
|
|
433
|
+
const chunk = [];
|
|
434
|
+
if (field instanceof relations.SQL.Aliased && field.isSelectionField) {
|
|
435
|
+
chunk.push(relations.name(field.fieldAlias));
|
|
436
|
+
}
|
|
437
|
+
else if (field instanceof relations.SQL.Aliased || field instanceof relations.SQL) {
|
|
438
|
+
const query = field instanceof relations.SQL.Aliased ? field.sql : field;
|
|
439
|
+
if (isSingleTable) {
|
|
440
|
+
chunk.push(new relations.SQL(query.queryChunks.map((c) => {
|
|
441
|
+
if (c instanceof MySqlColumn) {
|
|
442
|
+
return relations.name(c.name);
|
|
443
|
+
}
|
|
444
|
+
return c;
|
|
445
|
+
})));
|
|
446
|
+
}
|
|
447
|
+
else {
|
|
448
|
+
chunk.push(query);
|
|
449
|
+
}
|
|
450
|
+
if (field instanceof relations.SQL.Aliased) {
|
|
451
|
+
chunk.push(relations.sql ` as ${relations.name(field.fieldAlias)}`);
|
|
452
|
+
}
|
|
453
|
+
}
|
|
454
|
+
else if (field instanceof relations.Column) {
|
|
455
|
+
if (isSingleTable) {
|
|
456
|
+
chunk.push(relations.name(field.name));
|
|
457
|
+
}
|
|
458
|
+
else {
|
|
459
|
+
chunk.push(field);
|
|
460
|
+
}
|
|
461
|
+
}
|
|
462
|
+
if (i < columnsLen - 1) {
|
|
463
|
+
chunk.push(relations.sql `, `);
|
|
464
|
+
}
|
|
465
|
+
return chunk;
|
|
466
|
+
});
|
|
467
|
+
return relations.sql.fromList(chunks);
|
|
468
|
+
}
|
|
469
|
+
buildSelectQuery({ withList, fields, fieldsFlat, where, having, table, joins, orderBy, groupBy, limit, offset, lockingClause }) {
|
|
470
|
+
const fieldsList = fieldsFlat ?? relations.orderSelectedFields(fields);
|
|
471
|
+
for (const f of fieldsList) {
|
|
472
|
+
if (f.field instanceof relations.Column
|
|
473
|
+
&& relations.getTableName(f.field.table)
|
|
474
|
+
!== (table instanceof relations.Subquery
|
|
475
|
+
? table[relations.SubqueryConfig].alias
|
|
476
|
+
: table instanceof MySqlViewBase
|
|
477
|
+
? table[relations.ViewBaseConfig].name
|
|
478
|
+
: table instanceof relations.SQL
|
|
479
|
+
? undefined
|
|
480
|
+
: relations.getTableName(table))
|
|
481
|
+
&& !((table) => joins.some(({ alias }) => alias === relations.getTableName(table)))(f.field.table)) {
|
|
482
|
+
const tableName = relations.getTableName(f.field.table);
|
|
483
|
+
throw new Error(`Your "${f.path.join('->')}" field references a column "${tableName}"."${f.field.name}", but the table "${tableName}" is not part of the query! Did you forget to join it?`);
|
|
484
|
+
}
|
|
485
|
+
}
|
|
486
|
+
const isSingleTable = joins.length === 0;
|
|
487
|
+
let withSql;
|
|
488
|
+
if (withList.length) {
|
|
489
|
+
const withSqlChunks = [relations.sql `with `];
|
|
490
|
+
for (const [i, w] of withList.entries()) {
|
|
491
|
+
withSqlChunks.push(relations.sql `${relations.name(w[relations.SubqueryConfig].alias)} as (${w[relations.SubqueryConfig].sql})`);
|
|
492
|
+
if (i < withList.length - 1) {
|
|
493
|
+
withSqlChunks.push(relations.sql `, `);
|
|
494
|
+
}
|
|
495
|
+
}
|
|
496
|
+
withSqlChunks.push(relations.sql ` `);
|
|
497
|
+
withSql = relations.sql.fromList(withSqlChunks);
|
|
498
|
+
}
|
|
499
|
+
const selection = this.buildSelection(fieldsList, { isSingleTable });
|
|
500
|
+
const tableSql = (() => {
|
|
501
|
+
if (table instanceof relations.Table && table[relations.Table.Symbol.OriginalName] !== table[relations.Table.Symbol.Name]) {
|
|
502
|
+
return relations.sql `${relations.name(table[relations.Table.Symbol.OriginalName])} ${relations.name(table[relations.Table.Symbol.Name])}`;
|
|
503
|
+
}
|
|
504
|
+
return table;
|
|
505
|
+
})();
|
|
506
|
+
const joinsArray = [];
|
|
507
|
+
for (const [index, joinMeta] of joins.entries()) {
|
|
508
|
+
if (index === 0) {
|
|
509
|
+
joinsArray.push(relations.sql ` `);
|
|
510
|
+
}
|
|
511
|
+
const table = joinMeta.table;
|
|
512
|
+
if (table instanceof MySqlTable) {
|
|
513
|
+
const tableName = table[MySqlTable.Symbol.Name];
|
|
514
|
+
const tableSchema = table[MySqlTable.Symbol.Schema];
|
|
515
|
+
const origTableName = table[MySqlTable.Symbol.OriginalName];
|
|
516
|
+
const alias = tableName === origTableName ? undefined : joinMeta.alias;
|
|
517
|
+
joinsArray.push(relations.sql `${relations.sql.raw(joinMeta.joinType)} join ${tableSchema ? relations.sql `${relations.name(tableSchema)}.` : undefined}${relations.name(origTableName)}${alias && relations.sql ` ${relations.name(alias)}`} on ${joinMeta.on}`);
|
|
518
|
+
}
|
|
519
|
+
else if (table instanceof relations.View) {
|
|
520
|
+
const viewName = table[relations.ViewBaseConfig].name;
|
|
521
|
+
const viewSchema = table[relations.ViewBaseConfig].schema;
|
|
522
|
+
const origViewName = table[relations.ViewBaseConfig].originalName;
|
|
523
|
+
const alias = viewName === origViewName ? undefined : joinMeta.alias;
|
|
524
|
+
joinsArray.push(relations.sql `${relations.sql.raw(joinMeta.joinType)} join ${viewSchema ? relations.sql `${relations.name(viewSchema)}.` : undefined}${relations.name(origViewName)}${alias && relations.sql ` ${relations.name(alias)}`} on ${joinMeta.on}`);
|
|
525
|
+
}
|
|
526
|
+
else {
|
|
527
|
+
joinsArray.push(relations.sql `${relations.sql.raw(joinMeta.joinType)} join ${table} on ${joinMeta.on}`);
|
|
528
|
+
}
|
|
529
|
+
if (index < joins.length - 1) {
|
|
530
|
+
joinsArray.push(relations.sql ` `);
|
|
531
|
+
}
|
|
532
|
+
}
|
|
533
|
+
const joinsSql = relations.sql.fromList(joinsArray);
|
|
534
|
+
const whereSql = where ? relations.sql ` where ${where}` : undefined;
|
|
535
|
+
const havingSql = having ? relations.sql ` having ${having}` : undefined;
|
|
536
|
+
const orderByList = [];
|
|
537
|
+
for (const [index, orderByValue] of orderBy.entries()) {
|
|
538
|
+
orderByList.push(orderByValue);
|
|
539
|
+
if (index < orderBy.length - 1) {
|
|
540
|
+
orderByList.push(relations.sql `, `);
|
|
541
|
+
}
|
|
542
|
+
}
|
|
543
|
+
const orderBySql = orderByList.length > 0 ? relations.sql ` order by ${relations.sql.fromList(orderByList)}` : undefined;
|
|
544
|
+
const groupByList = [];
|
|
545
|
+
for (const [index, groupByValue] of groupBy.entries()) {
|
|
546
|
+
groupByList.push(groupByValue);
|
|
547
|
+
if (index < groupBy.length - 1) {
|
|
548
|
+
groupByList.push(relations.sql `, `);
|
|
549
|
+
}
|
|
550
|
+
}
|
|
551
|
+
const groupBySql = groupByList.length > 0 ? relations.sql ` group by ${relations.sql.fromList(groupByList)}` : undefined;
|
|
552
|
+
const limitSql = limit ? relations.sql ` limit ${limit}` : undefined;
|
|
553
|
+
const offsetSql = offset ? relations.sql ` offset ${offset}` : undefined;
|
|
554
|
+
let lockingClausesSql;
|
|
555
|
+
if (lockingClause) {
|
|
556
|
+
const { config, strength } = lockingClause;
|
|
557
|
+
lockingClausesSql = relations.sql ` for ${relations.sql.raw(strength)}`;
|
|
558
|
+
if (config.noWait) {
|
|
559
|
+
lockingClausesSql.append(relations.sql ` no wait`);
|
|
560
|
+
}
|
|
561
|
+
else if (config.skipLocked) {
|
|
562
|
+
lockingClausesSql.append(relations.sql ` skip locked`);
|
|
563
|
+
}
|
|
564
|
+
}
|
|
565
|
+
return relations.sql `${withSql}select ${selection} from ${tableSql}${joinsSql}${whereSql}${groupBySql}${havingSql}${orderBySql}${limitSql}${offsetSql}${lockingClausesSql}`;
|
|
566
|
+
}
|
|
567
|
+
buildInsertQuery({ table, values, ignore, onConflict }) {
|
|
568
|
+
const isSingleValue = values.length === 1;
|
|
569
|
+
const valuesSqlList = [];
|
|
570
|
+
const columns = table[relations.Table.Symbol.Columns];
|
|
571
|
+
const colEntries = isSingleValue
|
|
572
|
+
? Object.keys(values[0]).map((fieldName) => [fieldName, columns[fieldName]])
|
|
573
|
+
: Object.entries(columns);
|
|
574
|
+
const insertOrder = colEntries.map(([, column]) => relations.name(column.name));
|
|
575
|
+
for (const [valueIndex, value] of values.entries()) {
|
|
576
|
+
const valueList = [];
|
|
577
|
+
for (const [fieldName] of colEntries) {
|
|
578
|
+
const colValue = value[fieldName];
|
|
579
|
+
if (colValue === undefined || (colValue instanceof relations.Param && colValue.value === undefined)) {
|
|
580
|
+
valueList.push(relations.sql `default`);
|
|
581
|
+
}
|
|
582
|
+
else {
|
|
583
|
+
valueList.push(colValue);
|
|
584
|
+
}
|
|
585
|
+
}
|
|
586
|
+
valuesSqlList.push(valueList);
|
|
587
|
+
if (valueIndex < values.length - 1) {
|
|
588
|
+
valuesSqlList.push(relations.sql `, `);
|
|
589
|
+
}
|
|
590
|
+
}
|
|
591
|
+
const valuesSql = relations.sql.fromList(valuesSqlList);
|
|
592
|
+
const ignoreSql = ignore ? relations.sql ` ignore` : undefined;
|
|
593
|
+
const onConflictSql = onConflict ? relations.sql ` on duplicate key ${onConflict}` : undefined;
|
|
594
|
+
return relations.sql `insert${ignoreSql} into ${table} ${insertOrder} values ${valuesSql}${onConflictSql}`;
|
|
595
|
+
}
|
|
596
|
+
sqlToQuery(sql) {
|
|
597
|
+
return sql.toQuery({
|
|
598
|
+
escapeName: this.escapeName,
|
|
599
|
+
escapeParam: this.escapeParam,
|
|
600
|
+
escapeString: this.escapeString,
|
|
601
|
+
});
|
|
602
|
+
}
|
|
603
|
+
buildRelationalQuery(fullSchema, schema, tableNamesMap, table, tableConfig, config, tableAlias, relationColumns, isRoot = false) {
|
|
604
|
+
if (config === true) {
|
|
605
|
+
const selectionEntries = Object.entries(tableConfig.columns);
|
|
606
|
+
const selection = selectionEntries.map(([key, value]) => ({
|
|
607
|
+
dbKey: value.name,
|
|
608
|
+
tsKey: key,
|
|
609
|
+
field: value,
|
|
610
|
+
tableTsKey: undefined,
|
|
611
|
+
isJson: false,
|
|
612
|
+
selection: [],
|
|
613
|
+
}));
|
|
614
|
+
return {
|
|
615
|
+
tableTsKey: tableConfig.tsName,
|
|
616
|
+
sql: this.buildSelectQuery({
|
|
617
|
+
table,
|
|
618
|
+
fields: {},
|
|
619
|
+
fieldsFlat: selectionEntries.map(([, c]) => ({
|
|
620
|
+
path: [c.name],
|
|
621
|
+
field: c,
|
|
622
|
+
})),
|
|
623
|
+
groupBy: [],
|
|
624
|
+
orderBy: [],
|
|
625
|
+
joins: [],
|
|
626
|
+
withList: [],
|
|
627
|
+
}),
|
|
628
|
+
selection,
|
|
629
|
+
};
|
|
630
|
+
}
|
|
631
|
+
const aliasedColumns = Object.fromEntries(Object.entries(tableConfig.columns).map(([key, value]) => [key, relations.aliasedTableColumn(value, tableAlias)]));
|
|
632
|
+
const aliasedRelations = Object.fromEntries(Object.entries(tableConfig.relations).map(([key, value]) => [key, relations.aliasedRelation(value, tableAlias)]));
|
|
633
|
+
const aliasedFields = Object.assign({}, aliasedColumns, aliasedRelations);
|
|
634
|
+
const fieldsSelection = {};
|
|
635
|
+
let selectedColumns = [];
|
|
636
|
+
let selectedExtras = [];
|
|
637
|
+
let selectedRelations = [];
|
|
638
|
+
if (config.columns) {
|
|
639
|
+
let isIncludeMode = false;
|
|
640
|
+
for (const [field, value] of Object.entries(config.columns)) {
|
|
641
|
+
if (value === undefined) {
|
|
642
|
+
continue;
|
|
643
|
+
}
|
|
644
|
+
if (field in tableConfig.columns) {
|
|
645
|
+
if (!isIncludeMode && value === true) {
|
|
646
|
+
isIncludeMode = true;
|
|
647
|
+
}
|
|
648
|
+
selectedColumns.push(field);
|
|
649
|
+
}
|
|
650
|
+
}
|
|
651
|
+
if (selectedColumns.length > 0) {
|
|
652
|
+
selectedColumns = isIncludeMode
|
|
653
|
+
? selectedColumns.filter((c) => config.columns?.[c] === true)
|
|
654
|
+
: Object.keys(tableConfig.columns).filter((key) => !selectedColumns.includes(key));
|
|
655
|
+
}
|
|
656
|
+
}
|
|
657
|
+
if (config.with) {
|
|
658
|
+
selectedRelations = Object.entries(config.with)
|
|
659
|
+
.filter((entry) => !!entry[1])
|
|
660
|
+
.map(([key, value]) => ({ key, value }));
|
|
661
|
+
}
|
|
662
|
+
if (!config.columns) {
|
|
663
|
+
selectedColumns = Object.keys(tableConfig.columns);
|
|
664
|
+
}
|
|
665
|
+
if (config.extras) {
|
|
666
|
+
const extrasOrig = typeof config.extras === 'function'
|
|
667
|
+
? config.extras(aliasedFields, { sql: relations.sql })
|
|
668
|
+
: config.extras;
|
|
669
|
+
selectedExtras = Object.entries(extrasOrig).map(([key, value]) => ({
|
|
670
|
+
key,
|
|
671
|
+
value: relations.mapColumnsInAliasedSQLToAlias(value, tableAlias),
|
|
672
|
+
}));
|
|
673
|
+
}
|
|
674
|
+
for (const field of selectedColumns) {
|
|
675
|
+
const column = tableConfig.columns[field];
|
|
676
|
+
fieldsSelection[field] = column;
|
|
677
|
+
}
|
|
678
|
+
for (const { key, value } of selectedExtras) {
|
|
679
|
+
fieldsSelection[key] = value;
|
|
680
|
+
}
|
|
681
|
+
const builtRelations = [];
|
|
682
|
+
const joins = [];
|
|
683
|
+
const builtRelationFields = [];
|
|
684
|
+
for (const { key: selectedRelationKey, value: selectedRelationValue } of selectedRelations) {
|
|
685
|
+
let relation;
|
|
686
|
+
for (const [relationKey, relationValue] of Object.entries(tableConfig.relations)) {
|
|
687
|
+
if (relationValue instanceof relations.Relation && relationKey === selectedRelationKey) {
|
|
688
|
+
relation = relationValue;
|
|
689
|
+
break;
|
|
690
|
+
}
|
|
691
|
+
}
|
|
692
|
+
if (!relation) {
|
|
693
|
+
throw new Error(`Relation ${selectedRelationKey} not found`);
|
|
694
|
+
}
|
|
695
|
+
const normalizedRelation = relations.normalizeRelation(schema, tableNamesMap, relation);
|
|
696
|
+
const relationAlias = `${tableAlias}_${selectedRelationKey}`;
|
|
697
|
+
const builtRelation = this.buildRelationalQuery(fullSchema, schema, tableNamesMap, fullSchema[tableNamesMap[relation.referencedTable[relations.Table.Symbol.Name]]], schema[tableNamesMap[relation.referencedTable[relations.Table.Symbol.Name]]], selectedRelationValue, relationAlias, normalizedRelation.references);
|
|
698
|
+
builtRelations.push({ key: selectedRelationKey, value: builtRelation });
|
|
699
|
+
joins.push({
|
|
700
|
+
table: new relations.Subquery(builtRelation.sql, {}, relationAlias),
|
|
701
|
+
alias: selectedRelationKey,
|
|
702
|
+
on: relations.and(...normalizedRelation.fields.map((field, i) => relations.eq(relations.aliasedTableColumn(field, tableAlias), relations.aliasedTableColumn(normalizedRelation.references[i], relationAlias)))),
|
|
703
|
+
joinType: 'left',
|
|
704
|
+
});
|
|
705
|
+
const elseField = relations.sql `json_arrayagg(json_array(${relations.sql.join(builtRelation.selection.map(({ dbKey: key, isJson }) => {
|
|
706
|
+
const field = relations.sql `${relations.sql.identifier(relationAlias)}.${relations.sql.identifier(key)}`;
|
|
707
|
+
return isJson ? relations.sql `cast(${field} as json)` : field;
|
|
708
|
+
}), relations.sql `, `)}))`;
|
|
709
|
+
const field = relations.sql `if(count(${relations.sql.join(normalizedRelation.references.map((c) => relations.aliasedTableColumn(c, relationAlias)), relations.sql.raw(' or '))}) = 0, '[]', ${elseField})`.as(selectedRelationKey);
|
|
710
|
+
builtRelationFields.push({
|
|
711
|
+
path: [selectedRelationKey],
|
|
712
|
+
field,
|
|
713
|
+
});
|
|
714
|
+
}
|
|
715
|
+
const finalFieldsSelection = Object.entries(fieldsSelection).map(([key, value]) => {
|
|
716
|
+
return {
|
|
717
|
+
path: [key],
|
|
718
|
+
field: value instanceof relations.Column ? relations.aliasedTableColumn(value, tableAlias) : value,
|
|
719
|
+
};
|
|
720
|
+
});
|
|
721
|
+
const initialWhere = relations.and(...selectedRelations.filter(({ key }) => {
|
|
722
|
+
const relation = config.with?.[key];
|
|
723
|
+
return typeof relation === 'object' && relation.limit !== undefined;
|
|
724
|
+
}).map(({ key }) => {
|
|
725
|
+
const field = relations.sql `${relations.sql.identifier(`${tableAlias}_${key}`)}.${relations.sql.identifier('__drizzle_row_number')}`;
|
|
726
|
+
const value = config.with[key];
|
|
727
|
+
const cond = relations.or(relations.and(relations.sql `${field} <= ${value.limit}`), relations.sql `(${field} is null)`);
|
|
728
|
+
return cond;
|
|
729
|
+
}));
|
|
730
|
+
const groupBy = (builtRelationFields.length
|
|
731
|
+
? (tableConfig.primaryKey.length ? tableConfig.primaryKey : Object.values(tableConfig.columns)).map((c) => relations.aliasedTableColumn(c, tableAlias))
|
|
732
|
+
: []);
|
|
733
|
+
const finalFieldsFlat = isRoot
|
|
734
|
+
? [
|
|
735
|
+
...finalFieldsSelection.map(({ path, field }) => ({
|
|
736
|
+
path,
|
|
737
|
+
field: field instanceof relations.SQL.Aliased ? relations.sql `${relations.sql.identifier(field.fieldAlias)}` : field,
|
|
738
|
+
})),
|
|
739
|
+
...builtRelationFields.map(({ path, field }) => ({
|
|
740
|
+
path,
|
|
741
|
+
field: relations.sql `cast(${relations.sql.identifier(field.fieldAlias)} as json)`,
|
|
742
|
+
})),
|
|
743
|
+
]
|
|
744
|
+
: [
|
|
745
|
+
...Object.entries(tableConfig.columns).map(([tsKey, column]) => ({
|
|
746
|
+
path: [tsKey],
|
|
747
|
+
field: relations.aliasedTableColumn(column, tableAlias),
|
|
748
|
+
})),
|
|
749
|
+
...selectedExtras.map(({ key, value }) => ({
|
|
750
|
+
path: [key],
|
|
751
|
+
field: value,
|
|
752
|
+
})),
|
|
753
|
+
...builtRelationFields.map(({ path, field }) => ({
|
|
754
|
+
path,
|
|
755
|
+
field: relations.sql `${relations.sql.identifier(tableAlias)}.${relations.sql.identifier(field.fieldAlias)}`,
|
|
756
|
+
})),
|
|
757
|
+
];
|
|
758
|
+
if (finalFieldsFlat.length === 0) {
|
|
759
|
+
finalFieldsFlat.push({
|
|
760
|
+
path: [],
|
|
761
|
+
field: relations.sql.raw('1'),
|
|
762
|
+
});
|
|
763
|
+
}
|
|
764
|
+
const initialFieldsFlat = [
|
|
765
|
+
{
|
|
766
|
+
path: [],
|
|
767
|
+
field: relations.sql `${relations.sql.identifier(tableAlias)}.*`,
|
|
768
|
+
},
|
|
769
|
+
...selectedExtras.map(({ key, value }) => ({
|
|
770
|
+
path: [key],
|
|
771
|
+
field: value,
|
|
772
|
+
})),
|
|
773
|
+
...builtRelationFields,
|
|
774
|
+
];
|
|
775
|
+
let orderByOrig = typeof config.orderBy === 'function'
|
|
776
|
+
? config.orderBy(aliasedFields, relations.orderByOperators)
|
|
777
|
+
: config.orderBy ?? [];
|
|
778
|
+
if (!Array.isArray(orderByOrig)) {
|
|
779
|
+
orderByOrig = [orderByOrig];
|
|
780
|
+
}
|
|
781
|
+
const orderBy = orderByOrig.map((orderByValue) => {
|
|
782
|
+
if (orderByValue instanceof relations.Column) {
|
|
783
|
+
return relations.aliasedTableColumn(orderByValue, tableAlias);
|
|
784
|
+
}
|
|
785
|
+
return relations.mapColumnsInSQLToAlias(orderByValue, tableAlias);
|
|
786
|
+
});
|
|
787
|
+
if (!isRoot && !config.limit && orderBy.length > 0) {
|
|
788
|
+
finalFieldsFlat.push({
|
|
789
|
+
path: ['__drizzle_row_number'],
|
|
790
|
+
field: relations.sql `row_number() over(order by ${relations.sql.join(orderBy, relations.sql `, `)})`,
|
|
791
|
+
});
|
|
792
|
+
}
|
|
793
|
+
let limit, offset;
|
|
794
|
+
if (config.limit !== undefined || config.offset !== undefined) {
|
|
795
|
+
if (isRoot) {
|
|
796
|
+
limit = config.limit;
|
|
797
|
+
offset = config.offset;
|
|
798
|
+
}
|
|
799
|
+
else {
|
|
800
|
+
finalFieldsFlat.push({
|
|
801
|
+
path: ['__drizzle_row_number'],
|
|
802
|
+
field: relations.sql `row_number() over(partition by ${relationColumns.map((c) => relations.aliasedTableColumn(c, tableAlias))}${(orderBy.length > 0 && !isRoot) ? relations.sql ` order by ${relations.sql.join(orderBy, relations.sql `, `)}` : undefined})`
|
|
803
|
+
.as('__drizzle_row_number'),
|
|
804
|
+
});
|
|
805
|
+
}
|
|
806
|
+
}
|
|
807
|
+
let result = this.buildSelectQuery({
|
|
808
|
+
table: relations.aliasedTable(table, tableAlias),
|
|
809
|
+
fields: {},
|
|
810
|
+
fieldsFlat: initialFieldsFlat,
|
|
811
|
+
where: initialWhere,
|
|
812
|
+
groupBy,
|
|
813
|
+
orderBy: [],
|
|
814
|
+
joins,
|
|
815
|
+
withList: [],
|
|
816
|
+
});
|
|
817
|
+
let where;
|
|
818
|
+
if (config.where) {
|
|
819
|
+
const whereSql = typeof config.where === 'function' ? config.where(aliasedFields, relations.operators) : config.where;
|
|
820
|
+
where = whereSql && relations.mapColumnsInSQLToAlias(whereSql, tableAlias);
|
|
821
|
+
}
|
|
822
|
+
result = this.buildSelectQuery({
|
|
823
|
+
table: new relations.Subquery(result, {}, tableAlias),
|
|
824
|
+
fields: {},
|
|
825
|
+
fieldsFlat: finalFieldsFlat,
|
|
826
|
+
where,
|
|
827
|
+
groupBy: [],
|
|
828
|
+
orderBy: isRoot ? orderBy : [],
|
|
829
|
+
joins: [],
|
|
830
|
+
withList: [],
|
|
831
|
+
limit,
|
|
832
|
+
offset: offset,
|
|
833
|
+
});
|
|
834
|
+
return {
|
|
835
|
+
tableTsKey: tableConfig.tsName,
|
|
836
|
+
sql: result,
|
|
837
|
+
selection: [
|
|
838
|
+
...finalFieldsSelection.map(({ path, field }) => ({
|
|
839
|
+
dbKey: field instanceof relations.SQL.Aliased ? field.fieldAlias : tableConfig.columns[path[0]].name,
|
|
840
|
+
tsKey: path[0],
|
|
841
|
+
field,
|
|
842
|
+
tableTsKey: undefined,
|
|
843
|
+
isJson: false,
|
|
844
|
+
selection: [],
|
|
845
|
+
})),
|
|
846
|
+
...builtRelations.map(({ key, value }) => ({
|
|
847
|
+
dbKey: key,
|
|
848
|
+
tsKey: key,
|
|
849
|
+
field: undefined,
|
|
850
|
+
tableTsKey: value.tableTsKey,
|
|
851
|
+
isJson: true,
|
|
852
|
+
selection: value.selection,
|
|
853
|
+
})),
|
|
854
|
+
],
|
|
855
|
+
};
|
|
856
|
+
}
|
|
857
|
+
}
|
|
858
|
+
|
|
859
|
+
class MySqlSelectBuilder {
|
|
860
|
+
constructor(fields, session, dialect, withList = []) {
|
|
861
|
+
this.fields = fields;
|
|
862
|
+
this.session = session;
|
|
863
|
+
this.dialect = dialect;
|
|
864
|
+
this.withList = withList;
|
|
865
|
+
}
|
|
866
|
+
from(source) {
|
|
867
|
+
const isPartialSelect = !!this.fields;
|
|
868
|
+
let fields;
|
|
869
|
+
if (this.fields) {
|
|
870
|
+
fields = this.fields;
|
|
871
|
+
}
|
|
872
|
+
else if (source instanceof relations.Subquery) {
|
|
873
|
+
// This is required to use the proxy handler to get the correct field values from the subquery
|
|
874
|
+
fields = Object.fromEntries(Object.keys(source[relations.SubqueryConfig].selection).map((key) => [key, source[key]]));
|
|
875
|
+
}
|
|
876
|
+
else if (source instanceof MySqlViewBase) {
|
|
877
|
+
fields = source[relations.ViewBaseConfig].selectedFields;
|
|
878
|
+
}
|
|
879
|
+
else if (source instanceof relations.SQL) {
|
|
880
|
+
fields = {};
|
|
881
|
+
}
|
|
882
|
+
else {
|
|
883
|
+
fields = relations.getTableColumns(source);
|
|
884
|
+
}
|
|
885
|
+
return new MySqlSelect(source, fields, isPartialSelect, this.session, this.dialect, this.withList);
|
|
886
|
+
}
|
|
887
|
+
}
|
|
888
|
+
class MySqlSelectQueryBuilder extends relations.TypedQueryBuilder {
|
|
889
|
+
constructor(table, fields, isPartialSelect,
|
|
890
|
+
/** @internal */
|
|
891
|
+
session, dialect, withList) {
|
|
892
|
+
super();
|
|
893
|
+
this.isPartialSelect = isPartialSelect;
|
|
894
|
+
this.session = session;
|
|
895
|
+
this.dialect = dialect;
|
|
896
|
+
this.leftJoin = this.createJoin('left');
|
|
897
|
+
this.rightJoin = this.createJoin('right');
|
|
898
|
+
this.innerJoin = this.createJoin('inner');
|
|
899
|
+
this.fullJoin = this.createJoin('full');
|
|
900
|
+
this.config = {
|
|
901
|
+
withList,
|
|
902
|
+
table,
|
|
903
|
+
fields: { ...fields },
|
|
904
|
+
joins: [],
|
|
905
|
+
orderBy: [],
|
|
906
|
+
groupBy: [],
|
|
907
|
+
};
|
|
908
|
+
this._ = {
|
|
909
|
+
selectedFields: fields,
|
|
910
|
+
};
|
|
911
|
+
this.tableName = relations.getTableLikeName(table);
|
|
912
|
+
this.joinsNotNullableMap = typeof this.tableName === 'string' ? { [this.tableName]: true } : {};
|
|
913
|
+
}
|
|
914
|
+
createJoin(joinType) {
|
|
915
|
+
return (table, on) => {
|
|
916
|
+
const baseTableName = this.tableName;
|
|
917
|
+
const tableName = relations.getTableLikeName(table);
|
|
918
|
+
if (typeof tableName === 'string' && this.config.joins.some((join) => join.alias === tableName)) {
|
|
919
|
+
throw new Error(`Alias "${tableName}" is already used in this query`);
|
|
920
|
+
}
|
|
921
|
+
if (!this.isPartialSelect) {
|
|
922
|
+
// If this is the first join and this is not a partial select and we're not selecting from raw SQL, "move" the fields from the main table to the nested object
|
|
923
|
+
if (Object.keys(this.joinsNotNullableMap).length === 1 && typeof baseTableName === 'string') {
|
|
924
|
+
this.config.fields = {
|
|
925
|
+
[baseTableName]: this.config.fields,
|
|
926
|
+
};
|
|
927
|
+
}
|
|
928
|
+
if (typeof tableName === 'string' && !(table instanceof relations.SQL)) {
|
|
929
|
+
const selection = table instanceof relations.Subquery
|
|
930
|
+
? table[relations.SubqueryConfig].selection
|
|
931
|
+
: table instanceof relations.View
|
|
932
|
+
? table[relations.ViewBaseConfig].selectedFields
|
|
933
|
+
: table[relations.Table.Symbol.Columns];
|
|
934
|
+
this.config.fields[tableName] = selection;
|
|
935
|
+
}
|
|
936
|
+
}
|
|
937
|
+
if (typeof on === 'function') {
|
|
938
|
+
on = on(new Proxy(this.config.fields, new relations.SelectionProxyHandler({ sqlAliasedBehavior: 'sql', sqlBehavior: 'sql' })));
|
|
939
|
+
}
|
|
940
|
+
this.config.joins.push({ on, table, joinType, alias: tableName });
|
|
941
|
+
if (typeof tableName === 'string') {
|
|
942
|
+
switch (joinType) {
|
|
943
|
+
case 'left': {
|
|
944
|
+
this.joinsNotNullableMap[tableName] = false;
|
|
945
|
+
break;
|
|
946
|
+
}
|
|
947
|
+
case 'right': {
|
|
948
|
+
this.joinsNotNullableMap = Object.fromEntries(Object.entries(this.joinsNotNullableMap).map(([key]) => [key, false]));
|
|
949
|
+
this.joinsNotNullableMap[tableName] = true;
|
|
950
|
+
break;
|
|
951
|
+
}
|
|
952
|
+
case 'inner': {
|
|
953
|
+
this.joinsNotNullableMap[tableName] = true;
|
|
954
|
+
break;
|
|
955
|
+
}
|
|
956
|
+
case 'full': {
|
|
957
|
+
this.joinsNotNullableMap = Object.fromEntries(Object.entries(this.joinsNotNullableMap).map(([key]) => [key, false]));
|
|
958
|
+
this.joinsNotNullableMap[tableName] = false;
|
|
959
|
+
break;
|
|
960
|
+
}
|
|
961
|
+
}
|
|
962
|
+
}
|
|
963
|
+
return this;
|
|
964
|
+
};
|
|
965
|
+
}
|
|
966
|
+
where(where) {
|
|
967
|
+
if (typeof where === 'function') {
|
|
968
|
+
where = where(new Proxy(this.config.fields, new relations.SelectionProxyHandler({ sqlAliasedBehavior: 'sql', sqlBehavior: 'sql' })));
|
|
969
|
+
}
|
|
970
|
+
this.config.where = where;
|
|
971
|
+
return this;
|
|
972
|
+
}
|
|
973
|
+
having(having) {
|
|
974
|
+
if (typeof having === 'function') {
|
|
975
|
+
having = having(new Proxy(this.config.fields, new relations.SelectionProxyHandler({ sqlAliasedBehavior: 'sql', sqlBehavior: 'sql' })));
|
|
976
|
+
}
|
|
977
|
+
this.config.having = having;
|
|
978
|
+
return this;
|
|
979
|
+
}
|
|
980
|
+
groupBy(...columns) {
|
|
981
|
+
if (typeof columns[0] === 'function') {
|
|
982
|
+
const groupBy = columns[0](new Proxy(this.config.fields, new relations.SelectionProxyHandler({ sqlAliasedBehavior: 'alias', sqlBehavior: 'sql' })));
|
|
983
|
+
this.config.groupBy = Array.isArray(groupBy) ? groupBy : [groupBy];
|
|
984
|
+
}
|
|
985
|
+
else {
|
|
986
|
+
this.config.groupBy = columns;
|
|
987
|
+
}
|
|
988
|
+
return this;
|
|
989
|
+
}
|
|
990
|
+
orderBy(...columns) {
|
|
991
|
+
if (typeof columns[0] === 'function') {
|
|
992
|
+
const orderBy = columns[0](new Proxy(this.config.fields, new relations.SelectionProxyHandler({ sqlAliasedBehavior: 'alias', sqlBehavior: 'sql' })));
|
|
993
|
+
this.config.orderBy = Array.isArray(orderBy) ? orderBy : [orderBy];
|
|
994
|
+
}
|
|
995
|
+
else {
|
|
996
|
+
this.config.orderBy = columns;
|
|
997
|
+
}
|
|
998
|
+
return this;
|
|
999
|
+
}
|
|
1000
|
+
limit(limit) {
|
|
1001
|
+
this.config.limit = limit;
|
|
1002
|
+
return this;
|
|
1003
|
+
}
|
|
1004
|
+
offset(offset) {
|
|
1005
|
+
this.config.offset = offset;
|
|
1006
|
+
return this;
|
|
1007
|
+
}
|
|
1008
|
+
for(strength, config = {}) {
|
|
1009
|
+
this.config.lockingClause = { strength, config };
|
|
1010
|
+
return this;
|
|
1011
|
+
}
|
|
1012
|
+
/** @internal */
|
|
1013
|
+
getSQL() {
|
|
1014
|
+
return this.dialect.buildSelectQuery(this.config);
|
|
1015
|
+
}
|
|
1016
|
+
toSQL() {
|
|
1017
|
+
const { typings: _typings, ...rest } = this.dialect.sqlToQuery(this.getSQL());
|
|
1018
|
+
return rest;
|
|
1019
|
+
}
|
|
1020
|
+
as(alias) {
|
|
1021
|
+
return new Proxy(new relations.Subquery(this.getSQL(), this.config.fields, alias), new relations.SelectionProxyHandler({ alias, sqlAliasedBehavior: 'alias', sqlBehavior: 'error' }));
|
|
1022
|
+
}
|
|
1023
|
+
}
|
|
1024
|
+
class MySqlSelect extends MySqlSelectQueryBuilder {
|
|
1025
|
+
constructor() {
|
|
1026
|
+
super(...arguments);
|
|
1027
|
+
this.execute = ((placeholderValues) => {
|
|
1028
|
+
return this.prepare().execute(placeholderValues);
|
|
1029
|
+
});
|
|
1030
|
+
this.createIterator = () => {
|
|
1031
|
+
const self = this;
|
|
1032
|
+
return async function* (placeholderValues) {
|
|
1033
|
+
yield* self.prepare().iterator(placeholderValues);
|
|
1034
|
+
};
|
|
1035
|
+
};
|
|
1036
|
+
this.iterator = this.createIterator();
|
|
1037
|
+
}
|
|
1038
|
+
prepare() {
|
|
1039
|
+
if (!this.session) {
|
|
1040
|
+
throw new Error('Cannot execute a query on a query builder. Please use a database instance instead.');
|
|
1041
|
+
}
|
|
1042
|
+
const fieldsList = relations.orderSelectedFields(this.config.fields);
|
|
1043
|
+
const query = this.session.prepareQuery(this.dialect.sqlToQuery(this.getSQL()), fieldsList);
|
|
1044
|
+
query.joinsNotNullableMap = this.joinsNotNullableMap;
|
|
1045
|
+
return query;
|
|
1046
|
+
}
|
|
1047
|
+
}
|
|
1048
|
+
relations.applyMixins(MySqlSelect, [relations.QueryPromise]);
|
|
1049
|
+
|
|
1050
|
+
class QueryBuilder {
|
|
1051
|
+
$with(alias) {
|
|
1052
|
+
const queryBuilder = this;
|
|
1053
|
+
return {
|
|
1054
|
+
as(qb) {
|
|
1055
|
+
if (typeof qb === 'function') {
|
|
1056
|
+
qb = qb(queryBuilder);
|
|
1057
|
+
}
|
|
1058
|
+
return new Proxy(new relations.WithSubquery(qb.getSQL(), qb.getSelectedFields(), alias, true), new relations.SelectionProxyHandler({ alias, sqlAliasedBehavior: 'alias', sqlBehavior: 'error' }));
|
|
1059
|
+
},
|
|
1060
|
+
};
|
|
1061
|
+
}
|
|
1062
|
+
with(...queries) {
|
|
1063
|
+
const self = this;
|
|
1064
|
+
function select(fields) {
|
|
1065
|
+
return new MySqlSelectBuilder(fields ?? undefined, undefined, self.getDialect(), queries);
|
|
1066
|
+
}
|
|
1067
|
+
return { select };
|
|
1068
|
+
}
|
|
1069
|
+
select(fields) {
|
|
1070
|
+
return new MySqlSelectBuilder(fields ?? undefined, undefined, this.getDialect());
|
|
1071
|
+
}
|
|
1072
|
+
// Lazy load dialect to avoid circular dependency
|
|
1073
|
+
getDialect() {
|
|
1074
|
+
if (!this.dialect) {
|
|
1075
|
+
this.dialect = new MySqlDialect();
|
|
1076
|
+
}
|
|
1077
|
+
return this.dialect;
|
|
1078
|
+
}
|
|
1079
|
+
}
|
|
1080
|
+
|
|
1081
|
+
class MySqlUpdateBuilder {
|
|
1082
|
+
constructor(table, session, dialect) {
|
|
1083
|
+
this.table = table;
|
|
1084
|
+
this.session = session;
|
|
1085
|
+
this.dialect = dialect;
|
|
1086
|
+
}
|
|
1087
|
+
set(values) {
|
|
1088
|
+
return new MySqlUpdate(this.table, relations.mapUpdateSet(this.table, values), this.session, this.dialect);
|
|
1089
|
+
}
|
|
1090
|
+
}
|
|
1091
|
+
class MySqlUpdate extends relations.QueryPromise {
|
|
1092
|
+
constructor(table, set, session, dialect) {
|
|
1093
|
+
super();
|
|
1094
|
+
this.session = session;
|
|
1095
|
+
this.dialect = dialect;
|
|
1096
|
+
this.execute = (placeholderValues) => {
|
|
1097
|
+
return this.prepare().execute(placeholderValues);
|
|
1098
|
+
};
|
|
1099
|
+
this.createIterator = () => {
|
|
1100
|
+
const self = this;
|
|
1101
|
+
return async function* (placeholderValues) {
|
|
1102
|
+
yield* self.prepare().iterator(placeholderValues);
|
|
1103
|
+
};
|
|
1104
|
+
};
|
|
1105
|
+
this.iterator = this.createIterator();
|
|
1106
|
+
this.config = { set, table };
|
|
1107
|
+
}
|
|
1108
|
+
where(where) {
|
|
1109
|
+
this.config.where = where;
|
|
1110
|
+
return this;
|
|
1111
|
+
}
|
|
1112
|
+
/** @internal */
|
|
1113
|
+
getSQL() {
|
|
1114
|
+
return this.dialect.buildUpdateQuery(this.config);
|
|
1115
|
+
}
|
|
1116
|
+
toSQL() {
|
|
1117
|
+
const { typings: _typings, ...rest } = this.dialect.sqlToQuery(this.getSQL());
|
|
1118
|
+
return rest;
|
|
1119
|
+
}
|
|
1120
|
+
prepare() {
|
|
1121
|
+
return this.session.prepareQuery(this.dialect.sqlToQuery(this.getSQL()), this.config.returning);
|
|
1122
|
+
}
|
|
1123
|
+
}
|
|
1124
|
+
|
|
1125
|
+
class RelationalQueryBuilder {
|
|
1126
|
+
constructor(fullSchema, schema, tableNamesMap, table, tableConfig, dialect, session) {
|
|
1127
|
+
this.fullSchema = fullSchema;
|
|
1128
|
+
this.schema = schema;
|
|
1129
|
+
this.tableNamesMap = tableNamesMap;
|
|
1130
|
+
this.table = table;
|
|
1131
|
+
this.tableConfig = tableConfig;
|
|
1132
|
+
this.dialect = dialect;
|
|
1133
|
+
this.session = session;
|
|
1134
|
+
}
|
|
1135
|
+
findMany(config) {
|
|
1136
|
+
return new MySqlRelationalQuery(this.fullSchema, this.schema, this.tableNamesMap, this.table, this.tableConfig, this.dialect, this.session, config ? config : true, 'many');
|
|
1137
|
+
}
|
|
1138
|
+
findFirst(config) {
|
|
1139
|
+
return new MySqlRelationalQuery(this.fullSchema, this.schema, this.tableNamesMap, this.table, this.tableConfig, this.dialect, this.session, config ? { ...config, limit: 1 } : { limit: 1 }, 'first');
|
|
1140
|
+
}
|
|
1141
|
+
}
|
|
1142
|
+
class MySqlRelationalQuery extends relations.QueryPromise {
|
|
1143
|
+
constructor(fullSchema, schema, tableNamesMap, table, tableConfig, dialect, session, config, mode) {
|
|
1144
|
+
super();
|
|
1145
|
+
this.fullSchema = fullSchema;
|
|
1146
|
+
this.schema = schema;
|
|
1147
|
+
this.tableNamesMap = tableNamesMap;
|
|
1148
|
+
this.table = table;
|
|
1149
|
+
this.tableConfig = tableConfig;
|
|
1150
|
+
this.dialect = dialect;
|
|
1151
|
+
this.session = session;
|
|
1152
|
+
this.config = config;
|
|
1153
|
+
this.mode = mode;
|
|
1154
|
+
}
|
|
1155
|
+
prepare() {
|
|
1156
|
+
const query = this.dialect.buildRelationalQuery(this.fullSchema, this.schema, this.tableNamesMap, this.table, this.tableConfig, this.config, this.tableConfig.tsName, [], true);
|
|
1157
|
+
const builtQuery = this.dialect.sqlToQuery(query.sql);
|
|
1158
|
+
return this.session.prepareQuery(builtQuery, undefined, (rawRows) => {
|
|
1159
|
+
const rows = rawRows.map((row) => relations.mapRelationalRow(this.schema, this.tableConfig, row, query.selection));
|
|
1160
|
+
if (this.mode === 'first') {
|
|
1161
|
+
return rows[0];
|
|
1162
|
+
}
|
|
1163
|
+
return rows;
|
|
1164
|
+
});
|
|
1165
|
+
}
|
|
1166
|
+
execute() {
|
|
1167
|
+
return this.prepare().execute();
|
|
1168
|
+
}
|
|
1169
|
+
}
|
|
1170
|
+
|
|
1171
|
+
class MySqlDatabase {
|
|
1172
|
+
constructor(
|
|
1173
|
+
/** @internal */
|
|
1174
|
+
dialect,
|
|
1175
|
+
/** @internal */
|
|
1176
|
+
session, schema) {
|
|
1177
|
+
this.dialect = dialect;
|
|
1178
|
+
this.session = session;
|
|
1179
|
+
this._ = schema
|
|
1180
|
+
? { schema: schema.schema, tableNamesMap: schema.tableNamesMap }
|
|
1181
|
+
: { schema: undefined, tableNamesMap: {} };
|
|
1182
|
+
this.query = {};
|
|
1183
|
+
if (this._.schema) {
|
|
1184
|
+
for (const [tableName, columns] of Object.entries(this._.schema)) {
|
|
1185
|
+
this.query[tableName] = new RelationalQueryBuilder(schema.fullSchema, this._.schema, this._.tableNamesMap, schema.fullSchema[tableName], columns, dialect, session);
|
|
1186
|
+
}
|
|
1187
|
+
}
|
|
1188
|
+
}
|
|
1189
|
+
$with(alias) {
|
|
1190
|
+
return {
|
|
1191
|
+
as(qb) {
|
|
1192
|
+
if (typeof qb === 'function') {
|
|
1193
|
+
qb = qb(new QueryBuilder());
|
|
1194
|
+
}
|
|
1195
|
+
return new Proxy(new relations.WithSubquery(qb.getSQL(), qb.getSelectedFields(), alias, true), new relations.SelectionProxyHandler({ alias, sqlAliasedBehavior: 'alias', sqlBehavior: 'error' }));
|
|
1196
|
+
},
|
|
1197
|
+
};
|
|
1198
|
+
}
|
|
1199
|
+
with(...queries) {
|
|
1200
|
+
const self = this;
|
|
1201
|
+
function select(fields) {
|
|
1202
|
+
return new MySqlSelectBuilder(fields ?? undefined, self.session, self.dialect, queries);
|
|
1203
|
+
}
|
|
1204
|
+
return { select };
|
|
1205
|
+
}
|
|
1206
|
+
select(fields) {
|
|
1207
|
+
return new MySqlSelectBuilder(fields ?? undefined, this.session, this.dialect);
|
|
1208
|
+
}
|
|
1209
|
+
update(table) {
|
|
1210
|
+
return new MySqlUpdateBuilder(table, this.session, this.dialect);
|
|
1211
|
+
}
|
|
1212
|
+
insert(table) {
|
|
1213
|
+
return new MySqlInsertBuilder(table, this.session, this.dialect);
|
|
1214
|
+
}
|
|
1215
|
+
delete(table) {
|
|
1216
|
+
return new MySqlDelete(table, this.session, this.dialect);
|
|
1217
|
+
}
|
|
1218
|
+
execute(query) {
|
|
1219
|
+
return this.session.execute(query.getSQL());
|
|
1220
|
+
}
|
|
1221
|
+
transaction(transaction, config) {
|
|
1222
|
+
return this.session.transaction(transaction, config);
|
|
1223
|
+
}
|
|
1224
|
+
}
|
|
1225
|
+
|
|
1226
|
+
class PreparedQuery {
|
|
1227
|
+
}
|
|
1228
|
+
class MySqlSession {
|
|
1229
|
+
constructor(dialect) {
|
|
1230
|
+
this.dialect = dialect;
|
|
1231
|
+
}
|
|
1232
|
+
execute(query) {
|
|
1233
|
+
return this.prepareQuery(this.dialect.sqlToQuery(query), undefined).execute();
|
|
1234
|
+
}
|
|
1235
|
+
getSetTransactionSQL(config) {
|
|
1236
|
+
const parts = [];
|
|
1237
|
+
if (config.isolationLevel) {
|
|
1238
|
+
parts.push(`isolation level ${config.isolationLevel}`);
|
|
1239
|
+
}
|
|
1240
|
+
return parts.length ? relations.sql.fromList(['set transaction ', parts.join(' ')]) : undefined;
|
|
1241
|
+
}
|
|
1242
|
+
getStartTransactionSQL(config) {
|
|
1243
|
+
const parts = [];
|
|
1244
|
+
if (config.withConsistentSnapshot) {
|
|
1245
|
+
parts.push('with consistent snapshot');
|
|
1246
|
+
}
|
|
1247
|
+
if (config.accessMode) {
|
|
1248
|
+
parts.push(config.accessMode);
|
|
1249
|
+
}
|
|
1250
|
+
return parts.length ? relations.sql.fromList(['start transaction ', parts.join(' ')]) : undefined;
|
|
1251
|
+
}
|
|
1252
|
+
}
|
|
1253
|
+
class MySqlTransaction extends MySqlDatabase {
|
|
1254
|
+
constructor(dialect, session, schema, nestedIndex = 0) {
|
|
1255
|
+
super(dialect, session, schema);
|
|
1256
|
+
this.schema = schema;
|
|
1257
|
+
this.nestedIndex = nestedIndex;
|
|
1258
|
+
}
|
|
1259
|
+
rollback() {
|
|
1260
|
+
throw new errors.TransactionRollbackError();
|
|
1261
|
+
}
|
|
1262
|
+
}
|
|
1263
|
+
|
|
1264
|
+
exports.ForeignKey = ForeignKey;
|
|
1265
|
+
exports.ForeignKeyBuilder = ForeignKeyBuilder;
|
|
1266
|
+
exports.InlineForeignKeys = InlineForeignKeys;
|
|
1267
|
+
exports.ManualViewBuilder = ManualViewBuilder;
|
|
1268
|
+
exports.MySqlColumn = MySqlColumn;
|
|
1269
|
+
exports.MySqlColumnBuilder = MySqlColumnBuilder;
|
|
1270
|
+
exports.MySqlColumnBuilderWithAutoIncrement = MySqlColumnBuilderWithAutoIncrement;
|
|
1271
|
+
exports.MySqlColumnWithAutoIncrement = MySqlColumnWithAutoIncrement;
|
|
1272
|
+
exports.MySqlDatabase = MySqlDatabase;
|
|
1273
|
+
exports.MySqlDelete = MySqlDelete;
|
|
1274
|
+
exports.MySqlDialect = MySqlDialect;
|
|
1275
|
+
exports.MySqlInsert = MySqlInsert;
|
|
1276
|
+
exports.MySqlInsertBuilder = MySqlInsertBuilder;
|
|
1277
|
+
exports.MySqlSelect = MySqlSelect;
|
|
1278
|
+
exports.MySqlSelectBuilder = MySqlSelectBuilder;
|
|
1279
|
+
exports.MySqlSelectQueryBuilder = MySqlSelectQueryBuilder;
|
|
1280
|
+
exports.MySqlSession = MySqlSession;
|
|
1281
|
+
exports.MySqlTable = MySqlTable;
|
|
1282
|
+
exports.MySqlTransaction = MySqlTransaction;
|
|
1283
|
+
exports.MySqlUpdate = MySqlUpdate;
|
|
1284
|
+
exports.MySqlUpdateBuilder = MySqlUpdateBuilder;
|
|
1285
|
+
exports.MySqlView = MySqlView;
|
|
1286
|
+
exports.MySqlViewBase = MySqlViewBase;
|
|
1287
|
+
exports.MySqlViewConfig = MySqlViewConfig;
|
|
1288
|
+
exports.PreparedQuery = PreparedQuery;
|
|
1289
|
+
exports.QueryBuilder = QueryBuilder;
|
|
1290
|
+
exports.ViewBuilder = ViewBuilder;
|
|
1291
|
+
exports.ViewBuilderCore = ViewBuilderCore;
|
|
1292
|
+
exports.foreignKey = foreignKey;
|
|
1293
|
+
exports.mysqlTable = mysqlTable;
|
|
1294
|
+
exports.mysqlTableCreator = mysqlTableCreator;
|
|
1295
|
+
exports.mysqlTableWithSchema = mysqlTableWithSchema;
|
|
1296
|
+
exports.mysqlView = mysqlView;
|
|
1297
|
+
exports.mysqlViewWithSchema = mysqlViewWithSchema;
|
|
1298
|
+
//# sourceMappingURL=session-c62f6348.cjs.map
|