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
|
@@ -134,11 +134,20 @@ function Entity(options = {}) {
|
|
|
134
134
|
|
|
135
135
|
// src/decorators/column.ts
|
|
136
136
|
var normalizeColumnInput = (input) => {
|
|
137
|
+
const asOptions = input;
|
|
138
|
+
const asDefinition = input;
|
|
137
139
|
const column = {
|
|
138
|
-
type:
|
|
139
|
-
args:
|
|
140
|
-
notNull:
|
|
141
|
-
primary:
|
|
140
|
+
type: asOptions.type ?? asDefinition.type,
|
|
141
|
+
args: asOptions.args ?? asDefinition.args,
|
|
142
|
+
notNull: asOptions.notNull ?? asDefinition.notNull,
|
|
143
|
+
primary: asOptions.primary ?? asDefinition.primary,
|
|
144
|
+
unique: asDefinition.unique,
|
|
145
|
+
default: asDefinition.default,
|
|
146
|
+
autoIncrement: asDefinition.autoIncrement,
|
|
147
|
+
generated: asDefinition.generated,
|
|
148
|
+
check: asDefinition.check,
|
|
149
|
+
references: asDefinition.references,
|
|
150
|
+
comment: asDefinition.comment
|
|
142
151
|
};
|
|
143
152
|
if (!column.type) {
|
|
144
153
|
throw new Error("Column decorator requires a column type");
|
|
@@ -429,7 +438,7 @@ var StandardFunctionStrategy = class {
|
|
|
429
438
|
};
|
|
430
439
|
|
|
431
440
|
// src/core/dialect/abstract.ts
|
|
432
|
-
var Dialect = class {
|
|
441
|
+
var Dialect = class _Dialect {
|
|
433
442
|
/**
|
|
434
443
|
* Compiles a SELECT query AST to SQL
|
|
435
444
|
* @param ast - Query AST to compile
|
|
@@ -602,6 +611,35 @@ var Dialect = class {
|
|
|
602
611
|
this.registerDefaultOperandCompilers();
|
|
603
612
|
this.registerDefaultExpressionCompilers();
|
|
604
613
|
}
|
|
614
|
+
/**
|
|
615
|
+
* Creates a new Dialect instance (for testing purposes)
|
|
616
|
+
* @param functionStrategy - Optional function strategy
|
|
617
|
+
* @returns New Dialect instance
|
|
618
|
+
*/
|
|
619
|
+
static create(functionStrategy) {
|
|
620
|
+
class TestDialect extends _Dialect {
|
|
621
|
+
constructor() {
|
|
622
|
+
super(...arguments);
|
|
623
|
+
this.dialect = "sqlite";
|
|
624
|
+
}
|
|
625
|
+
quoteIdentifier(id) {
|
|
626
|
+
return `"${id}"`;
|
|
627
|
+
}
|
|
628
|
+
compileSelectAst() {
|
|
629
|
+
throw new Error("Not implemented");
|
|
630
|
+
}
|
|
631
|
+
compileInsertAst() {
|
|
632
|
+
throw new Error("Not implemented");
|
|
633
|
+
}
|
|
634
|
+
compileUpdateAst() {
|
|
635
|
+
throw new Error("Not implemented");
|
|
636
|
+
}
|
|
637
|
+
compileDeleteAst() {
|
|
638
|
+
throw new Error("Not implemented");
|
|
639
|
+
}
|
|
640
|
+
}
|
|
641
|
+
return new TestDialect(functionStrategy);
|
|
642
|
+
}
|
|
605
643
|
/**
|
|
606
644
|
* Registers an expression compiler for a specific node type
|
|
607
645
|
* @param type - Expression node type
|
|
@@ -3937,31 +3975,43 @@ var flattenResults = (results) => {
|
|
|
3937
3975
|
}
|
|
3938
3976
|
return rows;
|
|
3939
3977
|
};
|
|
3940
|
-
async
|
|
3978
|
+
var executeWithEntityContext = async (entityCtx, qb) => {
|
|
3941
3979
|
const ast = qb.getAST();
|
|
3942
|
-
const compiled =
|
|
3943
|
-
const executed = await
|
|
3980
|
+
const compiled = entityCtx.dialect.compileSelect(ast);
|
|
3981
|
+
const executed = await entityCtx.executor.executeSql(compiled.sql, compiled.params);
|
|
3944
3982
|
const rows = flattenResults(executed);
|
|
3945
3983
|
if (ast.setOps && ast.setOps.length > 0) {
|
|
3946
|
-
return rows.map(
|
|
3947
|
-
(row) => createEntityProxy(ctx, qb.getTable(), row, qb.getLazyRelations())
|
|
3948
|
-
);
|
|
3984
|
+
return rows.map((row) => createEntityProxy(entityCtx, qb.getTable(), row, qb.getLazyRelations()));
|
|
3949
3985
|
}
|
|
3950
3986
|
const hydrated = hydrateRows(rows, qb.getHydrationPlan());
|
|
3951
|
-
return hydrated.map(
|
|
3952
|
-
|
|
3953
|
-
|
|
3987
|
+
return hydrated.map((row) => createEntityFromRow(entityCtx, qb.getTable(), row, qb.getLazyRelations()));
|
|
3988
|
+
};
|
|
3989
|
+
async function executeHydrated(session, qb) {
|
|
3990
|
+
return executeWithEntityContext(session, qb);
|
|
3991
|
+
}
|
|
3992
|
+
async function executeHydratedWithContexts(_execCtx, hydCtx, qb) {
|
|
3993
|
+
const entityCtx = hydCtx.entityContext;
|
|
3994
|
+
if (!entityCtx) {
|
|
3995
|
+
throw new Error("Hydration context is missing an EntityContext");
|
|
3996
|
+
}
|
|
3997
|
+
return executeWithEntityContext(entityCtx, qb);
|
|
3954
3998
|
}
|
|
3955
3999
|
|
|
3956
4000
|
// src/query-builder/select.ts
|
|
3957
4001
|
var SelectQueryBuilder = class _SelectQueryBuilder {
|
|
3958
4002
|
/**
|
|
3959
|
-
|
|
3960
|
-
|
|
3961
|
-
|
|
3962
|
-
|
|
3963
|
-
|
|
3964
|
-
|
|
4003
|
+
|
|
4004
|
+
* Creates a new SelectQueryBuilder instance
|
|
4005
|
+
|
|
4006
|
+
* @param table - Table definition to query
|
|
4007
|
+
|
|
4008
|
+
* @param state - Optional initial query state
|
|
4009
|
+
|
|
4010
|
+
* @param hydration - Optional hydration manager
|
|
4011
|
+
|
|
4012
|
+
* @param dependencies - Optional query builder dependencies
|
|
4013
|
+
|
|
4014
|
+
*/
|
|
3965
4015
|
constructor(table, state, hydration, dependencies, lazyRelations) {
|
|
3966
4016
|
const deps = resolveSelectQueryBuilderDependencies(dependencies);
|
|
3967
4017
|
this.env = { table, deps };
|
|
@@ -3998,112 +4048,168 @@ var SelectQueryBuilder = class _SelectQueryBuilder {
|
|
|
3998
4048
|
return this.applyAst(this.context, (service) => service.withSetOperation(operator, subAst));
|
|
3999
4049
|
}
|
|
4000
4050
|
/**
|
|
4001
|
-
|
|
4002
|
-
|
|
4003
|
-
|
|
4004
|
-
|
|
4051
|
+
|
|
4052
|
+
* Selects specific columns for the query
|
|
4053
|
+
|
|
4054
|
+
* @param columns - Record of column definitions, function nodes, case expressions, or window functions
|
|
4055
|
+
|
|
4056
|
+
* @returns New query builder instance with selected columns
|
|
4057
|
+
|
|
4058
|
+
*/
|
|
4005
4059
|
select(columns) {
|
|
4006
4060
|
return this.clone(this.columnSelector.select(this.context, columns));
|
|
4007
4061
|
}
|
|
4008
4062
|
/**
|
|
4009
|
-
|
|
4010
|
-
|
|
4011
|
-
|
|
4012
|
-
|
|
4063
|
+
|
|
4064
|
+
* Selects raw column expressions
|
|
4065
|
+
|
|
4066
|
+
* @param cols - Column expressions as strings
|
|
4067
|
+
|
|
4068
|
+
* @returns New query builder instance with raw column selections
|
|
4069
|
+
|
|
4070
|
+
*/
|
|
4013
4071
|
selectRaw(...cols) {
|
|
4014
4072
|
return this.clone(this.columnSelector.selectRaw(this.context, cols));
|
|
4015
4073
|
}
|
|
4016
4074
|
/**
|
|
4017
|
-
|
|
4018
|
-
|
|
4019
|
-
|
|
4020
|
-
|
|
4021
|
-
|
|
4022
|
-
|
|
4075
|
+
|
|
4076
|
+
* Adds a Common Table Expression (CTE) to the query
|
|
4077
|
+
|
|
4078
|
+
* @param name - Name of the CTE
|
|
4079
|
+
|
|
4080
|
+
* @param query - Query builder or query node for the CTE
|
|
4081
|
+
|
|
4082
|
+
* @param columns - Optional column names for the CTE
|
|
4083
|
+
|
|
4084
|
+
* @returns New query builder instance with the CTE
|
|
4085
|
+
|
|
4086
|
+
*/
|
|
4023
4087
|
with(name, query, columns) {
|
|
4024
4088
|
const subAst = this.resolveQueryNode(query);
|
|
4025
4089
|
const nextContext = this.applyAst(this.context, (service) => service.withCte(name, subAst, columns, false));
|
|
4026
4090
|
return this.clone(nextContext);
|
|
4027
4091
|
}
|
|
4028
4092
|
/**
|
|
4029
|
-
|
|
4030
|
-
|
|
4031
|
-
|
|
4032
|
-
|
|
4033
|
-
|
|
4034
|
-
|
|
4093
|
+
|
|
4094
|
+
* Adds a recursive Common Table Expression (CTE) to the query
|
|
4095
|
+
|
|
4096
|
+
* @param name - Name of the CTE
|
|
4097
|
+
|
|
4098
|
+
* @param query - Query builder or query node for the CTE
|
|
4099
|
+
|
|
4100
|
+
* @param columns - Optional column names for the CTE
|
|
4101
|
+
|
|
4102
|
+
* @returns New query builder instance with the recursive CTE
|
|
4103
|
+
|
|
4104
|
+
*/
|
|
4035
4105
|
withRecursive(name, query, columns) {
|
|
4036
4106
|
const subAst = this.resolveQueryNode(query);
|
|
4037
4107
|
const nextContext = this.applyAst(this.context, (service) => service.withCte(name, subAst, columns, true));
|
|
4038
4108
|
return this.clone(nextContext);
|
|
4039
4109
|
}
|
|
4040
4110
|
/**
|
|
4041
|
-
|
|
4042
|
-
|
|
4043
|
-
|
|
4044
|
-
|
|
4045
|
-
|
|
4111
|
+
|
|
4112
|
+
* Selects a subquery as a column
|
|
4113
|
+
|
|
4114
|
+
* @param alias - Alias for the subquery column
|
|
4115
|
+
|
|
4116
|
+
* @param sub - Query builder or query node for the subquery
|
|
4117
|
+
|
|
4118
|
+
* @returns New query builder instance with the subquery selection
|
|
4119
|
+
|
|
4120
|
+
*/
|
|
4046
4121
|
selectSubquery(alias, sub) {
|
|
4047
4122
|
const query = this.resolveQueryNode(sub);
|
|
4048
4123
|
return this.clone(this.columnSelector.selectSubquery(this.context, alias, query));
|
|
4049
4124
|
}
|
|
4050
4125
|
/**
|
|
4051
|
-
|
|
4052
|
-
|
|
4053
|
-
|
|
4054
|
-
|
|
4055
|
-
|
|
4126
|
+
|
|
4127
|
+
* Adds an INNER JOIN to the query
|
|
4128
|
+
|
|
4129
|
+
* @param table - Table to join
|
|
4130
|
+
|
|
4131
|
+
* @param condition - Join condition expression
|
|
4132
|
+
|
|
4133
|
+
* @returns New query builder instance with the INNER JOIN
|
|
4134
|
+
|
|
4135
|
+
*/
|
|
4056
4136
|
innerJoin(table, condition) {
|
|
4057
4137
|
const nextContext = this.applyJoin(this.context, table, condition, JOIN_KINDS.INNER);
|
|
4058
4138
|
return this.clone(nextContext);
|
|
4059
4139
|
}
|
|
4060
4140
|
/**
|
|
4061
|
-
|
|
4062
|
-
|
|
4063
|
-
|
|
4064
|
-
|
|
4065
|
-
|
|
4141
|
+
|
|
4142
|
+
* Adds a LEFT JOIN to the query
|
|
4143
|
+
|
|
4144
|
+
* @param table - Table to join
|
|
4145
|
+
|
|
4146
|
+
* @param condition - Join condition expression
|
|
4147
|
+
|
|
4148
|
+
* @returns New query builder instance with the LEFT JOIN
|
|
4149
|
+
|
|
4150
|
+
*/
|
|
4066
4151
|
leftJoin(table, condition) {
|
|
4067
4152
|
const nextContext = this.applyJoin(this.context, table, condition, JOIN_KINDS.LEFT);
|
|
4068
4153
|
return this.clone(nextContext);
|
|
4069
4154
|
}
|
|
4070
4155
|
/**
|
|
4071
|
-
|
|
4072
|
-
|
|
4073
|
-
|
|
4074
|
-
|
|
4075
|
-
|
|
4156
|
+
|
|
4157
|
+
* Adds a RIGHT JOIN to the query
|
|
4158
|
+
|
|
4159
|
+
* @param table - Table to join
|
|
4160
|
+
|
|
4161
|
+
* @param condition - Join condition expression
|
|
4162
|
+
|
|
4163
|
+
* @returns New query builder instance with the RIGHT JOIN
|
|
4164
|
+
|
|
4165
|
+
*/
|
|
4076
4166
|
rightJoin(table, condition) {
|
|
4077
4167
|
const nextContext = this.applyJoin(this.context, table, condition, JOIN_KINDS.RIGHT);
|
|
4078
4168
|
return this.clone(nextContext);
|
|
4079
4169
|
}
|
|
4080
4170
|
/**
|
|
4081
|
-
|
|
4082
|
-
|
|
4083
|
-
|
|
4084
|
-
|
|
4085
|
-
|
|
4171
|
+
|
|
4172
|
+
* Matches records based on a relationship
|
|
4173
|
+
|
|
4174
|
+
* @param relationName - Name of the relationship to match
|
|
4175
|
+
|
|
4176
|
+
* @param predicate - Optional predicate expression
|
|
4177
|
+
|
|
4178
|
+
* @returns New query builder instance with the relationship match
|
|
4179
|
+
|
|
4180
|
+
*/
|
|
4086
4181
|
match(relationName, predicate) {
|
|
4087
4182
|
const nextContext = this.relationManager.match(this.context, relationName, predicate);
|
|
4088
4183
|
return this.clone(nextContext);
|
|
4089
4184
|
}
|
|
4090
4185
|
/**
|
|
4091
|
-
|
|
4092
|
-
|
|
4093
|
-
|
|
4094
|
-
|
|
4095
|
-
|
|
4096
|
-
|
|
4186
|
+
|
|
4187
|
+
* Joins a related table
|
|
4188
|
+
|
|
4189
|
+
* @param relationName - Name of the relationship to join
|
|
4190
|
+
|
|
4191
|
+
* @param joinKind - Type of join (defaults to INNER)
|
|
4192
|
+
|
|
4193
|
+
* @param extraCondition - Optional additional join condition
|
|
4194
|
+
|
|
4195
|
+
* @returns New query builder instance with the relationship join
|
|
4196
|
+
|
|
4197
|
+
*/
|
|
4097
4198
|
joinRelation(relationName, joinKind = JOIN_KINDS.INNER, extraCondition) {
|
|
4098
4199
|
const nextContext = this.relationManager.joinRelation(this.context, relationName, joinKind, extraCondition);
|
|
4099
4200
|
return this.clone(nextContext);
|
|
4100
4201
|
}
|
|
4101
4202
|
/**
|
|
4102
|
-
|
|
4103
|
-
|
|
4104
|
-
|
|
4105
|
-
|
|
4106
|
-
|
|
4203
|
+
|
|
4204
|
+
* Includes related data in the query results
|
|
4205
|
+
|
|
4206
|
+
* @param relationName - Name of the relationship to include
|
|
4207
|
+
|
|
4208
|
+
* @param options - Optional include options
|
|
4209
|
+
|
|
4210
|
+
* @returns New query builder instance with the relationship inclusion
|
|
4211
|
+
|
|
4212
|
+
*/
|
|
4107
4213
|
include(relationName, options) {
|
|
4108
4214
|
const nextContext = this.relationManager.include(this.context, relationName, options);
|
|
4109
4215
|
return this.clone(nextContext);
|
|
@@ -4122,125 +4228,186 @@ var SelectQueryBuilder = class _SelectQueryBuilder {
|
|
|
4122
4228
|
async execute(ctx) {
|
|
4123
4229
|
return executeHydrated(ctx, this);
|
|
4124
4230
|
}
|
|
4231
|
+
async executeWithContexts(execCtx, hydCtx) {
|
|
4232
|
+
return executeHydratedWithContexts(execCtx, hydCtx, this);
|
|
4233
|
+
}
|
|
4125
4234
|
/**
|
|
4126
|
-
|
|
4127
|
-
|
|
4128
|
-
|
|
4129
|
-
|
|
4235
|
+
|
|
4236
|
+
* Adds a WHERE condition to the query
|
|
4237
|
+
|
|
4238
|
+
* @param expr - Expression for the WHERE clause
|
|
4239
|
+
|
|
4240
|
+
* @returns New query builder instance with the WHERE condition
|
|
4241
|
+
|
|
4242
|
+
*/
|
|
4130
4243
|
where(expr) {
|
|
4131
4244
|
const nextContext = this.applyAst(this.context, (service) => service.withWhere(expr));
|
|
4132
4245
|
return this.clone(nextContext);
|
|
4133
4246
|
}
|
|
4134
4247
|
/**
|
|
4135
|
-
|
|
4136
|
-
|
|
4137
|
-
|
|
4138
|
-
|
|
4248
|
+
|
|
4249
|
+
* Adds a GROUP BY clause to the query
|
|
4250
|
+
|
|
4251
|
+
* @param col - Column definition or column node to group by
|
|
4252
|
+
|
|
4253
|
+
* @returns New query builder instance with the GROUP BY clause
|
|
4254
|
+
|
|
4255
|
+
*/
|
|
4139
4256
|
groupBy(col) {
|
|
4140
4257
|
const nextContext = this.applyAst(this.context, (service) => service.withGroupBy(col));
|
|
4141
4258
|
return this.clone(nextContext);
|
|
4142
4259
|
}
|
|
4143
4260
|
/**
|
|
4144
|
-
|
|
4145
|
-
|
|
4146
|
-
|
|
4147
|
-
|
|
4261
|
+
|
|
4262
|
+
* Adds a HAVING condition to the query
|
|
4263
|
+
|
|
4264
|
+
* @param expr - Expression for the HAVING clause
|
|
4265
|
+
|
|
4266
|
+
* @returns New query builder instance with the HAVING condition
|
|
4267
|
+
|
|
4268
|
+
*/
|
|
4148
4269
|
having(expr) {
|
|
4149
4270
|
const nextContext = this.applyAst(this.context, (service) => service.withHaving(expr));
|
|
4150
4271
|
return this.clone(nextContext);
|
|
4151
4272
|
}
|
|
4152
4273
|
/**
|
|
4153
|
-
|
|
4154
|
-
|
|
4155
|
-
|
|
4156
|
-
|
|
4157
|
-
|
|
4274
|
+
|
|
4275
|
+
* Adds an ORDER BY clause to the query
|
|
4276
|
+
|
|
4277
|
+
* @param col - Column definition or column node to order by
|
|
4278
|
+
|
|
4279
|
+
* @param direction - Order direction (defaults to ASC)
|
|
4280
|
+
|
|
4281
|
+
* @returns New query builder instance with the ORDER BY clause
|
|
4282
|
+
|
|
4283
|
+
*/
|
|
4158
4284
|
orderBy(col, direction = ORDER_DIRECTIONS.ASC) {
|
|
4159
4285
|
const nextContext = this.applyAst(this.context, (service) => service.withOrderBy(col, direction));
|
|
4160
4286
|
return this.clone(nextContext);
|
|
4161
4287
|
}
|
|
4162
4288
|
/**
|
|
4163
|
-
|
|
4164
|
-
|
|
4165
|
-
|
|
4166
|
-
|
|
4289
|
+
|
|
4290
|
+
* Adds a DISTINCT clause to the query
|
|
4291
|
+
|
|
4292
|
+
* @param cols - Columns to make distinct
|
|
4293
|
+
|
|
4294
|
+
* @returns New query builder instance with the DISTINCT clause
|
|
4295
|
+
|
|
4296
|
+
*/
|
|
4167
4297
|
distinct(...cols) {
|
|
4168
4298
|
return this.clone(this.columnSelector.distinct(this.context, cols));
|
|
4169
4299
|
}
|
|
4170
4300
|
/**
|
|
4171
|
-
|
|
4172
|
-
|
|
4173
|
-
|
|
4174
|
-
|
|
4301
|
+
|
|
4302
|
+
* Adds a LIMIT clause to the query
|
|
4303
|
+
|
|
4304
|
+
* @param n - Maximum number of rows to return
|
|
4305
|
+
|
|
4306
|
+
* @returns New query builder instance with the LIMIT clause
|
|
4307
|
+
|
|
4308
|
+
*/
|
|
4175
4309
|
limit(n) {
|
|
4176
4310
|
const nextContext = this.applyAst(this.context, (service) => service.withLimit(n));
|
|
4177
4311
|
return this.clone(nextContext);
|
|
4178
4312
|
}
|
|
4179
4313
|
/**
|
|
4180
|
-
|
|
4181
|
-
|
|
4182
|
-
|
|
4183
|
-
|
|
4314
|
+
|
|
4315
|
+
* Adds an OFFSET clause to the query
|
|
4316
|
+
|
|
4317
|
+
* @param n - Number of rows to skip
|
|
4318
|
+
|
|
4319
|
+
* @returns New query builder instance with the OFFSET clause
|
|
4320
|
+
|
|
4321
|
+
*/
|
|
4184
4322
|
offset(n) {
|
|
4185
4323
|
const nextContext = this.applyAst(this.context, (service) => service.withOffset(n));
|
|
4186
4324
|
return this.clone(nextContext);
|
|
4187
4325
|
}
|
|
4188
4326
|
/**
|
|
4189
|
-
|
|
4190
|
-
|
|
4191
|
-
|
|
4192
|
-
|
|
4327
|
+
|
|
4328
|
+
* Combines this query with another using UNION
|
|
4329
|
+
|
|
4330
|
+
* @param query - Query to union with
|
|
4331
|
+
|
|
4332
|
+
* @returns New query builder instance with the set operation
|
|
4333
|
+
|
|
4334
|
+
*/
|
|
4193
4335
|
union(query) {
|
|
4194
4336
|
return this.clone(this.applySetOperation("UNION", query));
|
|
4195
4337
|
}
|
|
4196
4338
|
/**
|
|
4197
|
-
|
|
4198
|
-
|
|
4199
|
-
|
|
4200
|
-
|
|
4339
|
+
|
|
4340
|
+
* Combines this query with another using UNION ALL
|
|
4341
|
+
|
|
4342
|
+
* @param query - Query to union with
|
|
4343
|
+
|
|
4344
|
+
* @returns New query builder instance with the set operation
|
|
4345
|
+
|
|
4346
|
+
*/
|
|
4201
4347
|
unionAll(query) {
|
|
4202
4348
|
return this.clone(this.applySetOperation("UNION ALL", query));
|
|
4203
4349
|
}
|
|
4204
4350
|
/**
|
|
4205
|
-
|
|
4206
|
-
|
|
4207
|
-
|
|
4208
|
-
|
|
4351
|
+
|
|
4352
|
+
* Combines this query with another using INTERSECT
|
|
4353
|
+
|
|
4354
|
+
* @param query - Query to intersect with
|
|
4355
|
+
|
|
4356
|
+
* @returns New query builder instance with the set operation
|
|
4357
|
+
|
|
4358
|
+
*/
|
|
4209
4359
|
intersect(query) {
|
|
4210
4360
|
return this.clone(this.applySetOperation("INTERSECT", query));
|
|
4211
4361
|
}
|
|
4212
4362
|
/**
|
|
4213
|
-
|
|
4214
|
-
|
|
4215
|
-
|
|
4216
|
-
|
|
4363
|
+
|
|
4364
|
+
* Combines this query with another using EXCEPT
|
|
4365
|
+
|
|
4366
|
+
* @param query - Query to subtract
|
|
4367
|
+
|
|
4368
|
+
* @returns New query builder instance with the set operation
|
|
4369
|
+
|
|
4370
|
+
*/
|
|
4217
4371
|
except(query) {
|
|
4218
4372
|
return this.clone(this.applySetOperation("EXCEPT", query));
|
|
4219
4373
|
}
|
|
4220
4374
|
/**
|
|
4221
|
-
|
|
4222
|
-
|
|
4223
|
-
|
|
4224
|
-
|
|
4375
|
+
|
|
4376
|
+
* Adds a WHERE EXISTS condition to the query
|
|
4377
|
+
|
|
4378
|
+
* @param subquery - Subquery to check for existence
|
|
4379
|
+
|
|
4380
|
+
* @returns New query builder instance with the WHERE EXISTS condition
|
|
4381
|
+
|
|
4382
|
+
*/
|
|
4225
4383
|
whereExists(subquery) {
|
|
4226
4384
|
const subAst = this.resolveQueryNode(subquery);
|
|
4227
4385
|
return this.where(exists(subAst));
|
|
4228
4386
|
}
|
|
4229
4387
|
/**
|
|
4230
|
-
|
|
4231
|
-
|
|
4232
|
-
|
|
4233
|
-
|
|
4388
|
+
|
|
4389
|
+
* Adds a WHERE NOT EXISTS condition to the query
|
|
4390
|
+
|
|
4391
|
+
* @param subquery - Subquery to check for non-existence
|
|
4392
|
+
|
|
4393
|
+
* @returns New query builder instance with the WHERE NOT EXISTS condition
|
|
4394
|
+
|
|
4395
|
+
*/
|
|
4234
4396
|
whereNotExists(subquery) {
|
|
4235
4397
|
const subAst = this.resolveQueryNode(subquery);
|
|
4236
4398
|
return this.where(notExists(subAst));
|
|
4237
4399
|
}
|
|
4238
4400
|
/**
|
|
4239
|
-
|
|
4240
|
-
|
|
4241
|
-
|
|
4242
|
-
|
|
4243
|
-
|
|
4401
|
+
|
|
4402
|
+
* Adds a WHERE EXISTS condition based on a relationship
|
|
4403
|
+
|
|
4404
|
+
* @param relationName - Name of the relationship to check
|
|
4405
|
+
|
|
4406
|
+
* @param callback - Optional callback to modify the relationship query
|
|
4407
|
+
|
|
4408
|
+
* @returns New query builder instance with the relationship existence check
|
|
4409
|
+
|
|
4410
|
+
*/
|
|
4244
4411
|
whereHas(relationName, callback) {
|
|
4245
4412
|
const relation = this.env.table.relations[relationName];
|
|
4246
4413
|
if (!relation) {
|
|
@@ -4255,11 +4422,16 @@ var SelectQueryBuilder = class _SelectQueryBuilder {
|
|
|
4255
4422
|
return this.where(exists(finalSubAst));
|
|
4256
4423
|
}
|
|
4257
4424
|
/**
|
|
4258
|
-
|
|
4259
|
-
|
|
4260
|
-
|
|
4261
|
-
|
|
4262
|
-
|
|
4425
|
+
|
|
4426
|
+
* Adds a WHERE NOT EXISTS condition based on a relationship
|
|
4427
|
+
|
|
4428
|
+
* @param relationName - Name of the relationship to check
|
|
4429
|
+
|
|
4430
|
+
* @param callback - Optional callback to modify the relationship query
|
|
4431
|
+
|
|
4432
|
+
* @returns New query builder instance with the relationship non-existence check
|
|
4433
|
+
|
|
4434
|
+
*/
|
|
4263
4435
|
whereHasNot(relationName, callback) {
|
|
4264
4436
|
const relation = this.env.table.relations[relationName];
|
|
4265
4437
|
if (!relation) {
|
|
@@ -4274,33 +4446,47 @@ var SelectQueryBuilder = class _SelectQueryBuilder {
|
|
|
4274
4446
|
return this.where(notExists(finalSubAst));
|
|
4275
4447
|
}
|
|
4276
4448
|
/**
|
|
4277
|
-
|
|
4278
|
-
|
|
4279
|
-
|
|
4280
|
-
|
|
4449
|
+
|
|
4450
|
+
* Compiles the query to SQL for a specific dialect
|
|
4451
|
+
|
|
4452
|
+
* @param dialect - Database dialect to compile for
|
|
4453
|
+
|
|
4454
|
+
* @returns Compiled query with SQL and parameters
|
|
4455
|
+
|
|
4456
|
+
*/
|
|
4281
4457
|
compile(dialect) {
|
|
4282
4458
|
const resolved = resolveDialectInput(dialect);
|
|
4283
4459
|
return resolved.compileSelect(this.context.state.ast);
|
|
4284
4460
|
}
|
|
4285
4461
|
/**
|
|
4286
|
-
|
|
4287
|
-
|
|
4288
|
-
|
|
4289
|
-
|
|
4462
|
+
|
|
4463
|
+
* Converts the query to SQL string for a specific dialect
|
|
4464
|
+
|
|
4465
|
+
* @param dialect - Database dialect to generate SQL for
|
|
4466
|
+
|
|
4467
|
+
* @returns SQL string representation of the query
|
|
4468
|
+
|
|
4469
|
+
*/
|
|
4290
4470
|
toSql(dialect) {
|
|
4291
4471
|
return this.compile(dialect).sql;
|
|
4292
4472
|
}
|
|
4293
4473
|
/**
|
|
4294
|
-
|
|
4295
|
-
|
|
4296
|
-
|
|
4474
|
+
|
|
4475
|
+
* Gets the hydration plan for the query
|
|
4476
|
+
|
|
4477
|
+
* @returns Hydration plan or undefined if none exists
|
|
4478
|
+
|
|
4479
|
+
*/
|
|
4297
4480
|
getHydrationPlan() {
|
|
4298
4481
|
return this.context.hydration.getPlan();
|
|
4299
4482
|
}
|
|
4300
4483
|
/**
|
|
4301
|
-
|
|
4302
|
-
|
|
4303
|
-
|
|
4484
|
+
|
|
4485
|
+
* Gets the Abstract Syntax Tree (AST) representation of the query
|
|
4486
|
+
|
|
4487
|
+
* @returns Query AST with hydration applied
|
|
4488
|
+
|
|
4489
|
+
*/
|
|
4304
4490
|
getAST() {
|
|
4305
4491
|
return this.context.hydration.applyToAst(this.context.state.ast);
|
|
4306
4492
|
}
|