@mikro-orm/sql 7.1.0-dev.4 → 7.1.0-dev.40

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 (55) hide show
  1. package/AbstractSqlConnection.d.ts +1 -1
  2. package/AbstractSqlConnection.js +27 -6
  3. package/AbstractSqlDriver.d.ts +26 -1
  4. package/AbstractSqlDriver.js +286 -35
  5. package/AbstractSqlPlatform.d.ts +15 -3
  6. package/AbstractSqlPlatform.js +25 -7
  7. package/PivotCollectionPersister.d.ts +2 -2
  8. package/PivotCollectionPersister.js +19 -3
  9. package/README.md +2 -1
  10. package/SqlEntityManager.d.ts +46 -3
  11. package/SqlEntityManager.js +77 -7
  12. package/SqlMikroORM.d.ts +23 -0
  13. package/SqlMikroORM.js +23 -0
  14. package/dialects/mysql/BaseMySqlPlatform.d.ts +4 -5
  15. package/dialects/mysql/BaseMySqlPlatform.js +9 -10
  16. package/dialects/mysql/MySqlSchemaHelper.d.ts +13 -3
  17. package/dialects/mysql/MySqlSchemaHelper.js +145 -21
  18. package/dialects/oracledb/OracleDialect.d.ts +1 -1
  19. package/dialects/oracledb/OracleDialect.js +2 -1
  20. package/dialects/postgresql/BasePostgreSqlEntityManager.d.ts +19 -0
  21. package/dialects/postgresql/BasePostgreSqlEntityManager.js +24 -0
  22. package/dialects/postgresql/BasePostgreSqlPlatform.d.ts +11 -5
  23. package/dialects/postgresql/BasePostgreSqlPlatform.js +75 -17
  24. package/dialects/postgresql/PostgreSqlSchemaHelper.d.ts +31 -1
  25. package/dialects/postgresql/PostgreSqlSchemaHelper.js +230 -5
  26. package/dialects/postgresql/index.d.ts +2 -0
  27. package/dialects/postgresql/index.js +2 -0
  28. package/dialects/postgresql/typeOverrides.d.ts +14 -0
  29. package/dialects/postgresql/typeOverrides.js +12 -0
  30. package/dialects/sqlite/SqlitePlatform.d.ts +2 -1
  31. package/dialects/sqlite/SqlitePlatform.js +4 -0
  32. package/dialects/sqlite/SqliteSchemaHelper.d.ts +9 -2
  33. package/dialects/sqlite/SqliteSchemaHelper.js +148 -19
  34. package/index.d.ts +2 -0
  35. package/index.js +2 -0
  36. package/package.json +4 -4
  37. package/plugin/transformer.d.ts +11 -3
  38. package/plugin/transformer.js +138 -29
  39. package/query/CriteriaNode.d.ts +1 -1
  40. package/query/CriteriaNode.js +2 -2
  41. package/query/ObjectCriteriaNode.js +1 -1
  42. package/query/QueryBuilder.d.ts +42 -1
  43. package/query/QueryBuilder.js +78 -7
  44. package/schema/DatabaseSchema.js +26 -4
  45. package/schema/DatabaseTable.d.ts +20 -1
  46. package/schema/DatabaseTable.js +182 -31
  47. package/schema/SchemaComparator.d.ts +10 -0
  48. package/schema/SchemaComparator.js +104 -1
  49. package/schema/SchemaHelper.d.ts +63 -1
  50. package/schema/SchemaHelper.js +235 -6
  51. package/schema/SqlSchemaGenerator.d.ts +2 -2
  52. package/schema/SqlSchemaGenerator.js +16 -9
  53. package/schema/partitioning.d.ts +13 -0
  54. package/schema/partitioning.js +326 -0
  55. package/typings.d.ts +34 -2
@@ -60,7 +60,7 @@ export declare abstract class AbstractSqlConnection extends Connection {
60
60
  /** Executes a SQL query and returns the result based on the method: `'all'` for rows, `'get'` for single row, `'run'` for affected count. */
61
61
  execute<T extends QueryResult | EntityData<AnyEntity> | EntityData<AnyEntity>[] = EntityData<AnyEntity>[]>(query: string | NativeQueryBuilder | RawQueryFragment, params?: readonly unknown[], method?: 'all' | 'get' | 'run', ctx?: Transaction, loggerContext?: LoggingOptions): Promise<T>;
62
62
  /** Executes a SQL query and returns an async iterable that yields results row by row. */
63
- stream<T extends EntityData<AnyEntity>>(query: string | NativeQueryBuilder | RawQueryFragment, params?: readonly unknown[], ctx?: Transaction<Kysely<any>>, loggerContext?: LoggingOptions): AsyncIterableIterator<T>;
63
+ stream<T extends EntityData<AnyEntity>>(query: string | NativeQueryBuilder | RawQueryFragment, params?: readonly unknown[], ctx?: Transaction<Kysely<any>>, loggerContext?: LoggingOptions, chunkSize?: number): AsyncIterableIterator<T>;
64
64
  /** @inheritDoc */
65
65
  executeDump(dump: string): Promise<void>;
66
66
  protected getSql(query: string, formatted: string, context?: LogContext): string;
@@ -1,6 +1,23 @@
1
1
  import { CompiledQuery, Kysely } from 'kysely';
2
2
  import { Connection, EventType, isRaw, Utils, } from '@mikro-orm/core';
3
3
  import { NativeQueryBuilder } from './query/NativeQueryBuilder.js';
4
+ /**
5
+ * Pulls cancellation controls out of a `loggerContext` payload, returning the abort options
6
+ * and a sanitized context that no longer carries them. The QueryBuilder/EM stash
7
+ * `signal`/`inflightQueryAbortStrategy` on `loggerContext` to avoid widening the public
8
+ * connection API; stripping them prevents leakage into user `Logger.logQuery` payloads.
9
+ */
10
+ function extractAbortOptions(loggerContext) {
11
+ const ctx = loggerContext;
12
+ if (ctx?.signal == null && ctx?.inflightQueryAbortStrategy == null) {
13
+ return { loggerContext };
14
+ }
15
+ const { signal, inflightQueryAbortStrategy, ...rest } = ctx;
16
+ return {
17
+ abort: { signal, inflightQueryAbortStrategy },
18
+ loggerContext: rest,
19
+ };
20
+ }
4
21
  /** Base class for SQL database connections, built on top of Kysely. */
5
22
  export class AbstractSqlConnection extends Connection {
6
23
  #client;
@@ -183,17 +200,19 @@ export class AbstractSqlConnection extends Connection {
183
200
  await this.ensureConnection();
184
201
  const q = this.prepareQuery(query, params);
185
202
  const sql = this.getSql(q.query, q.formatted, loggerContext);
203
+ const { abort, loggerContext: cleanCtx } = extractAbortOptions(loggerContext);
186
204
  return this.executeQuery(sql, async () => {
187
205
  const compiled = CompiledQuery.raw(q.formatted);
188
- const res = await (ctx ?? this.#client).executeQuery(compiled);
206
+ const res = await (ctx ?? this.#client).executeQuery(compiled, abort);
189
207
  return this.transformRawResult(res, method);
190
- }, { ...q, ...loggerContext });
208
+ }, { ...q, ...cleanCtx });
191
209
  }
192
210
  /** Executes a SQL query and returns an async iterable that yields results row by row. */
193
- async *stream(query, params = [], ctx, loggerContext) {
211
+ async *stream(query, params = [], ctx, loggerContext, chunkSize) {
194
212
  await this.ensureConnection();
195
213
  const q = this.prepareQuery(query, params);
196
214
  const sql = this.getSql(q.query, q.formatted, loggerContext);
215
+ const { abort, loggerContext: cleanCtx } = extractAbortOptions(loggerContext);
197
216
  // construct the compiled query manually with `kind: 'SelectQueryNode'` to avoid sqlite validation for select queries when streaming
198
217
  const compiled = {
199
218
  query: {
@@ -203,11 +222,13 @@ export class AbstractSqlConnection extends Connection {
203
222
  parameters: [],
204
223
  };
205
224
  try {
206
- const res = (ctx ?? this.getClient()).getExecutor().stream(compiled, 1);
225
+ const res = (ctx ?? this.getClient())
226
+ .getExecutor()
227
+ .stream(compiled, chunkSize ?? 100, abort ? { signal: abort.signal } : undefined);
207
228
  this.logQuery(sql, {
208
229
  sql,
209
230
  params,
210
- ...loggerContext,
231
+ ...cleanCtx,
211
232
  affected: Utils.isPlainObject(res) ? res.affectedRows : undefined,
212
233
  });
213
234
  for await (const items of res) {
@@ -217,7 +238,7 @@ export class AbstractSqlConnection extends Connection {
217
238
  }
218
239
  }
219
240
  catch (e) {
220
- this.logQuery(sql, { sql, params, ...loggerContext, level: 'error' });
241
+ this.logQuery(sql, { sql, params, ...cleanCtx, level: 'error' });
221
242
  throw e;
222
243
  }
223
244
  }
@@ -31,7 +31,7 @@ export declare abstract class AbstractSqlDriver<Connection extends AbstractSqlCo
31
31
  protected findFromVirtual<T extends object>(entityName: EntityName<T>, where: ObjectQuery<T>, options: FindOptions<T, any> | CountOptions<T, any>, type: QueryType): Promise<EntityData<T>[] | number>;
32
32
  protected streamFromVirtual<T extends object>(entityName: EntityName<T>, where: FilterQuery<T>, options: StreamOptions<T, any>): AsyncIterableIterator<EntityData<T>>;
33
33
  protected wrapVirtualExpressionInSubquery<T extends object>(meta: EntityMetadata<T>, expression: string, where: FilterQuery<T>, options: FindOptions<T, any>, type: QueryType): Promise<T[] | number>;
34
- protected wrapVirtualExpressionInSubqueryStream<T extends object>(meta: EntityMetadata<T>, expression: string, where: FilterQuery<T>, options: FindOptions<T, any, any, any>, type: QueryType.SELECT): AsyncIterableIterator<T>;
34
+ protected wrapVirtualExpressionInSubqueryStream<T extends object>(meta: EntityMetadata<T>, expression: string, where: FilterQuery<T>, options: StreamOptions<T, any, any, any>, type: QueryType.SELECT): AsyncIterableIterator<T>;
35
35
  /**
36
36
  * Virtual entities have no PKs, so to-many populate joins can't be deduplicated.
37
37
  * Force balanced strategy to load to-many relations via separate queries.
@@ -83,11 +83,22 @@ export declare abstract class AbstractSqlDriver<Connection extends AbstractSqlCo
83
83
  * Uses single query with join via virtual relation on pivot.
84
84
  */
85
85
  protected loadPolymorphicPivotInverseSide<T extends object, O extends object>(prop: EntityProperty, owners: Primary<O>[][], where: FilterQuery<any>, orderBy?: OrderDefinition<T>, ctx?: Transaction, options?: FindOptions<T, any, any, any>): Promise<Dictionary<T[]>>;
86
+ /**
87
+ * Load a union-target polymorphic M:N pivot (e.g. Post.attachments -> Image | Video).
88
+ * Each pivot row's discriminator column selects which target table to hydrate.
89
+ */
90
+ protected loadFromUnionTargetPolymorphicPivotTable<T extends object, O extends object>(prop: EntityProperty, owners: Primary<O>[][], where?: FilterQuery<any>, orderBy?: OrderDefinition<T>, ctx?: Transaction, options?: FindOptions<T, any, any, any>, pivotJoin?: boolean): Promise<Dictionary<T[]>>;
86
91
  /**
87
92
  * Build a map from owner PKs to their related entities from pivot table results.
88
93
  */
89
94
  private buildPivotResultMap;
90
95
  private wrapPopulateFilter;
96
+ /**
97
+ * The pivot query builder doesn't convert custom types — manually convert owner PKs to the DB
98
+ * representation. Returns `needsConversion` + `pkProp` so the caller can convert result FKs back
99
+ * to JS format for consistent key hashing in `buildPivotResultMap`.
100
+ */
101
+ private convertOwnerPksForPivotQuery;
91
102
  private getPivotOrderBy;
92
103
  execute<T extends QueryResult | EntityData<AnyEntity> | EntityData<AnyEntity>[] = EntityData<AnyEntity>[]>(query: string | NativeQueryBuilder | RawQueryFragment, params?: any[], method?: 'all' | 'get' | 'run', ctx?: Transaction, loggerContext?: LoggingOptions): Promise<T>;
93
104
  stream<T extends object>(entityName: EntityName<T>, where: FilterQuery<T>, options: StreamOptions<T, any, any, any>): AsyncIterableIterator<T>;
@@ -107,6 +118,13 @@ export declare abstract class AbstractSqlDriver<Connection extends AbstractSqlCo
107
118
  mergeJoinedResult<T extends object>(rawResults: EntityData<T>[], meta: EntityMetadata<T>, joinedProps: PopulateOptions<T>[]): EntityData<T>[];
108
119
  protected shouldHaveColumn<T, U>(meta: EntityMetadata<T>, prop: EntityProperty<U>, populate: readonly PopulateOptions<U>[], fields?: readonly InternalField<U>[], exclude?: readonly InternalField<U>[]): boolean;
109
120
  protected getFieldsForJoinedLoad<T extends object>(qb: AnyQueryBuilder<T>, meta: EntityMetadata<T>, options: FieldsForJoinedLoadOptions<T>): InternalField<T>[];
121
+ /**
122
+ * Walks the TPT inheritance chain of `leafMeta` and INNER JOINs each parent table.
123
+ * Registers the parent aliases in `qb.state.tptAlias` so column resolution finds them
124
+ * when filter conditions reference parent-table columns.
125
+ * @internal
126
+ */
127
+ protected addTPTParentJoinsForRelation<T extends object>(qb: AnyQueryBuilder<T>, leafMeta: EntityMetadata, leafAlias: string, basePath: string): void;
110
128
  /**
111
129
  * Adds LEFT JOINs and fields for TPT polymorphic loading when populating a relation to a TPT base class.
112
130
  * @internal
@@ -136,6 +154,13 @@ export declare abstract class AbstractSqlDriver<Connection extends AbstractSqlCo
136
154
  mapPropToFieldNames<T extends object>(qb: AnyQueryBuilder<T>, prop: EntityProperty<T>, tableAlias: string, meta: EntityMetadata<T>, schema?: string, explicitFields?: readonly InternalField<T>[]): InternalField<T>[];
137
155
  /** @internal */
138
156
  createQueryBuilder<T extends object>(entityName: EntityName<T> | AnyQueryBuilder<T>, ctx?: Transaction, preferredConnectionType?: ConnectionType, convertCustomTypes?: boolean, loggerContext?: LoggingOptions, alias?: string, em?: SqlEntityManager): AnyQueryBuilder<T>;
157
+ /**
158
+ * Renders a `FilterQuery` predicate into a SQL fragment (without the `WHERE` keyword and
159
+ * without table-alias prefixes) suitable for inlining into a partial-index DDL statement.
160
+ * Used by `DatabaseTable.addIndex` when the user passes an object `where` on `@Index` /
161
+ * `@Unique`. Strings are returned unchanged.
162
+ */
163
+ renderPartialIndexWhere<T extends object>(entityName: EntityName<T>, where: string | FilterQuery<T>): string;
139
164
  protected resolveConnectionType(args: {
140
165
  ctx?: Transaction;
141
166
  connectionType?: ConnectionType;