@mikro-orm/mariadb 7.0.2-dev.9 → 7.0.2

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.
@@ -1,12 +1,29 @@
1
- import { type AnyEntity, type Configuration, type ConnectionType, type LoggingOptions, type Transaction, type Constructor, type EntityName } from '@mikro-orm/core';
1
+ import {
2
+ type AnyEntity,
3
+ type Configuration,
4
+ type ConnectionType,
5
+ type LoggingOptions,
6
+ type Transaction,
7
+ type Constructor,
8
+ type EntityName,
9
+ } from '@mikro-orm/core';
2
10
  import { MySqlDriver, type SqlEntityManager } from '@mikro-orm/mysql';
3
11
  import { MariaDbPlatform } from './MariaDbPlatform.js';
4
12
  import { MariaDbQueryBuilder } from './MariaDbQueryBuilder.js';
5
13
  import { MariaDbMikroORM } from './MariaDbMikroORM.js';
14
+ /** Database driver for MariaDB, extending the MySQL driver with MariaDB-specific behavior. */
6
15
  export declare class MariaDbDriver extends MySqlDriver {
7
- readonly platform: MariaDbPlatform;
8
- constructor(config: Configuration);
9
- createQueryBuilder<T extends AnyEntity<T>>(entityName: EntityName<T>, ctx?: Transaction, preferredConnectionType?: ConnectionType, convertCustomTypes?: boolean, loggerContext?: LoggingOptions, alias?: string, em?: SqlEntityManager): MariaDbQueryBuilder<T, any, any, any>;
10
- /** @inheritDoc */
11
- getORMClass(): Constructor<MariaDbMikroORM>;
16
+ readonly platform: MariaDbPlatform;
17
+ constructor(config: Configuration);
18
+ createQueryBuilder<T extends AnyEntity<T>>(
19
+ entityName: EntityName<T>,
20
+ ctx?: Transaction,
21
+ preferredConnectionType?: ConnectionType,
22
+ convertCustomTypes?: boolean,
23
+ loggerContext?: LoggingOptions,
24
+ alias?: string,
25
+ em?: SqlEntityManager,
26
+ ): MariaDbQueryBuilder<T, any, any, any>;
27
+ /** @inheritDoc */
28
+ getORMClass(): Constructor<MariaDbMikroORM>;
12
29
  }
package/MariaDbDriver.js CHANGED
@@ -1,26 +1,27 @@
1
- import { QueryFlag, } from '@mikro-orm/core';
1
+ import { QueryFlag } from '@mikro-orm/core';
2
2
  import { MySqlDriver } from '@mikro-orm/mysql';
3
3
  import { MariaDbPlatform } from './MariaDbPlatform.js';
4
4
  import { MariaDbQueryBuilder } from './MariaDbQueryBuilder.js';
5
5
  import { MariaDbMikroORM } from './MariaDbMikroORM.js';
6
+ /** Database driver for MariaDB, extending the MySQL driver with MariaDB-specific behavior. */
6
7
  export class MariaDbDriver extends MySqlDriver {
7
- constructor(config) {
8
- super(config);
9
- this.platform = new MariaDbPlatform();
10
- }
11
- createQueryBuilder(entityName, ctx, preferredConnectionType, convertCustomTypes, loggerContext, alias, em) {
12
- // do not compute the connectionType if EM is provided as it will be computed from it in the QB later on
13
- const connectionType = em
14
- ? preferredConnectionType
15
- : this.resolveConnectionType({ ctx, connectionType: preferredConnectionType });
16
- const qb = new MariaDbQueryBuilder(entityName, this.metadata, this, ctx, alias, connectionType, em, loggerContext);
17
- if (!convertCustomTypes) {
18
- qb.unsetFlag(QueryFlag.CONVERT_CUSTOM_TYPES);
19
- }
20
- return qb;
21
- }
22
- /** @inheritDoc */
23
- getORMClass() {
24
- return MariaDbMikroORM;
8
+ constructor(config) {
9
+ super(config);
10
+ this.platform = new MariaDbPlatform();
11
+ }
12
+ createQueryBuilder(entityName, ctx, preferredConnectionType, convertCustomTypes, loggerContext, alias, em) {
13
+ // do not compute the connectionType if EM is provided as it will be computed from it in the QB later on
14
+ const connectionType = em
15
+ ? preferredConnectionType
16
+ : this.resolveConnectionType({ ctx, connectionType: preferredConnectionType });
17
+ const qb = new MariaDbQueryBuilder(entityName, this.metadata, this, ctx, alias, connectionType, em, loggerContext);
18
+ if (!convertCustomTypes) {
19
+ qb.unsetFlag(QueryFlag.CONVERT_CUSTOM_TYPES);
25
20
  }
21
+ return qb;
22
+ }
23
+ /** @inheritDoc */
24
+ getORMClass() {
25
+ return MariaDbMikroORM;
26
+ }
26
27
  }
@@ -1,18 +1,58 @@
1
- import { type AnyEntity, type EntityClass, type EntitySchema, MikroORM, type Options, type IDatabaseDriver, type EntityManager, type EntityManagerType } from '@mikro-orm/core';
1
+ import {
2
+ type AnyEntity,
3
+ type EntityClass,
4
+ type EntitySchema,
5
+ MikroORM,
6
+ type Options,
7
+ type IDatabaseDriver,
8
+ type EntityManager,
9
+ type EntityManagerType,
10
+ } from '@mikro-orm/core';
2
11
  import type { SqlEntityManager } from '@mikro-orm/mysql';
3
12
  import { MariaDbDriver } from './MariaDbDriver.js';
4
- export type MariaDbOptions<EM extends SqlEntityManager<MariaDbDriver> = SqlEntityManager<MariaDbDriver>, Entities extends (string | EntityClass<AnyEntity> | EntitySchema)[] = (string | EntityClass<AnyEntity> | EntitySchema)[]> = Partial<Options<MariaDbDriver, EM, Entities>>;
5
- export declare function defineMariaDbConfig<EM extends SqlEntityManager<MariaDbDriver> = SqlEntityManager<MariaDbDriver>, Entities extends (string | EntityClass<AnyEntity> | EntitySchema)[] = (string | EntityClass<AnyEntity> | EntitySchema)[]>(options: Partial<Options<MariaDbDriver, EM, Entities>>): Partial<Options<MariaDbDriver, EM, Entities>>;
13
+ /** Configuration options for the MariaDB driver. */
14
+ export type MariaDbOptions<
15
+ EM extends SqlEntityManager<MariaDbDriver> = SqlEntityManager<MariaDbDriver>,
16
+ Entities extends (string | EntityClass<AnyEntity> | EntitySchema)[] = (
17
+ | string
18
+ | EntityClass<AnyEntity>
19
+ | EntitySchema
20
+ )[],
21
+ > = Partial<Options<MariaDbDriver, EM, Entities>>;
22
+ /** Creates a type-safe configuration object for the MariaDB driver. */
23
+ export declare function defineMariaDbConfig<
24
+ EM extends SqlEntityManager<MariaDbDriver> = SqlEntityManager<MariaDbDriver>,
25
+ Entities extends (string | EntityClass<AnyEntity> | EntitySchema)[] = (
26
+ | string
27
+ | EntityClass<AnyEntity>
28
+ | EntitySchema
29
+ )[],
30
+ >(options: Partial<Options<MariaDbDriver, EM, Entities>>): Partial<Options<MariaDbDriver, EM, Entities>>;
6
31
  /**
7
32
  * @inheritDoc
8
33
  */
9
- export declare class MariaDbMikroORM<EM extends SqlEntityManager<MariaDbDriver> = SqlEntityManager<MariaDbDriver>, Entities extends (string | EntityClass<AnyEntity> | EntitySchema)[] = (string | EntityClass<AnyEntity> | EntitySchema)[]> extends MikroORM<MariaDbDriver, EM, Entities> {
10
- /**
11
- * @inheritDoc
12
- */
13
- static init<D extends IDatabaseDriver = MariaDbDriver, EM extends EntityManager<D> = D[typeof EntityManagerType] & EntityManager<D>, Entities extends (string | EntityClass<AnyEntity> | EntitySchema)[] = (string | EntityClass<AnyEntity> | EntitySchema)[]>(options: Partial<Options<D, EM, Entities>>): Promise<MikroORM<D, EM, Entities>>;
14
- /**
15
- * @inheritDoc
16
- */
17
- constructor(options: Partial<Options<MariaDbDriver, EM, Entities>>);
34
+ export declare class MariaDbMikroORM<
35
+ EM extends SqlEntityManager<MariaDbDriver> = SqlEntityManager<MariaDbDriver>,
36
+ Entities extends (string | EntityClass<AnyEntity> | EntitySchema)[] = (
37
+ | string
38
+ | EntityClass<AnyEntity>
39
+ | EntitySchema
40
+ )[],
41
+ > extends MikroORM<MariaDbDriver, EM, Entities> {
42
+ /**
43
+ * @inheritDoc
44
+ */
45
+ static init<
46
+ D extends IDatabaseDriver = MariaDbDriver,
47
+ EM extends EntityManager<D> = D[typeof EntityManagerType] & EntityManager<D>,
48
+ Entities extends (string | EntityClass<AnyEntity> | EntitySchema)[] = (
49
+ | string
50
+ | EntityClass<AnyEntity>
51
+ | EntitySchema
52
+ )[],
53
+ >(options: Partial<Options<D, EM, Entities>>): Promise<MikroORM<D, EM, Entities>>;
54
+ /**
55
+ * @inheritDoc
56
+ */
57
+ constructor(options: Partial<Options<MariaDbDriver, EM, Entities>>);
18
58
  }
@@ -1,22 +1,23 @@
1
- import { defineConfig, MikroORM, } from '@mikro-orm/core';
1
+ import { defineConfig, MikroORM } from '@mikro-orm/core';
2
2
  import { MariaDbDriver } from './MariaDbDriver.js';
3
+ /** Creates a type-safe configuration object for the MariaDB driver. */
3
4
  export function defineMariaDbConfig(options) {
4
- return defineConfig({ driver: MariaDbDriver, ...options });
5
+ return defineConfig({ driver: MariaDbDriver, ...options });
5
6
  }
6
7
  /**
7
8
  * @inheritDoc
8
9
  */
9
10
  export class MariaDbMikroORM extends MikroORM {
10
- /**
11
- * @inheritDoc
12
- */
13
- static async init(options) {
14
- return super.init(defineMariaDbConfig(options));
15
- }
16
- /**
17
- * @inheritDoc
18
- */
19
- constructor(options) {
20
- super(defineMariaDbConfig(options));
21
- }
11
+ /**
12
+ * @inheritDoc
13
+ */
14
+ static async init(options) {
15
+ return super.init(defineMariaDbConfig(options));
16
+ }
17
+ /**
18
+ * @inheritDoc
19
+ */
20
+ constructor(options) {
21
+ super(defineMariaDbConfig(options));
22
+ }
22
23
  }
@@ -1,7 +1,8 @@
1
1
  import { MySqlPlatform, type TransformContext } from '@mikro-orm/mysql';
2
2
  import { MariaDbSchemaHelper } from './MariaDbSchemaHelper.js';
3
+ /** Platform implementation for MariaDB. */
3
4
  export declare class MariaDbPlatform extends MySqlPlatform {
4
- protected readonly schemaHelper: MariaDbSchemaHelper;
5
- convertJsonToDatabaseValue(value: unknown, context?: TransformContext): unknown;
6
- convertsJsonAutomatically(): boolean;
5
+ protected readonly schemaHelper: MariaDbSchemaHelper;
6
+ convertJsonToDatabaseValue(value: unknown, context?: TransformContext): unknown;
7
+ convertsJsonAutomatically(): boolean;
7
8
  }
@@ -1,14 +1,15 @@
1
1
  import { MySqlPlatform } from '@mikro-orm/mysql';
2
2
  import { MariaDbSchemaHelper } from './MariaDbSchemaHelper.js';
3
+ /** Platform implementation for MariaDB. */
3
4
  export class MariaDbPlatform extends MySqlPlatform {
4
- schemaHelper = new MariaDbSchemaHelper(this);
5
- convertJsonToDatabaseValue(value, context) {
6
- if (context?.mode === 'hydration') {
7
- return value;
8
- }
9
- return JSON.stringify(value);
10
- }
11
- convertsJsonAutomatically() {
12
- return false;
5
+ schemaHelper = new MariaDbSchemaHelper(this);
6
+ convertJsonToDatabaseValue(value, context) {
7
+ if (context?.mode === 'hydration') {
8
+ return value;
13
9
  }
10
+ return JSON.stringify(value);
11
+ }
12
+ convertsJsonAutomatically() {
13
+ return false;
14
+ }
14
15
  }
@@ -3,6 +3,11 @@ import { QueryBuilder } from '@mikro-orm/mysql';
3
3
  /**
4
4
  * @inheritDoc
5
5
  */
6
- export declare class MariaDbQueryBuilder<Entity extends object = AnyEntity, RootAlias extends string = never, Hint extends string = never, Context extends object = never> extends QueryBuilder<Entity, RootAlias, Hint, Context> {
7
- protected wrapPaginateSubQuery(meta: EntityMetadata): void;
6
+ export declare class MariaDbQueryBuilder<
7
+ Entity extends object = AnyEntity,
8
+ RootAlias extends string = never,
9
+ Hint extends string = never,
10
+ Context extends object = never,
11
+ > extends QueryBuilder<Entity, RootAlias, Hint, Context> {
12
+ protected wrapPaginateSubQuery(meta: EntityMetadata): void;
8
13
  }
@@ -4,83 +4,80 @@ import { QueryBuilder } from '@mikro-orm/mysql';
4
4
  * @inheritDoc
5
5
  */
6
6
  export class MariaDbQueryBuilder extends QueryBuilder {
7
- wrapPaginateSubQuery(meta) {
8
- const pks = this.prepareFields(meta.primaryKeys, 'sub-query');
9
- const quotedPKs = pks.map(pk => this.platform.quoteIdentifier(pk));
10
- const subQuery = this.clone(['orderBy', 'fields'])
11
- .select(pks)
12
- .groupBy(pks)
13
- .limit(this.state.limit);
14
- // revert the on conditions added via populateWhere, we want to apply those only once
15
- Object.values(subQuery.state.joins).forEach(join => (join.cond = join.cond_ ?? {}));
16
- if (this.state.offset) {
17
- subQuery.offset(this.state.offset);
18
- }
19
- const addToSelect = [];
20
- if (this.state.orderBy.length > 0) {
21
- const orderBy = [];
22
- for (const orderMap of this.state.orderBy) {
23
- for (const field of Utils.getObjectQueryKeys(orderMap)) {
24
- const direction = orderMap[field];
25
- if (RawQueryFragment.isKnownFragmentSymbol(field)) {
26
- orderBy.push({ [field]: direction });
27
- continue;
28
- }
29
- const [a, f] = this.helper.splitField(field);
30
- const prop = this.helper.getProperty(f, a);
31
- const type = this.platform.castColumn(prop);
32
- const fieldName = this.helper.mapper(field, this.type, undefined, null);
33
- if (!prop?.persist && !prop?.formula && !pks.includes(fieldName)) {
34
- addToSelect.push(fieldName);
35
- }
36
- const key = raw(`min(${this.platform.quoteIdentifier(fieldName)}${type})`);
37
- orderBy.push({ [key]: direction });
38
- }
39
- }
40
- subQuery.orderBy(orderBy);
7
+ wrapPaginateSubQuery(meta) {
8
+ const pks = this.prepareFields(meta.primaryKeys, 'sub-query');
9
+ const quotedPKs = pks.map(pk => this.platform.quoteIdentifier(pk));
10
+ const subQuery = this.clone(['orderBy', 'fields']).select(pks).groupBy(pks).limit(this.state.limit);
11
+ // revert the on conditions added via populateWhere, we want to apply those only once
12
+ Object.values(subQuery.state.joins).forEach(join => (join.cond = join.cond_ ?? {}));
13
+ if (this.state.offset) {
14
+ subQuery.offset(this.state.offset);
15
+ }
16
+ const addToSelect = [];
17
+ if (this.state.orderBy.length > 0) {
18
+ const orderBy = [];
19
+ for (const orderMap of this.state.orderBy) {
20
+ for (const field of Utils.getObjectQueryKeys(orderMap)) {
21
+ const direction = orderMap[field];
22
+ if (RawQueryFragment.isKnownFragmentSymbol(field)) {
23
+ orderBy.push({ [field]: direction });
24
+ continue;
25
+ }
26
+ const [a, f] = this.helper.splitField(field);
27
+ const prop = this.helper.getProperty(f, a);
28
+ const type = this.platform.castColumn(prop);
29
+ const fieldName = this.helper.mapper(field, this.type, undefined, null);
30
+ if (!prop?.persist && !prop?.formula && !pks.includes(fieldName)) {
31
+ addToSelect.push(fieldName);
32
+ }
33
+ const key = raw(`min(${this.platform.quoteIdentifier(fieldName)}${type})`);
34
+ orderBy.push({ [key]: direction });
41
35
  }
42
- subQuery.state.finalized = true;
43
- const innerQuery = subQuery.as(this.mainAlias.aliasName).clear('select').select(pks);
44
- /* v8 ignore next */
45
- if (addToSelect.length > 0) {
46
- addToSelect.forEach(prop => {
47
- const field = this.state.fields.find(field => {
48
- if (typeof field === 'object' && field && '__as' in field) {
49
- return field.__as === prop;
50
- }
51
- if (field instanceof RawQueryFragment) {
52
- // not perfect, but should work most of the time, ideally we should check only the alias (`... as alias`)
53
- return field.sql.includes(prop);
54
- }
55
- return false;
56
- });
57
- if (field instanceof RawQueryFragment) {
58
- innerQuery.select(this.platform.formatQuery(field.sql, field.params));
59
- }
60
- else if (field) {
61
- innerQuery.select(field);
62
- }
63
- });
36
+ }
37
+ subQuery.orderBy(orderBy);
38
+ }
39
+ subQuery.state.finalized = true;
40
+ const innerQuery = subQuery.as(this.mainAlias.aliasName).clear('select').select(pks);
41
+ /* v8 ignore next */
42
+ if (addToSelect.length > 0) {
43
+ addToSelect.forEach(prop => {
44
+ const field = this.state.fields.find(field => {
45
+ if (typeof field === 'object' && field && '__as' in field) {
46
+ return field.__as === prop;
47
+ }
48
+ if (field instanceof RawQueryFragment) {
49
+ // not perfect, but should work most of the time, ideally we should check only the alias (`... as alias`)
50
+ return field.sql.includes(prop);
51
+ }
52
+ return false;
53
+ });
54
+ if (field instanceof RawQueryFragment) {
55
+ innerQuery.select(this.platform.formatQuery(field.sql, field.params));
56
+ } else if (field) {
57
+ innerQuery.select(field);
64
58
  }
65
- // multiple sub-queries are needed to get around mysql limitations with order by + limit + where in + group by (o.O)
66
- // https://stackoverflow.com/questions/17892762/mysql-this-version-of-mysql-doesnt-yet-support-limit-in-all-any-some-subqu
67
- const subSubQuery = this.platform.createNativeQueryBuilder();
68
- subSubQuery.select(raw(`json_arrayagg(${quotedPKs.join(', ')})`)).from(innerQuery);
69
- this.state.limit = undefined;
70
- this.state.offset = undefined;
71
- // Save the original WHERE conditions before pruning joins
72
- const originalCond = this.state.cond;
73
- const populatePaths = this.getPopulatePaths();
74
- // Remove joins that are not used for population or ordering
75
- this.pruneJoinsForPagination(meta, populatePaths);
76
- // Transfer WHERE conditions to ORDER BY joins (GH #6160)
77
- this.transferConditionsForOrderByJoins(meta, originalCond, populatePaths);
78
- const subquerySql = subSubQuery.toString();
79
- const key = meta.getPrimaryProps()[0].runtimeType === 'string'
80
- ? `concat('"', ${quotedPKs.join(', ')}, '"')`
81
- : quotedPKs.join(', ');
82
- const sql = `json_contains((${subquerySql}), ${key})`;
83
- this.state.cond = {};
84
- this.select(this.state.fields).where(sql);
59
+ });
85
60
  }
61
+ // multiple sub-queries are needed to get around mysql limitations with order by + limit + where in + group by (o.O)
62
+ // https://stackoverflow.com/questions/17892762/mysql-this-version-of-mysql-doesnt-yet-support-limit-in-all-any-some-subqu
63
+ const subSubQuery = this.platform.createNativeQueryBuilder();
64
+ subSubQuery.select(raw(`json_arrayagg(${quotedPKs.join(', ')})`)).from(innerQuery);
65
+ this.state.limit = undefined;
66
+ this.state.offset = undefined;
67
+ // Save the original WHERE conditions before pruning joins
68
+ const originalCond = this.state.cond;
69
+ const populatePaths = this.getPopulatePaths();
70
+ // Remove joins that are not used for population or ordering
71
+ this.pruneJoinsForPagination(meta, populatePaths);
72
+ // Transfer WHERE conditions to ORDER BY joins (GH #6160)
73
+ this.transferConditionsForOrderByJoins(meta, originalCond, populatePaths);
74
+ const subquerySql = subSubQuery.toString();
75
+ const key =
76
+ meta.getPrimaryProps()[0].runtimeType === 'string'
77
+ ? `concat('"', ${quotedPKs.join(', ')}, '"')`
78
+ : quotedPKs.join(', ');
79
+ const sql = `json_contains((${subquerySql}), ${key})`;
80
+ this.state.cond = {};
81
+ this.select(this.state.fields).where(sql);
82
+ }
86
83
  }
@@ -1,11 +1,24 @@
1
- import { type AbstractSqlConnection, type CheckDef, type Column, type IndexDef, type DatabaseSchema, type Table, MySqlSchemaHelper } from '@mikro-orm/mysql';
1
+ import {
2
+ type AbstractSqlConnection,
3
+ type CheckDef,
4
+ type Column,
5
+ type IndexDef,
6
+ type DatabaseSchema,
7
+ type Table,
8
+ MySqlSchemaHelper,
9
+ } from '@mikro-orm/mysql';
2
10
  import { type Dictionary, type Type } from '@mikro-orm/core';
11
+ /** Schema introspection helper for MariaDB. */
3
12
  export declare class MariaDbSchemaHelper extends MySqlSchemaHelper {
4
- protected appendMySqlIndexSuffix(sql: string, index: IndexDef): string;
5
- loadInformationSchema(schema: DatabaseSchema, connection: AbstractSqlConnection, tables: Table[]): Promise<void>;
6
- getAllIndexes(connection: AbstractSqlConnection, tables: Table[]): Promise<Dictionary<IndexDef[]>>;
7
- getAllColumns(connection: AbstractSqlConnection, tables: Table[]): Promise<Dictionary<Column[]>>;
8
- getAllChecks(connection: AbstractSqlConnection, tables: Table[], columns?: Dictionary<Column[]>): Promise<Dictionary<CheckDef[]>>;
9
- protected getChecksSQL(tables: Table[]): string;
10
- protected wrap(val: string | undefined | null, type: Type<unknown>): string | undefined | null;
13
+ protected appendMySqlIndexSuffix(sql: string, index: IndexDef): string;
14
+ loadInformationSchema(schema: DatabaseSchema, connection: AbstractSqlConnection, tables: Table[]): Promise<void>;
15
+ getAllIndexes(connection: AbstractSqlConnection, tables: Table[]): Promise<Dictionary<IndexDef[]>>;
16
+ getAllColumns(connection: AbstractSqlConnection, tables: Table[]): Promise<Dictionary<Column[]>>;
17
+ getAllChecks(
18
+ connection: AbstractSqlConnection,
19
+ tables: Table[],
20
+ columns?: Dictionary<Column[]>,
21
+ ): Promise<Dictionary<CheckDef[]>>;
22
+ protected getChecksSQL(tables: Table[]): string;
23
+ protected wrap(val: string | undefined | null, type: Type<unknown>): string | undefined | null;
11
24
  }