@hedystia/db 2.0.5 → 2.0.7

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 (55) hide show
  1. package/dist/cache/index.mjs +12 -0
  2. package/dist/cache/index.mjs.map +1 -0
  3. package/dist/cache/manager.mjs +156 -153
  4. package/dist/cache/manager.mjs.map +1 -1
  5. package/dist/cache/memory-store.mjs +113 -111
  6. package/dist/cache/memory-store.mjs.map +1 -1
  7. package/dist/cli/commands/migrate.cjs +78 -0
  8. package/dist/cli/commands/migrate.cjs.map +1 -0
  9. package/dist/cli/commands/migrate.mjs +83 -0
  10. package/dist/cli/commands/migrate.mjs.map +1 -0
  11. package/dist/cli.cjs +36 -0
  12. package/dist/cli.cjs.map +1 -1
  13. package/dist/cli.mjs +37 -0
  14. package/dist/cli.mjs.map +1 -1
  15. package/dist/core/database.cjs +72 -29
  16. package/dist/core/database.cjs.map +1 -1
  17. package/dist/core/database.d.cts +65 -0
  18. package/dist/core/database.d.mts +65 -0
  19. package/dist/core/database.mjs +88 -34
  20. package/dist/core/database.mjs.map +1 -1
  21. package/dist/core/repository.mjs +414 -410
  22. package/dist/core/repository.mjs.map +1 -1
  23. package/dist/drivers/driver.mjs +9 -7
  24. package/dist/drivers/driver.mjs.map +1 -1
  25. package/dist/drivers/file.mjs +315 -312
  26. package/dist/drivers/file.mjs.map +1 -1
  27. package/dist/drivers/index.mjs +15 -6
  28. package/dist/drivers/index.mjs.map +1 -1
  29. package/dist/drivers/mysql.mjs +261 -256
  30. package/dist/drivers/mysql.mjs.map +1 -1
  31. package/dist/drivers/sql-compiler.mjs +4 -1
  32. package/dist/drivers/sql-compiler.mjs.map +1 -1
  33. package/dist/drivers/sqlite.cjs +12 -1
  34. package/dist/drivers/sqlite.cjs.map +1 -1
  35. package/dist/drivers/sqlite.mjs +258 -242
  36. package/dist/drivers/sqlite.mjs.map +1 -1
  37. package/dist/errors.mjs +48 -64
  38. package/dist/errors.mjs.map +1 -1
  39. package/dist/index.mjs +21 -9
  40. package/dist/index.mjs.map +1 -1
  41. package/dist/schema/column.mjs +155 -157
  42. package/dist/schema/column.mjs.map +1 -1
  43. package/dist/schema/columns/index.mjs +103 -171
  44. package/dist/schema/columns/index.mjs.map +1 -1
  45. package/dist/schema/index.mjs +15 -0
  46. package/dist/schema/index.mjs.map +1 -0
  47. package/dist/schema/registry.mjs +122 -119
  48. package/dist/schema/registry.mjs.map +1 -1
  49. package/dist/schema/table.mjs +4 -1
  50. package/dist/schema/table.mjs.map +1 -1
  51. package/dist/sync/synchronizer.mjs +2 -1
  52. package/dist/sync/synchronizer.mjs.map +1 -1
  53. package/dist/types.d.cts +67 -6
  54. package/dist/types.d.mts +67 -6
  55. package/package.json +1 -1
@@ -1,272 +1,277 @@
1
- import { DriverError } from "../errors.mjs";
2
- import { BaseDriver } from "./driver.mjs";
3
- import { compileColumnDef, compileCreateTable } from "./sql-compiler.mjs";
1
+ import { __esmMin } from "../_virtual/_rolldown/runtime.mjs";
2
+ import { DriverError, init_errors } from "../errors.mjs";
3
+ import { BaseDriver, init_driver } from "./driver.mjs";
4
+ import { compileColumnDef, compileCreateTable, init_sql_compiler } from "./sql-compiler.mjs";
4
5
  //#region src/drivers/mysql.ts
5
- /**
6
- * MySQL database driver supporting mysql2 and mysql
7
- */
8
- var MySQLDriver = class extends BaseDriver {
9
- pool = null;
10
- config;
11
- provider;
12
- constructor(config, provider) {
13
- super();
14
- this.config = config;
15
- this.provider = provider;
16
- }
17
- /**
18
- * Connect to the MySQL/MariaDB database
19
- */
20
- async connect() {
21
- if (this.connected) return;
22
- const provider = this.provider;
23
- try {
24
- if (!provider || provider === "mysql2") try {
25
- this.pool = (await import("mysql2/promise")).createPool({
26
- host: this.config.host,
27
- port: this.config.port ?? 3306,
28
- user: this.config.user,
29
- password: this.config.password,
30
- database: this.config.database,
31
- waitForConnections: true,
32
- connectionLimit: 10,
33
- enableKeepAlive: true,
34
- keepAliveInitialDelay: 1e4
35
- });
36
- this.connected = true;
37
- return;
6
+ var MySQLDriver;
7
+ var init_mysql = __esmMin((() => {
8
+ init_errors();
9
+ init_driver();
10
+ init_sql_compiler();
11
+ MySQLDriver = class extends BaseDriver {
12
+ pool = null;
13
+ config;
14
+ provider;
15
+ constructor(config, provider) {
16
+ super();
17
+ this.config = config;
18
+ this.provider = provider;
19
+ }
20
+ /**
21
+ * Connect to the MySQL/MariaDB database
22
+ */
23
+ async connect() {
24
+ if (this.connected) return;
25
+ const provider = this.provider;
26
+ try {
27
+ if (!provider || provider === "mysql2") try {
28
+ this.pool = (await import("mysql2/promise")).createPool({
29
+ host: this.config.host,
30
+ port: this.config.port ?? 3306,
31
+ user: this.config.user,
32
+ password: this.config.password,
33
+ database: this.config.database,
34
+ waitForConnections: true,
35
+ connectionLimit: 10,
36
+ enableKeepAlive: true,
37
+ keepAliveInitialDelay: 1e4
38
+ });
39
+ this.connected = true;
40
+ return;
41
+ } catch (err) {
42
+ if (provider === "mysql2") throw err;
43
+ }
44
+ if (!provider || provider === "mysql") try {
45
+ const pool = (await import("mysql")).createPool({
46
+ host: this.config.host,
47
+ port: this.config.port ?? 3306,
48
+ user: this.config.user,
49
+ password: this.config.password,
50
+ database: this.config.database,
51
+ connectionLimit: 10,
52
+ waitForConnections: true,
53
+ acquireTimeout: 1e4
54
+ });
55
+ this.pool = {
56
+ execute: (sql, params) => new Promise((resolve, reject) => {
57
+ pool.query(sql, params, (err, results, fields) => {
58
+ if (err) return reject(err);
59
+ resolve([results, fields]);
60
+ });
61
+ }),
62
+ query: (sql, params) => new Promise((resolve, reject) => {
63
+ pool.query(sql, params, (err, results, fields) => {
64
+ if (err) return reject(err);
65
+ resolve([results, fields]);
66
+ });
67
+ }),
68
+ getConnection: () => new Promise((resolve, reject) => {
69
+ pool.getConnection((err, conn) => {
70
+ if (err) return reject(err);
71
+ resolve({
72
+ beginTransaction: () => new Promise((res, rej) => conn.beginTransaction((e) => e ? rej(e) : res())),
73
+ commit: () => new Promise((res, rej) => conn.commit((e) => e ? rej(e) : res())),
74
+ rollback: () => new Promise((res, rej) => conn.rollback((e) => e ? rej(e) : res())),
75
+ release: () => conn.release(),
76
+ query: (sql, params) => new Promise((res, rej) => {
77
+ conn.query(sql, params, (e, results, fields) => e ? rej(e) : res([results, fields]));
78
+ }),
79
+ execute: (sql, params) => new Promise((res, rej) => {
80
+ conn.query(sql, params, (e, results, fields) => e ? rej(e) : res([results, fields]));
81
+ })
82
+ });
83
+ });
84
+ }),
85
+ end: () => new Promise((res, rej) => pool.end((e) => e ? rej(e) : res()))
86
+ };
87
+ this.connected = true;
88
+ } catch (err) {
89
+ if (provider === "mysql") throw err;
90
+ throw new Error("No MySQL driver found. Please install mysql2 or mysql.");
91
+ }
38
92
  } catch (err) {
39
- if (provider === "mysql2") throw err;
93
+ throw new DriverError(`Failed to connect to MySQL database: ${err.message}`);
40
94
  }
41
- if (!provider || provider === "mysql") try {
42
- const pool = (await import("mysql")).createPool({
43
- host: this.config.host,
44
- port: this.config.port ?? 3306,
45
- user: this.config.user,
46
- password: this.config.password,
47
- database: this.config.database,
48
- connectionLimit: 10,
49
- waitForConnections: true,
50
- acquireTimeout: 1e4
51
- });
52
- this.pool = {
53
- execute: (sql, params) => new Promise((resolve, reject) => {
54
- pool.query(sql, params, (err, results, fields) => {
55
- if (err) return reject(err);
56
- resolve([results, fields]);
57
- });
58
- }),
59
- query: (sql, params) => new Promise((resolve, reject) => {
60
- pool.query(sql, params, (err, results, fields) => {
61
- if (err) return reject(err);
62
- resolve([results, fields]);
63
- });
64
- }),
65
- getConnection: () => new Promise((resolve, reject) => {
66
- pool.getConnection((err, conn) => {
67
- if (err) return reject(err);
68
- resolve({
69
- beginTransaction: () => new Promise((res, rej) => conn.beginTransaction((e) => e ? rej(e) : res())),
70
- commit: () => new Promise((res, rej) => conn.commit((e) => e ? rej(e) : res())),
71
- rollback: () => new Promise((res, rej) => conn.rollback((e) => e ? rej(e) : res())),
72
- release: () => conn.release(),
73
- query: (sql, params) => new Promise((res, rej) => {
74
- conn.query(sql, params, (e, results, fields) => e ? rej(e) : res([results, fields]));
75
- }),
76
- execute: (sql, params) => new Promise((res, rej) => {
77
- conn.query(sql, params, (e, results, fields) => e ? rej(e) : res([results, fields]));
78
- })
79
- });
80
- });
81
- }),
82
- end: () => new Promise((res, rej) => pool.end((e) => e ? rej(e) : res()))
95
+ }
96
+ async disconnect() {
97
+ if (this.pool) {
98
+ await this.pool.end();
99
+ this.pool = null;
100
+ this.connected = false;
101
+ }
102
+ }
103
+ getPool() {
104
+ if (!this.pool) throw new DriverError("Database not connected");
105
+ return this.pool;
106
+ }
107
+ /**
108
+ * Execute a SQL statement
109
+ * @param {string} sql - SQL statement
110
+ * @param {unknown[]} [params] - Query parameters
111
+ * @returns {Promise<any>} Execution result
112
+ */
113
+ async execute(sql, params = []) {
114
+ try {
115
+ const [result] = await this.getPool().query(sql, this.formatParams(params));
116
+ return {
117
+ insertId: result.insertId,
118
+ affectedRows: result.affectedRows
83
119
  };
84
- this.connected = true;
85
120
  } catch (err) {
86
- if (provider === "mysql") throw err;
87
- throw new Error("No MySQL driver found. Please install mysql2 or mysql.");
121
+ throw new DriverError(`MySQL execute error: ${err.message}`);
88
122
  }
89
- } catch (err) {
90
- throw new DriverError(`Failed to connect to MySQL database: ${err.message}`);
91
123
  }
92
- }
93
- async disconnect() {
94
- if (this.pool) {
95
- await this.pool.end();
96
- this.pool = null;
97
- this.connected = false;
124
+ /**
125
+ * Execute a SQL query
126
+ * @param {string} sql - SQL query
127
+ * @param {unknown[]} [params] - Query parameters
128
+ * @returns {Promise<any[]>} Query results
129
+ */
130
+ async query(sql, params = []) {
131
+ try {
132
+ const [rows] = await this.getPool().query(sql, this.formatParams(params));
133
+ return rows;
134
+ } catch (err) {
135
+ throw new DriverError(`MySQL query error: ${err.message}`);
136
+ }
98
137
  }
99
- }
100
- getPool() {
101
- if (!this.pool) throw new DriverError("Database not connected");
102
- return this.pool;
103
- }
104
- /**
105
- * Execute a SQL statement
106
- * @param {string} sql - SQL statement
107
- * @param {unknown[]} [params] - Query parameters
108
- * @returns {Promise<any>} Execution result
109
- */
110
- async execute(sql, params = []) {
111
- try {
112
- const [result] = await this.getPool().query(sql, this.formatParams(params));
113
- return {
114
- insertId: result.insertId,
115
- affectedRows: result.affectedRows
116
- };
117
- } catch (err) {
118
- throw new DriverError(`MySQL execute error: ${err.message}`);
138
+ formatParams(params) {
139
+ return params.map((p) => {
140
+ if (p instanceof Date) return p.toISOString().slice(0, 19).replace("T", " ");
141
+ return p;
142
+ });
119
143
  }
120
- }
121
- /**
122
- * Execute a SQL query
123
- * @param {string} sql - SQL query
124
- * @param {unknown[]} [params] - Query parameters
125
- * @returns {Promise<any[]>} Query results
126
- */
127
- async query(sql, params = []) {
128
- try {
129
- const [rows] = await this.getPool().query(sql, this.formatParams(params));
130
- return rows;
131
- } catch (err) {
132
- throw new DriverError(`MySQL query error: ${err.message}`);
144
+ /**
145
+ * Check if a table exists
146
+ * @param {string} name - Table name
147
+ * @returns {Promise<boolean>} Whether the table exists
148
+ */
149
+ async tableExists(name) {
150
+ return (await this.query("SELECT TABLE_NAME FROM information_schema.TABLES WHERE TABLE_SCHEMA = ? AND TABLE_NAME = ?", [this.config.database, name])).length > 0;
133
151
  }
134
- }
135
- formatParams(params) {
136
- return params.map((p) => {
137
- if (p instanceof Date) return p.toISOString().slice(0, 19).replace("T", " ");
138
- return p;
139
- });
140
- }
141
- /**
142
- * Check if a table exists
143
- * @param {string} name - Table name
144
- * @returns {Promise<boolean>} Whether the table exists
145
- */
146
- async tableExists(name) {
147
- return (await this.query("SELECT TABLE_NAME FROM information_schema.TABLES WHERE TABLE_SCHEMA = ? AND TABLE_NAME = ?", [this.config.database, name])).length > 0;
148
- }
149
- /**
150
- * Get column metadata for a table
151
- * @param {string} name - Table name
152
- * @returns {Promise<ColumnMetadata[]>} Column metadata
153
- */
154
- async getTableColumns(name) {
155
- return (await this.query("SELECT COLUMN_NAME, DATA_TYPE, IS_NULLABLE, COLUMN_KEY, EXTRA, COLUMN_DEFAULT FROM information_schema.COLUMNS WHERE TABLE_SCHEMA = ? AND TABLE_NAME = ? ORDER BY ORDINAL_POSITION", [this.config.database, name])).map((row) => ({
156
- name: row.COLUMN_NAME,
157
- type: this.mapMySQLType(row.DATA_TYPE),
158
- primaryKey: row.COLUMN_KEY === "PRI",
159
- autoIncrement: row.EXTRA?.includes("auto_increment") ?? false,
160
- notNull: row.IS_NULLABLE === "NO",
161
- unique: row.COLUMN_KEY === "UNI",
162
- defaultValue: row.COLUMN_DEFAULT
163
- }));
164
- }
165
- /**
166
- * Create a table from metadata
167
- * @param {TableMetadata} meta - Table metadata
168
- */
169
- async createTable(meta) {
170
- const sql = compileCreateTable(meta, "mysql");
171
- await this.execute(sql);
172
- }
173
- /**
174
- * Drop a table
175
- * @param {string} name - Table name
176
- */
177
- async dropTable(name) {
178
- await this.execute(`DROP TABLE IF EXISTS \`${name}\``);
179
- }
180
- /**
181
- * Add a column to a table
182
- * @param {string} table - Table name
183
- * @param {ColumnMetadata} column - Column metadata
184
- */
185
- async addColumn(table, column) {
186
- const colDef = compileColumnDef(column, "mysql");
187
- await this.execute(`ALTER TABLE \`${table}\` ADD COLUMN ${colDef}`);
188
- }
189
- /**
190
- * Drop a column from a table
191
- * @param {string} table - Table name
192
- * @param {string} name - Column name
193
- */
194
- async dropColumn(table, name) {
195
- await this.execute(`ALTER TABLE \`${table}\` DROP COLUMN \`${name}\``);
196
- }
197
- /**
198
- * Rename a column
199
- * @param {string} table - Table name
200
- * @param {string} oldName - Current name
201
- * @param {string} newName - New name
202
- */
203
- async renameColumn(table, oldName, newName) {
204
- await this.execute(`ALTER TABLE \`${table}\` RENAME COLUMN \`${oldName}\` TO \`${newName}\``);
205
- }
206
- /**
207
- * Execute within a transaction
208
- * @param {() => Promise<T>} fn - Function to execute
209
- * @returns {Promise<T>} Result
210
- */
211
- async transaction(fn) {
212
- const conn = await this.getPool().getConnection();
213
- try {
214
- await conn.beginTransaction();
215
- const result = await fn();
216
- await conn.commit();
217
- return result;
218
- } catch (err) {
219
- await conn.rollback();
220
- throw err;
221
- } finally {
222
- conn.release();
152
+ /**
153
+ * Get column metadata for a table
154
+ * @param {string} name - Table name
155
+ * @returns {Promise<ColumnMetadata[]>} Column metadata
156
+ */
157
+ async getTableColumns(name) {
158
+ return (await this.query("SELECT COLUMN_NAME, DATA_TYPE, IS_NULLABLE, COLUMN_KEY, EXTRA, COLUMN_DEFAULT FROM information_schema.COLUMNS WHERE TABLE_SCHEMA = ? AND TABLE_NAME = ? ORDER BY ORDINAL_POSITION", [this.config.database, name])).map((row) => ({
159
+ name: row.COLUMN_NAME,
160
+ type: this.mapMySQLType(row.DATA_TYPE),
161
+ primaryKey: row.COLUMN_KEY === "PRI",
162
+ autoIncrement: row.EXTRA?.includes("auto_increment") ?? false,
163
+ notNull: row.IS_NULLABLE === "NO",
164
+ unique: row.COLUMN_KEY === "UNI",
165
+ defaultValue: row.COLUMN_DEFAULT
166
+ }));
223
167
  }
224
- }
225
- /**
226
- * Fetch all column metadata for all tables in the database in a single query
227
- * @returns {Promise<Record<string, ColumnMetadata[]>>} Columns grouped by table name
228
- */
229
- async getAllTableColumns() {
230
- try {
231
- const rows = await this.query("SELECT TABLE_NAME, COLUMN_NAME, DATA_TYPE, IS_NULLABLE, COLUMN_KEY, EXTRA, COLUMN_DEFAULT FROM information_schema.COLUMNS WHERE TABLE_SCHEMA = ? ORDER BY TABLE_NAME, ORDINAL_POSITION", [this.config.database]);
232
- const result = {};
233
- for (let i = 0; i < rows.length; i++) {
234
- const row = rows[i];
235
- if (!row || !row.TABLE_NAME) continue;
236
- const tableName = row.TABLE_NAME;
237
- if (!result[tableName]) result[tableName] = [];
238
- result[tableName].push({
239
- name: row.COLUMN_NAME,
240
- type: this.mapMySQLType(row.DATA_TYPE),
241
- primaryKey: row.COLUMN_KEY === "PRI",
242
- autoIncrement: row.EXTRA?.includes("auto_increment") ?? false,
243
- notNull: row.IS_NULLABLE === "NO",
244
- unique: row.COLUMN_KEY === "UNI",
245
- defaultValue: row.COLUMN_DEFAULT
246
- });
168
+ /**
169
+ * Create a table from metadata
170
+ * @param {TableMetadata} meta - Table metadata
171
+ */
172
+ async createTable(meta) {
173
+ const sql = compileCreateTable(meta, "mysql");
174
+ await this.execute(sql);
175
+ }
176
+ /**
177
+ * Drop a table
178
+ * @param {string} name - Table name
179
+ */
180
+ async dropTable(name) {
181
+ await this.execute(`DROP TABLE IF EXISTS \`${name}\``);
182
+ }
183
+ /**
184
+ * Add a column to a table
185
+ * @param {string} table - Table name
186
+ * @param {ColumnMetadata} column - Column metadata
187
+ */
188
+ async addColumn(table, column) {
189
+ const colDef = compileColumnDef(column, "mysql");
190
+ await this.execute(`ALTER TABLE \`${table}\` ADD COLUMN ${colDef}`);
191
+ }
192
+ /**
193
+ * Drop a column from a table
194
+ * @param {string} table - Table name
195
+ * @param {string} name - Column name
196
+ */
197
+ async dropColumn(table, name) {
198
+ await this.execute(`ALTER TABLE \`${table}\` DROP COLUMN \`${name}\``);
199
+ }
200
+ /**
201
+ * Rename a column
202
+ * @param {string} table - Table name
203
+ * @param {string} oldName - Current name
204
+ * @param {string} newName - New name
205
+ */
206
+ async renameColumn(table, oldName, newName) {
207
+ await this.execute(`ALTER TABLE \`${table}\` RENAME COLUMN \`${oldName}\` TO \`${newName}\``);
208
+ }
209
+ /**
210
+ * Execute within a transaction
211
+ * @param {() => Promise<T>} fn - Function to execute
212
+ * @returns {Promise<T>} Result
213
+ */
214
+ async transaction(fn) {
215
+ const conn = await this.getPool().getConnection();
216
+ try {
217
+ await conn.beginTransaction();
218
+ const result = await fn();
219
+ await conn.commit();
220
+ return result;
221
+ } catch (err) {
222
+ await conn.rollback();
223
+ throw err;
224
+ } finally {
225
+ conn.release();
247
226
  }
248
- return result;
249
- } catch (err) {
250
- throw new DriverError(`Failed to fetch all table columns: ${err.message}`);
251
227
  }
252
- }
253
- mapMySQLType(type) {
254
- const lower = type.toLowerCase();
255
- if (lower === "int" || lower === "integer" || lower === "tinyint" || lower === "smallint" || lower === "mediumint") return "integer";
256
- if (lower === "bigint") return "bigint";
257
- if (lower === "varchar") return "varchar";
258
- if (lower === "char") return "char";
259
- if (lower === "text" || lower === "mediumtext" || lower === "longtext") return "text";
260
- if (lower === "json") return "json";
261
- if (lower === "datetime") return "datetime";
262
- if (lower === "timestamp") return "timestamp";
263
- if (lower === "decimal" || lower === "numeric") return "decimal";
264
- if (lower === "float" || lower === "double" || lower === "real") return "float";
265
- if (lower === "blob" || lower === "mediumblob" || lower === "longblob") return "blob";
266
- return "text";
267
- }
268
- };
228
+ /**
229
+ * Fetch all column metadata for all tables in the database in a single query
230
+ * @returns {Promise<Record<string, ColumnMetadata[]>>} Columns grouped by table name
231
+ */
232
+ async getAllTableColumns() {
233
+ try {
234
+ const rows = await this.query("SELECT TABLE_NAME, COLUMN_NAME, DATA_TYPE, IS_NULLABLE, COLUMN_KEY, EXTRA, COLUMN_DEFAULT FROM information_schema.COLUMNS WHERE TABLE_SCHEMA = ? ORDER BY TABLE_NAME, ORDINAL_POSITION", [this.config.database]);
235
+ const result = {};
236
+ for (let i = 0; i < rows.length; i++) {
237
+ const row = rows[i];
238
+ if (!row || !row.TABLE_NAME) continue;
239
+ const tableName = row.TABLE_NAME;
240
+ if (!result[tableName]) result[tableName] = [];
241
+ result[tableName].push({
242
+ name: row.COLUMN_NAME,
243
+ type: this.mapMySQLType(row.DATA_TYPE),
244
+ primaryKey: row.COLUMN_KEY === "PRI",
245
+ autoIncrement: row.EXTRA?.includes("auto_increment") ?? false,
246
+ notNull: row.IS_NULLABLE === "NO",
247
+ unique: row.COLUMN_KEY === "UNI",
248
+ defaultValue: row.COLUMN_DEFAULT
249
+ });
250
+ }
251
+ return result;
252
+ } catch (err) {
253
+ throw new DriverError(`Failed to fetch all table columns: ${err.message}`);
254
+ }
255
+ }
256
+ mapMySQLType(type) {
257
+ const lower = type.toLowerCase();
258
+ if (lower === "int" || lower === "integer" || lower === "tinyint" || lower === "smallint" || lower === "mediumint") return "integer";
259
+ if (lower === "bigint") return "bigint";
260
+ if (lower === "varchar") return "varchar";
261
+ if (lower === "char") return "char";
262
+ if (lower === "text" || lower === "mediumtext" || lower === "longtext") return "text";
263
+ if (lower === "json") return "json";
264
+ if (lower === "datetime") return "datetime";
265
+ if (lower === "timestamp") return "timestamp";
266
+ if (lower === "decimal" || lower === "numeric") return "decimal";
267
+ if (lower === "float" || lower === "double" || lower === "real") return "float";
268
+ if (lower === "blob" || lower === "mediumblob" || lower === "longblob") return "blob";
269
+ return "text";
270
+ }
271
+ };
272
+ }));
269
273
  //#endregion
270
- export { MySQLDriver };
274
+ init_mysql();
275
+ export { MySQLDriver, init_mysql };
271
276
 
272
277
  //# sourceMappingURL=mysql.mjs.map
@@ -1 +1 @@
1
- {"version":3,"file":"mysql.mjs","names":[],"sources":["../../src/drivers/mysql.ts"],"sourcesContent":["import { DriverError } from \"../errors\";\nimport type { ColumnMetadata, MySQLConnectionConfig, TableMetadata } from \"../types\";\nimport { BaseDriver } from \"./driver\";\nimport { compileColumnDef, compileCreateTable } from \"./sql-compiler\";\n\ninterface MySQLPool {\n query(sql: string, params?: any[]): Promise<[any, any]>;\n execute(sql: string, params?: any[]): Promise<[any, any]>;\n getConnection(): Promise<MySQLConnection>;\n end(): Promise<void>;\n}\n\ninterface MySQLConnection {\n beginTransaction(): Promise<void>;\n commit(): Promise<void>;\n rollback(): Promise<void>;\n release(): void;\n query(sql: string, params?: any[]): Promise<[any, any]>;\n execute(sql: string, params?: any[]): Promise<[any, any]>;\n}\n\n/**\n * MySQL database driver supporting mysql2 and mysql\n */\nexport class MySQLDriver extends BaseDriver {\n private pool: MySQLPool | null = null;\n private config: MySQLConnectionConfig;\n private provider?: \"mysql\" | \"mysql2\";\n\n constructor(config: MySQLConnectionConfig, provider?: \"mysql\" | \"mysql2\") {\n super();\n this.config = config;\n this.provider = provider;\n }\n\n /**\n * Connect to the MySQL/MariaDB database\n */\n async connect(): Promise<void> {\n if (this.connected) {\n return;\n }\n\n const provider = this.provider;\n\n try {\n if (!provider || provider === \"mysql2\") {\n try {\n const mysql2 = await import(\"mysql2/promise\");\n this.pool = mysql2.createPool({\n host: this.config.host,\n port: this.config.port ?? 3306,\n user: this.config.user,\n password: this.config.password,\n database: this.config.database,\n waitForConnections: true,\n connectionLimit: 10,\n enableKeepAlive: true,\n keepAliveInitialDelay: 10000,\n });\n this.connected = true;\n return;\n } catch (err) {\n if (provider === \"mysql2\") {\n throw err;\n }\n }\n }\n\n if (!provider || provider === \"mysql\") {\n try {\n const mysql = await import(\"mysql\");\n const pool = mysql.createPool({\n host: this.config.host,\n port: this.config.port ?? 3306,\n user: this.config.user,\n password: this.config.password,\n database: this.config.database,\n connectionLimit: 10,\n waitForConnections: true,\n acquireTimeout: 10000,\n });\n\n this.pool = {\n execute: (sql: string, params: any[]) =>\n new Promise((resolve, reject) => {\n pool.query(sql, params, (err, results, fields) => {\n if (err) {\n return reject(err);\n }\n resolve([results, fields]);\n });\n }),\n query: (sql: string, params: any[]) =>\n new Promise((resolve, reject) => {\n pool.query(sql, params, (err, results, fields) => {\n if (err) {\n return reject(err);\n }\n resolve([results, fields]);\n });\n }),\n getConnection: () =>\n new Promise((resolve, reject) => {\n pool.getConnection((err, conn) => {\n if (err) {\n return reject(err);\n }\n const wrappedConn: MySQLConnection = {\n beginTransaction: () =>\n new Promise<void>((res, rej) =>\n conn.beginTransaction((e) => (e ? rej(e) : res())),\n ),\n commit: () =>\n new Promise<void>((res, rej) => conn.commit((e) => (e ? rej(e) : res()))),\n rollback: () =>\n new Promise<void>((res, rej) => conn.rollback((e) => (e ? rej(e) : res()))),\n release: () => conn.release(),\n query: (sql: string, params: any[]) =>\n new Promise((res, rej) => {\n conn.query(sql, params, (e, results, fields) =>\n e ? rej(e) : res([results, fields]),\n );\n }),\n execute: (sql: string, params: any[]) =>\n new Promise((res, rej) => {\n conn.query(sql, params, (e, results, fields) =>\n e ? rej(e) : res([results, fields]),\n );\n }),\n };\n resolve(wrappedConn);\n });\n }),\n end: () => new Promise<void>((res, rej) => pool.end((e) => (e ? rej(e) : res()))),\n };\n this.connected = true;\n } catch (err) {\n if (provider === \"mysql\") {\n throw err;\n }\n throw new Error(\"No MySQL driver found. Please install mysql2 or mysql.\");\n }\n }\n } catch (err: any) {\n throw new DriverError(`Failed to connect to MySQL database: ${err.message}`);\n }\n }\n\n async disconnect(): Promise<void> {\n if (this.pool) {\n await this.pool.end();\n this.pool = null;\n this.connected = false;\n }\n }\n\n private getPool(): MySQLPool {\n if (!this.pool) {\n throw new DriverError(\"Database not connected\");\n }\n return this.pool;\n }\n\n /**\n * Execute a SQL statement\n * @param {string} sql - SQL statement\n * @param {unknown[]} [params] - Query parameters\n * @returns {Promise<any>} Execution result\n */\n async execute(sql: string, params: unknown[] = []): Promise<any> {\n try {\n const [result] = await this.getPool().query(sql, this.formatParams(params));\n return {\n insertId: result.insertId,\n affectedRows: result.affectedRows,\n };\n } catch (err: any) {\n throw new DriverError(`MySQL execute error: ${err.message}`);\n }\n }\n\n /**\n * Execute a SQL query\n * @param {string} sql - SQL query\n * @param {unknown[]} [params] - Query parameters\n * @returns {Promise<any[]>} Query results\n */\n async query(sql: string, params: unknown[] = []): Promise<any[]> {\n try {\n const [rows] = await this.getPool().query(sql, this.formatParams(params));\n return rows as any[];\n } catch (err: any) {\n throw new DriverError(`MySQL query error: ${err.message}`);\n }\n }\n\n private formatParams(params: unknown[]): unknown[] {\n return params.map((p) => {\n if (p instanceof Date) {\n return p.toISOString().slice(0, 19).replace(\"T\", \" \");\n }\n return p;\n });\n }\n\n /**\n * Check if a table exists\n * @param {string} name - Table name\n * @returns {Promise<boolean>} Whether the table exists\n */\n async tableExists(name: string): Promise<boolean> {\n const rows = await this.query(\n \"SELECT TABLE_NAME FROM information_schema.TABLES WHERE TABLE_SCHEMA = ? AND TABLE_NAME = ?\",\n [this.config.database, name],\n );\n return rows.length > 0;\n }\n\n /**\n * Get column metadata for a table\n * @param {string} name - Table name\n * @returns {Promise<ColumnMetadata[]>} Column metadata\n */\n async getTableColumns(name: string): Promise<ColumnMetadata[]> {\n const rows = await this.query(\n \"SELECT COLUMN_NAME, DATA_TYPE, IS_NULLABLE, COLUMN_KEY, EXTRA, COLUMN_DEFAULT FROM information_schema.COLUMNS WHERE TABLE_SCHEMA = ? AND TABLE_NAME = ? ORDER BY ORDINAL_POSITION\",\n [this.config.database, name],\n );\n return rows.map((row: any) => ({\n name: row.COLUMN_NAME,\n type: this.mapMySQLType(row.DATA_TYPE),\n primaryKey: row.COLUMN_KEY === \"PRI\",\n autoIncrement: row.EXTRA?.includes(\"auto_increment\") ?? false,\n notNull: row.IS_NULLABLE === \"NO\",\n unique: row.COLUMN_KEY === \"UNI\",\n defaultValue: row.COLUMN_DEFAULT,\n }));\n }\n\n /**\n * Create a table from metadata\n * @param {TableMetadata} meta - Table metadata\n */\n async createTable(meta: TableMetadata): Promise<void> {\n const sql = compileCreateTable(meta, \"mysql\");\n await this.execute(sql);\n }\n\n /**\n * Drop a table\n * @param {string} name - Table name\n */\n async dropTable(name: string): Promise<void> {\n await this.execute(`DROP TABLE IF EXISTS \\`${name}\\``);\n }\n\n /**\n * Add a column to a table\n * @param {string} table - Table name\n * @param {ColumnMetadata} column - Column metadata\n */\n async addColumn(table: string, column: ColumnMetadata): Promise<void> {\n const colDef = compileColumnDef(column, \"mysql\");\n await this.execute(`ALTER TABLE \\`${table}\\` ADD COLUMN ${colDef}`);\n }\n\n /**\n * Drop a column from a table\n * @param {string} table - Table name\n * @param {string} name - Column name\n */\n async dropColumn(table: string, name: string): Promise<void> {\n await this.execute(`ALTER TABLE \\`${table}\\` DROP COLUMN \\`${name}\\``);\n }\n\n /**\n * Rename a column\n * @param {string} table - Table name\n * @param {string} oldName - Current name\n * @param {string} newName - New name\n */\n async renameColumn(table: string, oldName: string, newName: string): Promise<void> {\n await this.execute(`ALTER TABLE \\`${table}\\` RENAME COLUMN \\`${oldName}\\` TO \\`${newName}\\``);\n }\n\n /**\n * Execute within a transaction\n * @param {() => Promise<T>} fn - Function to execute\n * @returns {Promise<T>} Result\n */\n async transaction<T>(fn: () => Promise<T>): Promise<T> {\n const conn = await this.getPool().getConnection();\n try {\n await conn.beginTransaction();\n const result = await fn();\n await conn.commit();\n return result;\n } catch (err) {\n await conn.rollback();\n throw err;\n } finally {\n conn.release();\n }\n }\n\n /**\n * Fetch all column metadata for all tables in the database in a single query\n * @returns {Promise<Record<string, ColumnMetadata[]>>} Columns grouped by table name\n */\n async getAllTableColumns(): Promise<Record<string, ColumnMetadata[]>> {\n try {\n const rows = await this.query(\n \"SELECT TABLE_NAME, COLUMN_NAME, DATA_TYPE, IS_NULLABLE, COLUMN_KEY, EXTRA, COLUMN_DEFAULT FROM information_schema.COLUMNS WHERE TABLE_SCHEMA = ? ORDER BY TABLE_NAME, ORDINAL_POSITION\",\n [this.config.database],\n );\n\n const result: Record<string, ColumnMetadata[]> = {};\n for (let i = 0; i < rows.length; i++) {\n const row = rows[i] as any;\n if (!row || !row.TABLE_NAME) {\n continue;\n }\n const tableName = row.TABLE_NAME;\n if (!result[tableName]) {\n result[tableName] = [];\n }\n result[tableName].push({\n name: row.COLUMN_NAME,\n type: this.mapMySQLType(row.DATA_TYPE),\n primaryKey: row.COLUMN_KEY === \"PRI\",\n autoIncrement: row.EXTRA?.includes(\"auto_increment\") ?? false,\n notNull: row.IS_NULLABLE === \"NO\",\n unique: row.COLUMN_KEY === \"UNI\",\n defaultValue: row.COLUMN_DEFAULT,\n });\n }\n return result;\n } catch (err: any) {\n throw new DriverError(`Failed to fetch all table columns: ${err.message}`);\n }\n }\n\n private mapMySQLType(type: string): ColumnMetadata[\"type\"] {\n const lower = type.toLowerCase();\n if (\n lower === \"int\" ||\n lower === \"integer\" ||\n lower === \"tinyint\" ||\n lower === \"smallint\" ||\n lower === \"mediumint\"\n ) {\n return \"integer\";\n }\n if (lower === \"bigint\") {\n return \"bigint\";\n }\n if (lower === \"varchar\") {\n return \"varchar\";\n }\n if (lower === \"char\") {\n return \"char\";\n }\n if (lower === \"text\" || lower === \"mediumtext\" || lower === \"longtext\") {\n return \"text\";\n }\n if (lower === \"json\") {\n return \"json\";\n }\n if (lower === \"datetime\") {\n return \"datetime\";\n }\n if (lower === \"timestamp\") {\n return \"timestamp\";\n }\n if (lower === \"decimal\" || lower === \"numeric\") {\n return \"decimal\";\n }\n if (lower === \"float\" || lower === \"double\" || lower === \"real\") {\n return \"float\";\n }\n if (lower === \"blob\" || lower === \"mediumblob\" || lower === \"longblob\") {\n return \"blob\";\n }\n return \"text\";\n }\n}\n"],"mappings":"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"}
1
+ {"version":3,"file":"mysql.mjs","names":[],"sources":["../../src/drivers/mysql.ts"],"sourcesContent":["import { DriverError } from \"../errors\";\nimport type { ColumnMetadata, MySQLConnectionConfig, TableMetadata } from \"../types\";\nimport { BaseDriver } from \"./driver\";\nimport { compileColumnDef, compileCreateTable } from \"./sql-compiler\";\n\ninterface MySQLPool {\n query(sql: string, params?: any[]): Promise<[any, any]>;\n execute(sql: string, params?: any[]): Promise<[any, any]>;\n getConnection(): Promise<MySQLConnection>;\n end(): Promise<void>;\n}\n\ninterface MySQLConnection {\n beginTransaction(): Promise<void>;\n commit(): Promise<void>;\n rollback(): Promise<void>;\n release(): void;\n query(sql: string, params?: any[]): Promise<[any, any]>;\n execute(sql: string, params?: any[]): Promise<[any, any]>;\n}\n\n/**\n * MySQL database driver supporting mysql2 and mysql\n */\nexport class MySQLDriver extends BaseDriver {\n private pool: MySQLPool | null = null;\n private config: MySQLConnectionConfig;\n private provider?: \"mysql\" | \"mysql2\";\n\n constructor(config: MySQLConnectionConfig, provider?: \"mysql\" | \"mysql2\") {\n super();\n this.config = config;\n this.provider = provider;\n }\n\n /**\n * Connect to the MySQL/MariaDB database\n */\n async connect(): Promise<void> {\n if (this.connected) {\n return;\n }\n\n const provider = this.provider;\n\n try {\n if (!provider || provider === \"mysql2\") {\n try {\n const mysql2 = await import(\"mysql2/promise\");\n this.pool = mysql2.createPool({\n host: this.config.host,\n port: this.config.port ?? 3306,\n user: this.config.user,\n password: this.config.password,\n database: this.config.database,\n waitForConnections: true,\n connectionLimit: 10,\n enableKeepAlive: true,\n keepAliveInitialDelay: 10000,\n });\n this.connected = true;\n return;\n } catch (err) {\n if (provider === \"mysql2\") {\n throw err;\n }\n }\n }\n\n if (!provider || provider === \"mysql\") {\n try {\n const mysql = await import(\"mysql\");\n const pool = mysql.createPool({\n host: this.config.host,\n port: this.config.port ?? 3306,\n user: this.config.user,\n password: this.config.password,\n database: this.config.database,\n connectionLimit: 10,\n waitForConnections: true,\n acquireTimeout: 10000,\n });\n\n this.pool = {\n execute: (sql: string, params: any[]) =>\n new Promise((resolve, reject) => {\n pool.query(sql, params, (err, results, fields) => {\n if (err) {\n return reject(err);\n }\n resolve([results, fields]);\n });\n }),\n query: (sql: string, params: any[]) =>\n new Promise((resolve, reject) => {\n pool.query(sql, params, (err, results, fields) => {\n if (err) {\n return reject(err);\n }\n resolve([results, fields]);\n });\n }),\n getConnection: () =>\n new Promise((resolve, reject) => {\n pool.getConnection((err, conn) => {\n if (err) {\n return reject(err);\n }\n const wrappedConn: MySQLConnection = {\n beginTransaction: () =>\n new Promise<void>((res, rej) =>\n conn.beginTransaction((e) => (e ? rej(e) : res())),\n ),\n commit: () =>\n new Promise<void>((res, rej) => conn.commit((e) => (e ? rej(e) : res()))),\n rollback: () =>\n new Promise<void>((res, rej) => conn.rollback((e) => (e ? rej(e) : res()))),\n release: () => conn.release(),\n query: (sql: string, params: any[]) =>\n new Promise((res, rej) => {\n conn.query(sql, params, (e, results, fields) =>\n e ? rej(e) : res([results, fields]),\n );\n }),\n execute: (sql: string, params: any[]) =>\n new Promise((res, rej) => {\n conn.query(sql, params, (e, results, fields) =>\n e ? rej(e) : res([results, fields]),\n );\n }),\n };\n resolve(wrappedConn);\n });\n }),\n end: () => new Promise<void>((res, rej) => pool.end((e) => (e ? rej(e) : res()))),\n };\n this.connected = true;\n } catch (err) {\n if (provider === \"mysql\") {\n throw err;\n }\n throw new Error(\"No MySQL driver found. Please install mysql2 or mysql.\");\n }\n }\n } catch (err: any) {\n throw new DriverError(`Failed to connect to MySQL database: ${err.message}`);\n }\n }\n\n async disconnect(): Promise<void> {\n if (this.pool) {\n await this.pool.end();\n this.pool = null;\n this.connected = false;\n }\n }\n\n private getPool(): MySQLPool {\n if (!this.pool) {\n throw new DriverError(\"Database not connected\");\n }\n return this.pool;\n }\n\n /**\n * Execute a SQL statement\n * @param {string} sql - SQL statement\n * @param {unknown[]} [params] - Query parameters\n * @returns {Promise<any>} Execution result\n */\n async execute(sql: string, params: unknown[] = []): Promise<any> {\n try {\n const [result] = await this.getPool().query(sql, this.formatParams(params));\n return {\n insertId: result.insertId,\n affectedRows: result.affectedRows,\n };\n } catch (err: any) {\n throw new DriverError(`MySQL execute error: ${err.message}`);\n }\n }\n\n /**\n * Execute a SQL query\n * @param {string} sql - SQL query\n * @param {unknown[]} [params] - Query parameters\n * @returns {Promise<any[]>} Query results\n */\n async query(sql: string, params: unknown[] = []): Promise<any[]> {\n try {\n const [rows] = await this.getPool().query(sql, this.formatParams(params));\n return rows as any[];\n } catch (err: any) {\n throw new DriverError(`MySQL query error: ${err.message}`);\n }\n }\n\n private formatParams(params: unknown[]): unknown[] {\n return params.map((p) => {\n if (p instanceof Date) {\n return p.toISOString().slice(0, 19).replace(\"T\", \" \");\n }\n return p;\n });\n }\n\n /**\n * Check if a table exists\n * @param {string} name - Table name\n * @returns {Promise<boolean>} Whether the table exists\n */\n async tableExists(name: string): Promise<boolean> {\n const rows = await this.query(\n \"SELECT TABLE_NAME FROM information_schema.TABLES WHERE TABLE_SCHEMA = ? AND TABLE_NAME = ?\",\n [this.config.database, name],\n );\n return rows.length > 0;\n }\n\n /**\n * Get column metadata for a table\n * @param {string} name - Table name\n * @returns {Promise<ColumnMetadata[]>} Column metadata\n */\n async getTableColumns(name: string): Promise<ColumnMetadata[]> {\n const rows = await this.query(\n \"SELECT COLUMN_NAME, DATA_TYPE, IS_NULLABLE, COLUMN_KEY, EXTRA, COLUMN_DEFAULT FROM information_schema.COLUMNS WHERE TABLE_SCHEMA = ? AND TABLE_NAME = ? ORDER BY ORDINAL_POSITION\",\n [this.config.database, name],\n );\n return rows.map((row: any) => ({\n name: row.COLUMN_NAME,\n type: this.mapMySQLType(row.DATA_TYPE),\n primaryKey: row.COLUMN_KEY === \"PRI\",\n autoIncrement: row.EXTRA?.includes(\"auto_increment\") ?? false,\n notNull: row.IS_NULLABLE === \"NO\",\n unique: row.COLUMN_KEY === \"UNI\",\n defaultValue: row.COLUMN_DEFAULT,\n }));\n }\n\n /**\n * Create a table from metadata\n * @param {TableMetadata} meta - Table metadata\n */\n async createTable(meta: TableMetadata): Promise<void> {\n const sql = compileCreateTable(meta, \"mysql\");\n await this.execute(sql);\n }\n\n /**\n * Drop a table\n * @param {string} name - Table name\n */\n async dropTable(name: string): Promise<void> {\n await this.execute(`DROP TABLE IF EXISTS \\`${name}\\``);\n }\n\n /**\n * Add a column to a table\n * @param {string} table - Table name\n * @param {ColumnMetadata} column - Column metadata\n */\n async addColumn(table: string, column: ColumnMetadata): Promise<void> {\n const colDef = compileColumnDef(column, \"mysql\");\n await this.execute(`ALTER TABLE \\`${table}\\` ADD COLUMN ${colDef}`);\n }\n\n /**\n * Drop a column from a table\n * @param {string} table - Table name\n * @param {string} name - Column name\n */\n async dropColumn(table: string, name: string): Promise<void> {\n await this.execute(`ALTER TABLE \\`${table}\\` DROP COLUMN \\`${name}\\``);\n }\n\n /**\n * Rename a column\n * @param {string} table - Table name\n * @param {string} oldName - Current name\n * @param {string} newName - New name\n */\n async renameColumn(table: string, oldName: string, newName: string): Promise<void> {\n await this.execute(`ALTER TABLE \\`${table}\\` RENAME COLUMN \\`${oldName}\\` TO \\`${newName}\\``);\n }\n\n /**\n * Execute within a transaction\n * @param {() => Promise<T>} fn - Function to execute\n * @returns {Promise<T>} Result\n */\n async transaction<T>(fn: () => Promise<T>): Promise<T> {\n const conn = await this.getPool().getConnection();\n try {\n await conn.beginTransaction();\n const result = await fn();\n await conn.commit();\n return result;\n } catch (err) {\n await conn.rollback();\n throw err;\n } finally {\n conn.release();\n }\n }\n\n /**\n * Fetch all column metadata for all tables in the database in a single query\n * @returns {Promise<Record<string, ColumnMetadata[]>>} Columns grouped by table name\n */\n async getAllTableColumns(): Promise<Record<string, ColumnMetadata[]>> {\n try {\n const rows = await this.query(\n \"SELECT TABLE_NAME, COLUMN_NAME, DATA_TYPE, IS_NULLABLE, COLUMN_KEY, EXTRA, COLUMN_DEFAULT FROM information_schema.COLUMNS WHERE TABLE_SCHEMA = ? ORDER BY TABLE_NAME, ORDINAL_POSITION\",\n [this.config.database],\n );\n\n const result: Record<string, ColumnMetadata[]> = {};\n for (let i = 0; i < rows.length; i++) {\n const row = rows[i] as any;\n if (!row || !row.TABLE_NAME) {\n continue;\n }\n const tableName = row.TABLE_NAME;\n if (!result[tableName]) {\n result[tableName] = [];\n }\n result[tableName].push({\n name: row.COLUMN_NAME,\n type: this.mapMySQLType(row.DATA_TYPE),\n primaryKey: row.COLUMN_KEY === \"PRI\",\n autoIncrement: row.EXTRA?.includes(\"auto_increment\") ?? false,\n notNull: row.IS_NULLABLE === \"NO\",\n unique: row.COLUMN_KEY === \"UNI\",\n defaultValue: row.COLUMN_DEFAULT,\n });\n }\n return result;\n } catch (err: any) {\n throw new DriverError(`Failed to fetch all table columns: ${err.message}`);\n }\n }\n\n private mapMySQLType(type: string): ColumnMetadata[\"type\"] {\n const lower = type.toLowerCase();\n if (\n lower === \"int\" ||\n lower === \"integer\" ||\n lower === \"tinyint\" ||\n lower === \"smallint\" ||\n lower === \"mediumint\"\n ) {\n return \"integer\";\n }\n if (lower === \"bigint\") {\n return \"bigint\";\n }\n if (lower === \"varchar\") {\n return \"varchar\";\n }\n if (lower === \"char\") {\n return \"char\";\n }\n if (lower === \"text\" || lower === \"mediumtext\" || lower === \"longtext\") {\n return \"text\";\n }\n if (lower === \"json\") {\n return \"json\";\n }\n if (lower === \"datetime\") {\n return \"datetime\";\n }\n if (lower === \"timestamp\") {\n return \"timestamp\";\n }\n if (lower === \"decimal\" || lower === \"numeric\") {\n return \"decimal\";\n }\n if (lower === \"float\" || lower === \"double\" || lower === \"real\") {\n return \"float\";\n }\n if (lower === \"blob\" || lower === \"mediumblob\" || lower === \"longblob\") {\n return \"blob\";\n }\n return \"text\";\n }\n}\n"],"mappings":"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"}
@@ -1,3 +1,4 @@
1
+ import { __esmMin } from "../_virtual/_rolldown/runtime.mjs";
1
2
  //#region src/drivers/sql-compiler.ts
2
3
  /**
3
4
  * Compile column type to SQL string for a specific database dialect
@@ -276,7 +277,9 @@ function compileDelete(tableName, where, params) {
276
277
  if (Object.keys(where).length > 0) sql += ` WHERE ${compileWhere(where, params)}`;
277
278
  return sql;
278
279
  }
280
+ var init_sql_compiler = __esmMin((() => {}));
279
281
  //#endregion
280
- export { compileBulkInsert, compileColumnDef, compileColumnType, compileCreateTable, compileDelete, compileInsert, compileSelect, compileUpdate, compileWhere };
282
+ init_sql_compiler();
283
+ export { compileBulkInsert, compileColumnDef, compileColumnType, compileCreateTable, compileDelete, compileInsert, compileSelect, compileUpdate, compileWhere, init_sql_compiler };
281
284
 
282
285
  //# sourceMappingURL=sql-compiler.mjs.map