@restura/core 1.8.0 → 1.9.1

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.d.ts CHANGED
@@ -1130,6 +1130,10 @@ declare class PsqlEngine extends SqlEngine {
1130
1130
  private readonly INITIAL_RECONNECT_DELAY;
1131
1131
  constructor(psqlConnectionPool: PsqlPool, shouldListenForDbTriggers?: boolean, scratchDatabaseSuffix?: string);
1132
1132
  close(): Promise<void>;
1133
+ /**
1134
+ * Setup the return types for the PostgreSQL connection.
1135
+ * For example return DATE as a string instead of a Date object and BIGINT as a number instead of a string.
1136
+ */
1133
1137
  private setupPgReturnTypes;
1134
1138
  private reconnectTriggerClient;
1135
1139
  private listenForDbTriggers;
package/dist/index.js CHANGED
@@ -2325,6 +2325,19 @@ var initializers = `
2325
2325
  });
2326
2326
  return column + ' IN (' + literals.join(', ') + ')';
2327
2327
  }
2328
+
2329
+ // Format column with optional cast
2330
+ function formatColumn(col) {
2331
+ if (!col.cast) {
2332
+ return col.sql;
2333
+ }
2334
+ // Wrap JSON field extractions in parentheses when casting
2335
+ // because :: has higher precedence than ->>
2336
+ if (col.isJsonField) {
2337
+ return '(' + col.sql + ')::' + col.cast;
2338
+ }
2339
+ return col.sql + '::' + col.cast;
2340
+ }
2328
2341
  `;
2329
2342
  var entryGrammar = `
2330
2343
  {
@@ -2443,10 +2456,10 @@ SimpleExpr
2443
2456
  / negate:"!"? _ "(" _ col:Column _ "," _ op:NullOperator _ ")" _
2444
2457
  { return (negate ? 'NOT ' : '') + '(' + op(col) + ')'; }
2445
2458
  / negate:"!"? _ "(" _ col:Column _ "," _ val:CastedValue _ ")" _
2446
- { return (negate ? 'NOT ' : '') + '(' + col + ' = ' + formatValueWithCast(val.value, val.cast) + ')'; }
2459
+ { return (negate ? 'NOT ' : '') + '(' + formatColumn(col) + ' = ' + formatValueWithCast(val.value, val.cast) + ')'; }
2447
2460
 
2448
2461
  Column
2449
- = first:ColPart rest:("." ColPart)* {
2462
+ = first:ColPart rest:("." ColPart)* cast:TypeCast? {
2450
2463
  const partsArray = [first];
2451
2464
  if (rest && rest.length > 0) {
2452
2465
  partsArray.push(...rest.map(item => item[1]));
@@ -2456,38 +2469,44 @@ Column
2456
2469
  throw new SyntaxError('Column path cannot have more than 3 parts (table.column.jsonField)');
2457
2470
  }
2458
2471
 
2472
+ var sql;
2473
+ var isJsonField = false;
2459
2474
  if (partsArray.length === 1) {
2460
- return quoteSqlIdentity(partsArray[0]);
2461
- }
2462
- const tableName = quoteSqlIdentity(partsArray[0]);
2463
-
2464
- if (partsArray.length === 2) {
2465
- return tableName + '.' + quoteSqlIdentity(partsArray[1]);
2475
+ sql = quoteSqlIdentity(partsArray[0]);
2476
+ } else {
2477
+ const tableName = quoteSqlIdentity(partsArray[0]);
2478
+
2479
+ if (partsArray.length === 2) {
2480
+ sql = tableName + '.' + quoteSqlIdentity(partsArray[1]);
2481
+ } else {
2482
+ const jsonColumn = quoteSqlIdentity(partsArray[1]);
2483
+ const lastPart = partsArray[partsArray.length - 1];
2484
+ const escapedLast = lastPart.replace(/'/g, "''");
2485
+ sql = tableName + '.' + jsonColumn + "->>'" + escapedLast + "'";
2486
+ isJsonField = true;
2487
+ }
2466
2488
  }
2467
2489
 
2468
- const jsonColumn = quoteSqlIdentity(partsArray[1]);
2469
- const lastPart = partsArray[partsArray.length - 1];
2470
- const escapedLast = lastPart.replace(/'/g, "''");
2471
- return tableName + '.' + jsonColumn + "->>'" + escapedLast + "'";
2490
+ return { sql: sql, cast: cast, isJsonField: isJsonField };
2472
2491
  }
2473
2492
 
2474
2493
  ColPart
2475
2494
  = chars:[a-zA-Z0-9_]+ { return chars.join(''); }
2476
2495
 
2477
2496
  NullOperator
2478
- = "notnull"i { return function(col) { return col + ' IS NOT NULL'; }; }
2479
- / "null"i { return function(col) { return col + ' IS NULL'; }; }
2497
+ = "notnull"i { return function(col) { return formatColumn(col) + ' IS NOT NULL'; }; }
2498
+ / "null"i { return function(col) { return formatColumn(col) + ' IS NULL'; }; }
2480
2499
 
2481
2500
  OperatorWithValue
2482
- = "in"i _ "," _ val:CastedValueWithPipes { return function(col) { return buildInClauseWithCast(col, val.value, val.cast); }; }
2483
- / "ne"i _ "," _ val:CastedValue { return function(col) { return col + ' <> ' + formatValueWithCast(val.value, val.cast); }; }
2484
- / "gte"i _ "," _ val:CastedValue { return function(col) { return col + ' >= ' + formatValueWithCast(val.value, val.cast); }; }
2485
- / "gt"i _ "," _ val:CastedValue { return function(col) { return col + ' > ' + formatValueWithCast(val.value, val.cast); }; }
2486
- / "lte"i _ "," _ val:CastedValue { return function(col) { return col + ' <= ' + formatValueWithCast(val.value, val.cast); }; }
2487
- / "lt"i _ "," _ val:CastedValue { return function(col) { return col + ' < ' + formatValueWithCast(val.value, val.cast); }; }
2488
- / "has"i _ "," _ val:CastedValue { return function(col) { var formatted = format.literal('%' + unescapeValue(val.value) + '%'); return col + ' ILIKE ' + (val.cast ? formatted + '::' + val.cast : formatted); }; }
2489
- / "sw"i _ "," _ val:CastedValue { return function(col) { var formatted = format.literal(unescapeValue(val.value) + '%'); return col + ' ILIKE ' + (val.cast ? formatted + '::' + val.cast : formatted); }; }
2490
- / "ew"i _ "," _ val:CastedValue { return function(col) { var formatted = format.literal('%' + unescapeValue(val.value)); return col + ' ILIKE ' + (val.cast ? formatted + '::' + val.cast : formatted); }; }
2501
+ = "in"i _ "," _ val:CastedValueWithPipes { return function(col) { return buildInClauseWithCast(formatColumn(col), val.value, val.cast); }; }
2502
+ / "ne"i _ "," _ val:CastedValue { return function(col) { return formatColumn(col) + ' <> ' + formatValueWithCast(val.value, val.cast); }; }
2503
+ / "gte"i _ "," _ val:CastedValue { return function(col) { return formatColumn(col) + ' >= ' + formatValueWithCast(val.value, val.cast); }; }
2504
+ / "gt"i _ "," _ val:CastedValue { return function(col) { return formatColumn(col) + ' > ' + formatValueWithCast(val.value, val.cast); }; }
2505
+ / "lte"i _ "," _ val:CastedValue { return function(col) { return formatColumn(col) + ' <= ' + formatValueWithCast(val.value, val.cast); }; }
2506
+ / "lt"i _ "," _ val:CastedValue { return function(col) { return formatColumn(col) + ' < ' + formatValueWithCast(val.value, val.cast); }; }
2507
+ / "has"i _ "," _ val:CastedValue { return function(col) { var formatted = format.literal('%' + unescapeValue(val.value) + '%'); return formatColumn(col) + ' ILIKE ' + (val.cast ? formatted + '::' + val.cast : formatted); }; }
2508
+ / "sw"i _ "," _ val:CastedValue { return function(col) { var formatted = format.literal(unescapeValue(val.value) + '%'); return formatColumn(col) + ' ILIKE ' + (val.cast ? formatted + '::' + val.cast : formatted); }; }
2509
+ / "ew"i _ "," _ val:CastedValue { return function(col) { var formatted = format.literal('%' + unescapeValue(val.value)); return formatColumn(col) + ' ILIKE ' + (val.cast ? formatted + '::' + val.cast : formatted); }; }
2491
2510
 
2492
2511
  CastedValue
2493
2512
  = val:Value cast:TypeCast? { return { value: val, cast: cast }; }
@@ -2557,15 +2576,25 @@ var PsqlEngine = class extends SqlEngine {
2557
2576
  await this.triggerClient.end();
2558
2577
  }
2559
2578
  }
2579
+ /**
2580
+ * Setup the return types for the PostgreSQL connection.
2581
+ * For example return DATE as a string instead of a Date object and BIGINT as a number instead of a string.
2582
+ */
2560
2583
  setupPgReturnTypes() {
2561
- const TIMESTAMPTZ_OID = 1184;
2562
- types.setTypeParser(TIMESTAMPTZ_OID, (val) => {
2563
- return val === null ? null : new Date(val).toISOString();
2564
- });
2565
- const BIGINT_OID = 20;
2566
- types.setTypeParser(BIGINT_OID, (val) => {
2567
- return val === null ? null : Number(val);
2568
- });
2584
+ const PG_TYPE_OID = {
2585
+ BIGINT: 20,
2586
+ DATE: 1082,
2587
+ TIME: 1083,
2588
+ TIMESTAMP: 1114,
2589
+ TIMESTAMPTZ: 1184,
2590
+ TIMETZ: 1266
2591
+ };
2592
+ types.setTypeParser(PG_TYPE_OID.BIGINT, (val) => val === null ? null : Number(val));
2593
+ types.setTypeParser(PG_TYPE_OID.DATE, (val) => val);
2594
+ types.setTypeParser(PG_TYPE_OID.TIME, (val) => val);
2595
+ types.setTypeParser(PG_TYPE_OID.TIMETZ, (val) => val);
2596
+ types.setTypeParser(PG_TYPE_OID.TIMESTAMP, (val) => val === null ? null : new Date(val).toISOString());
2597
+ types.setTypeParser(PG_TYPE_OID.TIMESTAMPTZ, (val) => val === null ? null : new Date(val).toISOString());
2569
2598
  }
2570
2599
  async reconnectTriggerClient() {
2571
2600
  if (this.reconnectAttempts >= this.MAX_RECONNECT_ATTEMPTS) {