Files
evento/node_modules/@mikro-orm/sql/typings.d.ts
2026-03-18 14:55:56 -03:00

441 lines
14 KiB
TypeScript

import type { Generated, Kysely } from 'kysely';
import type {
CheckCallback,
DeferMode,
Dictionary,
EntityName,
EntityProperty,
EntitySchemaWithMeta,
FilterQuery,
GroupOperator,
IndexColumnOptions,
InferEntityName,
Opt,
Primary,
PrimaryProperty,
QueryFlag,
QueryOrderMap,
RawQueryFragment,
Scalar,
Type,
} from '@mikro-orm/core';
import type { JoinType, QueryType } from './query/enums.js';
import type { DatabaseSchema } from './schema/DatabaseSchema.js';
import type { DatabaseTable } from './schema/DatabaseTable.js';
import type { AnyQueryBuilder } from './query/QueryBuilder.js';
import type { CteOptions, NativeQueryBuilder } from './query/NativeQueryBuilder.js';
import type { MikroKyselyPluginOptions } from './plugin/index.js';
export interface Table {
table_name: string;
schema_name?: string;
table_comment?: string;
}
/** @internal */
export type InternalField<T> = string | RawQueryFragment | AnyQueryBuilder | NativeQueryBuilder;
export interface JoinOptions {
table: string;
schema?: string;
type: JoinType;
alias: string;
ownerAlias: string;
inverseAlias?: string;
joinColumns?: string[];
inverseJoinColumns?: string[];
primaryKeys?: string[];
path?: string;
prop: EntityProperty;
cond: Dictionary;
cond_?: Dictionary;
subquery?: string;
nested?: Set<JoinOptions>;
parent?: JoinOptions;
}
export interface Column {
name: string;
type: string;
mappedType: Type<unknown>;
unsigned?: boolean;
autoincrement?: boolean;
nullable?: boolean;
length?: number;
precision?: number;
scale?: number;
default?: string | null;
defaultConstraint?: string;
comment?: string;
generated?: string;
nativeEnumName?: string;
enumItems?: string[];
primary?: boolean;
unique?: boolean;
/** mysql only */
extra?: string;
ignoreSchemaChanges?: ('type' | 'extra' | 'default')[];
}
export interface ForeignKey {
columnNames: string[];
constraintName: string;
localTableName: string;
referencedTableName: string;
referencedColumnNames: string[];
updateRule?: string;
deleteRule?: string;
deferMode?: DeferMode;
}
export interface IndexDef {
columnNames: string[];
keyName: string;
unique: boolean;
constraint: boolean;
primary: boolean;
composite?: boolean;
expression?: string;
options?: Dictionary;
type?:
| string
| Readonly<{
indexType?: string;
storageEngineIndexType?: 'hash' | 'btree';
predicate?: string;
}>;
deferMode?: DeferMode | `${DeferMode}`;
/**
* Advanced column options for the index.
* When specified, these options override the simple columnNames for index generation.
*/
columns?: IndexColumnOptions[];
/**
* Columns to include in the index but not as part of the key (PostgreSQL, MSSQL).
*/
include?: string[];
/** Fill factor for the index as a percentage 0-100 (PostgreSQL, MSSQL). */
fillFactor?: number;
/**
* Whether the index is invisible/hidden from the query optimizer (MySQL 8+, MariaDB 10.6+, MongoDB).
*/
invisible?: boolean;
/**
* Whether the index is disabled (MSSQL only).
*/
disabled?: boolean;
/**
* Whether the index should be clustered (MariaDB, MSSQL).
*/
clustered?: boolean;
}
export interface CheckDef<T = unknown> {
name: string;
expression: string | CheckCallback<T>;
definition?: string;
columnName?: string;
}
export interface ColumnDifference {
oldColumnName: string;
column: Column;
fromColumn: Column;
changedProperties: Set<string>;
}
export interface TableDifference {
name: string;
changedComment?: string;
fromTable: DatabaseTable;
toTable: DatabaseTable;
addedColumns: Dictionary<Column>;
changedColumns: Dictionary<ColumnDifference>;
removedColumns: Dictionary<Column>;
renamedColumns: Dictionary<Column>;
addedIndexes: Dictionary<IndexDef>;
changedIndexes: Dictionary<IndexDef>;
removedIndexes: Dictionary<IndexDef>;
renamedIndexes: Dictionary<IndexDef>;
addedChecks: Dictionary<CheckDef>;
changedChecks: Dictionary<CheckDef>;
removedChecks: Dictionary<CheckDef>;
addedForeignKeys: Dictionary<ForeignKey>;
changedForeignKeys: Dictionary<ForeignKey>;
removedForeignKeys: Dictionary<ForeignKey>;
}
export interface DatabaseView {
name: string;
schema?: string;
definition: string;
/** True if this is a materialized view (PostgreSQL only). */
materialized?: boolean;
/** For materialized views, whether data was populated on creation. */
withData?: boolean;
}
export interface SchemaDifference {
newNamespaces: Set<string>;
newNativeEnums: {
name: string;
schema?: string;
items: string[];
}[];
newTables: Dictionary<DatabaseTable>;
changedTables: Dictionary<TableDifference>;
removedTables: Dictionary<DatabaseTable>;
newViews: Dictionary<DatabaseView>;
changedViews: Dictionary<{
from: DatabaseView;
to: DatabaseView;
}>;
removedViews: Dictionary<DatabaseView>;
removedNamespaces: Set<string>;
removedNativeEnums: {
name: string;
schema?: string;
}[];
orphanedForeignKeys: ForeignKey[];
fromSchema: DatabaseSchema;
}
export interface IQueryBuilder<T> {
readonly alias: string;
readonly type: QueryType;
/** @internal */
state: {
fields?: InternalField<T>[];
[key: string]: any;
};
/** @internal */
helper: any;
select(fields: string | RawQueryFragment | (string | RawQueryFragment)[], distinct?: boolean): this;
addSelect(fields: string | string[]): this;
from<T extends object>(target: EntityName<T> | IQueryBuilder<T>, aliasName?: string): IQueryBuilder<T>;
insert(data: any): this;
update(data: any): this;
delete(cond?: FilterQuery<any>): this;
truncate(): this;
count(field?: string | string[], distinct?: boolean): this;
join(field: string, alias: string, cond?: FilterQuery<any>, type?: JoinType, path?: string): this;
innerJoin(field: string, alias: string, cond?: FilterQuery<any>): this;
leftJoin(field: string, alias: string, cond?: FilterQuery<any>): this;
joinAndSelect(field: any, alias: string, cond?: FilterQuery<any>): this;
leftJoinAndSelect(field: any, alias: string, cond?: FilterQuery<any>, fields?: string[]): this;
innerJoinAndSelect(field: any, alias: string, cond?: FilterQuery<any>, fields?: string[]): this;
withSubQuery(subQuery: RawQueryFragment | NativeQueryBuilder, alias: string): this;
where(
cond: FilterQuery<T> | string | RawQueryFragment | Dictionary,
operator?: keyof typeof GroupOperator | any[],
operator2?: keyof typeof GroupOperator,
): this;
andWhere(cond: FilterQuery<T> | string | RawQueryFragment | Dictionary, params?: any[]): this;
orWhere(cond: FilterQuery<T> | string | RawQueryFragment | Dictionary, params?: any[]): this;
orderBy(orderBy: QueryOrderMap<T>): this;
groupBy(fields: (string | keyof T) | (string | keyof T)[]): this;
having(cond?: FilterQuery<any> | string, params?: any[]): this;
getAliasForJoinPath(path: string, options?: ICriteriaNodeProcessOptions): string | undefined;
getJoinForPath(path?: string, options?: ICriteriaNodeProcessOptions): JoinOptions | undefined;
getNextAlias(entityName?: string | EntityName<T>): string;
clone(reset?: boolean | string[], preserve?: string[]): IQueryBuilder<T>;
setFlag(flag: QueryFlag): this;
unsetFlag(flag: QueryFlag): this;
hasFlag(flag: QueryFlag): boolean;
with(name: string, query: AnyQueryBuilder | NativeQueryBuilder | RawQueryFragment, options?: CteOptions): this;
withRecursive(
name: string,
query: AnyQueryBuilder | NativeQueryBuilder | RawQueryFragment,
options?: CteOptions,
): this;
scheduleFilterCheck(path: string): void;
withSchema(schema: string): this;
}
export interface ICriteriaNodeProcessOptions {
alias?: string;
matchPopulateJoins?: boolean;
ignoreBranching?: boolean;
preferNoBranch?: boolean;
type?: 'orderBy' | 'having';
filter?: boolean;
parentPath?: string;
}
export interface ICriteriaNode<T extends object> {
readonly entityName: EntityName<T>;
readonly parent?: ICriteriaNode<T> | undefined;
readonly key?: string | symbol | undefined;
readonly strict?: boolean;
payload: any;
prop?: EntityProperty;
index?: number;
process(qb: IQueryBuilder<T>, options?: ICriteriaNodeProcessOptions): any;
shouldInline(payload: any): boolean;
willAutoJoin(qb: IQueryBuilder<T>, alias?: string, options?: ICriteriaNodeProcessOptions): boolean;
shouldRename(payload: any): boolean;
renameFieldToPK<T>(qb: IQueryBuilder<T>, ownerAlias?: string): string;
getPath(opts?: { addIndex?: boolean }): string;
getPivotPath(path: string): string;
}
export type MaybeReturnType<T> = T extends (...args: any[]) => infer R ? R : T;
export type InferEntityProperties<Schema> =
Schema extends EntitySchemaWithMeta<any, any, any, any, infer Properties> ? Properties : never;
export type InferKyselyDB<
TEntities extends {
name: string;
},
TOptions extends MikroKyselyPluginOptions = {},
> = MapValueAsTable<MapTableName<TEntities, TOptions>, TOptions>;
export type InferDBFromKysely<TKysely extends Kysely<any>> = TKysely extends Kysely<infer TDB> ? TDB : never;
type PreferStringLiteral<TCandidate, TFallback> = [TCandidate] extends [never]
? TFallback
: string extends TCandidate
? TFallback
: TCandidate extends string
? TCandidate
: TFallback;
export type MapTableName<
T extends {
name: string;
tableName?: string;
},
TOptions extends MikroKyselyPluginOptions = {},
> = {
[P in T as TOptions['tableNamingStrategy'] extends 'entity'
? P['name']
: PreferStringLiteral<NonNullable<P['tableName']>, P['name']>]: P;
};
export type MapValueAsTable<TMap extends Record<string, any>, TOptions extends MikroKyselyPluginOptions = {}> = {
[K in keyof TMap as TransformName<
K,
TOptions['tableNamingStrategy'] extends 'entity' ? 'entity' : 'underscore'
>]: InferKyselyTable<TMap[K], TOptions>;
};
export type InferKyselyTable<
TSchema extends EntitySchemaWithMeta,
TOptions extends MikroKyselyPluginOptions = {},
> = ExcludeNever<{
-readonly [K in keyof InferEntityProperties<TSchema> as TransformColumnName<
K,
TOptions['columnNamingStrategy'] extends 'property' ? 'property' : 'underscore',
MaybeReturnType<InferEntityProperties<TSchema>[K]>
>]: InferColumnValue<
MaybeReturnType<InferEntityProperties<TSchema>[K]>,
TOptions['processOnCreateHooks'] extends true ? true : false
>;
}>;
type TransformName<TName, TNamingStrategy extends 'underscore' | 'entity'> = TNamingStrategy extends 'underscore'
? TName extends string
? SnakeCase<TName>
: TName
: TName;
type TransformColumnName<
TName,
TNamingStrategy extends 'underscore' | 'property',
TBuilder,
> = TNamingStrategy extends 'property'
? TName
: TBuilder extends {
'~options': {
fieldName: string;
};
}
? TBuilder['~options']['fieldName']
: TName extends string
? MaybeJoinColumnName<SnakeCase<TName>, TBuilder>
: never;
type MaybeJoinColumnName<TName extends string, TBuilder> = TBuilder extends {
'~type'?: {
value: infer Value;
};
'~options': {
kind: 'm:1';
};
}
? PrimaryProperty<Value> extends string
? `${TName}_${SnakeCase<PrimaryProperty<Value>>}`
: never
: TBuilder extends {
'~type'?: {
value: infer Value;
};
'~options': {
kind: '1:1';
owner: true;
};
}
? PrimaryProperty<Value> extends string
? `${TName}_${SnakeCase<PrimaryProperty<Value>>}`
: never
: TName;
export type SnakeCase<TName extends string> = TName extends `${infer A}${infer B}${infer Rest}`
? IsUpperLetter<B> extends never
? `${Lowercase<A>}${SnakeCase<`${B}${Rest}`>}`
: IsLowerLetter<A> extends never
? `${Lowercase<A>}${SnakeCase<`${B}${Rest}`>}`
: `${Lowercase<A>}_${SnakeCase<`${B}${Rest}`>}`
: Lowercase<TName>;
type IsLowerLetter<C extends string> = C extends Lowercase<C> ? (C extends Uppercase<C> ? never : C) : never;
type IsUpperLetter<C extends string> = C extends Uppercase<C> ? (C extends Lowercase<C> ? never : C) : never;
type InferColumnValue<TBuilder, TProcessOnCreate extends boolean> = TBuilder extends {
'~type'?: {
value: infer Value;
};
'~options': infer TOptions;
}
? MaybeNever<MaybeGenerated<MaybeJoinKey<Value, TOptions>, TOptions, TProcessOnCreate>, TOptions>
: never;
type MaybeGenerated<TValue, TOptions, TProcessOnCreate extends boolean> = TOptions extends {
nullable: true;
}
? TValue | null
: TOptions extends {
autoincrement: true;
}
? Generated<TValue>
: TOptions extends {
default: true;
}
? Generated<TValue>
: TOptions extends {
defaultRaw: true;
}
? Generated<TValue>
: TProcessOnCreate extends false
? TValue
: TOptions extends {
onCreate: Function;
}
? Generated<TValue>
: TValue;
type MaybeJoinKey<TValue, TOptions> = TOptions extends {
kind: 'm:1';
}
? UnwrapOpt<Primary<TValue>>
: TOptions extends {
kind: '1:1';
}
? TOptions extends {
owner: true;
}
? UnwrapOpt<Primary<TValue>>
: never
: TValue;
type UnwrapOpt<TValue> = TValue extends Opt<infer OriginalValue> ? OriginalValue : TValue;
type MaybeNever<TValue, TOptions> = TOptions extends
| {
persist: false;
}
| {
kind: 'm:n' | '1:m';
}
? never
: TValue;
type ExcludeNever<TMap extends Record<string, any>> = {
[K in keyof TMap as TMap[K] extends never ? never : K]: TMap[K];
};
export type InferClassEntityDB<TEntities, TOptions extends MikroKyselyPluginOptions = {}> =
ClassEntityDBMap<TEntities, TOptions> extends infer R ? ([keyof R] extends [never] ? unknown : R) : never;
type ClassEntityDBMap<TEntities, TOptions extends MikroKyselyPluginOptions = {}> = {
[T in TEntities as ClassEntityTableName<T, TOptions>]: ClassEntityColumns<T>;
};
type ClassEntityTableName<T, TOptions extends MikroKyselyPluginOptions = {}> = T extends abstract new (
...args: any[]
) => infer Instance
? TransformName<InferEntityName<Instance>, TOptions['tableNamingStrategy'] extends 'entity' ? 'entity' : 'underscore'>
: never;
type ClassEntityColumns<T> = T extends abstract new (...args: any[]) => infer Instance
? {
[K in keyof Instance as IsClassEntityColumn<K, Instance[K]>]: Instance[K];
}
: never;
type IsClassEntityColumn<K, V> = K extends symbol ? never : NonNullable<V> extends Scalar ? K : never;
export {};