@mikro-orm/core 7.0.0-dev.300 → 7.0.0-dev.302

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.
Files changed (61) hide show
  1. package/EntityManager.d.ts +1 -1
  2. package/EntityManager.js +94 -43
  3. package/MikroORM.js +4 -4
  4. package/cache/FileCacheAdapter.js +1 -3
  5. package/connections/Connection.js +16 -3
  6. package/drivers/DatabaseDriver.js +25 -7
  7. package/entity/Collection.js +43 -17
  8. package/entity/EntityAssigner.js +23 -11
  9. package/entity/EntityFactory.js +32 -12
  10. package/entity/EntityHelper.js +12 -8
  11. package/entity/EntityLoader.js +55 -22
  12. package/entity/Reference.d.ts +1 -1
  13. package/entity/Reference.js +37 -8
  14. package/entity/WrappedEntity.js +5 -1
  15. package/entity/defineEntity.d.ts +5 -7
  16. package/entity/utils.js +28 -26
  17. package/entity/validators.js +2 -1
  18. package/enums.js +12 -17
  19. package/errors.js +18 -8
  20. package/events/EventManager.js +1 -1
  21. package/exceptions.js +7 -2
  22. package/hydration/ObjectHydrator.js +27 -13
  23. package/index.d.ts +1 -1
  24. package/index.js +1 -1
  25. package/logging/DefaultLogger.js +3 -5
  26. package/logging/colors.js +3 -6
  27. package/metadata/EntitySchema.js +12 -2
  28. package/metadata/MetadataDiscovery.js +101 -46
  29. package/metadata/MetadataProvider.js +6 -1
  30. package/metadata/MetadataStorage.js +1 -3
  31. package/metadata/MetadataValidator.js +20 -5
  32. package/metadata/types.d.ts +2 -2
  33. package/naming-strategy/AbstractNamingStrategy.js +5 -2
  34. package/not-supported.js +5 -1
  35. package/package.json +38 -38
  36. package/platforms/Platform.js +46 -23
  37. package/serialization/EntitySerializer.js +7 -3
  38. package/serialization/SerializationContext.js +1 -1
  39. package/typings.d.ts +23 -23
  40. package/typings.js +9 -9
  41. package/unit-of-work/ChangeSet.js +4 -4
  42. package/unit-of-work/ChangeSetComputer.js +8 -6
  43. package/unit-of-work/ChangeSetPersister.js +13 -8
  44. package/unit-of-work/CommitOrderCalculator.js +4 -2
  45. package/unit-of-work/UnitOfWork.d.ts +7 -1
  46. package/unit-of-work/UnitOfWork.js +51 -22
  47. package/utils/AbstractMigrator.js +3 -5
  48. package/utils/AbstractSchemaGenerator.js +2 -1
  49. package/utils/AsyncContext.js +1 -1
  50. package/utils/Configuration.js +8 -4
  51. package/utils/Cursor.js +4 -2
  52. package/utils/DataloaderUtils.js +15 -12
  53. package/utils/EntityComparator.js +51 -43
  54. package/utils/QueryHelper.js +38 -26
  55. package/utils/RawQueryFragment.js +3 -2
  56. package/utils/TransactionManager.js +2 -1
  57. package/utils/Utils.d.ts +1 -1
  58. package/utils/Utils.js +36 -30
  59. package/utils/env-vars.js +6 -5
  60. package/utils/fs-utils.js +2 -5
  61. package/utils/upsert-utils.js +6 -3
@@ -33,7 +33,9 @@ export class MetadataDiscovery {
33
33
  async discover(preferTs = true) {
34
34
  this.discovered.length = 0;
35
35
  const startTime = Date.now();
36
- const suffix = this.metadataProvider.constructor === MetadataProvider ? '' : `, using ${colors.cyan(this.metadataProvider.constructor.name)}`;
36
+ const suffix = this.metadataProvider.constructor === MetadataProvider
37
+ ? ''
38
+ : `, using ${colors.cyan(this.metadataProvider.constructor.name)}`;
37
39
  this.logger.log('discovery', `ORM entity discovery started${suffix}`);
38
40
  await this.findEntities(preferTs);
39
41
  for (const meta of this.discovered) {
@@ -51,7 +53,9 @@ export class MetadataDiscovery {
51
53
  discoverSync() {
52
54
  this.discovered.length = 0;
53
55
  const startTime = Date.now();
54
- const suffix = this.metadataProvider.constructor === MetadataProvider ? '' : `, using ${colors.cyan(this.metadataProvider.constructor.name)}`;
56
+ const suffix = this.metadataProvider.constructor === MetadataProvider
57
+ ? ''
58
+ : `, using ${colors.cyan(this.metadataProvider.constructor.name)}`;
55
59
  this.logger.log('discovery', `ORM entity discovery started${suffix} in sync mode`);
56
60
  const refs = this.config.get('entities');
57
61
  this.discoverReferences(refs);
@@ -127,7 +131,7 @@ export class MetadataDiscovery {
127
131
  // ignore base entities (not annotated with @Entity)
128
132
  const filtered = discovered.filter(meta => meta.root.name);
129
133
  // sort so we discover entities first to get around issues with nested embeddables
130
- filtered.sort((a, b) => !a.embeddable === !b.embeddable ? 0 : (a.embeddable ? 1 : -1));
134
+ filtered.sort((a, b) => (!a.embeddable === !b.embeddable ? 0 : a.embeddable ? 1 : -1));
131
135
  filtered.forEach(meta => this.initSingleTableInheritance(meta, filtered));
132
136
  filtered.forEach(meta => this.initTPTRelationships(meta, filtered));
133
137
  filtered.forEach(meta => this.defineBaseEntityProperties(meta));
@@ -176,7 +180,7 @@ export class MetadataDiscovery {
176
180
  }
177
181
  async findEntities(preferTs) {
178
182
  const { entities, entitiesTs, baseDir } = this.config.getAll();
179
- const targets = (preferTs && entitiesTs.length > 0) ? entitiesTs : entities;
183
+ const targets = preferTs && entitiesTs.length > 0 ? entitiesTs : entities;
180
184
  const processed = [];
181
185
  const paths = [];
182
186
  for (const entity of targets) {
@@ -189,7 +193,7 @@ export class MetadataDiscovery {
189
193
  }
190
194
  if (paths.length > 0) {
191
195
  const { discoverEntities } = await import('@mikro-orm/core/file-discovery');
192
- processed.push(...await discoverEntities(paths, { baseDir }));
196
+ processed.push(...(await discoverEntities(paths, { baseDir })));
193
197
  }
194
198
  return this.discoverReferences(processed);
195
199
  }
@@ -210,10 +214,10 @@ export class MetadataDiscovery {
210
214
  }
211
215
  }
212
216
  if (prop.kind !== ReferenceKind.SCALAR) {
213
- const target = typeof prop.entity === 'function' && !prop.entity.prototype
214
- ? prop.entity()
215
- : prop.type;
216
- if (!unwrap(prop.type).split(/ ?\| ?/).every(type => this.discovered.find(m => m.className === type))) {
217
+ const target = typeof prop.entity === 'function' && !prop.entity.prototype ? prop.entity() : prop.type;
218
+ if (!unwrap(prop.type)
219
+ .split(/ ?\| ?/)
220
+ .every(type => this.discovered.find(m => m.className === type))) {
217
221
  missing.push(...Utils.asArray(target));
218
222
  }
219
223
  }
@@ -305,7 +309,8 @@ export class MetadataDiscovery {
305
309
  }
306
310
  getRootEntity(meta) {
307
311
  const base = meta.extends && this.metadata.find(meta.extends);
308
- if (!base || base === meta) { // make sure we do not fall into infinite loop
312
+ if (!base || base === meta) {
313
+ // make sure we do not fall into infinite loop
309
314
  return meta;
310
315
  }
311
316
  const root = this.getRootEntity(base);
@@ -365,7 +370,10 @@ export class MetadataDiscovery {
365
370
  initOwnColumns(meta) {
366
371
  meta.sync();
367
372
  for (const prop of meta.props) {
368
- if (!prop.joinColumns || !prop.columnTypes || prop.ownColumns || ![ReferenceKind.MANY_TO_ONE, ReferenceKind.ONE_TO_ONE].includes(prop.kind)) {
373
+ if (!prop.joinColumns ||
374
+ !prop.columnTypes ||
375
+ prop.ownColumns ||
376
+ ![ReferenceKind.MANY_TO_ONE, ReferenceKind.ONE_TO_ONE].includes(prop.kind)) {
369
377
  continue;
370
378
  }
371
379
  // For polymorphic relations, ownColumns should include all fieldNames
@@ -553,7 +561,8 @@ export class MetadataDiscovery {
553
561
  this.initRelation(prop);
554
562
  }
555
563
  this.initOwnColumns(meta);
556
- meta.simplePK = pks.length === 1 && pks[0].kind === ReferenceKind.SCALAR && !pks[0].customType && pks[0].runtimeType !== 'Date';
564
+ meta.simplePK =
565
+ pks.length === 1 && pks[0].kind === ReferenceKind.SCALAR && !pks[0].customType && pks[0].runtimeType !== 'Date';
557
566
  meta.serializedPrimaryKey ??= meta.props.find(prop => prop.serializedPrimaryKey)?.name;
558
567
  if (meta.serializedPrimaryKey && meta.serializedPrimaryKey !== meta.primaryKeys[0]) {
559
568
  meta.properties[meta.serializedPrimaryKey].persist ??= false;
@@ -685,7 +694,8 @@ export class MetadataDiscovery {
685
694
  pivotMeta2.compositePK = true;
686
695
  }
687
696
  // handle self-referenced m:n with same default field names
688
- if (meta.className === targetType && prop.joinColumns.every((joinColumn, idx) => joinColumn === prop.inverseJoinColumns[idx])) {
697
+ if (meta.className === targetType &&
698
+ prop.joinColumns.every((joinColumn, idx) => joinColumn === prop.inverseJoinColumns[idx])) {
689
699
  // use tableName only when explicitly provided by user, otherwise use className for backwards compatibility
690
700
  const baseName = this.isExplicitTableName(meta) ? meta.tableName : meta.className;
691
701
  prop.joinColumns = prop.referencedColumnNames.map(name => this.namingStrategy.joinKeyColumnName(baseName + '_1', name, meta.compositePK));
@@ -775,7 +785,9 @@ export class MetadataDiscovery {
775
785
  if (isCompositePK) {
776
786
  // Create separate properties for each PK column (nullable for other entity types)
777
787
  for (let i = 0; i < prop.joinColumns.length; i++) {
778
- pivotMeta.properties[prop.joinColumns[i]] = this.createPivotScalarProperty(prop.joinColumns[i], [columnTypes[i]]);
788
+ pivotMeta.properties[prop.joinColumns[i]] = this.createPivotScalarProperty(prop.joinColumns[i], [
789
+ columnTypes[i],
790
+ ]);
779
791
  }
780
792
  // Virtual property combining all columns (for compatibility)
781
793
  pivotMeta.properties[prop.discriminator] = this.createPivotScalarProperty(prop.discriminator, columnTypes, [...prop.joinColumns], { type: meta.className, persist: false });
@@ -915,7 +927,8 @@ export class MetadataDiscovery {
915
927
  }
916
928
  defineBaseEntityProperties(meta) {
917
929
  const base = meta.extends && this.metadata.get(meta.extends);
918
- if (!base || base === meta) { // make sure we do not fall into infinite loop
930
+ if (!base || base === meta) {
931
+ // make sure we do not fall into infinite loop
919
932
  return 0;
920
933
  }
921
934
  let order = this.defineBaseEntityProperties(base);
@@ -927,10 +940,12 @@ export class MetadataDiscovery {
927
940
  meta.properties[prop.name] = prop;
928
941
  }
929
942
  });
930
- ownProps.forEach(prop => meta.properties[prop.name] = prop);
943
+ ownProps.forEach(prop => (meta.properties[prop.name] = prop));
931
944
  meta.filters = { ...base.filters, ...meta.filters };
932
945
  if (!meta.discriminatorValue) {
933
- Object.values(base.properties).filter(prop => !old.includes(prop.name)).forEach(prop => {
946
+ Object.values(base.properties)
947
+ .filter(prop => !old.includes(prop.name))
948
+ .forEach(prop => {
934
949
  meta.properties[prop.name] = { ...prop };
935
950
  meta.propertyOrder.set(prop.name, (order += 0.01));
936
951
  });
@@ -938,7 +953,9 @@ export class MetadataDiscovery {
938
953
  meta.indexes = Utils.unique([...base.indexes, ...meta.indexes]);
939
954
  meta.uniques = Utils.unique([...base.uniques, ...meta.uniques]);
940
955
  meta.checks = Utils.unique([...base.checks, ...meta.checks]);
941
- const pks = Object.values(meta.properties).filter(p => p.primary).map(p => p.name);
956
+ const pks = Object.values(meta.properties)
957
+ .filter(p => p.primary)
958
+ .map(p => p.name);
942
959
  if (pks.length > 0 && meta.primaryKeys.length === 0) {
943
960
  meta.primaryKeys = pks;
944
961
  }
@@ -971,7 +988,7 @@ export class MetadataDiscovery {
971
988
  properties[prop.name].runtimeType = 'any';
972
989
  return properties[prop.name];
973
990
  }
974
- return properties[prop.name] = prop;
991
+ return (properties[prop.name] = prop);
975
992
  });
976
993
  };
977
994
  const processExtensions = (meta) => {
@@ -989,7 +1006,10 @@ export class MetadataDiscovery {
989
1006
  inlineProperties(meta);
990
1007
  processExtensions(meta);
991
1008
  });
992
- const name = polymorphs.map(t => t.className).sort().join(' | ');
1009
+ const name = polymorphs
1010
+ .map(t => t.className)
1011
+ .sort()
1012
+ .join(' | ');
993
1013
  embeddable = new EntityMetadata({
994
1014
  name,
995
1015
  className: name,
@@ -1001,7 +1021,7 @@ export class MetadataDiscovery {
1001
1021
  });
1002
1022
  embeddable.sync();
1003
1023
  discovered.push(embeddable);
1004
- polymorphs.forEach(meta => meta.root = embeddable);
1024
+ polymorphs.forEach(meta => (meta.root = embeddable));
1005
1025
  }
1006
1026
  }
1007
1027
  initPolymorphicRelation(meta, prop, discovered) {
@@ -1171,7 +1191,7 @@ export class MetadataDiscovery {
1171
1191
  const map = meta.root.discriminatorMap;
1172
1192
  Object.keys(map)
1173
1193
  .filter(key => typeof map[key] === 'string')
1174
- .forEach(key => map[key] = this.metadata.getByClassName(map[key]).class);
1194
+ .forEach(key => (map[key] = this.metadata.getByClassName(map[key]).class));
1175
1195
  }
1176
1196
  else {
1177
1197
  meta.root.discriminatorMap = {};
@@ -1195,7 +1215,9 @@ export class MetadataDiscovery {
1195
1215
  Object.values(meta.properties).forEach(prop => {
1196
1216
  const newProp = { ...prop };
1197
1217
  const rootProp = meta.root.properties[prop.name];
1198
- if (rootProp && (rootProp.type !== prop.type || (rootProp.fieldNames && prop.fieldNames && !compareArrays(rootProp.fieldNames, prop.fieldNames)))) {
1218
+ if (rootProp &&
1219
+ (rootProp.type !== prop.type ||
1220
+ (rootProp.fieldNames && prop.fieldNames && !compareArrays(rootProp.fieldNames, prop.fieldNames)))) {
1199
1221
  const name = newProp.name;
1200
1222
  this.initFieldName(newProp, newProp.object);
1201
1223
  newProp.renamedFrom = name;
@@ -1210,7 +1232,8 @@ export class MetadataDiscovery {
1210
1232
  // Find which discriminator owns the original fieldNames
1211
1233
  for (const [discValue, childClass] of Object.entries(meta.root.discriminatorMap)) {
1212
1234
  const childMeta = this.metadata.find(childClass);
1213
- if (childMeta?.properties[prop.name]?.fieldNames && compareArrays(childMeta.properties[prop.name].fieldNames, rootProp.fieldNames)) {
1235
+ if (childMeta?.properties[prop.name]?.fieldNames &&
1236
+ compareArrays(childMeta.properties[prop.name].fieldNames, rootProp.fieldNames)) {
1214
1237
  rootProp.stiFieldNameMap[discValue] = rootProp.fieldNames[0];
1215
1238
  break;
1216
1239
  }
@@ -1442,7 +1465,10 @@ export class MetadataDiscovery {
1442
1465
  }
1443
1466
  if (this.platform.usesEnumCheckConstraints() && !meta.embeddable) {
1444
1467
  for (const prop of meta.props) {
1445
- if (prop.enum && prop.persist !== false && !prop.nativeEnumName && prop.items?.every(item => typeof item === 'string')) {
1468
+ if (prop.enum &&
1469
+ prop.persist !== false &&
1470
+ !prop.nativeEnumName &&
1471
+ prop.items?.every(item => typeof item === 'string')) {
1446
1472
  this.initFieldName(prop);
1447
1473
  meta.checks.push({
1448
1474
  name: this.namingStrategy.indexName(meta.tableName, prop.fieldNames, 'check'),
@@ -1495,7 +1521,11 @@ export class MetadataDiscovery {
1495
1521
  const entity1 = new meta.class();
1496
1522
  const entity2 = new meta.class();
1497
1523
  // we compare the two values by reference, this will discard things like `new Date()` or `Date.now()`
1498
- if (this.config.get('discovery').inferDefaultValues && prop.default === undefined && entity1[prop.name] != null && entity1[prop.name] === entity2[prop.name] && entity1[prop.name] !== now) {
1524
+ if (this.config.get('discovery').inferDefaultValues &&
1525
+ prop.default === undefined &&
1526
+ entity1[prop.name] != null &&
1527
+ entity1[prop.name] === entity2[prop.name] &&
1528
+ entity1[prop.name] !== now) {
1499
1529
  prop.default ??= entity1[prop.name];
1500
1530
  }
1501
1531
  // if the default value is null, infer nullability
@@ -1562,7 +1592,9 @@ export class MetadataDiscovery {
1562
1592
  prop.type = prop.customType.constructor.name;
1563
1593
  }
1564
1594
  // `prop.type` might also be custom type class (not instance), so `typeof MyType` will give us `function`, not `object`
1565
- if (typeof prop.type === 'function' && Type.isMappedType(prop.type.prototype) && !prop.customType) {
1595
+ if (typeof prop.type === 'function' &&
1596
+ Type.isMappedType(prop.type.prototype) &&
1597
+ !prop.customType) {
1566
1598
  // if the type is an ORM defined mapped type without `ensureComparable: true`,
1567
1599
  // we use just the type name, to have more performant hydration code
1568
1600
  const type = Utils.keys(t).find(type => {
@@ -1582,7 +1614,10 @@ export class MetadataDiscovery {
1582
1614
  if (!prop.customType && ['json', 'jsonb'].includes(prop.type?.toLowerCase())) {
1583
1615
  prop.customType = new t.json();
1584
1616
  }
1585
- if (prop.kind === ReferenceKind.SCALAR && !prop.customType && prop.columnTypes && ['json', 'jsonb'].includes(prop.columnTypes[0])) {
1617
+ if (prop.kind === ReferenceKind.SCALAR &&
1618
+ !prop.customType &&
1619
+ prop.columnTypes &&
1620
+ ['json', 'jsonb'].includes(prop.columnTypes[0])) {
1586
1621
  prop.customType = new t.json();
1587
1622
  }
1588
1623
  if (prop.kind === ReferenceKind.EMBEDDED && !prop.customType && (prop.object || prop.array)) {
@@ -1613,10 +1648,12 @@ export class MetadataDiscovery {
1613
1648
  if (prop.fieldNames?.length === 1 && !prop.customType) {
1614
1649
  [t.bigint, t.double, t.decimal, t.interval, t.date]
1615
1650
  .filter(type => mappedType instanceof type)
1616
- .forEach((type) => prop.customType = new type());
1651
+ .forEach((type) => (prop.customType = new type()));
1617
1652
  }
1618
1653
  if (prop.customType && !prop.columnTypes) {
1619
- const mappedType = this.getMappedType({ columnTypes: [prop.customType.getColumnType(prop, this.platform)] });
1654
+ const mappedType = this.getMappedType({
1655
+ columnTypes: [prop.customType.getColumnType(prop, this.platform)],
1656
+ });
1620
1657
  if (prop.customType.compareAsType() === 'any' && ![t.json].some(t => prop.customType instanceof t)) {
1621
1658
  prop.runtimeType ??= mappedType.runtimeType;
1622
1659
  }
@@ -1635,23 +1672,33 @@ export class MetadataDiscovery {
1635
1672
  prop.customType.meta = meta;
1636
1673
  prop.customType.prop = prop;
1637
1674
  prop.columnTypes ??= [prop.customType.getColumnType(prop, this.platform)];
1638
- prop.hasConvertToJSValueSQL = !!prop.customType.convertToJSValueSQL && prop.customType.convertToJSValueSQL('', this.platform) !== '';
1639
- prop.hasConvertToDatabaseValueSQL = !!prop.customType.convertToDatabaseValueSQL && prop.customType.convertToDatabaseValueSQL('', this.platform) !== '';
1640
- if (prop.customType instanceof t.bigint && ['string', 'bigint', 'number'].includes(prop.runtimeType.toLowerCase())) {
1675
+ prop.hasConvertToJSValueSQL =
1676
+ !!prop.customType.convertToJSValueSQL && prop.customType.convertToJSValueSQL('', this.platform) !== '';
1677
+ prop.hasConvertToDatabaseValueSQL =
1678
+ !!prop.customType.convertToDatabaseValueSQL &&
1679
+ prop.customType.convertToDatabaseValueSQL('', this.platform) !== '';
1680
+ if (prop.customType instanceof t.bigint &&
1681
+ ['string', 'bigint', 'number'].includes(prop.runtimeType.toLowerCase())) {
1641
1682
  prop.customType.mode = prop.runtimeType.toLowerCase();
1642
1683
  }
1643
1684
  }
1644
1685
  if (Type.isMappedType(prop.customType) && prop.kind === ReferenceKind.SCALAR && !isArray) {
1645
1686
  prop.type = prop.customType.name;
1646
1687
  }
1647
- if (!prop.customType && [ReferenceKind.ONE_TO_ONE, ReferenceKind.MANY_TO_ONE].includes(prop.kind) && !prop.polymorphic && prop.targetMeta.compositePK) {
1688
+ if (!prop.customType &&
1689
+ [ReferenceKind.ONE_TO_ONE, ReferenceKind.MANY_TO_ONE].includes(prop.kind) &&
1690
+ !prop.polymorphic &&
1691
+ prop.targetMeta.compositePK) {
1648
1692
  prop.customTypes = [];
1649
1693
  for (const pk of prop.targetMeta.getPrimaryProps()) {
1650
1694
  if (pk.customType) {
1651
1695
  prop.customTypes.push(pk.customType);
1652
- prop.hasConvertToJSValueSQL ||= !!pk.customType.convertToJSValueSQL && pk.customType.convertToJSValueSQL('', this.platform) !== '';
1696
+ prop.hasConvertToJSValueSQL ||=
1697
+ !!pk.customType.convertToJSValueSQL && pk.customType.convertToJSValueSQL('', this.platform) !== '';
1653
1698
  /* v8 ignore next */
1654
- prop.hasConvertToDatabaseValueSQL ||= !!pk.customType.convertToDatabaseValueSQL && pk.customType.convertToDatabaseValueSQL('', this.platform) !== '';
1699
+ prop.hasConvertToDatabaseValueSQL ||=
1700
+ !!pk.customType.convertToDatabaseValueSQL &&
1701
+ pk.customType.convertToDatabaseValueSQL('', this.platform) !== '';
1655
1702
  }
1656
1703
  else {
1657
1704
  prop.customTypes.push(undefined);
@@ -1659,7 +1706,11 @@ export class MetadataDiscovery {
1659
1706
  }
1660
1707
  }
1661
1708
  if (prop.kind === ReferenceKind.SCALAR && !(mappedType instanceof t.unknown)) {
1662
- if (!prop.columnTypes && prop.nativeEnumName && meta.schema !== this.platform.getDefaultSchemaName() && meta.schema && !prop.nativeEnumName.includes('.')) {
1709
+ if (!prop.columnTypes &&
1710
+ prop.nativeEnumName &&
1711
+ meta.schema !== this.platform.getDefaultSchemaName() &&
1712
+ meta.schema &&
1713
+ !prop.nativeEnumName.includes('.')) {
1663
1714
  prop.columnTypes = [`${meta.schema}.${prop.nativeEnumName}`];
1664
1715
  }
1665
1716
  else {
@@ -1686,7 +1737,10 @@ export class MetadataDiscovery {
1686
1737
  }
1687
1738
  // Auto-generate formula for persist: false relations, but only for single-column FKs
1688
1739
  // Composite FK relations need standard JOIN conditions, not formula-based
1689
- if (!prop.formula && prop.persist === false && [ReferenceKind.MANY_TO_ONE, ReferenceKind.ONE_TO_ONE].includes(prop.kind) && !prop.embedded) {
1740
+ if (!prop.formula &&
1741
+ prop.persist === false &&
1742
+ [ReferenceKind.MANY_TO_ONE, ReferenceKind.ONE_TO_ONE].includes(prop.kind) &&
1743
+ !prop.embedded) {
1690
1744
  this.initFieldName(prop);
1691
1745
  if (prop.fieldNames?.length === 1) {
1692
1746
  prop.formula = table => `${table}.${this.platform.quoteIdentifier(prop.fieldNames[0])}`;
@@ -1697,7 +1751,9 @@ export class MetadataDiscovery {
1697
1751
  this.initUnsigned(prop);
1698
1752
  // Get the target properties for FK relations - use targetKey property if specified, otherwise PKs
1699
1753
  const targetProps = prop.targetMeta
1700
- ? (prop.targetKey ? [prop.targetMeta.properties[prop.targetKey]] : prop.targetMeta.getPrimaryProps())
1754
+ ? prop.targetKey
1755
+ ? [prop.targetMeta.properties[prop.targetKey]]
1756
+ : prop.targetMeta.getPrimaryProps()
1701
1757
  : [];
1702
1758
  targetProps.map(targetProp => {
1703
1759
  prop.length ??= targetProp.length;
@@ -1715,11 +1771,11 @@ export class MetadataDiscovery {
1715
1771
  if (prop.kind === ReferenceKind.SCALAR) {
1716
1772
  const mappedType = this.getMappedType(prop);
1717
1773
  const SCALAR_TYPES = ['string', 'number', 'boolean', 'bigint', 'Date', 'Buffer', 'RegExp', 'any', 'unknown'];
1718
- if (mappedType instanceof t.unknown
1774
+ if (mappedType instanceof t.unknown &&
1719
1775
  // it could be a runtime type from reflect-metadata
1720
- && !SCALAR_TYPES.includes(prop.type)
1776
+ !SCALAR_TYPES.includes(prop.type) &&
1721
1777
  // or it might be inferred via ts-morph to some generic type alias
1722
- && !prop.type.match(/[<>:"';{}]/)) {
1778
+ !prop.type.match(/[<>:"';{}]/)) {
1723
1779
  const type = prop.length != null && !prop.type.endsWith(`(${prop.length})`) ? `${prop.type}(${prop.length})` : prop.type;
1724
1780
  prop.columnTypes = [type];
1725
1781
  }
@@ -1736,9 +1792,7 @@ export class MetadataDiscovery {
1736
1792
  const targetMeta = prop.targetMeta;
1737
1793
  prop.columnTypes = [];
1738
1794
  // Use targetKey property if specified, otherwise use primary key properties
1739
- const referencedProps = prop.targetKey
1740
- ? [targetMeta.properties[prop.targetKey]]
1741
- : targetMeta.getPrimaryProps();
1795
+ const referencedProps = prop.targetKey ? [targetMeta.properties[prop.targetKey]] : targetMeta.getPrimaryProps();
1742
1796
  if (prop.polymorphic && prop.polymorphTargets) {
1743
1797
  prop.columnTypes.push(this.platform.getVarcharTypeDeclarationSQL(prop));
1744
1798
  }
@@ -1796,7 +1850,8 @@ export class MetadataDiscovery {
1796
1850
  });
1797
1851
  return;
1798
1852
  }
1799
- prop.unsigned ??= (prop.primary || prop.unsigned) && this.platform.isNumericProperty(prop) && this.platform.supportsUnsigned();
1853
+ prop.unsigned ??=
1854
+ (prop.primary || prop.unsigned) && this.platform.isNumericProperty(prop) && this.platform.supportsUnsigned();
1800
1855
  }
1801
1856
  initIndexes(meta, prop) {
1802
1857
  const hasIndex = meta.indexes.some(idx => idx.properties?.length === 1 && idx.properties[0] === prop.name);
@@ -13,7 +13,12 @@ export class MetadataProvider {
13
13
  }
14
14
  else if (prop.entity) {
15
15
  const tmp = prop.entity();
16
- prop.type = Array.isArray(tmp) ? tmp.map(t => Utils.className(t)).sort().join(' | ') : Utils.className(tmp);
16
+ prop.type = Array.isArray(tmp)
17
+ ? tmp
18
+ .map(t => Utils.className(t))
19
+ .sort()
20
+ .join(' | ')
21
+ : Utils.className(tmp);
17
22
  prop.target = tmp instanceof EntitySchema ? tmp.meta.class : tmp;
18
23
  }
19
24
  else if (!prop.type && !((prop.enum || prop.array) && (prop.items?.length ?? 0) > 0)) {
@@ -90,9 +90,7 @@ export class MetadataStorage {
90
90
  }
91
91
  }
92
92
  decorate(em) {
93
- [...this.metadata.values()]
94
- .filter(meta => meta.prototype)
95
- .forEach(meta => EntityHelper.decorate(meta, em));
93
+ [...this.metadata.values()].filter(meta => meta.prototype).forEach(meta => EntityHelper.decorate(meta, em));
96
94
  }
97
95
  *[Symbol.iterator]() {
98
96
  for (const meta of this.metadata.values()) {
@@ -63,7 +63,11 @@ export class MetadataValidator {
63
63
  }
64
64
  // Validate no mixing of STI and TPT in the same hierarchy
65
65
  this.validateInheritanceStrategies(discovered);
66
- const tableNames = discovered.filter(meta => !meta.abstract && !meta.embeddable && meta === meta.root && (meta.tableName || meta.collection) && meta.schema !== '*');
66
+ const tableNames = discovered.filter(meta => !meta.abstract &&
67
+ !meta.embeddable &&
68
+ meta === meta.root &&
69
+ (meta.tableName || meta.collection) &&
70
+ meta.schema !== '*');
67
71
  const duplicateTableNames = Utils.findDuplicates(tableNames.map(meta => {
68
72
  const tableName = meta.tableName || meta.collection;
69
73
  return (meta.schema ? '.' + meta.schema : '') + tableName;
@@ -88,7 +92,10 @@ export class MetadataValidator {
88
92
  const pivotProps = new Map();
89
93
  // check for not discovered entities
90
94
  discovered.forEach(meta => Object.values(meta.properties).forEach(prop => {
91
- if (prop.kind !== ReferenceKind.SCALAR && !unwrap(prop.type).split(/ ?\| ?/).every(type => discovered.find(m => m.className === type))) {
95
+ if (prop.kind !== ReferenceKind.SCALAR &&
96
+ !unwrap(prop.type)
97
+ .split(/ ?\| ?/)
98
+ .every(type => discovered.find(m => m.className === type))) {
92
99
  throw MetadataError.fromUnknownEntity(prop.type, `${meta.className}.${prop.name}`);
93
100
  }
94
101
  if (prop.pivotEntity) {
@@ -122,7 +129,10 @@ export class MetadataValidator {
122
129
  if (targetMeta.abstract && !targetMeta.root?.inheritanceType && !targetMeta.embeddable) {
123
130
  throw MetadataError.targetIsAbstract(meta, prop);
124
131
  }
125
- if ([ReferenceKind.MANY_TO_ONE, ReferenceKind.ONE_TO_ONE].includes(prop.kind) && prop.persist === false && targetMeta.compositePK && options.checkNonPersistentCompositeProps) {
132
+ if ([ReferenceKind.MANY_TO_ONE, ReferenceKind.ONE_TO_ONE].includes(prop.kind) &&
133
+ prop.persist === false &&
134
+ targetMeta.compositePK &&
135
+ options.checkNonPersistentCompositeProps) {
126
136
  throw MetadataError.nonPersistentCompositeProp(meta, prop);
127
137
  }
128
138
  this.validateTargetKey(meta, prop, targetMeta);
@@ -248,7 +258,9 @@ export class MetadataValidator {
248
258
  // has correct `mappedBy` reference type
249
259
  // For polymorphic relations, check if this entity is one of the polymorphic targets
250
260
  const isValidPolymorphicInverse = owner.polymorphic && owner.polymorphTargets?.some(target => target.class === meta.root.class);
251
- if (!isValidPolymorphicInverse && owner.type !== meta.className && owner.targetMeta?.root.class !== meta.root.class) {
261
+ if (!isValidPolymorphicInverse &&
262
+ owner.type !== meta.className &&
263
+ owner.targetMeta?.root.class !== meta.root.class) {
252
264
  throw MetadataError.fromWrongReference(meta, prop, 'mappedBy', owner);
253
265
  }
254
266
  // owning side is not defined as inverse
@@ -280,7 +292,10 @@ export class MetadataValidator {
280
292
  }
281
293
  validateDuplicateFieldNames(meta, options) {
282
294
  const candidates = Object.values(meta.properties)
283
- .filter(prop => prop.persist !== false && !prop.inherited && prop.fieldNames?.length === 1 && (prop.kind !== ReferenceKind.EMBEDDED || prop.object))
295
+ .filter(prop => prop.persist !== false &&
296
+ !prop.inherited &&
297
+ prop.fieldNames?.length === 1 &&
298
+ (prop.kind !== ReferenceKind.EMBEDDED || prop.object))
284
299
  .map(prop => prop.fieldNames[0]);
285
300
  const duplicates = Utils.findDuplicates(candidates);
286
301
  if (duplicates.length > 0 && options.checkDuplicateFieldNames) {
@@ -526,7 +526,7 @@ export interface IndexColumnOptions {
526
526
  }
527
527
  interface BaseOptions<T, H extends string> {
528
528
  name?: string;
529
- properties?: (T extends EntityClass<infer P> ? Properties<P, H> : Properties<T, H>);
529
+ properties?: T extends EntityClass<infer P> ? Properties<P, H> : Properties<T, H>;
530
530
  options?: Dictionary;
531
531
  expression?: string | (T extends EntityClass<infer P> ? IndexCallback<P> : IndexCallback<T>);
532
532
  /**
@@ -540,7 +540,7 @@ interface BaseOptions<T, H extends string> {
540
540
  * Columns to include in the index but not as part of the key (PostgreSQL, MSSQL).
541
541
  * These columns are stored in the leaf level of the index but not used for searching.
542
542
  */
543
- include?: (T extends EntityClass<infer P> ? Properties<P, H> : Properties<T, H>);
543
+ include?: T extends EntityClass<infer P> ? Properties<P, H> : Properties<T, H>;
544
544
  /** Fill factor for the index as a percentage 0-100 (PostgreSQL, MSSQL). */
545
545
  fillFactor?: number;
546
546
  }
@@ -35,10 +35,13 @@ export class AbstractNamingStrategy {
35
35
  */
36
36
  getEntityName(tableName, schemaName) {
37
37
  const name = tableName.match(/^[^$_\p{ID_Start}]/u) ? `E_${tableName}` : tableName;
38
- return this.getClassName(name.replaceAll(/[^\u200C\u200D\p{ID_Continue}]+/ug, r => r.split('').map(c => `$${c.codePointAt(0)}`).join('')), '_');
38
+ return this.getClassName(name.replaceAll(/[^\u200C\u200D\p{ID_Continue}]+/gu, r => r
39
+ .split('')
40
+ .map(c => `$${c.codePointAt(0)}`)
41
+ .join('')), '_');
39
42
  }
40
43
  columnNameToProperty(columnName) {
41
- const propName = columnName.replace(/[_\- ]+(\w)/ug, (_, p1) => p1.toUpperCase());
44
+ const propName = columnName.replace(/[_\- ]+(\w)/gu, (_, p1) => p1.toUpperCase());
42
45
  if (populatePathMembers.includes(propName.replace(/^\${2,}/u, '$$').replace(/^\$\*$/u, '*'))) {
43
46
  return `$${propName}`;
44
47
  }
package/not-supported.js CHANGED
@@ -1,4 +1,8 @@
1
1
  export function discoverEntities() {
2
2
  throw new Error('Folder-based discovery is not supported in this environment.');
3
3
  }
4
- export const fs = new Proxy({}, { get: () => { throw new Error('File system is not supported in this environment.'); } });
4
+ export const fs = new Proxy({}, {
5
+ get: () => {
6
+ throw new Error('File system is not supported in this environment.');
7
+ },
8
+ });
package/package.json CHANGED
@@ -1,8 +1,39 @@
1
1
  {
2
2
  "name": "@mikro-orm/core",
3
- "type": "module",
4
- "version": "7.0.0-dev.300",
3
+ "version": "7.0.0-dev.302",
5
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
+ "keywords": [
6
+ "data-mapper",
7
+ "ddd",
8
+ "entity",
9
+ "identity-map",
10
+ "javascript",
11
+ "js",
12
+ "mariadb",
13
+ "mikro-orm",
14
+ "mongo",
15
+ "mongodb",
16
+ "mysql",
17
+ "orm",
18
+ "postgresql",
19
+ "sqlite",
20
+ "sqlite3",
21
+ "ts",
22
+ "typescript",
23
+ "unit-of-work"
24
+ ],
25
+ "homepage": "https://mikro-orm.io",
26
+ "bugs": {
27
+ "url": "https://github.com/mikro-orm/mikro-orm/issues"
28
+ },
29
+ "license": "MIT",
30
+ "author": "Martin Adámek",
31
+ "repository": {
32
+ "type": "git",
33
+ "url": "git+ssh://git@github.com/mikro-orm/mikro-orm.git"
34
+ },
35
+ "funding": "https://github.com/sponsors/b4nan",
36
+ "type": "module",
6
37
  "exports": {
7
38
  "./package.json": "./package.json",
8
39
  ".": "./index.js",
@@ -18,39 +49,8 @@
18
49
  "./schema": "./utils/AbstractSchemaGenerator.js",
19
50
  "./dataloader": "./utils/DataloaderUtils.js"
20
51
  },
21
- "repository": {
22
- "type": "git",
23
- "url": "git+ssh://git@github.com/mikro-orm/mikro-orm.git"
24
- },
25
- "funding": "https://github.com/sponsors/b4nan",
26
- "keywords": [
27
- "orm",
28
- "mongo",
29
- "mongodb",
30
- "mysql",
31
- "mariadb",
32
- "postgresql",
33
- "sqlite",
34
- "sqlite3",
35
- "ts",
36
- "typescript",
37
- "js",
38
- "javascript",
39
- "entity",
40
- "ddd",
41
- "mikro-orm",
42
- "unit-of-work",
43
- "data-mapper",
44
- "identity-map"
45
- ],
46
- "author": "Martin Adámek",
47
- "license": "MIT",
48
- "bugs": {
49
- "url": "https://github.com/mikro-orm/mikro-orm/issues"
50
- },
51
- "homepage": "https://mikro-orm.io",
52
- "engines": {
53
- "node": ">= 22.17.0"
52
+ "publishConfig": {
53
+ "access": "public"
54
54
  },
55
55
  "scripts": {
56
56
  "build": "yarn compile && yarn copy",
@@ -58,9 +58,6 @@
58
58
  "compile": "yarn run -T tsc -p tsconfig.build.json",
59
59
  "copy": "node ../../scripts/copy.mjs"
60
60
  },
61
- "publishConfig": {
62
- "access": "public"
63
- },
64
61
  "peerDependencies": {
65
62
  "dataloader": "2.2.3"
66
63
  },
@@ -68,5 +65,8 @@
68
65
  "dataloader": {
69
66
  "optional": true
70
67
  }
68
+ },
69
+ "engines": {
70
+ "node": ">= 22.17.0"
71
71
  }
72
72
  }