metal-orm 1.0.15 → 1.0.16
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 +34 -27
- package/dist/decorators/index.cjs +339 -153
- package/dist/decorators/index.cjs.map +1 -1
- package/dist/decorators/index.d.cts +1 -5
- package/dist/decorators/index.d.ts +1 -5
- package/dist/decorators/index.js +339 -153
- package/dist/decorators/index.js.map +1 -1
- package/dist/index.cjs +838 -484
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +17 -14
- package/dist/index.d.ts +17 -14
- package/dist/index.js +833 -483
- package/dist/index.js.map +1 -1
- package/dist/{select-Bkv8g8u_.d.cts → select-BKZrMRCQ.d.cts} +363 -28
- package/dist/{select-Bkv8g8u_.d.ts → select-BKZrMRCQ.d.ts} +363 -28
- package/package.json +1 -1
- package/src/codegen/naming-strategy.ts +64 -0
- package/src/codegen/typescript.ts +48 -53
- package/src/core/ddl/schema-generator.ts +3 -2
- package/src/core/ddl/schema-introspect.ts +1 -1
- package/src/core/dialect/abstract.ts +28 -0
- package/src/decorators/column.ts +13 -4
- package/src/index.ts +8 -1
- package/src/orm/entity-context.ts +30 -0
- package/src/orm/entity-meta.ts +2 -2
- package/src/orm/entity-metadata.ts +1 -6
- package/src/orm/entity.ts +88 -88
- package/src/orm/execute.ts +42 -25
- package/src/orm/execution-context.ts +12 -0
- package/src/orm/hydration-context.ts +14 -0
- package/src/orm/identity-map.ts +4 -0
- package/src/orm/interceptor-pipeline.ts +29 -0
- package/src/orm/lazy-batch.ts +6 -6
- package/src/orm/orm-session.ts +234 -0
- package/src/orm/orm.ts +58 -0
- package/src/orm/relation-change-processor.ts +5 -1
- package/src/orm/relations/belongs-to.ts +45 -44
- package/src/orm/relations/has-many.ts +44 -43
- package/src/orm/relations/has-one.ts +140 -139
- package/src/orm/relations/many-to-many.ts +46 -45
- package/src/orm/unit-of-work.ts +6 -1
- package/src/query-builder/select.ts +509 -3
- package/src/orm/orm-context.ts +0 -159
package/dist/decorators/index.js
CHANGED
|
@@ -100,11 +100,20 @@ function Entity(options = {}) {
|
|
|
100
100
|
|
|
101
101
|
// src/decorators/column.ts
|
|
102
102
|
var normalizeColumnInput = (input) => {
|
|
103
|
+
const asOptions = input;
|
|
104
|
+
const asDefinition = input;
|
|
103
105
|
const column = {
|
|
104
|
-
type:
|
|
105
|
-
args:
|
|
106
|
-
notNull:
|
|
107
|
-
primary:
|
|
106
|
+
type: asOptions.type ?? asDefinition.type,
|
|
107
|
+
args: asOptions.args ?? asDefinition.args,
|
|
108
|
+
notNull: asOptions.notNull ?? asDefinition.notNull,
|
|
109
|
+
primary: asOptions.primary ?? asDefinition.primary,
|
|
110
|
+
unique: asDefinition.unique,
|
|
111
|
+
default: asDefinition.default,
|
|
112
|
+
autoIncrement: asDefinition.autoIncrement,
|
|
113
|
+
generated: asDefinition.generated,
|
|
114
|
+
check: asDefinition.check,
|
|
115
|
+
references: asDefinition.references,
|
|
116
|
+
comment: asDefinition.comment
|
|
108
117
|
};
|
|
109
118
|
if (!column.type) {
|
|
110
119
|
throw new Error("Column decorator requires a column type");
|
|
@@ -395,7 +404,7 @@ var StandardFunctionStrategy = class {
|
|
|
395
404
|
};
|
|
396
405
|
|
|
397
406
|
// src/core/dialect/abstract.ts
|
|
398
|
-
var Dialect = class {
|
|
407
|
+
var Dialect = class _Dialect {
|
|
399
408
|
/**
|
|
400
409
|
* Compiles a SELECT query AST to SQL
|
|
401
410
|
* @param ast - Query AST to compile
|
|
@@ -568,6 +577,35 @@ var Dialect = class {
|
|
|
568
577
|
this.registerDefaultOperandCompilers();
|
|
569
578
|
this.registerDefaultExpressionCompilers();
|
|
570
579
|
}
|
|
580
|
+
/**
|
|
581
|
+
* Creates a new Dialect instance (for testing purposes)
|
|
582
|
+
* @param functionStrategy - Optional function strategy
|
|
583
|
+
* @returns New Dialect instance
|
|
584
|
+
*/
|
|
585
|
+
static create(functionStrategy) {
|
|
586
|
+
class TestDialect extends _Dialect {
|
|
587
|
+
constructor() {
|
|
588
|
+
super(...arguments);
|
|
589
|
+
this.dialect = "sqlite";
|
|
590
|
+
}
|
|
591
|
+
quoteIdentifier(id) {
|
|
592
|
+
return `"${id}"`;
|
|
593
|
+
}
|
|
594
|
+
compileSelectAst() {
|
|
595
|
+
throw new Error("Not implemented");
|
|
596
|
+
}
|
|
597
|
+
compileInsertAst() {
|
|
598
|
+
throw new Error("Not implemented");
|
|
599
|
+
}
|
|
600
|
+
compileUpdateAst() {
|
|
601
|
+
throw new Error("Not implemented");
|
|
602
|
+
}
|
|
603
|
+
compileDeleteAst() {
|
|
604
|
+
throw new Error("Not implemented");
|
|
605
|
+
}
|
|
606
|
+
}
|
|
607
|
+
return new TestDialect(functionStrategy);
|
|
608
|
+
}
|
|
571
609
|
/**
|
|
572
610
|
* Registers an expression compiler for a specific node type
|
|
573
611
|
* @param type - Expression node type
|
|
@@ -3903,31 +3941,43 @@ var flattenResults = (results) => {
|
|
|
3903
3941
|
}
|
|
3904
3942
|
return rows;
|
|
3905
3943
|
};
|
|
3906
|
-
async
|
|
3944
|
+
var executeWithEntityContext = async (entityCtx, qb) => {
|
|
3907
3945
|
const ast = qb.getAST();
|
|
3908
|
-
const compiled =
|
|
3909
|
-
const executed = await
|
|
3946
|
+
const compiled = entityCtx.dialect.compileSelect(ast);
|
|
3947
|
+
const executed = await entityCtx.executor.executeSql(compiled.sql, compiled.params);
|
|
3910
3948
|
const rows = flattenResults(executed);
|
|
3911
3949
|
if (ast.setOps && ast.setOps.length > 0) {
|
|
3912
|
-
return rows.map(
|
|
3913
|
-
(row) => createEntityProxy(ctx, qb.getTable(), row, qb.getLazyRelations())
|
|
3914
|
-
);
|
|
3950
|
+
return rows.map((row) => createEntityProxy(entityCtx, qb.getTable(), row, qb.getLazyRelations()));
|
|
3915
3951
|
}
|
|
3916
3952
|
const hydrated = hydrateRows(rows, qb.getHydrationPlan());
|
|
3917
|
-
return hydrated.map(
|
|
3918
|
-
|
|
3919
|
-
|
|
3953
|
+
return hydrated.map((row) => createEntityFromRow(entityCtx, qb.getTable(), row, qb.getLazyRelations()));
|
|
3954
|
+
};
|
|
3955
|
+
async function executeHydrated(session, qb) {
|
|
3956
|
+
return executeWithEntityContext(session, qb);
|
|
3957
|
+
}
|
|
3958
|
+
async function executeHydratedWithContexts(_execCtx, hydCtx, qb) {
|
|
3959
|
+
const entityCtx = hydCtx.entityContext;
|
|
3960
|
+
if (!entityCtx) {
|
|
3961
|
+
throw new Error("Hydration context is missing an EntityContext");
|
|
3962
|
+
}
|
|
3963
|
+
return executeWithEntityContext(entityCtx, qb);
|
|
3920
3964
|
}
|
|
3921
3965
|
|
|
3922
3966
|
// src/query-builder/select.ts
|
|
3923
3967
|
var SelectQueryBuilder = class _SelectQueryBuilder {
|
|
3924
3968
|
/**
|
|
3925
|
-
|
|
3926
|
-
|
|
3927
|
-
|
|
3928
|
-
|
|
3929
|
-
|
|
3930
|
-
|
|
3969
|
+
|
|
3970
|
+
* Creates a new SelectQueryBuilder instance
|
|
3971
|
+
|
|
3972
|
+
* @param table - Table definition to query
|
|
3973
|
+
|
|
3974
|
+
* @param state - Optional initial query state
|
|
3975
|
+
|
|
3976
|
+
* @param hydration - Optional hydration manager
|
|
3977
|
+
|
|
3978
|
+
* @param dependencies - Optional query builder dependencies
|
|
3979
|
+
|
|
3980
|
+
*/
|
|
3931
3981
|
constructor(table, state, hydration, dependencies, lazyRelations) {
|
|
3932
3982
|
const deps = resolveSelectQueryBuilderDependencies(dependencies);
|
|
3933
3983
|
this.env = { table, deps };
|
|
@@ -3964,112 +4014,168 @@ var SelectQueryBuilder = class _SelectQueryBuilder {
|
|
|
3964
4014
|
return this.applyAst(this.context, (service) => service.withSetOperation(operator, subAst));
|
|
3965
4015
|
}
|
|
3966
4016
|
/**
|
|
3967
|
-
|
|
3968
|
-
|
|
3969
|
-
|
|
3970
|
-
|
|
4017
|
+
|
|
4018
|
+
* Selects specific columns for the query
|
|
4019
|
+
|
|
4020
|
+
* @param columns - Record of column definitions, function nodes, case expressions, or window functions
|
|
4021
|
+
|
|
4022
|
+
* @returns New query builder instance with selected columns
|
|
4023
|
+
|
|
4024
|
+
*/
|
|
3971
4025
|
select(columns) {
|
|
3972
4026
|
return this.clone(this.columnSelector.select(this.context, columns));
|
|
3973
4027
|
}
|
|
3974
4028
|
/**
|
|
3975
|
-
|
|
3976
|
-
|
|
3977
|
-
|
|
3978
|
-
|
|
4029
|
+
|
|
4030
|
+
* Selects raw column expressions
|
|
4031
|
+
|
|
4032
|
+
* @param cols - Column expressions as strings
|
|
4033
|
+
|
|
4034
|
+
* @returns New query builder instance with raw column selections
|
|
4035
|
+
|
|
4036
|
+
*/
|
|
3979
4037
|
selectRaw(...cols) {
|
|
3980
4038
|
return this.clone(this.columnSelector.selectRaw(this.context, cols));
|
|
3981
4039
|
}
|
|
3982
4040
|
/**
|
|
3983
|
-
|
|
3984
|
-
|
|
3985
|
-
|
|
3986
|
-
|
|
3987
|
-
|
|
3988
|
-
|
|
4041
|
+
|
|
4042
|
+
* Adds a Common Table Expression (CTE) to the query
|
|
4043
|
+
|
|
4044
|
+
* @param name - Name of the CTE
|
|
4045
|
+
|
|
4046
|
+
* @param query - Query builder or query node for the CTE
|
|
4047
|
+
|
|
4048
|
+
* @param columns - Optional column names for the CTE
|
|
4049
|
+
|
|
4050
|
+
* @returns New query builder instance with the CTE
|
|
4051
|
+
|
|
4052
|
+
*/
|
|
3989
4053
|
with(name, query, columns) {
|
|
3990
4054
|
const subAst = this.resolveQueryNode(query);
|
|
3991
4055
|
const nextContext = this.applyAst(this.context, (service) => service.withCte(name, subAst, columns, false));
|
|
3992
4056
|
return this.clone(nextContext);
|
|
3993
4057
|
}
|
|
3994
4058
|
/**
|
|
3995
|
-
|
|
3996
|
-
|
|
3997
|
-
|
|
3998
|
-
|
|
3999
|
-
|
|
4000
|
-
|
|
4059
|
+
|
|
4060
|
+
* Adds a recursive Common Table Expression (CTE) to the query
|
|
4061
|
+
|
|
4062
|
+
* @param name - Name of the CTE
|
|
4063
|
+
|
|
4064
|
+
* @param query - Query builder or query node for the CTE
|
|
4065
|
+
|
|
4066
|
+
* @param columns - Optional column names for the CTE
|
|
4067
|
+
|
|
4068
|
+
* @returns New query builder instance with the recursive CTE
|
|
4069
|
+
|
|
4070
|
+
*/
|
|
4001
4071
|
withRecursive(name, query, columns) {
|
|
4002
4072
|
const subAst = this.resolveQueryNode(query);
|
|
4003
4073
|
const nextContext = this.applyAst(this.context, (service) => service.withCte(name, subAst, columns, true));
|
|
4004
4074
|
return this.clone(nextContext);
|
|
4005
4075
|
}
|
|
4006
4076
|
/**
|
|
4007
|
-
|
|
4008
|
-
|
|
4009
|
-
|
|
4010
|
-
|
|
4011
|
-
|
|
4077
|
+
|
|
4078
|
+
* Selects a subquery as a column
|
|
4079
|
+
|
|
4080
|
+
* @param alias - Alias for the subquery column
|
|
4081
|
+
|
|
4082
|
+
* @param sub - Query builder or query node for the subquery
|
|
4083
|
+
|
|
4084
|
+
* @returns New query builder instance with the subquery selection
|
|
4085
|
+
|
|
4086
|
+
*/
|
|
4012
4087
|
selectSubquery(alias, sub) {
|
|
4013
4088
|
const query = this.resolveQueryNode(sub);
|
|
4014
4089
|
return this.clone(this.columnSelector.selectSubquery(this.context, alias, query));
|
|
4015
4090
|
}
|
|
4016
4091
|
/**
|
|
4017
|
-
|
|
4018
|
-
|
|
4019
|
-
|
|
4020
|
-
|
|
4021
|
-
|
|
4092
|
+
|
|
4093
|
+
* Adds an INNER JOIN to the query
|
|
4094
|
+
|
|
4095
|
+
* @param table - Table to join
|
|
4096
|
+
|
|
4097
|
+
* @param condition - Join condition expression
|
|
4098
|
+
|
|
4099
|
+
* @returns New query builder instance with the INNER JOIN
|
|
4100
|
+
|
|
4101
|
+
*/
|
|
4022
4102
|
innerJoin(table, condition) {
|
|
4023
4103
|
const nextContext = this.applyJoin(this.context, table, condition, JOIN_KINDS.INNER);
|
|
4024
4104
|
return this.clone(nextContext);
|
|
4025
4105
|
}
|
|
4026
4106
|
/**
|
|
4027
|
-
|
|
4028
|
-
|
|
4029
|
-
|
|
4030
|
-
|
|
4031
|
-
|
|
4107
|
+
|
|
4108
|
+
* Adds a LEFT JOIN to the query
|
|
4109
|
+
|
|
4110
|
+
* @param table - Table to join
|
|
4111
|
+
|
|
4112
|
+
* @param condition - Join condition expression
|
|
4113
|
+
|
|
4114
|
+
* @returns New query builder instance with the LEFT JOIN
|
|
4115
|
+
|
|
4116
|
+
*/
|
|
4032
4117
|
leftJoin(table, condition) {
|
|
4033
4118
|
const nextContext = this.applyJoin(this.context, table, condition, JOIN_KINDS.LEFT);
|
|
4034
4119
|
return this.clone(nextContext);
|
|
4035
4120
|
}
|
|
4036
4121
|
/**
|
|
4037
|
-
|
|
4038
|
-
|
|
4039
|
-
|
|
4040
|
-
|
|
4041
|
-
|
|
4122
|
+
|
|
4123
|
+
* Adds a RIGHT JOIN to the query
|
|
4124
|
+
|
|
4125
|
+
* @param table - Table to join
|
|
4126
|
+
|
|
4127
|
+
* @param condition - Join condition expression
|
|
4128
|
+
|
|
4129
|
+
* @returns New query builder instance with the RIGHT JOIN
|
|
4130
|
+
|
|
4131
|
+
*/
|
|
4042
4132
|
rightJoin(table, condition) {
|
|
4043
4133
|
const nextContext = this.applyJoin(this.context, table, condition, JOIN_KINDS.RIGHT);
|
|
4044
4134
|
return this.clone(nextContext);
|
|
4045
4135
|
}
|
|
4046
4136
|
/**
|
|
4047
|
-
|
|
4048
|
-
|
|
4049
|
-
|
|
4050
|
-
|
|
4051
|
-
|
|
4137
|
+
|
|
4138
|
+
* Matches records based on a relationship
|
|
4139
|
+
|
|
4140
|
+
* @param relationName - Name of the relationship to match
|
|
4141
|
+
|
|
4142
|
+
* @param predicate - Optional predicate expression
|
|
4143
|
+
|
|
4144
|
+
* @returns New query builder instance with the relationship match
|
|
4145
|
+
|
|
4146
|
+
*/
|
|
4052
4147
|
match(relationName, predicate) {
|
|
4053
4148
|
const nextContext = this.relationManager.match(this.context, relationName, predicate);
|
|
4054
4149
|
return this.clone(nextContext);
|
|
4055
4150
|
}
|
|
4056
4151
|
/**
|
|
4057
|
-
|
|
4058
|
-
|
|
4059
|
-
|
|
4060
|
-
|
|
4061
|
-
|
|
4062
|
-
|
|
4152
|
+
|
|
4153
|
+
* Joins a related table
|
|
4154
|
+
|
|
4155
|
+
* @param relationName - Name of the relationship to join
|
|
4156
|
+
|
|
4157
|
+
* @param joinKind - Type of join (defaults to INNER)
|
|
4158
|
+
|
|
4159
|
+
* @param extraCondition - Optional additional join condition
|
|
4160
|
+
|
|
4161
|
+
* @returns New query builder instance with the relationship join
|
|
4162
|
+
|
|
4163
|
+
*/
|
|
4063
4164
|
joinRelation(relationName, joinKind = JOIN_KINDS.INNER, extraCondition) {
|
|
4064
4165
|
const nextContext = this.relationManager.joinRelation(this.context, relationName, joinKind, extraCondition);
|
|
4065
4166
|
return this.clone(nextContext);
|
|
4066
4167
|
}
|
|
4067
4168
|
/**
|
|
4068
|
-
|
|
4069
|
-
|
|
4070
|
-
|
|
4071
|
-
|
|
4072
|
-
|
|
4169
|
+
|
|
4170
|
+
* Includes related data in the query results
|
|
4171
|
+
|
|
4172
|
+
* @param relationName - Name of the relationship to include
|
|
4173
|
+
|
|
4174
|
+
* @param options - Optional include options
|
|
4175
|
+
|
|
4176
|
+
* @returns New query builder instance with the relationship inclusion
|
|
4177
|
+
|
|
4178
|
+
*/
|
|
4073
4179
|
include(relationName, options) {
|
|
4074
4180
|
const nextContext = this.relationManager.include(this.context, relationName, options);
|
|
4075
4181
|
return this.clone(nextContext);
|
|
@@ -4088,125 +4194,186 @@ var SelectQueryBuilder = class _SelectQueryBuilder {
|
|
|
4088
4194
|
async execute(ctx) {
|
|
4089
4195
|
return executeHydrated(ctx, this);
|
|
4090
4196
|
}
|
|
4197
|
+
async executeWithContexts(execCtx, hydCtx) {
|
|
4198
|
+
return executeHydratedWithContexts(execCtx, hydCtx, this);
|
|
4199
|
+
}
|
|
4091
4200
|
/**
|
|
4092
|
-
|
|
4093
|
-
|
|
4094
|
-
|
|
4095
|
-
|
|
4201
|
+
|
|
4202
|
+
* Adds a WHERE condition to the query
|
|
4203
|
+
|
|
4204
|
+
* @param expr - Expression for the WHERE clause
|
|
4205
|
+
|
|
4206
|
+
* @returns New query builder instance with the WHERE condition
|
|
4207
|
+
|
|
4208
|
+
*/
|
|
4096
4209
|
where(expr) {
|
|
4097
4210
|
const nextContext = this.applyAst(this.context, (service) => service.withWhere(expr));
|
|
4098
4211
|
return this.clone(nextContext);
|
|
4099
4212
|
}
|
|
4100
4213
|
/**
|
|
4101
|
-
|
|
4102
|
-
|
|
4103
|
-
|
|
4104
|
-
|
|
4214
|
+
|
|
4215
|
+
* Adds a GROUP BY clause to the query
|
|
4216
|
+
|
|
4217
|
+
* @param col - Column definition or column node to group by
|
|
4218
|
+
|
|
4219
|
+
* @returns New query builder instance with the GROUP BY clause
|
|
4220
|
+
|
|
4221
|
+
*/
|
|
4105
4222
|
groupBy(col) {
|
|
4106
4223
|
const nextContext = this.applyAst(this.context, (service) => service.withGroupBy(col));
|
|
4107
4224
|
return this.clone(nextContext);
|
|
4108
4225
|
}
|
|
4109
4226
|
/**
|
|
4110
|
-
|
|
4111
|
-
|
|
4112
|
-
|
|
4113
|
-
|
|
4227
|
+
|
|
4228
|
+
* Adds a HAVING condition to the query
|
|
4229
|
+
|
|
4230
|
+
* @param expr - Expression for the HAVING clause
|
|
4231
|
+
|
|
4232
|
+
* @returns New query builder instance with the HAVING condition
|
|
4233
|
+
|
|
4234
|
+
*/
|
|
4114
4235
|
having(expr) {
|
|
4115
4236
|
const nextContext = this.applyAst(this.context, (service) => service.withHaving(expr));
|
|
4116
4237
|
return this.clone(nextContext);
|
|
4117
4238
|
}
|
|
4118
4239
|
/**
|
|
4119
|
-
|
|
4120
|
-
|
|
4121
|
-
|
|
4122
|
-
|
|
4123
|
-
|
|
4240
|
+
|
|
4241
|
+
* Adds an ORDER BY clause to the query
|
|
4242
|
+
|
|
4243
|
+
* @param col - Column definition or column node to order by
|
|
4244
|
+
|
|
4245
|
+
* @param direction - Order direction (defaults to ASC)
|
|
4246
|
+
|
|
4247
|
+
* @returns New query builder instance with the ORDER BY clause
|
|
4248
|
+
|
|
4249
|
+
*/
|
|
4124
4250
|
orderBy(col, direction = ORDER_DIRECTIONS.ASC) {
|
|
4125
4251
|
const nextContext = this.applyAst(this.context, (service) => service.withOrderBy(col, direction));
|
|
4126
4252
|
return this.clone(nextContext);
|
|
4127
4253
|
}
|
|
4128
4254
|
/**
|
|
4129
|
-
|
|
4130
|
-
|
|
4131
|
-
|
|
4132
|
-
|
|
4255
|
+
|
|
4256
|
+
* Adds a DISTINCT clause to the query
|
|
4257
|
+
|
|
4258
|
+
* @param cols - Columns to make distinct
|
|
4259
|
+
|
|
4260
|
+
* @returns New query builder instance with the DISTINCT clause
|
|
4261
|
+
|
|
4262
|
+
*/
|
|
4133
4263
|
distinct(...cols) {
|
|
4134
4264
|
return this.clone(this.columnSelector.distinct(this.context, cols));
|
|
4135
4265
|
}
|
|
4136
4266
|
/**
|
|
4137
|
-
|
|
4138
|
-
|
|
4139
|
-
|
|
4140
|
-
|
|
4267
|
+
|
|
4268
|
+
* Adds a LIMIT clause to the query
|
|
4269
|
+
|
|
4270
|
+
* @param n - Maximum number of rows to return
|
|
4271
|
+
|
|
4272
|
+
* @returns New query builder instance with the LIMIT clause
|
|
4273
|
+
|
|
4274
|
+
*/
|
|
4141
4275
|
limit(n) {
|
|
4142
4276
|
const nextContext = this.applyAst(this.context, (service) => service.withLimit(n));
|
|
4143
4277
|
return this.clone(nextContext);
|
|
4144
4278
|
}
|
|
4145
4279
|
/**
|
|
4146
|
-
|
|
4147
|
-
|
|
4148
|
-
|
|
4149
|
-
|
|
4280
|
+
|
|
4281
|
+
* Adds an OFFSET clause to the query
|
|
4282
|
+
|
|
4283
|
+
* @param n - Number of rows to skip
|
|
4284
|
+
|
|
4285
|
+
* @returns New query builder instance with the OFFSET clause
|
|
4286
|
+
|
|
4287
|
+
*/
|
|
4150
4288
|
offset(n) {
|
|
4151
4289
|
const nextContext = this.applyAst(this.context, (service) => service.withOffset(n));
|
|
4152
4290
|
return this.clone(nextContext);
|
|
4153
4291
|
}
|
|
4154
4292
|
/**
|
|
4155
|
-
|
|
4156
|
-
|
|
4157
|
-
|
|
4158
|
-
|
|
4293
|
+
|
|
4294
|
+
* Combines this query with another using UNION
|
|
4295
|
+
|
|
4296
|
+
* @param query - Query to union with
|
|
4297
|
+
|
|
4298
|
+
* @returns New query builder instance with the set operation
|
|
4299
|
+
|
|
4300
|
+
*/
|
|
4159
4301
|
union(query) {
|
|
4160
4302
|
return this.clone(this.applySetOperation("UNION", query));
|
|
4161
4303
|
}
|
|
4162
4304
|
/**
|
|
4163
|
-
|
|
4164
|
-
|
|
4165
|
-
|
|
4166
|
-
|
|
4305
|
+
|
|
4306
|
+
* Combines this query with another using UNION ALL
|
|
4307
|
+
|
|
4308
|
+
* @param query - Query to union with
|
|
4309
|
+
|
|
4310
|
+
* @returns New query builder instance with the set operation
|
|
4311
|
+
|
|
4312
|
+
*/
|
|
4167
4313
|
unionAll(query) {
|
|
4168
4314
|
return this.clone(this.applySetOperation("UNION ALL", query));
|
|
4169
4315
|
}
|
|
4170
4316
|
/**
|
|
4171
|
-
|
|
4172
|
-
|
|
4173
|
-
|
|
4174
|
-
|
|
4317
|
+
|
|
4318
|
+
* Combines this query with another using INTERSECT
|
|
4319
|
+
|
|
4320
|
+
* @param query - Query to intersect with
|
|
4321
|
+
|
|
4322
|
+
* @returns New query builder instance with the set operation
|
|
4323
|
+
|
|
4324
|
+
*/
|
|
4175
4325
|
intersect(query) {
|
|
4176
4326
|
return this.clone(this.applySetOperation("INTERSECT", query));
|
|
4177
4327
|
}
|
|
4178
4328
|
/**
|
|
4179
|
-
|
|
4180
|
-
|
|
4181
|
-
|
|
4182
|
-
|
|
4329
|
+
|
|
4330
|
+
* Combines this query with another using EXCEPT
|
|
4331
|
+
|
|
4332
|
+
* @param query - Query to subtract
|
|
4333
|
+
|
|
4334
|
+
* @returns New query builder instance with the set operation
|
|
4335
|
+
|
|
4336
|
+
*/
|
|
4183
4337
|
except(query) {
|
|
4184
4338
|
return this.clone(this.applySetOperation("EXCEPT", query));
|
|
4185
4339
|
}
|
|
4186
4340
|
/**
|
|
4187
|
-
|
|
4188
|
-
|
|
4189
|
-
|
|
4190
|
-
|
|
4341
|
+
|
|
4342
|
+
* Adds a WHERE EXISTS condition to the query
|
|
4343
|
+
|
|
4344
|
+
* @param subquery - Subquery to check for existence
|
|
4345
|
+
|
|
4346
|
+
* @returns New query builder instance with the WHERE EXISTS condition
|
|
4347
|
+
|
|
4348
|
+
*/
|
|
4191
4349
|
whereExists(subquery) {
|
|
4192
4350
|
const subAst = this.resolveQueryNode(subquery);
|
|
4193
4351
|
return this.where(exists(subAst));
|
|
4194
4352
|
}
|
|
4195
4353
|
/**
|
|
4196
|
-
|
|
4197
|
-
|
|
4198
|
-
|
|
4199
|
-
|
|
4354
|
+
|
|
4355
|
+
* Adds a WHERE NOT EXISTS condition to the query
|
|
4356
|
+
|
|
4357
|
+
* @param subquery - Subquery to check for non-existence
|
|
4358
|
+
|
|
4359
|
+
* @returns New query builder instance with the WHERE NOT EXISTS condition
|
|
4360
|
+
|
|
4361
|
+
*/
|
|
4200
4362
|
whereNotExists(subquery) {
|
|
4201
4363
|
const subAst = this.resolveQueryNode(subquery);
|
|
4202
4364
|
return this.where(notExists(subAst));
|
|
4203
4365
|
}
|
|
4204
4366
|
/**
|
|
4205
|
-
|
|
4206
|
-
|
|
4207
|
-
|
|
4208
|
-
|
|
4209
|
-
|
|
4367
|
+
|
|
4368
|
+
* Adds a WHERE EXISTS condition based on a relationship
|
|
4369
|
+
|
|
4370
|
+
* @param relationName - Name of the relationship to check
|
|
4371
|
+
|
|
4372
|
+
* @param callback - Optional callback to modify the relationship query
|
|
4373
|
+
|
|
4374
|
+
* @returns New query builder instance with the relationship existence check
|
|
4375
|
+
|
|
4376
|
+
*/
|
|
4210
4377
|
whereHas(relationName, callback) {
|
|
4211
4378
|
const relation = this.env.table.relations[relationName];
|
|
4212
4379
|
if (!relation) {
|
|
@@ -4221,11 +4388,16 @@ var SelectQueryBuilder = class _SelectQueryBuilder {
|
|
|
4221
4388
|
return this.where(exists(finalSubAst));
|
|
4222
4389
|
}
|
|
4223
4390
|
/**
|
|
4224
|
-
|
|
4225
|
-
|
|
4226
|
-
|
|
4227
|
-
|
|
4228
|
-
|
|
4391
|
+
|
|
4392
|
+
* Adds a WHERE NOT EXISTS condition based on a relationship
|
|
4393
|
+
|
|
4394
|
+
* @param relationName - Name of the relationship to check
|
|
4395
|
+
|
|
4396
|
+
* @param callback - Optional callback to modify the relationship query
|
|
4397
|
+
|
|
4398
|
+
* @returns New query builder instance with the relationship non-existence check
|
|
4399
|
+
|
|
4400
|
+
*/
|
|
4229
4401
|
whereHasNot(relationName, callback) {
|
|
4230
4402
|
const relation = this.env.table.relations[relationName];
|
|
4231
4403
|
if (!relation) {
|
|
@@ -4240,33 +4412,47 @@ var SelectQueryBuilder = class _SelectQueryBuilder {
|
|
|
4240
4412
|
return this.where(notExists(finalSubAst));
|
|
4241
4413
|
}
|
|
4242
4414
|
/**
|
|
4243
|
-
|
|
4244
|
-
|
|
4245
|
-
|
|
4246
|
-
|
|
4415
|
+
|
|
4416
|
+
* Compiles the query to SQL for a specific dialect
|
|
4417
|
+
|
|
4418
|
+
* @param dialect - Database dialect to compile for
|
|
4419
|
+
|
|
4420
|
+
* @returns Compiled query with SQL and parameters
|
|
4421
|
+
|
|
4422
|
+
*/
|
|
4247
4423
|
compile(dialect) {
|
|
4248
4424
|
const resolved = resolveDialectInput(dialect);
|
|
4249
4425
|
return resolved.compileSelect(this.context.state.ast);
|
|
4250
4426
|
}
|
|
4251
4427
|
/**
|
|
4252
|
-
|
|
4253
|
-
|
|
4254
|
-
|
|
4255
|
-
|
|
4428
|
+
|
|
4429
|
+
* Converts the query to SQL string for a specific dialect
|
|
4430
|
+
|
|
4431
|
+
* @param dialect - Database dialect to generate SQL for
|
|
4432
|
+
|
|
4433
|
+
* @returns SQL string representation of the query
|
|
4434
|
+
|
|
4435
|
+
*/
|
|
4256
4436
|
toSql(dialect) {
|
|
4257
4437
|
return this.compile(dialect).sql;
|
|
4258
4438
|
}
|
|
4259
4439
|
/**
|
|
4260
|
-
|
|
4261
|
-
|
|
4262
|
-
|
|
4440
|
+
|
|
4441
|
+
* Gets the hydration plan for the query
|
|
4442
|
+
|
|
4443
|
+
* @returns Hydration plan or undefined if none exists
|
|
4444
|
+
|
|
4445
|
+
*/
|
|
4263
4446
|
getHydrationPlan() {
|
|
4264
4447
|
return this.context.hydration.getPlan();
|
|
4265
4448
|
}
|
|
4266
4449
|
/**
|
|
4267
|
-
|
|
4268
|
-
|
|
4269
|
-
|
|
4450
|
+
|
|
4451
|
+
* Gets the Abstract Syntax Tree (AST) representation of the query
|
|
4452
|
+
|
|
4453
|
+
* @returns Query AST with hydration applied
|
|
4454
|
+
|
|
4455
|
+
*/
|
|
4270
4456
|
getAST() {
|
|
4271
4457
|
return this.context.hydration.applyToAst(this.context.state.ast);
|
|
4272
4458
|
}
|