pqb 0.52.3 → 0.53.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.js CHANGED
@@ -4,6 +4,7 @@ var orchidCore = require('orchid-core');
4
4
  var pg = require('pg');
5
5
  var node_util = require('node:util');
6
6
  var node_async_hooks = require('node:async_hooks');
7
+ var pqb = require('pqb');
7
8
 
8
9
  const used = [];
9
10
  const literalValues = [];
@@ -2752,7 +2753,7 @@ const _joinLateralProcessArg = (q, arg, cb) => {
2752
2753
  } else {
2753
2754
  const w = q.q.withShapes?.[arg];
2754
2755
  if (w) {
2755
- const t = Object.create(q.queryBuilder);
2756
+ const t = Object.create(q.qb);
2756
2757
  t.table = arg;
2757
2758
  t.shape = w.shape;
2758
2759
  t.computeds = w.computeds;
@@ -3881,7 +3882,7 @@ function queryFrom(self, arg) {
3881
3882
  if (typeof arg === "string") {
3882
3883
  data.as || (data.as = arg);
3883
3884
  const w = data.withShapes?.[arg];
3884
- data.shape = w?.shape ?? orchidCore.emptyObject;
3885
+ data.shape = w?.shape ?? anyShape;
3885
3886
  data.computeds = w?.computeds;
3886
3887
  } else if (orchidCore.isExpression(arg)) {
3887
3888
  data.as || (data.as = "t");
@@ -4664,17 +4665,19 @@ const makeInsertSql = (ctx, q, query, quotedAs) => {
4664
4665
  let values = query.values;
4665
4666
  if (quotedColumns.length === 0) {
4666
4667
  const key = Object.keys(q.shape)[0];
4667
- const column = q.shape[key];
4668
- quotedColumns[0] = `"${column?.data.name || key}"`;
4669
- if (Array.isArray(values) && Array.isArray(values[0])) {
4670
- values = values.map(() => [void 0]);
4668
+ if (key) {
4669
+ const column = q.shape[key];
4670
+ quotedColumns[0] = `"${column?.data.name || key}"`;
4671
+ if (Array.isArray(values) && Array.isArray(values[0])) {
4672
+ values = values.map(() => [void 0]);
4673
+ }
4671
4674
  }
4672
4675
  }
4673
4676
  ctx.sql.push(
4674
- `INSERT INTO ${quotedAs}(${quotedColumns.join(", ")})`,
4677
+ `INSERT INTO ${quotedAs}${quotedColumns.length ? "(" + quotedColumns.join(", ") + ")" : ""}`,
4675
4678
  null
4676
4679
  );
4677
- const QueryClass = ctx.queryBuilder.constructor;
4680
+ const QueryClass = ctx.qb.constructor;
4678
4681
  if (query.onConflict) {
4679
4682
  ctx.sql.push("ON CONFLICT");
4680
4683
  const { target } = query.onConflict;
@@ -5480,7 +5483,10 @@ const getTsVector = (ctx, data, lang, source, quotedAs) => {
5480
5483
  };
5481
5484
 
5482
5485
  const pushUpdateSql = (ctx, table, query, quotedAs) => {
5483
- const quotedTable = quoteSchemaAndTable(query.schema, table.table);
5486
+ const quotedTable = quoteSchemaAndTable(
5487
+ query.schema,
5488
+ table.table || query.from
5489
+ );
5484
5490
  const set = [];
5485
5491
  processData(ctx, table, set, query.updateData, quotedAs);
5486
5492
  if (!set.length) {
@@ -5524,7 +5530,7 @@ const pushUpdateReturning = (ctx, table, query, quotedAs, keyword) => {
5524
5530
  };
5525
5531
  const processData = (ctx, table, set, data, quotedAs) => {
5526
5532
  let append;
5527
- const QueryClass = ctx.queryBuilder.constructor;
5533
+ const QueryClass = ctx.qb.constructor;
5528
5534
  for (const item of data) {
5529
5535
  if (typeof item === "function") {
5530
5536
  const result = item(data);
@@ -5570,7 +5576,7 @@ const processValue = (ctx, table, QueryClass, key, value, quotedAs) => {
5570
5576
  };
5571
5577
 
5572
5578
  const pushDeleteSql = (ctx, table, query, quotedAs) => {
5573
- const from = `"${table.table}"`;
5579
+ const from = `"${table.table || query.from}"`;
5574
5580
  ctx.sql.push(`DELETE FROM ${from}`);
5575
5581
  if (from !== quotedAs) {
5576
5582
  ctx.sql.push(quotedAs);
@@ -5678,7 +5684,7 @@ const toSQL = (table, options) => {
5678
5684
  const sql = [];
5679
5685
  const values = options?.values || [];
5680
5686
  const ctx = {
5681
- queryBuilder: table.queryBuilder,
5687
+ qb: table.qb,
5682
5688
  q: query,
5683
5689
  sql,
5684
5690
  values,
@@ -5998,7 +6004,7 @@ const processWhere = (ands, ctx, table, query, data, quotedAs) => {
5998
6004
  throw new Error(`Unknown column ${key} provided to condition`);
5999
6005
  }
6000
6006
  }
6001
- if (value instanceof ctx.queryBuilder.constructor) {
6007
+ if (value instanceof ctx.qb.constructor) {
6002
6008
  ands.push(
6003
6009
  `${quotedColumn} = (${getSqlText(value.toSQL(ctx))})`
6004
6010
  );
@@ -6299,7 +6305,7 @@ const processJoinArgs = (joinTo, first, args, joinSubQuery, whereExists) => {
6299
6305
  if (!w) {
6300
6306
  throw new Error("Cannot find a `with` statement");
6301
6307
  }
6302
- const j = joinTo.queryBuilder.baseQuery.clone();
6308
+ const j = joinTo.qb.baseQuery.clone();
6303
6309
  j.table = first;
6304
6310
  j.q = {
6305
6311
  shape: w.shape,
@@ -7488,6 +7494,7 @@ class VirtualColumn extends ColumnType {
7488
7494
  this.dataType = "";
7489
7495
  this.operators = Operators.any;
7490
7496
  this.data.explicitSelect = true;
7497
+ this.data.insertable = this.data.updatable = false;
7491
7498
  }
7492
7499
  toCode() {
7493
7500
  throw new Error(`toCode is not implemented for virtual column`);
@@ -7499,6 +7506,7 @@ const _UnknownColumn = class _UnknownColumn extends VirtualColumn {
7499
7506
  super(schema, schema.unknown());
7500
7507
  this.selectable = true;
7501
7508
  this.data.explicitSelect = void 0;
7509
+ this.data.insertable = this.data.updatable = true;
7502
7510
  }
7503
7511
  };
7504
7512
  _UnknownColumn.instance = new _UnknownColumn(defaultSchemaConfig);
@@ -7566,6 +7574,12 @@ const makeColumnsByType = (schema) => {
7566
7574
  };
7567
7575
  };
7568
7576
 
7577
+ const anyShape = new Proxy(orchidCore.emptyObject, {
7578
+ get() {
7579
+ return UnknownColumn.instance;
7580
+ }
7581
+ });
7582
+
7569
7583
  const { types } = pg;
7570
7584
  const defaultTypeParsers = {};
7571
7585
  for (const key in types.builtins) {
@@ -8426,14 +8440,7 @@ const createSelect = (q) => {
8426
8440
  const processCreateItem = (q, item, rowIndex, ctx, encoders) => {
8427
8441
  const { shape } = q.q;
8428
8442
  for (const key in item) {
8429
- if (shape[key] instanceof VirtualColumn) {
8430
- shape[key].create?.(
8431
- q,
8432
- ctx,
8433
- item,
8434
- rowIndex
8435
- );
8436
- } else {
8443
+ if (shape[key]?.data.insertable !== false) {
8437
8444
  if (typeof item[key] === "function") {
8438
8445
  item[key] = resolveSubQueryCallbackV2(
8439
8446
  q,
@@ -8444,6 +8451,13 @@ const processCreateItem = (q, item, rowIndex, ctx, encoders) => {
8444
8451
  ctx.columns.set(key, ctx.columns.size);
8445
8452
  encoders[key] = shape[key]?.data.encode;
8446
8453
  }
8454
+ } else if (shape[key] instanceof VirtualColumn) {
8455
+ shape[key].create?.(
8456
+ q,
8457
+ ctx,
8458
+ item,
8459
+ rowIndex
8460
+ );
8447
8461
  }
8448
8462
  }
8449
8463
  };
@@ -8656,7 +8670,7 @@ class Create {
8656
8670
  * `create` and `insert` can be used in {@link WithMethods.with} expressions:
8657
8671
  *
8658
8672
  * ```ts
8659
- * db.$queryBuilder
8673
+ * db.$qb
8660
8674
  * // create a record in one table
8661
8675
  * .with('a', db.table.select('id').create(data))
8662
8676
  * // create a record in other table using the first table record id
@@ -9195,7 +9209,7 @@ class Delete {
9195
9209
  * `delete` can be used in {@link WithMethods.with} expressions:
9196
9210
  *
9197
9211
  * ```ts
9198
- * db.$queryBuilder
9212
+ * db.$qb
9199
9213
  * // delete a record in one table
9200
9214
  * .with('a', db.table.find(1).select('id').delete())
9201
9215
  * // delete a record in other table using the first table record id
@@ -10603,7 +10617,7 @@ class WithMethods {
10603
10617
  let [options, queryArg] = third ? [second, third] : [void 0, second];
10604
10618
  let query;
10605
10619
  if (typeof queryArg === "function") {
10606
- const arg = q.queryBuilder.clone();
10620
+ const arg = q.qb.clone();
10607
10621
  arg.q.withShapes = q.q.withShapes;
10608
10622
  query = queryArg(arg);
10609
10623
  } else {
@@ -10630,7 +10644,7 @@ class WithMethods {
10630
10644
  var _a;
10631
10645
  const q = _clone(this);
10632
10646
  let [options, baseFn, recursiveFn] = args.length === 2 ? [{}, args[0], args[1]] : args;
10633
- const arg = q.queryBuilder.clone();
10647
+ const arg = q.qb.clone();
10634
10648
  arg.q.withShapes = q.q.withShapes;
10635
10649
  let query = typeof baseFn === "function" ? baseFn(arg) : baseFn;
10636
10650
  const shape = getShapeFromSelect(query, true);
@@ -10911,7 +10925,7 @@ class Update {
10911
10925
  * `update` can be used in {@link WithMethods.with} expressions:
10912
10926
  *
10913
10927
  * ```ts
10914
- * db.$queryBuilder
10928
+ * db.$qb
10915
10929
  * // update record in one table
10916
10930
  * .with('a', db.table.find(1).select('id').update(data))
10917
10931
  * // update record in other table using the first table record id
@@ -11373,12 +11387,12 @@ function orCreate(query, data, updateData, mergeData) {
11373
11387
  q2.q.inCTE = inCTE;
11374
11388
  const c = q2.create(data);
11375
11389
  c.q.select = q2.q.select;
11376
- let q22 = q2.queryBuilder.with("f", q2).with("c", c);
11390
+ let q22 = q2.qb.with("f", q2).with("c", c);
11377
11391
  q22.q.returnsOne = true;
11378
11392
  queryFrom(q22, "f");
11379
11393
  q22 = _queryUnion(
11380
11394
  q22,
11381
- [q2.queryBuilder.from("c")],
11395
+ [q2.qb.from("c")],
11382
11396
  "UNION ALL",
11383
11397
  true,
11384
11398
  true
@@ -12813,12 +12827,49 @@ const parseIndexOrExclude = (item) => {
12813
12827
  return item;
12814
12828
  };
12815
12829
 
12816
- const anyShape = {};
12830
+ const performQuery = async (q, args, method) => {
12831
+ const trx = q.internal.transactionStorage.getStore();
12832
+ let sql;
12833
+ if (orchidCore.isRawSQL(args[0])) {
12834
+ const values = [];
12835
+ sql = {
12836
+ text: args[0].toSQL({ values }),
12837
+ values
12838
+ };
12839
+ } else {
12840
+ const values = [];
12841
+ sql = {
12842
+ text: pqb.templateLiteralToSQL(args, {
12843
+ qb: q.qb,
12844
+ q: q.q,
12845
+ sql: [],
12846
+ values
12847
+ }),
12848
+ values
12849
+ };
12850
+ }
12851
+ const log = trx?.log ?? q.q.log;
12852
+ let logData;
12853
+ if (log) logData = log.beforeQuery(sql);
12854
+ try {
12855
+ const result = await (trx?.adapter || q.adapter)[method](
12856
+ sql
12857
+ );
12858
+ if (log) log.afterQuery(sql, logData);
12859
+ return result;
12860
+ } catch (err) {
12861
+ if (log) {
12862
+ log.onError(err, sql, logData);
12863
+ }
12864
+ throw err;
12865
+ }
12866
+ };
12867
+
12817
12868
  class Db extends QueryMethods {
12818
- constructor(adapter, queryBuilder, table = void 0, shape = anyShape, columnTypes, transactionStorage, options, tableData = {}) {
12869
+ constructor(adapter, qb, table = void 0, shape = anyShape, columnTypes, transactionStorage, options, tableData = {}) {
12819
12870
  super();
12820
12871
  this.adapter = adapter;
12821
- this.queryBuilder = queryBuilder;
12872
+ this.qb = qb;
12822
12873
  this.table = table;
12823
12874
  this.shape = shape;
12824
12875
  this.columnTypes = columnTypes;
@@ -12995,11 +13046,54 @@ class Db extends QueryMethods {
12995
13046
  *
12996
13047
  * @param args - SQL template literal, or an object { raw: string, values?: unknown[] }
12997
13048
  */
12998
- query(...args) {
12999
- return performQuery(this, args, "query");
13049
+ get query() {
13050
+ const q = this;
13051
+ let query = q._query;
13052
+ if (!query) {
13053
+ q._query = query = Object.assign(
13054
+ (...args) => performQuery(q, args, "query"),
13055
+ {
13056
+ async records(...args) {
13057
+ const { rows } = await performQuery(q, args, "query");
13058
+ return rows;
13059
+ },
13060
+ async take(...args) {
13061
+ const {
13062
+ rows: [row]
13063
+ } = await performQuery(q, args, "query");
13064
+ if (!row) throw new NotFoundError(q);
13065
+ return row;
13066
+ },
13067
+ async takeOptional(...args) {
13068
+ const { rows } = await performQuery(q, args, "query");
13069
+ return rows[0];
13070
+ },
13071
+ async rows(...args) {
13072
+ const { rows } = await performQuery(q, args, "arrays");
13073
+ return rows;
13074
+ },
13075
+ async pluck(...args) {
13076
+ const { rows } = await performQuery(q, args, "arrays");
13077
+ return rows.map((row) => row[0]);
13078
+ },
13079
+ async get(...args) {
13080
+ const {
13081
+ rows: [row]
13082
+ } = await performQuery(q, args, "arrays");
13083
+ if (!row) throw new NotFoundError(q);
13084
+ return row[0];
13085
+ },
13086
+ async getOptional(...args) {
13087
+ const { rows } = await performQuery(q, args, "arrays");
13088
+ return rows[0]?.[0];
13089
+ }
13090
+ }
13091
+ );
13092
+ }
13093
+ return query;
13000
13094
  }
13001
13095
  /**
13002
- * The same as the {@link query}, but returns an array of arrays instead of objects:
13096
+ * Performs a SQL query, returns a db result with array of arrays instead of objects:
13003
13097
  *
13004
13098
  * ```ts
13005
13099
  * const value = 1;
@@ -13034,43 +13128,6 @@ class Db extends QueryMethods {
13034
13128
  return map.get(name);
13035
13129
  }
13036
13130
  }
13037
- const performQuery = async (q, args, method) => {
13038
- const trx = q.internal.transactionStorage.getStore();
13039
- let sql;
13040
- if (orchidCore.isRawSQL(args[0])) {
13041
- const values = [];
13042
- sql = {
13043
- text: args[0].toSQL({ values }),
13044
- values
13045
- };
13046
- } else {
13047
- const values = [];
13048
- sql = {
13049
- text: templateLiteralToSQL(args, {
13050
- queryBuilder: q.queryBuilder,
13051
- q: q.q,
13052
- sql: [],
13053
- values
13054
- }),
13055
- values
13056
- };
13057
- }
13058
- const log = trx?.log ?? q.q.log;
13059
- let logData;
13060
- if (log) logData = log.beforeQuery(sql);
13061
- try {
13062
- const result = await (trx?.adapter || q.adapter)[method](
13063
- sql
13064
- );
13065
- if (log) log.afterQuery(sql, logData);
13066
- return result;
13067
- } catch (err) {
13068
- if (log) {
13069
- log.onError(err, sql, logData);
13070
- }
13071
- throw err;
13072
- }
13073
- };
13074
13131
  orchidCore.applyMixins(Db, [QueryMethods]);
13075
13132
  Db.prototype.constructor = Db;
13076
13133
  const createDb = ({
@@ -13119,9 +13176,7 @@ const createDb = ({
13119
13176
  adapter,
13120
13177
  close: () => adapter.close()
13121
13178
  });
13122
- for (const name of Object.getOwnPropertyNames(Db.prototype)) {
13123
- db[name] = Db.prototype[name];
13124
- }
13179
+ Object.setPrototypeOf(db, Db.prototype);
13125
13180
  db.sql = (...args) => {
13126
13181
  const sql = raw(...args);
13127
13182
  sql.columnTypes = ct;
@@ -13154,13 +13209,13 @@ const _initQueryBuilder = (adapter, columnTypes, transactionStorage, commonOptio
13154
13209
  }
13155
13210
  qb.internal.domains = options.domains;
13156
13211
  qb.internal.generatorIgnore = options.generatorIgnore;
13157
- return qb.queryBuilder = qb;
13212
+ return qb.qb = qb;
13158
13213
  };
13159
13214
 
13160
13215
  class Rollback extends Error {
13161
13216
  }
13162
13217
  const trxForTest = Symbol("trxForTest");
13163
- const argToDb = (arg) => "$queryBuilder" in arg ? arg.$queryBuilder : arg;
13218
+ const argToDb = (arg) => "$qb" in arg ? arg.$qb : arg;
13164
13219
  const testTransaction = {
13165
13220
  /**
13166
13221
  * Start a test transaction.