@type32/tauri-sqlite-orm 0.1.18-5 → 0.1.18-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.
package/dist/index.mjs CHANGED
@@ -41,7 +41,7 @@ var SQLiteColumn = class _SQLiteColumn {
41
41
  return new _SQLiteColumn(
42
42
  this._.name,
43
43
  this.type,
44
- { ...this.options, primaryKey: true },
44
+ { ...this.options, primaryKey: true, notNull: true },
45
45
  this._.mode
46
46
  );
47
47
  }
@@ -83,6 +83,9 @@ var SQLiteColumn = class _SQLiteColumn {
83
83
  this._.mode
84
84
  );
85
85
  }
86
+ as(alias2) {
87
+ return this;
88
+ }
86
89
  };
87
90
  var text = (name) => new SQLiteColumn(name, "TEXT");
88
91
  var integer = (name, config) => new SQLiteColumn(name, "INTEGER", {}, config?.mode || "default");
@@ -113,6 +116,10 @@ var or = (...conditions) => ({
113
116
  sql: conditions.map((c) => `(${c.sql})`).join(" OR "),
114
117
  params: conditions.flatMap((c) => c.params)
115
118
  });
119
+ var not = (condition) => ({
120
+ sql: `NOT (${condition.sql})`,
121
+ params: condition.params
122
+ });
116
123
  var gt = (column, value) => ({
117
124
  sql: `${column._.name} > ?`,
118
125
  params: [value]
@@ -145,6 +152,58 @@ var inArray = (column, values) => ({
145
152
  sql: `${column._.name} IN (${values.map(() => "?").join(",")})`,
146
153
  params: values
147
154
  });
155
+ var asc = (column) => ({
156
+ sql: `${column._.name} ASC`,
157
+ params: []
158
+ });
159
+ var desc = (column) => ({
160
+ sql: `${column._.name} DESC`,
161
+ params: []
162
+ });
163
+ var count = (column) => ({
164
+ sql: `COUNT(${column ? column._.name : "*"})`,
165
+ params: []
166
+ });
167
+ var countDistinct = (column) => ({
168
+ sql: `COUNT(DISTINCT ${column._.name})`,
169
+ params: []
170
+ });
171
+ var sum = (column) => ({
172
+ sql: `SUM(${column._.name})`,
173
+ params: []
174
+ });
175
+ var avg = (column) => ({
176
+ sql: `AVG(${column._.name})`,
177
+ params: []
178
+ });
179
+ var max = (column) => ({
180
+ sql: `MAX(${column._.name})`,
181
+ params: []
182
+ });
183
+ var min = (column) => ({
184
+ sql: `MIN(${column._.name})`,
185
+ params: []
186
+ });
187
+ var sql = (strings, ...values) => {
188
+ const queryParts = [];
189
+ const params = [];
190
+ strings.forEach((str, i) => {
191
+ queryParts.push(str);
192
+ if (values[i] !== void 0) {
193
+ if (typeof values[i] === "object" && values[i].sql) {
194
+ queryParts.push(values[i].sql);
195
+ params.push(...values[i].params);
196
+ } else {
197
+ queryParts.push("?");
198
+ params.push(values[i]);
199
+ }
200
+ }
201
+ });
202
+ return {
203
+ sql: queryParts.join(""),
204
+ params
205
+ };
206
+ };
148
207
  var BaseQueryBuilder = class {
149
208
  constructor(db) {
150
209
  this.db = db;
@@ -157,15 +216,20 @@ var BaseQueryBuilder = class {
157
216
  return this;
158
217
  }
159
218
  orderBy(column, direction = "ASC") {
160
- this.query += ` ORDER BY ${column._.name} ${direction}`;
219
+ if ("sql" in column) {
220
+ this.query += ` ORDER BY ${column.sql} ${direction}`;
221
+ this.params.push(...column.params);
222
+ } else {
223
+ this.query += ` ORDER BY ${column._.name} ${direction}`;
224
+ }
161
225
  return this;
162
226
  }
163
- limit(count) {
164
- this.query += ` LIMIT ${count}`;
227
+ limit(count2) {
228
+ this.query += ` LIMIT ${count2}`;
165
229
  return this;
166
230
  }
167
- offset(count) {
168
- this.query += ` OFFSET ${count}`;
231
+ offset(count2) {
232
+ this.query += ` OFFSET ${count2}`;
169
233
  return this;
170
234
  }
171
235
  build() {
@@ -183,9 +247,37 @@ var SelectQueryBuilder = class extends BaseQueryBuilder {
183
247
  const columnNames = columns ? columns.map((c) => table._.columns[c]._.name) : ["*"];
184
248
  this.query = `SELECT ${columnNames.join(", ")} FROM ${table._.name}`;
185
249
  }
250
+ isDistinct = false;
251
+ groupByColumns = [];
252
+ havingCondition = null;
253
+ distinct() {
254
+ this.isDistinct = true;
255
+ this.query = this.query.replace("SELECT", "SELECT DISTINCT");
256
+ return this;
257
+ }
258
+ groupBy(...columns) {
259
+ this.groupByColumns.push(...columns);
260
+ const columnNames = columns.map((col) => col._.name).join(", ");
261
+ this.query += ` GROUP BY ${columnNames}`;
262
+ return this;
263
+ }
264
+ having(condition) {
265
+ this.havingCondition = condition;
266
+ this.query += ` HAVING ${condition.sql}`;
267
+ this.params.push(...condition.params);
268
+ return this;
269
+ }
186
270
  async execute() {
187
- const { sql, params } = this.build();
188
- return this.db.select(sql, params);
271
+ const { sql: sql2, params } = this.build();
272
+ return this.db.select(sql2, params);
273
+ }
274
+ async all() {
275
+ return this.execute();
276
+ }
277
+ async get() {
278
+ this.limit(1);
279
+ const result = await this.execute();
280
+ return result[0];
189
281
  }
190
282
  };
191
283
  var InsertQueryBuilder = class extends BaseQueryBuilder {
@@ -195,26 +287,69 @@ var InsertQueryBuilder = class extends BaseQueryBuilder {
195
287
  this.query = `INSERT INTO ${table._.name}`;
196
288
  }
197
289
  dataSets = [];
290
+ returningColumns = [];
291
+ onConflictAction = null;
292
+ conflictTarget = [];
293
+ updateSet = {};
198
294
  values(data) {
199
295
  const dataArray = Array.isArray(data) ? data : [data];
200
296
  this.dataSets.push(...dataArray);
201
297
  return this;
202
298
  }
299
+ returning(...columns) {
300
+ this.returningColumns = columns;
301
+ return this;
302
+ }
303
+ onConflictDoNothing(target) {
304
+ this.onConflictAction = "nothing";
305
+ if (target) {
306
+ this.conflictTarget = Array.isArray(target) ? target : [target];
307
+ }
308
+ return this;
309
+ }
310
+ onConflictDoUpdate(config) {
311
+ this.onConflictAction = "update";
312
+ this.conflictTarget = Array.isArray(config.target) ? config.target : [config.target];
313
+ this.updateSet = config.set;
314
+ return this;
315
+ }
316
+ processDefaultValues(data) {
317
+ const finalData = { ...data };
318
+ for (const [key, column] of Object.entries(this.table._.columns)) {
319
+ const typedKey = key;
320
+ if (finalData[typedKey] === void 0) {
321
+ if (column.options.$defaultFn) {
322
+ finalData[typedKey] = column.options.$defaultFn();
323
+ }
324
+ }
325
+ }
326
+ return finalData;
327
+ }
328
+ buildConflictClause() {
329
+ if (!this.onConflictAction) return "";
330
+ let clause = " ON CONFLICT";
331
+ if (this.conflictTarget.length > 0) {
332
+ const targetNames = this.conflictTarget.map((col) => col._.name).join(", ");
333
+ clause += ` (${targetNames})`;
334
+ }
335
+ if (this.onConflictAction === "nothing") {
336
+ clause += " DO NOTHING";
337
+ } else if (this.onConflictAction === "update") {
338
+ const setEntries = Object.entries(this.updateSet);
339
+ if (setEntries.length > 0) {
340
+ const setClause = setEntries.map(([key]) => `${key} = ?`).join(", ");
341
+ clause += ` DO UPDATE SET ${setClause}`;
342
+ }
343
+ }
344
+ return clause;
345
+ }
203
346
  async execute() {
204
347
  if (this.dataSets.length === 0) {
205
348
  throw new Error("No data provided for insert");
206
349
  }
207
- const processedDataSets = this.dataSets.map((dataSet) => {
208
- const finalData = { ...dataSet };
209
- for (const [key, column] of Object.entries(this.table._.columns)) {
210
- if (finalData[key] === void 0) {
211
- if (column.options.$defaultFn) {
212
- finalData[key] = column.options.$defaultFn();
213
- }
214
- }
215
- }
216
- return finalData;
217
- });
350
+ const processedDataSets = this.dataSets.map(
351
+ (data) => this.processDefaultValues(data)
352
+ );
218
353
  const groups = /* @__PURE__ */ new Map();
219
354
  for (const dataSet of processedDataSets) {
220
355
  const keys = Object.keys(dataSet).sort().join(",");
@@ -223,7 +358,9 @@ var InsertQueryBuilder = class extends BaseQueryBuilder {
223
358
  }
224
359
  groups.get(keys).push(dataSet);
225
360
  }
226
- let lastInsertId = void 0;
361
+ let results = [];
362
+ let lastInsertId;
363
+ let rowsAffected = 0;
227
364
  for (const [_, dataSets] of groups) {
228
365
  const columns = Object.keys(dataSets[0]);
229
366
  const columnNames = columns.map(
@@ -231,16 +368,40 @@ var InsertQueryBuilder = class extends BaseQueryBuilder {
231
368
  );
232
369
  const placeholders = `(${columns.map(() => "?").join(", ")})`;
233
370
  const valuesSql = dataSets.map(() => placeholders).join(", ");
371
+ const conflictClause = this.buildConflictClause();
234
372
  const finalQuery = `${this.query} (${columnNames.join(
235
373
  ", "
236
- )}) VALUES ${valuesSql}`;
374
+ )}) VALUES ${valuesSql}${conflictClause}`;
237
375
  const params = dataSets.flatMap(
238
376
  (data) => columns.map((col) => data[col] ?? null)
239
377
  );
240
- const result = await this.db.execute(finalQuery, params);
241
- lastInsertId = result.lastInsertId;
378
+ if (this.onConflictAction === "update") {
379
+ const setValues = Object.entries(this.updateSet).map(
380
+ ([, value]) => value
381
+ );
382
+ params.push(...setValues);
383
+ }
384
+ if (this.returningColumns.length > 0) {
385
+ const returningNames = this.returningColumns.map((col) => this.table._.columns[col]._.name).join(", ");
386
+ const queryWithReturning = `${finalQuery} RETURNING ${returningNames}`;
387
+ const rows = await this.db.select(queryWithReturning, params);
388
+ results = results.concat(rows);
389
+ } else {
390
+ const result = await this.db.execute(finalQuery, params);
391
+ lastInsertId = result.lastInsertId;
392
+ rowsAffected += result.rowsAffected;
393
+ }
394
+ }
395
+ if (this.returningColumns.length > 0) {
396
+ return results;
242
397
  }
243
- return lastInsertId ?? 0;
398
+ return [{ lastInsertId, rowsAffected }];
399
+ }
400
+ async returningAll() {
401
+ const allColumns = Object.keys(
402
+ this.table._.columns
403
+ );
404
+ return this.returning(...allColumns).execute();
244
405
  }
245
406
  };
246
407
  var UpdateQueryBuilder = class extends BaseQueryBuilder {
@@ -250,15 +411,21 @@ var UpdateQueryBuilder = class extends BaseQueryBuilder {
250
411
  this.query = `UPDATE ${table._.name}`;
251
412
  }
252
413
  updateData = {};
414
+ returningColumns = [];
253
415
  set(data) {
254
416
  this.updateData = { ...this.updateData, ...data };
255
417
  return this;
256
418
  }
257
- build() {
419
+ returning(...columns) {
420
+ this.returningColumns = columns;
421
+ return this;
422
+ }
423
+ buildUpdateClause() {
258
424
  const finalUpdateData = { ...this.updateData };
259
425
  for (const [key, column] of Object.entries(this.table._.columns)) {
260
- if (finalUpdateData[key] === void 0 && column.options.$onUpdateFn) {
261
- finalUpdateData[key] = column.options.$onUpdateFn();
426
+ const typedKey = key;
427
+ if (finalUpdateData[typedKey] === void 0 && column.options.$onUpdateFn) {
428
+ finalUpdateData[typedKey] = column.options.$onUpdateFn();
262
429
  }
263
430
  }
264
431
  const baseQuery = this.query;
@@ -284,14 +451,26 @@ var UpdateQueryBuilder = class extends BaseQueryBuilder {
284
451
  return `${column._.name} = ?`;
285
452
  }).join(", ");
286
453
  const setParams = entries.map(([, value]) => value);
287
- const sql = `${tablePart} SET ${setClause}${whereClause}`;
454
+ const sql2 = `${tablePart} SET ${setClause}${whereClause}`;
288
455
  const params = [...setParams, ...whereParams];
289
- return { sql, params };
456
+ return { sql: sql2, params };
290
457
  }
291
458
  async execute() {
292
- const { sql, params } = this.build();
293
- const result = await this.db.execute(sql, params);
294
- return result.rowsAffected;
459
+ const { sql: updateSql, params } = this.buildUpdateClause();
460
+ if (this.returningColumns.length > 0) {
461
+ const returningNames = this.returningColumns.map((col) => this.table._.columns[col]._.name).join(", ");
462
+ const sqlWithReturning = `${updateSql} RETURNING ${returningNames}`;
463
+ return this.db.select(sqlWithReturning, params);
464
+ } else {
465
+ const result = await this.db.execute(updateSql, params);
466
+ return [{ rowsAffected: result.rowsAffected }];
467
+ }
468
+ }
469
+ async returningAll() {
470
+ const allColumns = Object.keys(
471
+ this.table._.columns
472
+ );
473
+ return this.returning(...allColumns).execute();
295
474
  }
296
475
  };
297
476
  var DeleteQueryBuilder = class extends BaseQueryBuilder {
@@ -300,10 +479,67 @@ var DeleteQueryBuilder = class extends BaseQueryBuilder {
300
479
  this.table = table;
301
480
  this.query = `DELETE FROM ${table._.name}`;
302
481
  }
482
+ returningColumns = [];
483
+ returning(...columns) {
484
+ this.returningColumns = columns;
485
+ return this;
486
+ }
303
487
  async execute() {
304
- const { sql, params } = this.build();
305
- const result = await this.db.execute(sql, params);
306
- return result.rowsAffected;
488
+ const { sql: sql2, params } = this.build();
489
+ if (this.returningColumns.length > 0) {
490
+ const returningNames = this.returningColumns.map((col) => this.table._.columns[col]._.name).join(", ");
491
+ const sqlWithReturning = `${sql2} RETURNING ${returningNames}`;
492
+ return this.db.select(sqlWithReturning, params);
493
+ } else {
494
+ const result = await this.db.execute(sql2, params);
495
+ return [{ rowsAffected: result.rowsAffected }];
496
+ }
497
+ }
498
+ async returningAll() {
499
+ const allColumns = Object.keys(
500
+ this.table._.columns
501
+ );
502
+ return this.returning(...allColumns).execute();
503
+ }
504
+ };
505
+ var WithQueryBuilder = class {
506
+ constructor(db) {
507
+ this.db = db;
508
+ }
509
+ ctes = [];
510
+ with(alias2, query) {
511
+ this.ctes.push({ alias: alias2, query: query.sql, params: query.params });
512
+ return this;
513
+ }
514
+ select(table, columns) {
515
+ const builder = new SelectQueryBuilder(this.db, table, columns);
516
+ this.applyWithClause(builder);
517
+ return builder;
518
+ }
519
+ insert(table) {
520
+ const builder = new InsertQueryBuilder(this.db, table);
521
+ this.applyWithClause(builder);
522
+ return builder;
523
+ }
524
+ update(table) {
525
+ const builder = new UpdateQueryBuilder(this.db, table);
526
+ this.applyWithClause(builder);
527
+ return builder;
528
+ }
529
+ delete(table) {
530
+ const builder = new DeleteQueryBuilder(this.db, table);
531
+ this.applyWithClause(builder);
532
+ return builder;
533
+ }
534
+ applyWithClause(builder) {
535
+ if (this.ctes.length > 0) {
536
+ const cteSql = this.ctes.map((cte) => `${cte.alias} AS (${cte.query})`).join(", ");
537
+ builder["query"] = `WITH ${cteSql} ${builder["query"]}`;
538
+ builder["params"] = [
539
+ ...this.ctes.flatMap((cte) => cte.params),
540
+ ...builder["params"]
541
+ ];
542
+ }
307
543
  }
308
544
  };
309
545
  var TauriORM = class {
@@ -317,23 +553,23 @@ var TauriORM = class {
317
553
  }
318
554
  tables = /* @__PURE__ */ new Map();
319
555
  buildColumnDefinition(col, forAlterTable = false) {
320
- let sql = `${col._.name} ${col.type}`;
556
+ let sql2 = `${col._.name} ${col.type}`;
321
557
  if (col.options.primaryKey && !forAlterTable) {
322
- sql += " PRIMARY KEY";
558
+ sql2 += " PRIMARY KEY";
323
559
  if (col._.autoincrement) {
324
- sql += " AUTOINCREMENT";
560
+ sql2 += " AUTOINCREMENT";
325
561
  }
326
562
  }
327
- if (col._.notNull) sql += " NOT NULL";
328
- if (col.options.unique) sql += " UNIQUE";
563
+ if (col._.notNull) sql2 += " NOT NULL";
564
+ if (col.options.unique) sql2 += " UNIQUE";
329
565
  if (col.options.default !== void 0) {
330
566
  const value = col.options.default;
331
- sql += ` DEFAULT ${typeof value === "string" ? `'${value.replace(/'/g, "''")}'` : value}`;
567
+ sql2 += ` DEFAULT ${typeof value === "string" ? `'${value.replace(/'/g, "''")}'` : value}`;
332
568
  }
333
569
  if (col.options.references) {
334
- sql += ` REFERENCES ${col.options.references.table._.name}(${col.options.references.column._.name})`;
570
+ sql2 += ` REFERENCES ${col.options.references.table._.name}(${col.options.references.column._.name})`;
335
571
  }
336
- return sql;
572
+ return sql2;
337
573
  }
338
574
  async migrate() {
339
575
  for (const table of this.tables.values()) {
@@ -370,6 +606,15 @@ var TauriORM = class {
370
606
  delete(table) {
371
607
  return new DeleteQueryBuilder(this.db, table);
372
608
  }
609
+ $with(alias2) {
610
+ const withBuilder = new WithQueryBuilder(this.db);
611
+ return {
612
+ as: (query) => {
613
+ withBuilder.with(alias2, query);
614
+ return withBuilder;
615
+ }
616
+ };
617
+ }
373
618
  async transaction(callback) {
374
619
  await this.db.execute("BEGIN TRANSACTION");
375
620
  try {
@@ -381,6 +626,9 @@ var TauriORM = class {
381
626
  throw error;
382
627
  }
383
628
  }
629
+ rollback() {
630
+ throw new Error("Transaction rolled back");
631
+ }
384
632
  // --- Schema detection / signature ---
385
633
  async ensureSchemaMeta() {
386
634
  await this.db.execute(
@@ -458,6 +706,12 @@ var relations = (table, relationsCallback) => {
458
706
  })
459
707
  });
460
708
  };
709
+ var getTableColumns = (table) => {
710
+ return table._.columns;
711
+ };
712
+ var alias = (table, alias2) => {
713
+ return table;
714
+ };
461
715
  export {
462
716
  DeleteQueryBuilder,
463
717
  InsertQueryBuilder,
@@ -466,10 +720,18 @@ export {
466
720
  Table,
467
721
  TauriORM,
468
722
  UpdateQueryBuilder,
723
+ WithQueryBuilder,
724
+ alias,
469
725
  and,
726
+ asc,
727
+ avg,
470
728
  blob,
471
729
  boolean,
730
+ count,
731
+ countDistinct,
732
+ desc,
472
733
  eq,
734
+ getTableColumns,
473
735
  gt,
474
736
  gte,
475
737
  inArray,
@@ -479,9 +741,14 @@ export {
479
741
  like,
480
742
  lt,
481
743
  lte,
744
+ max,
745
+ min,
746
+ not,
482
747
  or,
483
748
  real,
484
749
  relations,
750
+ sql,
485
751
  sqliteTable,
752
+ sum,
486
753
  text
487
754
  };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@type32/tauri-sqlite-orm",
3
- "version": "0.1.18-5",
3
+ "version": "0.1.18-7",
4
4
  "description": "A Drizzle-like ORM for Tauri v2's SQL JS API plugin.",
5
5
  "main": "./dist/index.js",
6
6
  "module": "./dist/index.mjs",