@mikro-orm/knex 6.0.0-dev.26 → 6.0.0-dev.27
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/AbstractSqlDriver.js +8 -8
- package/index.mjs +1 -1
- package/package.json +2 -2
- package/query/CriteriaNode.js +8 -8
- package/query/CriteriaNodeFactory.js +3 -3
- package/query/ObjectCriteriaNode.js +5 -5
- package/query/QueryBuilder.js +8 -8
- package/query/QueryBuilderHelper.js +3 -3
- package/query/ScalarCriteriaNode.js +6 -6
- package/schema/DatabaseSchema.js +3 -3
- package/schema/DatabaseTable.d.ts +1 -1
- package/schema/DatabaseTable.js +16 -16
package/AbstractSqlDriver.js
CHANGED
|
@@ -166,7 +166,7 @@ class AbstractSqlDriver extends core_1.DatabaseDriver {
|
|
|
166
166
|
}));
|
|
167
167
|
if (!hasPK) {
|
|
168
168
|
// initialize empty collections
|
|
169
|
-
if ([core_1.
|
|
169
|
+
if ([core_1.ReferenceKind.MANY_TO_MANY, core_1.ReferenceKind.ONE_TO_MANY].includes(relation.kind)) {
|
|
170
170
|
result[relation.name] = result[relation.name] || [];
|
|
171
171
|
}
|
|
172
172
|
return;
|
|
@@ -191,7 +191,7 @@ class AbstractSqlDriver extends core_1.DatabaseDriver {
|
|
|
191
191
|
else {
|
|
192
192
|
map[key] = result;
|
|
193
193
|
}
|
|
194
|
-
if ([core_1.
|
|
194
|
+
if ([core_1.ReferenceKind.MANY_TO_MANY, core_1.ReferenceKind.ONE_TO_MANY].includes(relation.kind)) {
|
|
195
195
|
result[relation.name] = result[relation.name] || [];
|
|
196
196
|
this.appendToCollection(meta2, result[relation.name], relationPojo);
|
|
197
197
|
}
|
|
@@ -450,7 +450,7 @@ class AbstractSqlDriver extends core_1.DatabaseDriver {
|
|
|
450
450
|
deleteDiff.push(...snapshot);
|
|
451
451
|
insertDiff.push(...current);
|
|
452
452
|
}
|
|
453
|
-
if (coll.property.
|
|
453
|
+
if (coll.property.kind === core_1.ReferenceKind.ONE_TO_MANY) {
|
|
454
454
|
const cols = coll.property.referencedColumnNames;
|
|
455
455
|
const qb = this.createQueryBuilder(coll.property.type, ctx, 'write')
|
|
456
456
|
.withSchema(this.getSchemaName(meta, options))
|
|
@@ -532,7 +532,7 @@ class AbstractSqlDriver extends core_1.DatabaseDriver {
|
|
|
532
532
|
}
|
|
533
533
|
const relationsToPopulate = populate.map(({ field }) => field);
|
|
534
534
|
const toPopulate = meta.relations
|
|
535
|
-
.filter(prop => prop.
|
|
535
|
+
.filter(prop => prop.kind === core_1.ReferenceKind.ONE_TO_ONE && !prop.owner && !relationsToPopulate.includes(prop.name))
|
|
536
536
|
.filter(prop => fields.length === 0 || fields.some(f => prop.name === f || prop.name.startsWith(`${String(f)}.`)))
|
|
537
537
|
.map(prop => ({ field: prop.name, strategy: prop.strategy }));
|
|
538
538
|
return [...populate, ...toPopulate];
|
|
@@ -540,7 +540,7 @@ class AbstractSqlDriver extends core_1.DatabaseDriver {
|
|
|
540
540
|
joinedProps(meta, populate) {
|
|
541
541
|
return populate.filter(p => {
|
|
542
542
|
const prop = meta.properties[p.field] || {};
|
|
543
|
-
return (p.strategy || prop.strategy || this.config.get('loadStrategy')) === core_1.LoadStrategy.JOINED && prop.
|
|
543
|
+
return (p.strategy || prop.strategy || this.config.get('loadStrategy')) === core_1.LoadStrategy.JOINED && prop.kind !== core_1.ReferenceKind.SCALAR;
|
|
544
544
|
});
|
|
545
545
|
}
|
|
546
546
|
/**
|
|
@@ -643,7 +643,7 @@ class AbstractSqlDriver extends core_1.DatabaseDriver {
|
|
|
643
643
|
}
|
|
644
644
|
const ret = {};
|
|
645
645
|
this.metadata.find(entityName).relations.forEach(prop => {
|
|
646
|
-
if (prop.
|
|
646
|
+
if (prop.kind === core_1.ReferenceKind.MANY_TO_MANY && data[prop.name]) {
|
|
647
647
|
ret[prop.name] = data[prop.name].map((item) => core_1.Utils.asArray(item));
|
|
648
648
|
delete data[prop.name];
|
|
649
649
|
}
|
|
@@ -745,10 +745,10 @@ class AbstractSqlDriver extends core_1.DatabaseDriver {
|
|
|
745
745
|
return ret;
|
|
746
746
|
}
|
|
747
747
|
processField(meta, prop, field, ret, populate, joinedProps, qb) {
|
|
748
|
-
if (!prop || (prop.
|
|
748
|
+
if (!prop || (prop.kind === core_1.ReferenceKind.ONE_TO_ONE && !prop.owner)) {
|
|
749
749
|
return;
|
|
750
750
|
}
|
|
751
|
-
if (prop.
|
|
751
|
+
if (prop.kind === core_1.ReferenceKind.EMBEDDED) {
|
|
752
752
|
if (prop.object) {
|
|
753
753
|
ret.push(prop.fieldNames[0]);
|
|
754
754
|
return;
|
package/index.mjs
CHANGED
|
@@ -136,7 +136,7 @@ export const QueryOrderNumeric = mod.QueryOrderNumeric;
|
|
|
136
136
|
export const QueryType = mod.QueryType;
|
|
137
137
|
export const ReadOnlyException = mod.ReadOnlyException;
|
|
138
138
|
export const Reference = mod.Reference;
|
|
139
|
-
export const
|
|
139
|
+
export const ReferenceKind = mod.ReferenceKind;
|
|
140
140
|
export const ReflectMetadataProvider = mod.ReflectMetadataProvider;
|
|
141
141
|
export const RequestContext = mod.RequestContext;
|
|
142
142
|
export const SCALAR_TYPES = mod.SCALAR_TYPES;
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@mikro-orm/knex",
|
|
3
|
-
"version": "6.0.0-dev.
|
|
3
|
+
"version": "6.0.0-dev.27",
|
|
4
4
|
"description": "TypeScript ORM for Node.js based on Data Mapper, Unit of Work and Identity Map patterns. Supports MongoDB, MySQL, PostgreSQL and SQLite databases as well as usage with vanilla JavaScript.",
|
|
5
5
|
"main": "index.js",
|
|
6
6
|
"module": "index.mjs",
|
|
@@ -66,6 +66,6 @@
|
|
|
66
66
|
"@mikro-orm/core": "^5.6.8"
|
|
67
67
|
},
|
|
68
68
|
"peerDependencies": {
|
|
69
|
-
"@mikro-orm/core": "~6.0.0-dev.
|
|
69
|
+
"@mikro-orm/core": "~6.0.0-dev.27"
|
|
70
70
|
}
|
|
71
71
|
}
|
package/query/CriteriaNode.js
CHANGED
|
@@ -40,7 +40,7 @@ class CriteriaNode {
|
|
|
40
40
|
return false;
|
|
41
41
|
}
|
|
42
42
|
shouldRename(payload) {
|
|
43
|
-
const type = this.prop ? this.prop.
|
|
43
|
+
const type = this.prop ? this.prop.kind : null;
|
|
44
44
|
const composite = this.prop?.joinColumns ? this.prop.joinColumns.length > 1 : false;
|
|
45
45
|
const customExpression = CriteriaNode.isCustomExpression(this.key);
|
|
46
46
|
const scalar = payload === null || core_1.Utils.isPrimaryKey(payload) || payload instanceof RegExp || payload instanceof Date || customExpression;
|
|
@@ -49,17 +49,17 @@ class CriteriaNode {
|
|
|
49
49
|
return true;
|
|
50
50
|
}
|
|
51
51
|
switch (type) {
|
|
52
|
-
case core_1.
|
|
53
|
-
case core_1.
|
|
54
|
-
case core_1.
|
|
55
|
-
case core_1.
|
|
52
|
+
case core_1.ReferenceKind.MANY_TO_ONE: return false;
|
|
53
|
+
case core_1.ReferenceKind.ONE_TO_ONE: return !this.prop.owner;
|
|
54
|
+
case core_1.ReferenceKind.ONE_TO_MANY: return scalar || operator;
|
|
55
|
+
case core_1.ReferenceKind.MANY_TO_MANY: return scalar || operator;
|
|
56
56
|
default: return false;
|
|
57
57
|
}
|
|
58
58
|
}
|
|
59
59
|
renameFieldToPK(qb) {
|
|
60
60
|
const joinAlias = qb.getAliasForJoinPath(this.getPath());
|
|
61
61
|
const alias = joinAlias ?? qb.alias;
|
|
62
|
-
if (this.prop.
|
|
62
|
+
if (this.prop.kind === core_1.ReferenceKind.MANY_TO_MANY) {
|
|
63
63
|
return core_1.Utils.getPrimaryKeyHash(this.prop.inverseJoinColumns.map(col => `${alias}.${col}`));
|
|
64
64
|
}
|
|
65
65
|
// if we found a matching join, we need to use the target table column names, as we use that alias instead of the root
|
|
@@ -70,7 +70,7 @@ class CriteriaNode {
|
|
|
70
70
|
}
|
|
71
71
|
getPath(addIndex = false) {
|
|
72
72
|
// use index on parent only if we are processing to-many relation
|
|
73
|
-
const addParentIndex = this.prop && [core_1.
|
|
73
|
+
const addParentIndex = this.prop && [core_1.ReferenceKind.ONE_TO_MANY, core_1.ReferenceKind.MANY_TO_MANY].includes(this.prop.kind);
|
|
74
74
|
const parentPath = this.parent?.getPath(addParentIndex) ?? this.entityName;
|
|
75
75
|
const index = addIndex && this.index != null ? `[${this.index}]` : '';
|
|
76
76
|
// ignore group operators to allow easier mapping (e.g. for orderBy)
|
|
@@ -89,7 +89,7 @@ class CriteriaNode {
|
|
|
89
89
|
const customExpression = CriteriaNode.isCustomExpression(this.key);
|
|
90
90
|
const scalar = this.payload === null || core_1.Utils.isPrimaryKey(this.payload) || this.payload instanceof RegExp || this.payload instanceof Date || customExpression;
|
|
91
91
|
const operator = core_1.Utils.isObject(this.payload) && Object.keys(this.payload).every(k => core_1.Utils.isOperator(k, false));
|
|
92
|
-
return this.prop.
|
|
92
|
+
return this.prop.kind === core_1.ReferenceKind.MANY_TO_MANY && (scalar || operator);
|
|
93
93
|
}
|
|
94
94
|
getPivotPath(path) {
|
|
95
95
|
return `${path}[pivot]`;
|
|
@@ -37,7 +37,7 @@ class CriteriaNodeFactory {
|
|
|
37
37
|
}
|
|
38
38
|
static createObjectNode(metadata, entityName, payload, parent, key) {
|
|
39
39
|
const meta = metadata.find(entityName);
|
|
40
|
-
if (!parent && Object.keys(payload).every(k => meta?.properties[k]?.
|
|
40
|
+
if (!parent && Object.keys(payload).every(k => meta?.properties[k]?.kind === core_1.ReferenceKind.SCALAR)) {
|
|
41
41
|
return this.createScalarNode(metadata, entityName, payload, parent, key);
|
|
42
42
|
}
|
|
43
43
|
const node = new ObjectCriteriaNode_1.ObjectCriteriaNode(metadata, entityName, parent, key);
|
|
@@ -49,8 +49,8 @@ class CriteriaNodeFactory {
|
|
|
49
49
|
}
|
|
50
50
|
static createObjectItemNode(metadata, entityName, node, payload, item, meta) {
|
|
51
51
|
const prop = meta?.properties[item];
|
|
52
|
-
if (prop?.
|
|
53
|
-
const childEntity = prop && prop.
|
|
52
|
+
if (prop?.kind !== core_1.ReferenceKind.EMBEDDED) {
|
|
53
|
+
const childEntity = prop && prop.kind !== core_1.ReferenceKind.SCALAR ? prop.type : entityName;
|
|
54
54
|
return this.createNode(metadata, childEntity, payload[item], node, item);
|
|
55
55
|
}
|
|
56
56
|
const operator = Object.keys(payload[item]).some(f => core_1.Utils.isOperator(f));
|
|
@@ -60,7 +60,7 @@ class ObjectCriteriaNode extends CriteriaNode_1.CriteriaNode {
|
|
|
60
60
|
const customExpression = ObjectCriteriaNode.isCustomExpression(this.key);
|
|
61
61
|
const scalar = core_1.Utils.isPrimaryKey(payload) || payload instanceof RegExp || payload instanceof Date || customExpression;
|
|
62
62
|
const operator = core_1.Utils.isObject(payload) && Object.keys(payload).every(k => core_1.Utils.isOperator(k, false));
|
|
63
|
-
return !!this.prop && this.prop.
|
|
63
|
+
return !!this.prop && this.prop.kind !== core_1.ReferenceKind.SCALAR && !scalar && !operator;
|
|
64
64
|
}
|
|
65
65
|
inlineChildPayload(o, payload, field, alias, childAlias) {
|
|
66
66
|
const prop = this.metadata.find(this.entityName).properties[field];
|
|
@@ -104,15 +104,15 @@ class ObjectCriteriaNode extends CriteriaNode_1.CriteriaNode {
|
|
|
104
104
|
if (!this.prop || !this.parent) {
|
|
105
105
|
return false;
|
|
106
106
|
}
|
|
107
|
-
const embeddable = this.prop.
|
|
108
|
-
const knownKey = [core_1.
|
|
107
|
+
const embeddable = this.prop.kind === core_1.ReferenceKind.EMBEDDED;
|
|
108
|
+
const knownKey = [core_1.ReferenceKind.SCALAR, core_1.ReferenceKind.MANY_TO_ONE, core_1.ReferenceKind.EMBEDDED].includes(this.prop.kind) || (this.prop.kind === core_1.ReferenceKind.ONE_TO_ONE && this.prop.owner);
|
|
109
109
|
const operatorKeys = knownKey && Object.keys(this.payload).every(key => core_1.Utils.isOperator(key, false));
|
|
110
110
|
const primaryKeys = knownKey && Object.keys(this.payload).every(key => {
|
|
111
111
|
const meta = this.metadata.find(this.entityName);
|
|
112
112
|
if (!meta.primaryKeys.includes(key)) {
|
|
113
113
|
return false;
|
|
114
114
|
}
|
|
115
|
-
if (!core_1.Utils.isPlainObject(this.payload[key].payload) || ![core_1.
|
|
115
|
+
if (!core_1.Utils.isPlainObject(this.payload[key].payload) || ![core_1.ReferenceKind.ONE_TO_ONE, core_1.ReferenceKind.MANY_TO_ONE].includes(meta.properties[key].kind)) {
|
|
116
116
|
return true;
|
|
117
117
|
}
|
|
118
118
|
return Object.keys(this.payload[key].payload).every(k => meta.properties[key].targetMeta.primaryKeys.includes(k));
|
|
@@ -125,7 +125,7 @@ class ObjectCriteriaNode extends CriteriaNode_1.CriteriaNode {
|
|
|
125
125
|
const scalar = core_1.Utils.isPrimaryKey(this.payload) || this.payload instanceof RegExp || this.payload instanceof Date || customExpression;
|
|
126
126
|
const operator = core_1.Utils.isPlainObject(this.payload) && Object.keys(this.payload).every(k => core_1.Utils.isOperator(k, false));
|
|
127
127
|
const field = `${alias}.${this.prop.name}`;
|
|
128
|
-
if (this.prop.
|
|
128
|
+
if (this.prop.kind === core_1.ReferenceKind.MANY_TO_MANY && (scalar || operator)) {
|
|
129
129
|
qb.join(field, nestedAlias, undefined, 'pivotJoin', this.getPath());
|
|
130
130
|
}
|
|
131
131
|
else {
|
package/query/QueryBuilder.js
CHANGED
|
@@ -581,10 +581,10 @@ class QueryBuilder {
|
|
|
581
581
|
});
|
|
582
582
|
let aliasedName = `${fromAlias}.${prop.name}#${alias}`;
|
|
583
583
|
path ?? (path = `${(Object.values(this._joins).find(j => j.alias === fromAlias)?.path ?? entityName)}.${prop.name}`);
|
|
584
|
-
if (prop.
|
|
584
|
+
if (prop.kind === core_1.ReferenceKind.ONE_TO_MANY) {
|
|
585
585
|
this._joins[aliasedName] = this.helper.joinOneToReference(prop, fromAlias, alias, type, cond);
|
|
586
586
|
}
|
|
587
|
-
else if (prop.
|
|
587
|
+
else if (prop.kind === core_1.ReferenceKind.MANY_TO_MANY) {
|
|
588
588
|
let pivotAlias = alias;
|
|
589
589
|
if (type !== 'pivotJoin') {
|
|
590
590
|
const oldPivotAlias = this.getAliasForJoinPath(path + '[pivot]');
|
|
@@ -595,7 +595,7 @@ class QueryBuilder {
|
|
|
595
595
|
Object.assign(this._joins, joins);
|
|
596
596
|
this.createAlias(prop.pivotEntity, pivotAlias);
|
|
597
597
|
}
|
|
598
|
-
else if (prop.
|
|
598
|
+
else if (prop.kind === core_1.ReferenceKind.ONE_TO_ONE) {
|
|
599
599
|
this._joins[aliasedName] = this.helper.joinOneToReference(prop, fromAlias, alias, type, cond);
|
|
600
600
|
}
|
|
601
601
|
else { // MANY_TO_ONE
|
|
@@ -619,7 +619,7 @@ class QueryBuilder {
|
|
|
619
619
|
const [a, f] = this.helper.splitField(field);
|
|
620
620
|
const prop = this.helper.getProperty(f, a);
|
|
621
621
|
/* istanbul ignore next */
|
|
622
|
-
if (prop && [core_1.
|
|
622
|
+
if (prop && [core_1.ReferenceKind.ONE_TO_MANY, core_1.ReferenceKind.MANY_TO_MANY].includes(prop.kind)) {
|
|
623
623
|
return;
|
|
624
624
|
}
|
|
625
625
|
if (prop?.embedded) {
|
|
@@ -627,7 +627,7 @@ class QueryBuilder {
|
|
|
627
627
|
ret.push(fieldName);
|
|
628
628
|
return;
|
|
629
629
|
}
|
|
630
|
-
if (prop?.
|
|
630
|
+
if (prop?.kind === core_1.ReferenceKind.EMBEDDED) {
|
|
631
631
|
if (prop.object) {
|
|
632
632
|
ret.push(this.helper.mapper(prop.fieldNames[0], this.type));
|
|
633
633
|
}
|
|
@@ -659,7 +659,7 @@ class QueryBuilder {
|
|
|
659
659
|
const cols = this.helper.mapJoinColumns(this.type ?? enums_1.QueryType.SELECT, this._joins[f]);
|
|
660
660
|
ret.push(...cols);
|
|
661
661
|
}
|
|
662
|
-
if (this._joins[f].prop.
|
|
662
|
+
if (this._joins[f].prop.kind !== core_1.ReferenceKind.ONE_TO_ONE && this._joins[f].inverseJoinColumns) {
|
|
663
663
|
this._joins[f].inverseJoinColumns.forEach(inverseJoinColumn => {
|
|
664
664
|
core_1.Utils.renameKey(this._cond, inverseJoinColumn, `${this._joins[f].alias}.${inverseJoinColumn}`);
|
|
665
665
|
});
|
|
@@ -744,7 +744,7 @@ class QueryBuilder {
|
|
|
744
744
|
if (meta && this.flags.has(core_1.QueryFlag.AUTO_JOIN_ONE_TO_ONE_OWNER)) {
|
|
745
745
|
const relationsToPopulate = this._populate.map(({ field }) => field);
|
|
746
746
|
meta.relations
|
|
747
|
-
.filter(prop => prop.
|
|
747
|
+
.filter(prop => prop.kind === core_1.ReferenceKind.ONE_TO_ONE && !prop.owner && !relationsToPopulate.includes(prop.name))
|
|
748
748
|
.map(prop => ({ field: prop.name }))
|
|
749
749
|
.forEach(item => this._populate.push(item));
|
|
750
750
|
}
|
|
@@ -794,7 +794,7 @@ class QueryBuilder {
|
|
|
794
794
|
}
|
|
795
795
|
hasToManyJoins() {
|
|
796
796
|
return Object.values(this._joins).some(join => {
|
|
797
|
-
return [core_1.
|
|
797
|
+
return [core_1.ReferenceKind.ONE_TO_MANY, core_1.ReferenceKind.MANY_TO_MANY].includes(join.prop.kind);
|
|
798
798
|
});
|
|
799
799
|
}
|
|
800
800
|
wrapPaginateSubQuery(meta) {
|
|
@@ -253,7 +253,7 @@ class QueryBuilderHelper {
|
|
|
253
253
|
return `(${parts.join(` ${core_1.GroupOperator[operator]} `)})`;
|
|
254
254
|
}
|
|
255
255
|
mapJoinColumns(type, join) {
|
|
256
|
-
if (join.prop && join.prop.
|
|
256
|
+
if (join.prop && join.prop.kind === core_1.ReferenceKind.ONE_TO_ONE && !join.prop.owner) {
|
|
257
257
|
return join.prop.fieldNames.map((fieldName, idx) => {
|
|
258
258
|
return this.mapper(`${join.alias}.${join.inverseJoinColumns[idx]}`, type, undefined, fieldName);
|
|
259
259
|
});
|
|
@@ -266,7 +266,7 @@ class QueryBuilderHelper {
|
|
|
266
266
|
isOneToOneInverse(field) {
|
|
267
267
|
const meta = this.metadata.find(this.entityName);
|
|
268
268
|
const prop = meta.properties[field];
|
|
269
|
-
return prop && prop.
|
|
269
|
+
return prop && prop.kind === core_1.ReferenceKind.ONE_TO_ONE && !prop.owner;
|
|
270
270
|
}
|
|
271
271
|
getTableName(entityName) {
|
|
272
272
|
const meta = this.metadata.find(entityName);
|
|
@@ -577,7 +577,7 @@ class QueryBuilderHelper {
|
|
|
577
577
|
// check if `alias` is not matching an embedded property name instead of alias, e.g. `address.city`
|
|
578
578
|
if (alias && meta) {
|
|
579
579
|
const prop = meta.properties[alias];
|
|
580
|
-
if (prop?.
|
|
580
|
+
if (prop?.kind === core_1.ReferenceKind.EMBEDDED) {
|
|
581
581
|
// we want to select the full object property so hydration works as expected
|
|
582
582
|
if (prop.object) {
|
|
583
583
|
return prop;
|
|
@@ -13,10 +13,10 @@ class ScalarCriteriaNode extends CriteriaNode_1.CriteriaNode {
|
|
|
13
13
|
const parentPath = this.parent.getPath(); // the parent is always there, otherwise `shouldJoin` would return `false`
|
|
14
14
|
const nestedAlias = qb.getAliasForJoinPath(path) || qb.getNextAlias(this.prop?.pivotTable ?? this.entityName);
|
|
15
15
|
const field = `${alias}.${this.prop.name}`;
|
|
16
|
-
const type = this.prop.
|
|
16
|
+
const type = this.prop.kind === core_1.ReferenceKind.MANY_TO_MANY ? 'pivotJoin' : 'leftJoin';
|
|
17
17
|
qb.join(field, nestedAlias, undefined, type, path);
|
|
18
18
|
// select the owner as virtual property when joining from 1:1 inverse side, but only if the parent is root entity
|
|
19
|
-
if (this.prop.
|
|
19
|
+
if (this.prop.kind === core_1.ReferenceKind.ONE_TO_ONE && !parentPath.includes('.')) {
|
|
20
20
|
qb.addSelect(field);
|
|
21
21
|
}
|
|
22
22
|
}
|
|
@@ -26,10 +26,10 @@ class ScalarCriteriaNode extends CriteriaNode_1.CriteriaNode {
|
|
|
26
26
|
if (!this.parent || !this.prop) {
|
|
27
27
|
return false;
|
|
28
28
|
}
|
|
29
|
-
switch (this.prop.
|
|
30
|
-
case core_1.
|
|
31
|
-
case core_1.
|
|
32
|
-
case core_1.
|
|
29
|
+
switch (this.prop.kind) {
|
|
30
|
+
case core_1.ReferenceKind.ONE_TO_MANY: return true;
|
|
31
|
+
case core_1.ReferenceKind.MANY_TO_MANY: return true;
|
|
32
|
+
case core_1.ReferenceKind.ONE_TO_ONE: return !this.prop.owner;
|
|
33
33
|
default: return false; // SCALAR, MANY_TO_ONE
|
|
34
34
|
}
|
|
35
35
|
}
|
package/schema/DatabaseSchema.js
CHANGED
|
@@ -78,15 +78,15 @@ class DatabaseSchema {
|
|
|
78
78
|
if (prop.persist === false || !prop.fieldNames) {
|
|
79
79
|
return false;
|
|
80
80
|
}
|
|
81
|
-
if (meta.pivotTable || (core_1.
|
|
81
|
+
if (meta.pivotTable || (core_1.ReferenceKind.EMBEDDED && prop.object)) {
|
|
82
82
|
return true;
|
|
83
83
|
}
|
|
84
84
|
const getRootProperty = (prop) => prop.embedded ? getRootProperty(meta.properties[prop.embedded[0]]) : prop;
|
|
85
85
|
const rootProp = getRootProperty(prop);
|
|
86
|
-
if (rootProp.
|
|
86
|
+
if (rootProp.kind === core_1.ReferenceKind.EMBEDDED) {
|
|
87
87
|
return prop === rootProp || !rootProp.object;
|
|
88
88
|
}
|
|
89
|
-
return [core_1.
|
|
89
|
+
return [core_1.ReferenceKind.SCALAR, core_1.ReferenceKind.MANY_TO_ONE].includes(prop.kind) || (prop.kind === core_1.ReferenceKind.ONE_TO_ONE && prop.owner);
|
|
90
90
|
}
|
|
91
91
|
toJSON() {
|
|
92
92
|
const { platform, namespaces, ...rest } = this;
|
|
@@ -37,7 +37,7 @@ export declare class DatabaseTable {
|
|
|
37
37
|
getPrimaryKey(): IndexDef | undefined;
|
|
38
38
|
hasPrimaryKey(): boolean;
|
|
39
39
|
private getPropertyDeclaration;
|
|
40
|
-
private
|
|
40
|
+
private getReferenceKind;
|
|
41
41
|
private getPropertyName;
|
|
42
42
|
private getPropertyType;
|
|
43
43
|
private getPropertyDefaultValue;
|
package/schema/DatabaseTable.js
CHANGED
|
@@ -66,7 +66,7 @@ class DatabaseTable {
|
|
|
66
66
|
if (mappedType instanceof core_1.DateTimeType) {
|
|
67
67
|
prop.length ?? (prop.length = this.platform.getDefaultDateTimeLength());
|
|
68
68
|
}
|
|
69
|
-
const primary = !meta.compositePK && !!prop.primary && prop.
|
|
69
|
+
const primary = !meta.compositePK && !!prop.primary && prop.kind === core_1.ReferenceKind.SCALAR && this.platform.isNumericColumn(mappedType);
|
|
70
70
|
this.columns[field] = {
|
|
71
71
|
name: prop.fieldNames[idx],
|
|
72
72
|
type: prop.columnTypes[idx],
|
|
@@ -88,7 +88,7 @@ class DatabaseTable {
|
|
|
88
88
|
const defaultValue = this.platform.getSchemaHelper().normalizeDefaultValue(prop.defaultRaw, prop.length);
|
|
89
89
|
this.columns[field].default = defaultValue;
|
|
90
90
|
});
|
|
91
|
-
if ([core_1.
|
|
91
|
+
if ([core_1.ReferenceKind.MANY_TO_ONE, core_1.ReferenceKind.ONE_TO_ONE].includes(prop.kind)) {
|
|
92
92
|
const constraintName = this.getIndexName(true, prop.fieldNames, 'foreign');
|
|
93
93
|
let schema = prop.targetMeta.schema === '*' ? this.schema : prop.targetMeta.schema ?? this.schema;
|
|
94
94
|
if (prop.referencedTableName.includes('.')) {
|
|
@@ -102,11 +102,11 @@ class DatabaseTable {
|
|
|
102
102
|
referencedTableName: schema ? `${schema}.${prop.referencedTableName}` : prop.referencedTableName,
|
|
103
103
|
};
|
|
104
104
|
const cascade = prop.cascade.includes(core_1.Cascade.REMOVE) || prop.cascade.includes(core_1.Cascade.ALL);
|
|
105
|
-
if (prop.
|
|
106
|
-
this.foreignKeys[constraintName].deleteRule = prop.
|
|
105
|
+
if (prop.deleteRule || cascade || prop.nullable) {
|
|
106
|
+
this.foreignKeys[constraintName].deleteRule = prop.deleteRule || (cascade ? 'cascade' : 'set null');
|
|
107
107
|
}
|
|
108
|
-
if (prop.
|
|
109
|
-
this.foreignKeys[constraintName].updateRule = prop.
|
|
108
|
+
if (prop.updateRule || prop.cascade.includes(core_1.Cascade.PERSIST) || prop.cascade.includes(core_1.Cascade.ALL)) {
|
|
109
|
+
this.foreignKeys[constraintName].updateRule = prop.updateRule || 'cascade';
|
|
110
110
|
}
|
|
111
111
|
}
|
|
112
112
|
if (prop.index) {
|
|
@@ -164,8 +164,8 @@ class DatabaseTable {
|
|
|
164
164
|
}
|
|
165
165
|
const meta = schema.init().meta;
|
|
166
166
|
meta.relations
|
|
167
|
-
.filter(prop => prop.primary && prop.
|
|
168
|
-
.forEach(prop => prop.
|
|
167
|
+
.filter(prop => prop.primary && prop.kind === core_1.ReferenceKind.MANY_TO_ONE && !meta.compositePK)
|
|
168
|
+
.forEach(prop => prop.kind = core_1.ReferenceKind.ONE_TO_ONE);
|
|
169
169
|
return meta;
|
|
170
170
|
}
|
|
171
171
|
/**
|
|
@@ -206,20 +206,20 @@ class DatabaseTable {
|
|
|
206
206
|
const prop = this.getPropertyName(namingStrategy, column);
|
|
207
207
|
const index = compositeFkIndexes[prop] || this.indexes.find(idx => idx.columnNames[0] === column.name && !idx.composite && !idx.unique && !idx.primary);
|
|
208
208
|
const unique = compositeFkUniques[prop] || this.indexes.find(idx => idx.columnNames[0] === column.name && !idx.composite && idx.unique && !idx.primary);
|
|
209
|
-
const
|
|
209
|
+
const kind = this.getReferenceKind(fk, unique);
|
|
210
210
|
const type = this.getPropertyType(namingStrategy, column, fk);
|
|
211
211
|
const fkOptions = {};
|
|
212
212
|
if (fk) {
|
|
213
213
|
fkOptions.fieldNames = fk.columnNames;
|
|
214
214
|
fkOptions.referencedTableName = fk.referencedTableName;
|
|
215
215
|
fkOptions.referencedColumnNames = fk.referencedColumnNames;
|
|
216
|
-
fkOptions.
|
|
217
|
-
fkOptions.
|
|
216
|
+
fkOptions.updateRule = fk.updateRule?.toLowerCase();
|
|
217
|
+
fkOptions.deleteRule = fk.deleteRule?.toLowerCase();
|
|
218
218
|
}
|
|
219
219
|
return {
|
|
220
220
|
name: prop,
|
|
221
221
|
type,
|
|
222
|
-
|
|
222
|
+
kind,
|
|
223
223
|
columnType: column.type,
|
|
224
224
|
default: this.getPropertyDefaultValue(schemaHelper, column, type),
|
|
225
225
|
defaultRaw: this.getPropertyDefaultValue(schemaHelper, column, type, true),
|
|
@@ -234,14 +234,14 @@ class DatabaseTable {
|
|
|
234
234
|
...fkOptions,
|
|
235
235
|
};
|
|
236
236
|
}
|
|
237
|
-
|
|
237
|
+
getReferenceKind(fk, unique) {
|
|
238
238
|
if (fk && unique) {
|
|
239
|
-
return core_1.
|
|
239
|
+
return core_1.ReferenceKind.ONE_TO_ONE;
|
|
240
240
|
}
|
|
241
241
|
if (fk) {
|
|
242
|
-
return core_1.
|
|
242
|
+
return core_1.ReferenceKind.MANY_TO_ONE;
|
|
243
243
|
}
|
|
244
|
-
return core_1.
|
|
244
|
+
return core_1.ReferenceKind.SCALAR;
|
|
245
245
|
}
|
|
246
246
|
getPropertyName(namingStrategy, column) {
|
|
247
247
|
const fk = Object.values(this.foreignKeys).find(fk => fk.columnNames.includes(column.name));
|