forge-sql-orm 2.1.22 → 2.1.24
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/README.md +6 -2
- package/dist/core/ForgeSQLAnalyseOperations.d.ts +4 -0
- package/dist/core/ForgeSQLAnalyseOperations.d.ts.map +1 -1
- package/dist/core/ForgeSQLAnalyseOperations.js +17 -21
- package/dist/core/ForgeSQLAnalyseOperations.js.map +1 -1
- package/dist/core/ForgeSQLCrudOperations.d.ts +16 -0
- package/dist/core/ForgeSQLCrudOperations.d.ts.map +1 -1
- package/dist/core/ForgeSQLCrudOperations.js +60 -28
- package/dist/core/ForgeSQLCrudOperations.js.map +1 -1
- package/dist/core/ForgeSQLQueryBuilder.d.ts +15 -28
- package/dist/core/ForgeSQLQueryBuilder.d.ts.map +1 -1
- package/dist/core/ForgeSQLQueryBuilder.js +20 -47
- package/dist/core/ForgeSQLQueryBuilder.js.map +1 -1
- package/dist/core/Rovo.d.ts +32 -0
- package/dist/core/Rovo.d.ts.map +1 -1
- package/dist/core/Rovo.js +116 -67
- package/dist/core/Rovo.js.map +1 -1
- package/dist/lib/drizzle/extensions/additionalActions.d.ts.map +1 -1
- package/dist/lib/drizzle/extensions/additionalActions.js +168 -118
- package/dist/lib/drizzle/extensions/additionalActions.js.map +1 -1
- package/dist/utils/cacheTableUtils.d.ts +0 -8
- package/dist/utils/cacheTableUtils.d.ts.map +1 -1
- package/dist/utils/cacheTableUtils.js +183 -126
- package/dist/utils/cacheTableUtils.js.map +1 -1
- package/dist/utils/forgeDriverProxy.d.ts.map +1 -1
- package/dist/utils/forgeDriverProxy.js +31 -20
- package/dist/utils/forgeDriverProxy.js.map +1 -1
- package/dist/utils/sqlHints.d.ts.map +1 -1
- package/dist/utils/sqlHints.js +19 -29
- package/dist/utils/sqlHints.js.map +1 -1
- package/dist/utils/sqlUtils.d.ts +0 -29
- package/dist/utils/sqlUtils.d.ts.map +1 -1
- package/dist/utils/sqlUtils.js +107 -78
- package/dist/utils/sqlUtils.js.map +1 -1
- package/package.json +13 -13
- package/src/core/ForgeSQLAnalyseOperations.ts +18 -21
- package/src/core/ForgeSQLCrudOperations.ts +83 -33
- package/src/core/ForgeSQLQueryBuilder.ts +59 -154
- package/src/core/Rovo.ts +158 -98
- package/src/lib/drizzle/extensions/additionalActions.ts +287 -382
- package/src/utils/cacheTableUtils.ts +202 -144
- package/src/utils/forgeDriverProxy.ts +39 -21
- package/src/utils/sqlHints.ts +21 -26
- package/src/utils/sqlUtils.ts +151 -101
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
// qlty-ignore: +qlty:file-complexity
|
|
1
2
|
import {
|
|
2
3
|
MySqlRawQueryResult,
|
|
3
4
|
MySqlRemoteDatabase,
|
|
@@ -6,7 +7,12 @@ import {
|
|
|
6
7
|
} from "drizzle-orm/mysql-proxy";
|
|
7
8
|
|
|
8
9
|
import { SelectedFields } from "drizzle-orm/mysql-core/query-builders/select.types";
|
|
9
|
-
import {
|
|
10
|
+
import {
|
|
11
|
+
applyFromDriverTransform,
|
|
12
|
+
ForgeSqlOrmOptions,
|
|
13
|
+
mapSelectFieldsWithAlias,
|
|
14
|
+
SelectFromReturnType,
|
|
15
|
+
} from "../../..";
|
|
10
16
|
import { MySqlSelectBase, MySqlSelectBuilder } from "drizzle-orm/mysql-core";
|
|
11
17
|
import { MySqlTable } from "drizzle-orm/mysql-core/table";
|
|
12
18
|
import {
|
|
@@ -308,25 +314,26 @@ async function handleSuccessfulExecution(
|
|
|
308
314
|
}
|
|
309
315
|
}
|
|
310
316
|
|
|
317
|
+
/**
|
|
318
|
+
* Configuration for function call handling.
|
|
319
|
+
*/
|
|
320
|
+
interface FunctionCallConfig {
|
|
321
|
+
value: Function;
|
|
322
|
+
target: any;
|
|
323
|
+
args: any[];
|
|
324
|
+
table: MySqlTable;
|
|
325
|
+
options: ForgeSqlOrmOptions;
|
|
326
|
+
isCached: boolean;
|
|
327
|
+
}
|
|
328
|
+
|
|
311
329
|
/**
|
|
312
330
|
* Handles function calls on the wrapped builder.
|
|
313
331
|
*
|
|
314
|
-
* @param
|
|
315
|
-
* @param target - The target object
|
|
316
|
-
* @param args - Function arguments
|
|
317
|
-
* @param table - The table being modified
|
|
318
|
-
* @param options - ForgeSQL ORM options
|
|
319
|
-
* @param isCached - Whether to clear cache immediately
|
|
332
|
+
* @param config - Configuration for function call handling
|
|
320
333
|
* @returns Function result or wrapped builder
|
|
321
334
|
*/
|
|
322
|
-
function handleFunctionCall(
|
|
323
|
-
value
|
|
324
|
-
target: any,
|
|
325
|
-
args: any[],
|
|
326
|
-
table: MySqlTable,
|
|
327
|
-
options: ForgeSqlOrmOptions,
|
|
328
|
-
isCached: boolean,
|
|
329
|
-
): any {
|
|
335
|
+
function handleFunctionCall(config: FunctionCallConfig): any {
|
|
336
|
+
const { value, target, args, table, options, isCached } = config;
|
|
330
337
|
const result = value.apply(target, args);
|
|
331
338
|
if (typeof result === "object" && result !== null && "execute" in result) {
|
|
332
339
|
return wrapCacheEvictBuilder(result as QueryBuilder, table, options, isCached);
|
|
@@ -367,7 +374,14 @@ const wrapCacheEvictBuilder = <TTable extends MySqlTable>(
|
|
|
367
374
|
|
|
368
375
|
if (typeof value === "function") {
|
|
369
376
|
return (...args: any[]) =>
|
|
370
|
-
handleFunctionCall(
|
|
377
|
+
handleFunctionCall({
|
|
378
|
+
value,
|
|
379
|
+
target,
|
|
380
|
+
args,
|
|
381
|
+
table,
|
|
382
|
+
options,
|
|
383
|
+
isCached,
|
|
384
|
+
});
|
|
371
385
|
}
|
|
372
386
|
|
|
373
387
|
return value;
|
|
@@ -375,6 +389,19 @@ const wrapCacheEvictBuilder = <TTable extends MySqlTable>(
|
|
|
375
389
|
});
|
|
376
390
|
};
|
|
377
391
|
|
|
392
|
+
/**
|
|
393
|
+
* Creates a query builder with cache eviction wrapper.
|
|
394
|
+
* Generic helper to reduce duplication between insert/update/delete builders.
|
|
395
|
+
*/
|
|
396
|
+
function createCacheEvictBuilder<TTable extends MySqlTable, TBuilder>(
|
|
397
|
+
builder: QueryBuilder,
|
|
398
|
+
table: TTable,
|
|
399
|
+
options: ForgeSqlOrmOptions,
|
|
400
|
+
isCached: boolean,
|
|
401
|
+
): TBuilder {
|
|
402
|
+
return wrapCacheEvictBuilder(builder, table, options, isCached) as unknown as TBuilder;
|
|
403
|
+
}
|
|
404
|
+
|
|
378
405
|
/**
|
|
379
406
|
* Creates an insert query builder that automatically evicts cache after execution.
|
|
380
407
|
*
|
|
@@ -390,16 +417,10 @@ function insertAndEvictCacheBuilder<TTable extends MySqlTable>(
|
|
|
390
417
|
isCached: boolean,
|
|
391
418
|
): MySqlInsertBuilder<TTable, MySqlRemoteQueryResultHKT, MySqlRemotePreparedQueryHKT> {
|
|
392
419
|
const builder = db.insert(table);
|
|
393
|
-
return
|
|
394
|
-
builder as unknown as QueryBuilder,
|
|
395
|
-
table,
|
|
396
|
-
options,
|
|
397
|
-
isCached,
|
|
398
|
-
) as unknown as MySqlInsertBuilder<
|
|
420
|
+
return createCacheEvictBuilder<
|
|
399
421
|
TTable,
|
|
400
|
-
MySqlRemoteQueryResultHKT,
|
|
401
|
-
|
|
402
|
-
>;
|
|
422
|
+
MySqlInsertBuilder<TTable, MySqlRemoteQueryResultHKT, MySqlRemotePreparedQueryHKT>
|
|
423
|
+
>(builder as unknown as QueryBuilder, table, options, isCached);
|
|
403
424
|
}
|
|
404
425
|
|
|
405
426
|
/**
|
|
@@ -417,16 +438,10 @@ function updateAndEvictCacheBuilder<TTable extends MySqlTable>(
|
|
|
417
438
|
isCached: boolean,
|
|
418
439
|
): MySqlUpdateBuilder<TTable, MySqlRemoteQueryResultHKT, MySqlRemotePreparedQueryHKT> {
|
|
419
440
|
const builder = db.update(table);
|
|
420
|
-
return
|
|
421
|
-
builder as unknown as QueryBuilder,
|
|
422
|
-
table,
|
|
423
|
-
options,
|
|
424
|
-
isCached,
|
|
425
|
-
) as unknown as MySqlUpdateBuilder<
|
|
441
|
+
return createCacheEvictBuilder<
|
|
426
442
|
TTable,
|
|
427
|
-
MySqlRemoteQueryResultHKT,
|
|
428
|
-
|
|
429
|
-
>;
|
|
443
|
+
MySqlUpdateBuilder<TTable, MySqlRemoteQueryResultHKT, MySqlRemotePreparedQueryHKT>
|
|
444
|
+
>(builder as unknown as QueryBuilder, table, options, isCached);
|
|
430
445
|
}
|
|
431
446
|
|
|
432
447
|
/**
|
|
@@ -444,35 +459,33 @@ function deleteAndEvictCacheBuilder<TTable extends MySqlTable>(
|
|
|
444
459
|
isCached: boolean,
|
|
445
460
|
): MySqlDeleteBase<TTable, MySqlRemoteQueryResultHKT, MySqlRemotePreparedQueryHKT> {
|
|
446
461
|
const builder = db.delete(table);
|
|
447
|
-
return
|
|
448
|
-
|
|
449
|
-
|
|
450
|
-
|
|
451
|
-
|
|
452
|
-
|
|
462
|
+
return createCacheEvictBuilder<
|
|
463
|
+
TTable,
|
|
464
|
+
MySqlDeleteBase<TTable, MySqlRemoteQueryResultHKT, MySqlRemotePreparedQueryHKT>
|
|
465
|
+
>(builder as unknown as QueryBuilder, table, options, isCached);
|
|
466
|
+
}
|
|
467
|
+
|
|
468
|
+
/**
|
|
469
|
+
* Configuration for cached query handling.
|
|
470
|
+
*/
|
|
471
|
+
interface CachedQueryConfig {
|
|
472
|
+
target: any;
|
|
473
|
+
options: ForgeSqlOrmOptions;
|
|
474
|
+
cacheTtl: number;
|
|
475
|
+
selections: any;
|
|
476
|
+
aliasMap: any;
|
|
477
|
+
onfulfilled?: any;
|
|
478
|
+
onrejected?: any;
|
|
453
479
|
}
|
|
454
480
|
|
|
455
481
|
/**
|
|
456
482
|
* Handles cached query execution with proper error handling.
|
|
457
483
|
*
|
|
458
|
-
* @param
|
|
459
|
-
* @param options - ForgeSQL ORM options
|
|
460
|
-
* @param cacheTtl - Cache TTL
|
|
461
|
-
* @param selections - Field selections
|
|
462
|
-
* @param aliasMap - Field alias mapping
|
|
463
|
-
* @param onfulfilled - Success callback
|
|
464
|
-
* @param onrejected - Error callback
|
|
484
|
+
* @param config - Configuration for cached query handling
|
|
465
485
|
* @returns Promise with cached result
|
|
466
486
|
*/
|
|
467
|
-
async function handleCachedQuery(
|
|
468
|
-
target
|
|
469
|
-
options: ForgeSqlOrmOptions,
|
|
470
|
-
cacheTtl: number,
|
|
471
|
-
selections: any,
|
|
472
|
-
aliasMap: any,
|
|
473
|
-
onfulfilled?: any,
|
|
474
|
-
onrejected?: any,
|
|
475
|
-
): Promise<any> {
|
|
487
|
+
async function handleCachedQuery(config: CachedQueryConfig): Promise<any> {
|
|
488
|
+
const { target, options, cacheTtl, selections, aliasMap, onfulfilled, onrejected } = config;
|
|
476
489
|
try {
|
|
477
490
|
const localCached = await getQueryLocalCacheQuery(target, options);
|
|
478
491
|
if (localCached) {
|
|
@@ -500,25 +513,26 @@ async function handleCachedQuery(
|
|
|
500
513
|
}
|
|
501
514
|
}
|
|
502
515
|
|
|
516
|
+
/**
|
|
517
|
+
* Configuration for non-cached query handling.
|
|
518
|
+
*/
|
|
519
|
+
interface NonCachedQueryConfig {
|
|
520
|
+
target: any;
|
|
521
|
+
options: any;
|
|
522
|
+
selections: any;
|
|
523
|
+
aliasMap: any;
|
|
524
|
+
onfulfilled?: any;
|
|
525
|
+
onrejected?: any;
|
|
526
|
+
}
|
|
527
|
+
|
|
503
528
|
/**
|
|
504
529
|
* Handles non-cached query execution.
|
|
505
530
|
*
|
|
506
|
-
* @param
|
|
507
|
-
* @param options - ForgeSQL ORM options
|
|
508
|
-
* @param selections - Field selections
|
|
509
|
-
* @param aliasMap - Field alias mapping
|
|
510
|
-
* @param onfulfilled - Success callback
|
|
511
|
-
* @param onrejected - Error callback
|
|
531
|
+
* @param config - Configuration for non-cached query handling
|
|
512
532
|
* @returns Promise with transformed result
|
|
513
533
|
*/
|
|
514
|
-
async function handleNonCachedQuery(
|
|
515
|
-
target
|
|
516
|
-
options: any,
|
|
517
|
-
selections: any,
|
|
518
|
-
aliasMap: any,
|
|
519
|
-
onfulfilled?: any,
|
|
520
|
-
onrejected?: any,
|
|
521
|
-
): Promise<any> {
|
|
534
|
+
async function handleNonCachedQuery(config: NonCachedQueryConfig): Promise<any> {
|
|
535
|
+
const { target, options, selections, aliasMap, onfulfilled, onrejected } = config;
|
|
522
536
|
try {
|
|
523
537
|
const localCached = await getQueryLocalCacheQuery(target, options);
|
|
524
538
|
if (localCached) {
|
|
@@ -577,7 +591,15 @@ function createCachedThenHandler(
|
|
|
577
591
|
): (onfulfilled?: any, onrejected?: any) => Promise<any> {
|
|
578
592
|
return (onfulfilled?: any, onrejected?: any) => {
|
|
579
593
|
const ttl = cacheTtl ?? options.cacheTTL ?? 120;
|
|
580
|
-
return handleCachedQuery(
|
|
594
|
+
return handleCachedQuery({
|
|
595
|
+
target,
|
|
596
|
+
options,
|
|
597
|
+
cacheTtl: ttl,
|
|
598
|
+
selections,
|
|
599
|
+
aliasMap,
|
|
600
|
+
onfulfilled,
|
|
601
|
+
onrejected,
|
|
602
|
+
});
|
|
581
603
|
};
|
|
582
604
|
}
|
|
583
605
|
|
|
@@ -591,7 +613,14 @@ function createNonCachedThenHandler(
|
|
|
591
613
|
aliasMap: any,
|
|
592
614
|
): (onfulfilled?: any, onrejected?: any) => Promise<any> {
|
|
593
615
|
return (onfulfilled?: any, onrejected?: any) => {
|
|
594
|
-
return handleNonCachedQuery(
|
|
616
|
+
return handleNonCachedQuery({
|
|
617
|
+
target,
|
|
618
|
+
options,
|
|
619
|
+
selections,
|
|
620
|
+
aliasMap,
|
|
621
|
+
onfulfilled,
|
|
622
|
+
onrejected,
|
|
623
|
+
});
|
|
595
624
|
};
|
|
596
625
|
}
|
|
597
626
|
|
|
@@ -637,47 +666,83 @@ function createFunctionCallHandler(
|
|
|
637
666
|
* @param cacheTtl - Optional cache TTL override
|
|
638
667
|
* @returns Select query builder with aliasing and optional caching
|
|
639
668
|
*/
|
|
669
|
+
/**
|
|
670
|
+
* Configuration for aliased select proxy handler.
|
|
671
|
+
*/
|
|
672
|
+
interface AliasedSelectProxyConfig {
|
|
673
|
+
selections: any;
|
|
674
|
+
aliasMap: any;
|
|
675
|
+
useCache: boolean;
|
|
676
|
+
options: ForgeSqlOrmOptions;
|
|
677
|
+
cacheTtl: number | undefined;
|
|
678
|
+
wrapBuilder: (rawBuilder: any) => any;
|
|
679
|
+
}
|
|
680
|
+
|
|
681
|
+
/**
|
|
682
|
+
* Creates a Proxy handler for aliased select builders.
|
|
683
|
+
*/
|
|
684
|
+
function createAliasedSelectProxyHandler(config: AliasedSelectProxyConfig) {
|
|
685
|
+
const { selections, aliasMap, useCache, options, cacheTtl, wrapBuilder } = config;
|
|
686
|
+
return {
|
|
687
|
+
get(target: any, prop: string | symbol, receiver: any) {
|
|
688
|
+
// Handle 'then' separately to avoid thenable object issues
|
|
689
|
+
if (prop === "then") {
|
|
690
|
+
return useCache
|
|
691
|
+
? createCachedThenHandler(target, options, cacheTtl, selections, aliasMap)
|
|
692
|
+
: createNonCachedThenHandler(target, options, selections, aliasMap);
|
|
693
|
+
}
|
|
694
|
+
|
|
695
|
+
// Handle other special properties with a map
|
|
696
|
+
const specialHandlers: Record<string | symbol, () => any> = {
|
|
697
|
+
execute: () => createExecuteHandler(target, selections, aliasMap),
|
|
698
|
+
catch: () => createCatchHandler(receiver),
|
|
699
|
+
finally: () => createFinallyHandler(receiver),
|
|
700
|
+
};
|
|
701
|
+
|
|
702
|
+
if (prop in specialHandlers) {
|
|
703
|
+
return specialHandlers[prop]();
|
|
704
|
+
}
|
|
705
|
+
|
|
706
|
+
const value = Reflect.get(target, prop, receiver);
|
|
707
|
+
|
|
708
|
+
if (typeof value === "function") {
|
|
709
|
+
return createFunctionCallHandler(value, target, wrapBuilder);
|
|
710
|
+
}
|
|
711
|
+
|
|
712
|
+
return value;
|
|
713
|
+
},
|
|
714
|
+
};
|
|
715
|
+
}
|
|
716
|
+
|
|
717
|
+
/**
|
|
718
|
+
* Configuration for creating aliased select builder.
|
|
719
|
+
*/
|
|
720
|
+
interface AliasedSelectBuilderConfig<TSelection extends SelectedFields> {
|
|
721
|
+
db: MySqlRemoteDatabase<any>;
|
|
722
|
+
fields: TSelection;
|
|
723
|
+
selectFn: (selections: any) => MySqlSelectBuilder<TSelection, MySqlRemotePreparedQueryHKT>;
|
|
724
|
+
useCache: boolean;
|
|
725
|
+
options: ForgeSqlOrmOptions;
|
|
726
|
+
cacheTtl?: number;
|
|
727
|
+
}
|
|
728
|
+
|
|
640
729
|
function createAliasedSelectBuilder<TSelection extends SelectedFields>(
|
|
641
|
-
|
|
642
|
-
fields: TSelection,
|
|
643
|
-
selectFn: (selections: any) => MySqlSelectBuilder<TSelection, MySqlRemotePreparedQueryHKT>,
|
|
644
|
-
useCache: boolean,
|
|
645
|
-
options: ForgeSqlOrmOptions,
|
|
646
|
-
cacheTtl?: number,
|
|
730
|
+
config: AliasedSelectBuilderConfig<TSelection>,
|
|
647
731
|
): MySqlSelectBuilder<TSelection, MySqlRemotePreparedQueryHKT> {
|
|
732
|
+
const { fields, selectFn, useCache, options, cacheTtl } = config;
|
|
648
733
|
const { selections, aliasMap } = mapSelectFieldsWithAlias(fields);
|
|
649
734
|
const builder = selectFn(selections);
|
|
650
735
|
|
|
651
736
|
const wrapBuilder = (rawBuilder: any): any => {
|
|
652
|
-
|
|
653
|
-
|
|
654
|
-
|
|
655
|
-
|
|
656
|
-
|
|
657
|
-
|
|
658
|
-
|
|
659
|
-
return useCache
|
|
660
|
-
? createCachedThenHandler(target, options, cacheTtl, selections, aliasMap)
|
|
661
|
-
: createNonCachedThenHandler(target, options, selections, aliasMap);
|
|
662
|
-
}
|
|
663
|
-
|
|
664
|
-
if (prop === "catch") {
|
|
665
|
-
return createCatchHandler(receiver);
|
|
666
|
-
}
|
|
667
|
-
|
|
668
|
-
if (prop === "finally") {
|
|
669
|
-
return createFinallyHandler(receiver);
|
|
670
|
-
}
|
|
671
|
-
|
|
672
|
-
const value = Reflect.get(target, prop, receiver);
|
|
673
|
-
|
|
674
|
-
if (typeof value === "function") {
|
|
675
|
-
return createFunctionCallHandler(value, target, wrapBuilder);
|
|
676
|
-
}
|
|
677
|
-
|
|
678
|
-
return value;
|
|
679
|
-
},
|
|
737
|
+
const handler = createAliasedSelectProxyHandler({
|
|
738
|
+
selections,
|
|
739
|
+
aliasMap,
|
|
740
|
+
useCache,
|
|
741
|
+
options,
|
|
742
|
+
cacheTtl,
|
|
743
|
+
wrapBuilder,
|
|
680
744
|
});
|
|
745
|
+
return new Proxy(rawBuilder, handler);
|
|
681
746
|
};
|
|
682
747
|
|
|
683
748
|
return wrapBuilder(builder);
|
|
@@ -763,55 +828,25 @@ function createRawQueryExecutor(
|
|
|
763
828
|
}
|
|
764
829
|
|
|
765
830
|
// ============================================================================
|
|
766
|
-
//
|
|
831
|
+
// HELPER FUNCTIONS FOR PATCHING
|
|
767
832
|
// ============================================================================
|
|
768
833
|
|
|
769
834
|
/**
|
|
770
|
-
*
|
|
771
|
-
*
|
|
772
|
-
* This function extends the database instance with:
|
|
773
|
-
* - selectAliased: Select with field aliasing support
|
|
774
|
-
* - selectAliasedDistinct: Select distinct with field aliasing support
|
|
775
|
-
* - selectAliasedCacheable: Select with field aliasing and caching
|
|
776
|
-
* - selectAliasedDistinctCacheable: Select distinct with field aliasing and caching
|
|
777
|
-
* - insertAndEvictCache: Insert operations that automatically evict cache
|
|
778
|
-
* - updateAndEvictCache: Update operations that automatically evict cache
|
|
779
|
-
* - deleteAndEvictCache: Delete operations that automatically evict cache
|
|
780
|
-
*
|
|
781
|
-
* @param db - The Drizzle database instance to patch
|
|
782
|
-
* @param options - Optional ForgeSQL ORM configuration
|
|
783
|
-
* @returns The patched database instance with additional methods
|
|
835
|
+
* Sets up select methods with field aliasing.
|
|
784
836
|
*/
|
|
785
|
-
|
|
837
|
+
function setupSelectAliasedMethods(
|
|
786
838
|
db: MySqlRemoteDatabase<any>,
|
|
787
|
-
|
|
788
|
-
):
|
|
789
|
-
selectAliased: SelectAliasedType;
|
|
790
|
-
selectAliasedDistinct: SelectAliasedDistinctType;
|
|
791
|
-
selectAliasedCacheable: SelectAliasedCacheableType;
|
|
792
|
-
selectAliasedDistinctCacheable: SelectAliasedDistinctCacheableType;
|
|
793
|
-
insertWithCacheContext: InsertAndEvictCacheType;
|
|
794
|
-
insertAndEvictCache: InsertAndEvictCacheType;
|
|
795
|
-
updateAndEvictCache: UpdateAndEvictCacheType;
|
|
796
|
-
updateWithCacheContext: UpdateAndEvictCacheType;
|
|
797
|
-
deleteAndEvictCache: DeleteAndEvictCacheType;
|
|
798
|
-
deleteWithCacheContext: DeleteAndEvictCacheType;
|
|
799
|
-
} {
|
|
800
|
-
const newOptions = { ...DEFAULT_OPTIONS, ...options };
|
|
801
|
-
|
|
802
|
-
// ============================================================================
|
|
803
|
-
// SELECT METHODS WITH FIELD ALIASING
|
|
804
|
-
// ============================================================================
|
|
805
|
-
|
|
839
|
+
newOptions: ForgeSqlOrmOptions,
|
|
840
|
+
): void {
|
|
806
841
|
// Select aliased without cache
|
|
807
842
|
db.selectAliased = function <TSelection extends SelectedFields>(fields: TSelection) {
|
|
808
|
-
return createAliasedSelectBuilder(
|
|
843
|
+
return createAliasedSelectBuilder({
|
|
809
844
|
db,
|
|
810
845
|
fields,
|
|
811
|
-
(selections) => db.select(selections),
|
|
812
|
-
false,
|
|
813
|
-
newOptions,
|
|
814
|
-
);
|
|
846
|
+
selectFn: (selections) => db.select(selections),
|
|
847
|
+
useCache: false,
|
|
848
|
+
options: newOptions,
|
|
849
|
+
});
|
|
815
850
|
};
|
|
816
851
|
|
|
817
852
|
// Select aliased with cache
|
|
@@ -819,25 +854,25 @@ export function patchDbWithSelectAliased(
|
|
|
819
854
|
fields: TSelection,
|
|
820
855
|
cacheTtl?: number,
|
|
821
856
|
) {
|
|
822
|
-
return createAliasedSelectBuilder(
|
|
857
|
+
return createAliasedSelectBuilder({
|
|
823
858
|
db,
|
|
824
859
|
fields,
|
|
825
|
-
(selections) => db.select(selections),
|
|
826
|
-
true,
|
|
827
|
-
newOptions,
|
|
860
|
+
selectFn: (selections) => db.select(selections),
|
|
861
|
+
useCache: true,
|
|
862
|
+
options: newOptions,
|
|
828
863
|
cacheTtl,
|
|
829
|
-
);
|
|
864
|
+
});
|
|
830
865
|
};
|
|
831
866
|
|
|
832
867
|
// Select aliased distinct without cache
|
|
833
868
|
db.selectAliasedDistinct = function <TSelection extends SelectedFields>(fields: TSelection) {
|
|
834
|
-
return createAliasedSelectBuilder(
|
|
869
|
+
return createAliasedSelectBuilder({
|
|
835
870
|
db,
|
|
836
871
|
fields,
|
|
837
|
-
(selections) => db.selectDistinct(selections),
|
|
838
|
-
false,
|
|
839
|
-
newOptions,
|
|
840
|
-
);
|
|
872
|
+
selectFn: (selections) => db.selectDistinct(selections),
|
|
873
|
+
useCache: false,
|
|
874
|
+
options: newOptions,
|
|
875
|
+
});
|
|
841
876
|
};
|
|
842
877
|
|
|
843
878
|
// Select aliased distinct with cache
|
|
@@ -845,20 +880,21 @@ export function patchDbWithSelectAliased(
|
|
|
845
880
|
fields: TSelection,
|
|
846
881
|
cacheTtl?: number,
|
|
847
882
|
) {
|
|
848
|
-
return createAliasedSelectBuilder(
|
|
883
|
+
return createAliasedSelectBuilder({
|
|
849
884
|
db,
|
|
850
885
|
fields,
|
|
851
|
-
(selections) => db.selectDistinct(selections),
|
|
852
|
-
true,
|
|
853
|
-
newOptions,
|
|
886
|
+
selectFn: (selections) => db.selectDistinct(selections),
|
|
887
|
+
useCache: true,
|
|
888
|
+
options: newOptions,
|
|
854
889
|
cacheTtl,
|
|
855
|
-
);
|
|
890
|
+
});
|
|
856
891
|
};
|
|
892
|
+
}
|
|
857
893
|
|
|
858
|
-
|
|
859
|
-
|
|
860
|
-
|
|
861
|
-
|
|
894
|
+
/**
|
|
895
|
+
* Sets up table-based select methods.
|
|
896
|
+
*/
|
|
897
|
+
function setupTableBasedSelectMethods(db: MySqlRemoteDatabase<any>): void {
|
|
862
898
|
/**
|
|
863
899
|
* Creates a select query builder for all columns from a table with field aliasing support.
|
|
864
900
|
* This is a convenience method that automatically selects all columns from the specified table.
|
|
@@ -870,52 +906,10 @@ export function patchDbWithSelectAliased(
|
|
|
870
906
|
* const users = await db.selectFrom(userTable).where(eq(userTable.id, 1));
|
|
871
907
|
* ```
|
|
872
908
|
*/
|
|
873
|
-
db.selectFrom = function <T extends MySqlTable>(
|
|
874
|
-
|
|
875
|
-
|
|
876
|
-
|
|
877
|
-
GetSelectTableSelection<T>,
|
|
878
|
-
"single",
|
|
879
|
-
MySqlRemotePreparedQueryHKT,
|
|
880
|
-
GetSelectTableName<T> extends string ? Record<string & GetSelectTableName<T>, "not-null"> : {},
|
|
881
|
-
false,
|
|
882
|
-
never,
|
|
883
|
-
{
|
|
884
|
-
[K in keyof {
|
|
885
|
-
[Key in keyof GetSelectTableSelection<T>]: SelectResultField<
|
|
886
|
-
GetSelectTableSelection<T>[Key]
|
|
887
|
-
>;
|
|
888
|
-
}]: {
|
|
889
|
-
[Key in keyof GetSelectTableSelection<T>]: SelectResultField<
|
|
890
|
-
GetSelectTableSelection<T>[Key]
|
|
891
|
-
>;
|
|
892
|
-
}[K];
|
|
893
|
-
}[],
|
|
894
|
-
any
|
|
895
|
-
> {
|
|
896
|
-
return db.selectAliased(getTableColumns(table)).from(table) as unknown as MySqlSelectBase<
|
|
897
|
-
GetSelectTableName<T>,
|
|
898
|
-
GetSelectTableSelection<T>,
|
|
899
|
-
"single",
|
|
900
|
-
MySqlRemotePreparedQueryHKT,
|
|
901
|
-
GetSelectTableName<T> extends string
|
|
902
|
-
? Record<string & GetSelectTableName<T>, "not-null">
|
|
903
|
-
: {},
|
|
904
|
-
false,
|
|
905
|
-
never,
|
|
906
|
-
{
|
|
907
|
-
[K in keyof {
|
|
908
|
-
[Key in keyof GetSelectTableSelection<T>]: SelectResultField<
|
|
909
|
-
GetSelectTableSelection<T>[Key]
|
|
910
|
-
>;
|
|
911
|
-
}]: {
|
|
912
|
-
[Key in keyof GetSelectTableSelection<T>]: SelectResultField<
|
|
913
|
-
GetSelectTableSelection<T>[Key]
|
|
914
|
-
>;
|
|
915
|
-
}[K];
|
|
916
|
-
}[],
|
|
917
|
-
any
|
|
918
|
-
>;
|
|
909
|
+
db.selectFrom = function <T extends MySqlTable>(table: T): SelectFromReturnType<T> {
|
|
910
|
+
return db
|
|
911
|
+
.selectAliased(getTableColumns(table))
|
|
912
|
+
.from(table) as unknown as SelectFromReturnType<T>;
|
|
919
913
|
};
|
|
920
914
|
|
|
921
915
|
/**
|
|
@@ -933,52 +927,10 @@ export function patchDbWithSelectAliased(
|
|
|
933
927
|
db.selectFromCacheable = function <T extends MySqlTable>(
|
|
934
928
|
table: T,
|
|
935
929
|
cacheTtl?: number,
|
|
936
|
-
):
|
|
937
|
-
GetSelectTableName<T>,
|
|
938
|
-
GetSelectTableSelection<T>,
|
|
939
|
-
"single",
|
|
940
|
-
MySqlRemotePreparedQueryHKT,
|
|
941
|
-
GetSelectTableName<T> extends string ? Record<string & GetSelectTableName<T>, "not-null"> : {},
|
|
942
|
-
false,
|
|
943
|
-
never,
|
|
944
|
-
{
|
|
945
|
-
[K in keyof {
|
|
946
|
-
[Key in keyof GetSelectTableSelection<T>]: SelectResultField<
|
|
947
|
-
GetSelectTableSelection<T>[Key]
|
|
948
|
-
>;
|
|
949
|
-
}]: {
|
|
950
|
-
[Key in keyof GetSelectTableSelection<T>]: SelectResultField<
|
|
951
|
-
GetSelectTableSelection<T>[Key]
|
|
952
|
-
>;
|
|
953
|
-
}[K];
|
|
954
|
-
}[],
|
|
955
|
-
any
|
|
956
|
-
> {
|
|
930
|
+
): SelectFromReturnType<T> {
|
|
957
931
|
return db
|
|
958
932
|
.selectAliasedCacheable(getTableColumns(table), cacheTtl)
|
|
959
|
-
.from(table) as unknown as
|
|
960
|
-
GetSelectTableName<T>,
|
|
961
|
-
GetSelectTableSelection<T>,
|
|
962
|
-
"single",
|
|
963
|
-
MySqlRemotePreparedQueryHKT,
|
|
964
|
-
GetSelectTableName<T> extends string
|
|
965
|
-
? Record<string & GetSelectTableName<T>, "not-null">
|
|
966
|
-
: {},
|
|
967
|
-
false,
|
|
968
|
-
never,
|
|
969
|
-
{
|
|
970
|
-
[K in keyof {
|
|
971
|
-
[Key in keyof GetSelectTableSelection<T>]: SelectResultField<
|
|
972
|
-
GetSelectTableSelection<T>[Key]
|
|
973
|
-
>;
|
|
974
|
-
}]: {
|
|
975
|
-
[Key in keyof GetSelectTableSelection<T>]: SelectResultField<
|
|
976
|
-
GetSelectTableSelection<T>[Key]
|
|
977
|
-
>;
|
|
978
|
-
}[K];
|
|
979
|
-
}[],
|
|
980
|
-
any
|
|
981
|
-
>;
|
|
933
|
+
.from(table) as unknown as SelectFromReturnType<T>;
|
|
982
934
|
};
|
|
983
935
|
|
|
984
936
|
/**
|
|
@@ -992,54 +944,10 @@ export function patchDbWithSelectAliased(
|
|
|
992
944
|
* const uniqueUsers = await db.selectDistinctFrom(userTable).where(eq(userTable.status, 'active'));
|
|
993
945
|
* ```
|
|
994
946
|
*/
|
|
995
|
-
db.selectDistinctFrom = function <T extends MySqlTable>(
|
|
996
|
-
table: T,
|
|
997
|
-
): MySqlSelectBase<
|
|
998
|
-
GetSelectTableName<T>,
|
|
999
|
-
GetSelectTableSelection<T>,
|
|
1000
|
-
"single",
|
|
1001
|
-
MySqlRemotePreparedQueryHKT,
|
|
1002
|
-
GetSelectTableName<T> extends string ? Record<string & GetSelectTableName<T>, "not-null"> : {},
|
|
1003
|
-
false,
|
|
1004
|
-
never,
|
|
1005
|
-
{
|
|
1006
|
-
[K in keyof {
|
|
1007
|
-
[Key in keyof GetSelectTableSelection<T>]: SelectResultField<
|
|
1008
|
-
GetSelectTableSelection<T>[Key]
|
|
1009
|
-
>;
|
|
1010
|
-
}]: {
|
|
1011
|
-
[Key in keyof GetSelectTableSelection<T>]: SelectResultField<
|
|
1012
|
-
GetSelectTableSelection<T>[Key]
|
|
1013
|
-
>;
|
|
1014
|
-
}[K];
|
|
1015
|
-
}[],
|
|
1016
|
-
any
|
|
1017
|
-
> {
|
|
947
|
+
db.selectDistinctFrom = function <T extends MySqlTable>(table: T): SelectFromReturnType<T> {
|
|
1018
948
|
return db
|
|
1019
949
|
.selectAliasedDistinct(getTableColumns(table))
|
|
1020
|
-
.from(table) as unknown as
|
|
1021
|
-
GetSelectTableName<T>,
|
|
1022
|
-
GetSelectTableSelection<T>,
|
|
1023
|
-
"single",
|
|
1024
|
-
MySqlRemotePreparedQueryHKT,
|
|
1025
|
-
GetSelectTableName<T> extends string
|
|
1026
|
-
? Record<string & GetSelectTableName<T>, "not-null">
|
|
1027
|
-
: {},
|
|
1028
|
-
false,
|
|
1029
|
-
never,
|
|
1030
|
-
{
|
|
1031
|
-
[K in keyof {
|
|
1032
|
-
[Key in keyof GetSelectTableSelection<T>]: SelectResultField<
|
|
1033
|
-
GetSelectTableSelection<T>[Key]
|
|
1034
|
-
>;
|
|
1035
|
-
}]: {
|
|
1036
|
-
[Key in keyof GetSelectTableSelection<T>]: SelectResultField<
|
|
1037
|
-
GetSelectTableSelection<T>[Key]
|
|
1038
|
-
>;
|
|
1039
|
-
}[K];
|
|
1040
|
-
}[],
|
|
1041
|
-
any
|
|
1042
|
-
>;
|
|
950
|
+
.from(table) as unknown as SelectFromReturnType<T>;
|
|
1043
951
|
};
|
|
1044
952
|
|
|
1045
953
|
/**
|
|
@@ -1057,92 +965,46 @@ export function patchDbWithSelectAliased(
|
|
|
1057
965
|
db.selectDistinctFromCacheable = function <T extends MySqlTable>(
|
|
1058
966
|
table: T,
|
|
1059
967
|
cacheTtl?: number,
|
|
1060
|
-
):
|
|
1061
|
-
GetSelectTableName<T>,
|
|
1062
|
-
GetSelectTableSelection<T>,
|
|
1063
|
-
"single",
|
|
1064
|
-
MySqlRemotePreparedQueryHKT,
|
|
1065
|
-
GetSelectTableName<T> extends string ? Record<string & GetSelectTableName<T>, "not-null"> : {},
|
|
1066
|
-
false,
|
|
1067
|
-
never,
|
|
1068
|
-
{
|
|
1069
|
-
[K in keyof {
|
|
1070
|
-
[Key in keyof GetSelectTableSelection<T>]: SelectResultField<
|
|
1071
|
-
GetSelectTableSelection<T>[Key]
|
|
1072
|
-
>;
|
|
1073
|
-
}]: {
|
|
1074
|
-
[Key in keyof GetSelectTableSelection<T>]: SelectResultField<
|
|
1075
|
-
GetSelectTableSelection<T>[Key]
|
|
1076
|
-
>;
|
|
1077
|
-
}[K];
|
|
1078
|
-
}[],
|
|
1079
|
-
any
|
|
1080
|
-
> {
|
|
968
|
+
): SelectFromReturnType<T> {
|
|
1081
969
|
return db
|
|
1082
970
|
.selectAliasedDistinctCacheable(getTableColumns(table), cacheTtl)
|
|
1083
|
-
.from(table) as unknown as
|
|
1084
|
-
GetSelectTableName<T>,
|
|
1085
|
-
GetSelectTableSelection<T>,
|
|
1086
|
-
"single",
|
|
1087
|
-
MySqlRemotePreparedQueryHKT,
|
|
1088
|
-
GetSelectTableName<T> extends string
|
|
1089
|
-
? Record<string & GetSelectTableName<T>, "not-null">
|
|
1090
|
-
: {},
|
|
1091
|
-
false,
|
|
1092
|
-
never,
|
|
1093
|
-
{
|
|
1094
|
-
[K in keyof {
|
|
1095
|
-
[Key in keyof GetSelectTableSelection<T>]: SelectResultField<
|
|
1096
|
-
GetSelectTableSelection<T>[Key]
|
|
1097
|
-
>;
|
|
1098
|
-
}]: {
|
|
1099
|
-
[Key in keyof GetSelectTableSelection<T>]: SelectResultField<
|
|
1100
|
-
GetSelectTableSelection<T>[Key]
|
|
1101
|
-
>;
|
|
1102
|
-
}[K];
|
|
1103
|
-
}[],
|
|
1104
|
-
any
|
|
1105
|
-
>;
|
|
1106
|
-
};
|
|
1107
|
-
|
|
1108
|
-
// ============================================================================
|
|
1109
|
-
// CACHE-AWARE MODIFY OPERATIONS
|
|
1110
|
-
// ============================================================================
|
|
1111
|
-
|
|
1112
|
-
// Insert with cache context support (participates in cache clearing when used within cache context)
|
|
1113
|
-
db.insertWithCacheContext = function <TTable extends MySqlTable>(table: TTable) {
|
|
1114
|
-
return insertAndEvictCacheBuilder(db, table, newOptions, false);
|
|
1115
|
-
};
|
|
1116
|
-
|
|
1117
|
-
// Insert with cache eviction
|
|
1118
|
-
db.insertAndEvictCache = function <TTable extends MySqlTable>(table: TTable) {
|
|
1119
|
-
return insertAndEvictCacheBuilder(db, table, newOptions, true);
|
|
1120
|
-
};
|
|
1121
|
-
|
|
1122
|
-
// Update with cache context support (participates in cache clearing when used within cache context)
|
|
1123
|
-
db.updateWithCacheContext = function <TTable extends MySqlTable>(table: TTable) {
|
|
1124
|
-
return updateAndEvictCacheBuilder(db, table, newOptions, false);
|
|
1125
|
-
};
|
|
1126
|
-
|
|
1127
|
-
// Update with cache eviction
|
|
1128
|
-
db.updateAndEvictCache = function <TTable extends MySqlTable>(table: TTable) {
|
|
1129
|
-
return updateAndEvictCacheBuilder(db, table, newOptions, true);
|
|
1130
|
-
};
|
|
1131
|
-
|
|
1132
|
-
// Delete with cache context support (participates in cache clearing when used within cache context)
|
|
1133
|
-
db.deleteWithCacheContext = function <TTable extends MySqlTable>(table: TTable) {
|
|
1134
|
-
return deleteAndEvictCacheBuilder(db, table, newOptions, false);
|
|
1135
|
-
};
|
|
1136
|
-
|
|
1137
|
-
// Delete with cache eviction
|
|
1138
|
-
db.deleteAndEvictCache = function <TTable extends MySqlTable>(table: TTable) {
|
|
1139
|
-
return deleteAndEvictCacheBuilder(db, table, newOptions, true);
|
|
971
|
+
.from(table) as unknown as SelectFromReturnType<T>;
|
|
1140
972
|
};
|
|
973
|
+
}
|
|
1141
974
|
|
|
1142
|
-
|
|
1143
|
-
|
|
1144
|
-
|
|
975
|
+
/**
|
|
976
|
+
* Sets up cache-aware modify operations.
|
|
977
|
+
*/
|
|
978
|
+
function setupCacheAwareModifyMethods(
|
|
979
|
+
db: MySqlRemoteDatabase<any>,
|
|
980
|
+
newOptions: ForgeSqlOrmOptions,
|
|
981
|
+
): void {
|
|
982
|
+
// Insert operations
|
|
983
|
+
db.insertWithCacheContext = <TTable extends MySqlTable>(table: TTable) =>
|
|
984
|
+
insertAndEvictCacheBuilder(db, table, newOptions, false);
|
|
985
|
+
db.insertAndEvictCache = <TTable extends MySqlTable>(table: TTable) =>
|
|
986
|
+
insertAndEvictCacheBuilder(db, table, newOptions, true);
|
|
987
|
+
|
|
988
|
+
// Update operations
|
|
989
|
+
db.updateWithCacheContext = <TTable extends MySqlTable>(table: TTable) =>
|
|
990
|
+
updateAndEvictCacheBuilder(db, table, newOptions, false);
|
|
991
|
+
db.updateAndEvictCache = <TTable extends MySqlTable>(table: TTable) =>
|
|
992
|
+
updateAndEvictCacheBuilder(db, table, newOptions, true);
|
|
993
|
+
|
|
994
|
+
// Delete operations
|
|
995
|
+
db.deleteWithCacheContext = <TTable extends MySqlTable>(table: TTable) =>
|
|
996
|
+
deleteAndEvictCacheBuilder(db, table, newOptions, false);
|
|
997
|
+
db.deleteAndEvictCache = <TTable extends MySqlTable>(table: TTable) =>
|
|
998
|
+
deleteAndEvictCacheBuilder(db, table, newOptions, true);
|
|
999
|
+
}
|
|
1145
1000
|
|
|
1001
|
+
/**
|
|
1002
|
+
* Sets up raw SQL query executors.
|
|
1003
|
+
*/
|
|
1004
|
+
function setupRawQueryExecutors(
|
|
1005
|
+
db: MySqlRemoteDatabase<any>,
|
|
1006
|
+
newOptions: ForgeSqlOrmOptions,
|
|
1007
|
+
): void {
|
|
1146
1008
|
/**
|
|
1147
1009
|
* Executes a raw SQL query with local cache support.
|
|
1148
1010
|
* This method provides local caching for raw SQL queries within the current invocation context.
|
|
@@ -1180,6 +1042,49 @@ export function patchDbWithSelectAliased(
|
|
|
1180
1042
|
* ```
|
|
1181
1043
|
*/
|
|
1182
1044
|
db.executeQueryCacheable = createRawQueryExecutor(db, newOptions, true);
|
|
1045
|
+
}
|
|
1046
|
+
|
|
1047
|
+
// ============================================================================
|
|
1048
|
+
// MAIN PATCH FUNCTION
|
|
1049
|
+
// ============================================================================
|
|
1050
|
+
|
|
1051
|
+
/**
|
|
1052
|
+
* Patches a Drizzle database instance with additional methods for aliased selects and cache management.
|
|
1053
|
+
*
|
|
1054
|
+
* This function extends the database instance with:
|
|
1055
|
+
* - selectAliased: Select with field aliasing support
|
|
1056
|
+
* - selectAliasedDistinct: Select distinct with field aliasing support
|
|
1057
|
+
* - selectAliasedCacheable: Select with field aliasing and caching
|
|
1058
|
+
* - selectAliasedDistinctCacheable: Select distinct with field aliasing and caching
|
|
1059
|
+
* - insertAndEvictCache: Insert operations that automatically evict cache
|
|
1060
|
+
* - updateAndEvictCache: Update operations that automatically evict cache
|
|
1061
|
+
* - deleteAndEvictCache: Delete operations that automatically evict cache
|
|
1062
|
+
*
|
|
1063
|
+
* @param db - The Drizzle database instance to patch
|
|
1064
|
+
* @param options - Optional ForgeSQL ORM configuration
|
|
1065
|
+
* @returns The patched database instance with additional methods
|
|
1066
|
+
*/
|
|
1067
|
+
export function patchDbWithSelectAliased(
|
|
1068
|
+
db: MySqlRemoteDatabase<any>,
|
|
1069
|
+
options?: ForgeSqlOrmOptions,
|
|
1070
|
+
): MySqlRemoteDatabase<any> & {
|
|
1071
|
+
selectAliased: SelectAliasedType;
|
|
1072
|
+
selectAliasedDistinct: SelectAliasedDistinctType;
|
|
1073
|
+
selectAliasedCacheable: SelectAliasedCacheableType;
|
|
1074
|
+
selectAliasedDistinctCacheable: SelectAliasedDistinctCacheableType;
|
|
1075
|
+
insertWithCacheContext: InsertAndEvictCacheType;
|
|
1076
|
+
insertAndEvictCache: InsertAndEvictCacheType;
|
|
1077
|
+
updateAndEvictCache: UpdateAndEvictCacheType;
|
|
1078
|
+
updateWithCacheContext: UpdateAndEvictCacheType;
|
|
1079
|
+
deleteAndEvictCache: DeleteAndEvictCacheType;
|
|
1080
|
+
deleteWithCacheContext: DeleteAndEvictCacheType;
|
|
1081
|
+
} {
|
|
1082
|
+
const newOptions = { ...DEFAULT_OPTIONS, ...options };
|
|
1083
|
+
|
|
1084
|
+
setupSelectAliasedMethods(db, newOptions);
|
|
1085
|
+
setupTableBasedSelectMethods(db);
|
|
1086
|
+
setupCacheAwareModifyMethods(db, newOptions);
|
|
1087
|
+
setupRawQueryExecutors(db, newOptions);
|
|
1183
1088
|
|
|
1184
1089
|
return db;
|
|
1185
1090
|
}
|