typeorm 0.3.29 → 0.3.30

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 (37) hide show
  1. package/browser/driver/cockroachdb/CockroachQueryRunner.js +4 -4
  2. package/browser/driver/cockroachdb/CockroachQueryRunner.js.map +1 -1
  3. package/browser/driver/sqlserver/SqlServerQueryRunner.js +4 -2
  4. package/browser/driver/sqlserver/SqlServerQueryRunner.js.map +1 -1
  5. package/browser/entity-manager/EntityManager.js +8 -4
  6. package/browser/entity-manager/EntityManager.js.map +1 -1
  7. package/browser/find-options/operator/JsonContains.d.ts +1 -1
  8. package/browser/find-options/operator/JsonContains.js.map +1 -1
  9. package/browser/persistence/SubjectChangedColumnsComputer.js +6 -2
  10. package/browser/persistence/SubjectChangedColumnsComputer.js.map +1 -1
  11. package/browser/query-builder/QueryBuilder.js +7 -24
  12. package/browser/query-builder/QueryBuilder.js.map +1 -1
  13. package/browser/query-builder/SelectQueryBuilder.d.ts +6 -6
  14. package/browser/query-builder/SelectQueryBuilder.js +27 -22
  15. package/browser/query-builder/SelectQueryBuilder.js.map +1 -1
  16. package/browser/util/OrmUtils.d.ts +13 -0
  17. package/browser/util/OrmUtils.js +53 -0
  18. package/browser/util/OrmUtils.js.map +1 -1
  19. package/driver/cockroachdb/CockroachQueryRunner.js +4 -4
  20. package/driver/cockroachdb/CockroachQueryRunner.js.map +1 -1
  21. package/driver/sqlserver/SqlServerQueryRunner.js +4 -2
  22. package/driver/sqlserver/SqlServerQueryRunner.js.map +1 -1
  23. package/entity-manager/EntityManager.js +8 -4
  24. package/entity-manager/EntityManager.js.map +1 -1
  25. package/find-options/operator/JsonContains.d.ts +1 -1
  26. package/find-options/operator/JsonContains.js.map +1 -1
  27. package/package.json +6 -6
  28. package/persistence/SubjectChangedColumnsComputer.js +6 -2
  29. package/persistence/SubjectChangedColumnsComputer.js.map +1 -1
  30. package/query-builder/QueryBuilder.js +7 -24
  31. package/query-builder/QueryBuilder.js.map +1 -1
  32. package/query-builder/SelectQueryBuilder.d.ts +6 -6
  33. package/query-builder/SelectQueryBuilder.js +27 -22
  34. package/query-builder/SelectQueryBuilder.js.map +1 -1
  35. package/util/OrmUtils.d.ts +13 -0
  36. package/util/OrmUtils.js +53 -0
  37. package/util/OrmUtils.js.map +1 -1
@@ -532,9 +532,9 @@ export class SelectQueryBuilder extends QueryBuilder {
532
532
  }
533
533
  /**
534
534
  * Sets LIMIT - maximum number of rows to be selected.
535
- * When joins are present, a two-query distinct-id strategy is used
536
- * so that LIMIT applies to root entities rather than raw joined rows.
537
- * @param limit
535
+ * NOTE that it may not work as you expect if you are using joins.
536
+ * If you want to implement pagination, and you are having join in your query,
537
+ * then use the take method instead.
538
538
  */
539
539
  limit(limit) {
540
540
  this.expressionMap.limit = this.validateNumericInput("limit", limit);
@@ -542,9 +542,9 @@ export class SelectQueryBuilder extends QueryBuilder {
542
542
  }
543
543
  /**
544
544
  * Sets OFFSET - selection offset.
545
- * When joins are present, a two-query distinct-id strategy is used
546
- * so that OFFSET applies to root entities rather than raw joined rows.
547
- * @param offset
545
+ * NOTE that it may not work as you expect if you are using joins.
546
+ * If you want to implement pagination, and you are having join in your query,
547
+ * then use the skip method instead.
548
548
  */
549
549
  offset(offset) {
550
550
  this.expressionMap.offset = this.validateNumericInput("offset", offset);
@@ -1982,10 +1982,7 @@ export class SelectQueryBuilder extends QueryBuilder {
1982
1982
  // where we make two queries to find the data we need
1983
1983
  // first query find ids in skip and take range
1984
1984
  // and second query loads the actual data in given ids range
1985
- if ((this.expressionMap.skip ||
1986
- this.expressionMap.take ||
1987
- this.expressionMap.offset ||
1988
- this.expressionMap.limit) &&
1985
+ if ((this.expressionMap.skip || this.expressionMap.take) &&
1989
1986
  this.expressionMap.joinAttributes.length > 0) {
1990
1987
  // we are skipping order by here because its not working in subqueries anyway
1991
1988
  // to make order by working we need to apply it on a distinct query
@@ -2002,9 +1999,6 @@ export class SelectQueryBuilder extends QueryBuilder {
2002
1999
  return `${distinctAlias}.${columnAlias} AS ${this.escape(alias)}`;
2003
2000
  });
2004
2001
  const originalQuery = this.clone();
2005
- // clear limit/offset from the inner query since pagination is handled by the outer distinct query
2006
- originalQuery.expressionMap.limit = undefined;
2007
- originalQuery.expressionMap.offset = undefined;
2008
2002
  // preserve original timeTravel value since we set it to "false" in subquery
2009
2003
  const originalQueryTimeTravel = originalQuery.expressionMap.timeTravel;
2010
2004
  rawResults = await new SelectQueryBuilder(this.connection, queryRunner)
@@ -2015,8 +2009,8 @@ export class SelectQueryBuilder extends QueryBuilder {
2015
2009
  .timeTravelQuery(false) // set it to "false" since time travel clause must appear at the very end and applies to the entire SELECT clause.
2016
2010
  .getQuery()})`, "distinctAlias")
2017
2011
  .timeTravelQuery(originalQueryTimeTravel)
2018
- .offset(this.expressionMap.skip ?? this.expressionMap.offset)
2019
- .limit(this.expressionMap.take ?? this.expressionMap.limit)
2012
+ .offset(this.expressionMap.skip)
2013
+ .limit(this.expressionMap.take)
2020
2014
  .orderBy(orderBys)
2021
2015
  .cache(this.expressionMap.cache && this.expressionMap.cacheId
2022
2016
  ? `${this.expressionMap.cacheId}-pagination`
@@ -2059,14 +2053,12 @@ export class SelectQueryBuilder extends QueryBuilder {
2059
2053
  " IN (:...orm_distinct_ids)";
2060
2054
  }
2061
2055
  }
2062
- const secondQuery = this.clone()
2056
+ rawResults = await this.clone()
2063
2057
  .mergeExpressionMap({
2064
2058
  extraAppendedAndWhereCondition: condition,
2065
2059
  })
2066
- .setParameters(parameters);
2067
- secondQuery.expressionMap.limit = undefined;
2068
- secondQuery.expressionMap.offset = undefined;
2069
- rawResults = await secondQuery.loadRawResults(queryRunner);
2060
+ .setParameters(parameters)
2061
+ .loadRawResults(queryRunner);
2070
2062
  }
2071
2063
  }
2072
2064
  else {
@@ -2572,8 +2564,21 @@ export class SelectQueryBuilder extends QueryBuilder {
2572
2564
  // if all properties of where are undefined we don't need to join anything
2573
2565
  // this can happen when user defines map with conditional queries inside
2574
2566
  if (typeof where[key] === "object") {
2575
- const allAllUndefined = Object.keys(where[key]).every((k) => where[key][k] === undefined);
2576
- if (allAllUndefined) {
2567
+ const whereKeys = Object.keys(where[key]);
2568
+ // empty object — no predicates to apply, skip the join
2569
+ if (whereKeys.length === 0) {
2570
+ continue;
2571
+ }
2572
+ const allUndefined = whereKeys.every((k) => where[key][k] === undefined);
2573
+ if (allUndefined) {
2574
+ const undefinedBehavior = this.connection.options
2575
+ .invalidWhereValuesBehavior?.undefined ||
2576
+ "ignore";
2577
+ if (undefinedBehavior === "throw") {
2578
+ throw new TypeORMError(`Undefined value encountered in nested relation '${alias}.${key}' of a where condition. ` +
2579
+ `All properties of the nested object are undefined. ` +
2580
+ `Set 'invalidWhereValuesBehavior.undefined' to 'ignore' in connection options to skip properties with undefined values.`);
2581
+ }
2577
2582
  continue;
2578
2583
  }
2579
2584
  }