velocious 1.0.436 → 1.0.438
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/build/database/query/model-class-query.js +7 -4
- package/build/database/query/preloader/has-many.js +29 -1
- package/build/database/record/index.js +10 -0
- package/build/database/record/instance-relationships/has-many.js +6 -1
- package/build/database/record/relationships/base.js +9 -0
- package/build/src/database/query/model-class-query.d.ts.map +1 -1
- package/build/src/database/query/model-class-query.js +8 -5
- package/build/src/database/query/preloader/has-many.d.ts +8 -0
- package/build/src/database/query/preloader/has-many.d.ts.map +1 -1
- package/build/src/database/query/preloader/has-many.js +26 -2
- package/build/src/database/record/index.d.ts +7 -0
- package/build/src/database/record/index.d.ts.map +1 -1
- package/build/src/database/record/index.js +10 -1
- package/build/src/database/record/instance-relationships/has-many.d.ts.map +1 -1
- package/build/src/database/record/instance-relationships/has-many.js +4 -2
- package/build/src/database/record/relationships/base.d.ts +8 -0
- package/build/src/database/record/relationships/base.d.ts.map +1 -1
- package/build/src/database/record/relationships/base.js +9 -1
- package/package.json +1 -1
- package/src/database/query/model-class-query.js +7 -4
- package/src/database/query/preloader/has-many.js +29 -1
- package/src/database/record/index.js +10 -0
- package/src/database/record/instance-relationships/has-many.js +6 -1
- package/src/database/record/relationships/base.js +9 -0
|
@@ -301,14 +301,17 @@ export default class VelociousDatabaseQueryModelClassQuery extends DatabaseQuery
|
|
|
301
301
|
* @returns {Promise<number>} - Resolves with the count.
|
|
302
302
|
*/
|
|
303
303
|
async count() {
|
|
304
|
-
|
|
304
|
+
// Pagination, or a model with no single primary key (setPrimaryKey(null), e.g. composite-key
|
|
305
|
+
// legacy tables with no id column), count via the subquery form. It references no primary-key
|
|
306
|
+
// column and preserves DISTINCT over joins — which a bare COUNT(*) would not (it would count
|
|
307
|
+
// joined duplicate rows instead of distinct root rows). primaryKey() falls back to "id" for the
|
|
308
|
+
// no-pk case, so hasPrimaryKey() is used to detect it.
|
|
309
|
+
if (this._limit !== null || this._offset !== null || !this.getModelClass().hasPrimaryKey()) {
|
|
305
310
|
return await this.paginatedCount()
|
|
306
311
|
}
|
|
307
312
|
|
|
308
|
-
// Models without a single primary key (composite-key tables) count via COUNT(*), not COUNT(<table>.id).
|
|
309
|
-
const primaryKeyColumn = this.getModelClass().primaryKey()
|
|
310
313
|
const distinctPrefix = this._distinct ? "DISTINCT " : ""
|
|
311
|
-
let sql =
|
|
314
|
+
let sql = `COUNT(${distinctPrefix}${this.driver.quoteTable(this.getModelClass().tableName())}.${this.driver.quoteColumn(this.getModelClass().primaryKey())})`
|
|
312
315
|
|
|
313
316
|
if (this.driver.getType() == "pgsql") sql += "::int"
|
|
314
317
|
|
|
@@ -4,6 +4,34 @@ import ensureModelClassInitialized from "./ensure-model-class-initialized.js"
|
|
|
4
4
|
import PreloaderSelection from "./selection.js"
|
|
5
5
|
import restArgsError from "../../../utils/rest-args-error.js"
|
|
6
6
|
|
|
7
|
+
/**
|
|
8
|
+
* Resolves the target column that references the through model.
|
|
9
|
+
* @param {import("../../record/relationships/has-many.js").default} relationship - Has-many through relationship.
|
|
10
|
+
* @param {typeof import("../../record/index.js").default} throughModelClass - Model used by the through relationship.
|
|
11
|
+
* @param {typeof import("../../record/index.js").default} targetModelClass - Model loaded by the through relationship.
|
|
12
|
+
* @returns {string} Target model foreign key column.
|
|
13
|
+
*/
|
|
14
|
+
export function hasManyThroughTargetForeignKey(relationship, throughModelClass, targetModelClass) {
|
|
15
|
+
// An explicit foreign key on the has-many names the exact target column that references the
|
|
16
|
+
// through model — honor it. The target can have several belongs-to pointing at the through model
|
|
17
|
+
// (e.g. a default plus an alternate), so picking the first match would otherwise be ambiguous.
|
|
18
|
+
const explicitForeignKey = relationship.getExplicitForeignKey()
|
|
19
|
+
|
|
20
|
+
if (explicitForeignKey) return explicitForeignKey
|
|
21
|
+
|
|
22
|
+
for (const targetRelationship of targetModelClass.getRelationships()) {
|
|
23
|
+
if (targetRelationship.getType() != "belongsTo") continue
|
|
24
|
+
|
|
25
|
+
const relationshipTargetModelClass = targetRelationship.getTargetModelClass()
|
|
26
|
+
|
|
27
|
+
if (relationshipTargetModelClass === throughModelClass) {
|
|
28
|
+
return targetRelationship.getForeignKey()
|
|
29
|
+
}
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
return relationship.getForeignKey()
|
|
33
|
+
}
|
|
34
|
+
|
|
7
35
|
export default class VelociousDatabaseQueryPreloaderHasMany {
|
|
8
36
|
/**
|
|
9
37
|
* Runs constructor.
|
|
@@ -90,7 +118,7 @@ export default class VelociousDatabaseQueryPreloaderHasMany {
|
|
|
90
118
|
|
|
91
119
|
if (!targetModelClass) throw new Error("No target model class could be gotten from relationship")
|
|
92
120
|
|
|
93
|
-
const targetForeignKey = this.relationship
|
|
121
|
+
const targetForeignKey = hasManyThroughTargetForeignKey(this.relationship, throughModelClass, targetModelClass)
|
|
94
122
|
const {modelsToLoad, satisfiedTargets} = this._partition(targetModelClass, [targetForeignKey])
|
|
95
123
|
|
|
96
124
|
if (modelsToLoad.length == 0) return satisfiedTargets
|
|
@@ -2291,6 +2291,16 @@ class VelociousDatabaseRecord {
|
|
|
2291
2291
|
return "id"
|
|
2292
2292
|
}
|
|
2293
2293
|
|
|
2294
|
+
/**
|
|
2295
|
+
* Whether the model has a single primary key column. `setPrimaryKey(null)` (e.g. composite-key
|
|
2296
|
+
* legacy tables) declares no single primary key; `primaryKey()` still falls back to "id" for the
|
|
2297
|
+
* default case, so callers that must distinguish "no primary key" use this instead.
|
|
2298
|
+
* @returns {boolean} - False only when the primary key was explicitly set to null.
|
|
2299
|
+
*/
|
|
2300
|
+
static hasPrimaryKey() {
|
|
2301
|
+
return this._primaryKey !== null
|
|
2302
|
+
}
|
|
2303
|
+
|
|
2294
2304
|
/**
|
|
2295
2305
|
* Runs save.
|
|
2296
2306
|
* @returns {Promise<void>} - Resolves when complete.
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
// @ts-check
|
|
2
2
|
|
|
3
3
|
import BaseInstanceRelationship from "./base.js"
|
|
4
|
+
import {hasManyThroughTargetForeignKey} from "../../query/preloader/has-many.js"
|
|
4
5
|
|
|
5
6
|
/**
|
|
6
7
|
* A generic query over some model type.
|
|
@@ -192,7 +193,11 @@ export default class VelociousDatabaseRecordHasManyInstanceRelationship extends
|
|
|
192
193
|
|
|
193
194
|
const throughForeignKey = throughRelationship.getForeignKey()
|
|
194
195
|
const throughPrimaryKey = throughRelationship.getPrimaryKey()
|
|
195
|
-
const targetForeignKey =
|
|
196
|
+
const targetForeignKey = hasManyThroughTargetForeignKey(
|
|
197
|
+
/** @type {import("../relationships/has-many.js").default} */ (this.getRelationship()),
|
|
198
|
+
throughModelClass,
|
|
199
|
+
TargetModelClass
|
|
200
|
+
)
|
|
196
201
|
const targetTable = TargetModelClass.tableName()
|
|
197
202
|
const throughTable = throughModelClass.tableName()
|
|
198
203
|
const driver = TargetModelClass.connection()
|
|
@@ -46,6 +46,7 @@ export default class VelociousDatabaseRecordBaseRelationship {
|
|
|
46
46
|
this._counterCache = counterCache || false
|
|
47
47
|
this._dependent = dependent
|
|
48
48
|
this.foreignKey = foreignKey
|
|
49
|
+
this._explicitForeignKey = foreignKey
|
|
49
50
|
this._inverseOf = inverseOf
|
|
50
51
|
this.klass = klass
|
|
51
52
|
this.modelClass = modelClass
|
|
@@ -77,6 +78,14 @@ export default class VelociousDatabaseRecordBaseRelationship {
|
|
|
77
78
|
*/
|
|
78
79
|
getDependent() { return this._dependent }
|
|
79
80
|
|
|
81
|
+
/**
|
|
82
|
+
* The foreign key explicitly passed when the relationship was declared, if any. Unlike
|
|
83
|
+
* `getForeignKey()` this never falls back to a computed default, so callers can tell whether the
|
|
84
|
+
* developer named a specific column (e.g. to disambiguate multiple belongs-to on a through target).
|
|
85
|
+
* @returns {string | undefined} - The explicitly declared foreign key, or undefined.
|
|
86
|
+
*/
|
|
87
|
+
getExplicitForeignKey() { return this._explicitForeignKey }
|
|
88
|
+
|
|
80
89
|
/**
|
|
81
90
|
* Runs get foreign key.
|
|
82
91
|
* @abstract
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"model-class-query.d.ts","sourceRoot":"","sources":["../../../../src/database/query/model-class-query.js"],"names":[],"mappings":"AAmKA;;;GAGG;AACH;;;;GAIG;AAEH;;;GAGG;AACH,2DAZ4D,EAAE,SAAjD,cAAe,oBAAoB,EAAE,OAAQ;IAaxD;;;OAGG;IACH,kBAFW,uBAAuB,CAAC,EAAE,CAAC,EA+BrC;IArBC;;mBAEe;IACf,YADS,EAAE,CACiB;IAE5B;;yBAEqB;IACrB,eADS,MAAM,EAAE,CAC2B;IAC5C,0BAAsF;IACtF,gCAAiE;IAEjE;;2DAEuD;IACvD,YADS,OAAO,iBAAiB,EAAE,cAAc,EAAE,CACQ;IAE3D;;2DAEuD;IACvD,YADS,OAAO,iBAAiB,EAAE,cAAc,EAAE,CACQ;IAG7D;;;OAGG;IACH,SAFa,IAAI,CAgChB;IAED;;;;;;OAMG;IACH,gBAHW,OAAO,iBAAiB,EAAE,aAAa,GACrC,IAAI,CAQhB;IAED;;;;;;;;;;;;OAYG;IACH,gBAHW,OAAO,iBAAiB,EAAE,aAAa,GACrC,IAAI,CAQhB;IAED;;;;;;;;OAQG;IACH,sBAHc,MAAM,EAAA,GACP,MAAM,CAIlB;IAED;;;OAGG;IACH,SAFa,OAAO,CAAC,MAAM,CAAC,
|
|
1
|
+
{"version":3,"file":"model-class-query.d.ts","sourceRoot":"","sources":["../../../../src/database/query/model-class-query.js"],"names":[],"mappings":"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"}
|