import type { PgDatabase, PgQueryResultHKT, PgTransaction, PgTransactionConfig } from 'drizzle-orm/pg-core'
import type { ExtractTablesWithRelations } from 'drizzle-orm'

/** The host's drizzle schema (pgTables + relations). db core defines none — it is generic over this. */
export type Schema = Record<string, unknown>

/** Query-capable handle WITHOUT interactive transactions. What `./postgres/neon-http` returns. */
export type Database<S extends Schema = Record<string, never>> =
  Omit<PgDatabase<PgQueryResultHKT, S, ExtractTablesWithRelations<S>>, 'transaction'>

/** The handle inside a `.transaction()` callback. */
export type Transaction<S extends Schema = Record<string, never>> =
  PgTransaction<PgQueryResultHKT, S, ExtractTablesWithRelations<S>>

/** Adds interactive transactions back. What `./postgres/neon-serverless`, `./postgres/postgres-js`, `./postgres/pglite` return. */
export type TransactionalDatabase<S extends Schema = Record<string, never>> = Database<S> & {
  transaction<T>(fn: (tx: Transaction<S>) => Promise<T>, config?: PgTransactionConfig): Promise<T>
}

/** The workhorse: ANY query-capable handle — in or out of a tx. EVERY query helper accepts this. */
export type Querier<S extends Schema = Record<string, never>> = Database<S> | Transaction<S>

/** Dialect identifier for adapter selection */
export type Dialect = 'postgres' | 'sqlite'
