import {
  type EntitySchemaWithMeta,
  EntityManager,
  type AnyEntity,
  type ConnectionType,
  type EntityData,
  type EntityName,
  type EntityRepository,
  type GetRepository,
  type QueryResult,
  type FilterQuery,
  type LoggingOptions,
  type RawQueryFragment,
} from '@mikro-orm/core';
import type { AbstractSqlDriver } from './AbstractSqlDriver.js';
import type { NativeQueryBuilder } from './query/NativeQueryBuilder.js';
import type { QueryBuilder } from './query/QueryBuilder.js';
import type { SqlEntityRepository } from './SqlEntityRepository.js';
import type { Kysely } from 'kysely';
import type { InferClassEntityDB, InferKyselyDB } from './typings.js';
import { type MikroKyselyPluginOptions } from './plugin/index.js';
/** Options for `SqlEntityManager.getKysely()`. */
export interface GetKyselyOptions extends MikroKyselyPluginOptions {
  /** Connection type to use (`'read'` or `'write'`). */
  type?: ConnectionType;
}
/**
 * @inheritDoc
 */
export declare class SqlEntityManager<
  Driver extends AbstractSqlDriver = AbstractSqlDriver,
> extends EntityManager<Driver> {
  /**
   * Creates a QueryBuilder instance
   */
  createQueryBuilder<Entity extends object, RootAlias extends string = never>(
    entityName: EntityName<Entity> | QueryBuilder<Entity>,
    alias?: RootAlias,
    type?: ConnectionType,
    loggerContext?: LoggingOptions,
  ): QueryBuilder<Entity, RootAlias>;
  /**
   * Shortcut for `createQueryBuilder()`
   */
  qb<Entity extends object, RootAlias extends string = never>(
    entityName: EntityName<Entity>,
    alias?: RootAlias,
    type?: ConnectionType,
    loggerContext?: LoggingOptions,
  ): QueryBuilder<Entity, RootAlias>;
  /**
   * Returns configured Kysely instance.
   */
  getKysely<TDB = undefined, TOptions extends GetKyselyOptions = GetKyselyOptions>(
    options?: TOptions,
  ): Kysely<
    TDB extends undefined
      ? InferKyselyDB<EntitiesFromManager<this>, TOptions> & InferClassEntityDB<AllEntitiesFromManager<this>, TOptions>
      : TDB
  >;
  /** Executes a raw SQL query, using the current transaction context if available. */
  execute<T extends QueryResult | EntityData<AnyEntity> | EntityData<AnyEntity>[] = EntityData<AnyEntity>[]>(
    query: string | NativeQueryBuilder | RawQueryFragment,
    params?: any[],
    method?: 'all' | 'get' | 'run',
    loggerContext?: LoggingOptions,
  ): Promise<T>;
  getRepository<T extends object, U extends EntityRepository<T> = SqlEntityRepository<T>>(
    entityName: EntityName<T>,
  ): GetRepository<T, U>;
  protected applyDiscriminatorCondition<Entity extends object>(
    entityName: EntityName<Entity>,
    where: FilterQuery<Entity>,
  ): FilterQuery<Entity>;
}
type EntitiesFromManager<TEntityManager extends EntityManager<any>> =
  NonNullable<TEntityManager['~entities']> extends any[]
    ? Extract<NonNullable<TEntityManager['~entities']>[number], EntitySchemaWithMeta>
    : never;
type AllEntitiesFromManager<TEntityManager extends EntityManager<any>> =
  NonNullable<TEntityManager['~entities']> extends any[] ? NonNullable<TEntityManager['~entities']>[number] : never;
export {};
