UNPKG

@decaf-ts/core

Version:

Core persistence module for the decaf framework

95 lines (94 loc) 4.35 kB
import { type Constructor, Model } from "@decaf-ts/decorator-validation"; import type { Executor, RawExecutor } from "../interfaces"; import type { FromSelector, GroupBySelector, OrderBySelector, SelectSelector } from "./selectors"; import { Condition } from "./Condition"; import type { CountOption, DistinctOption, LimitOption, MaxOption, MinOption, OffsetOption, OrderAndGroupOption, SelectOption, WhereOption } from "./options"; import { Paginatable } from "../interfaces/Paginatable"; import { Paginator } from "./Paginator"; import { Adapter } from "../persistence"; import { Logger } from "@decaf-ts/logging"; import { LoggedClass } from "@decaf-ts/logging"; /** * @description Base class for database query statements * @summary Provides a foundation for building and executing database queries * * This abstract class implements the query builder pattern for constructing * database queries. It supports various query operations like select, from, * where, orderBy, groupBy, limit, and offset. It also provides methods for * executing queries and handling pagination. * * @template Q - The query type specific to the database adapter * @template M - The model type this statement operates on * @template R - The return type of the query * @param {Adapter<any, Q, any, any>} adapter - The database adapter to use for executing queries * @class Statement * @example * // Create a statement to query users * const statement = new SQLStatement(adapter); * const users = await statement * .select() * .from(User) * .where(Condition.attribute("status").eq("active")) * .orderBy(["createdAt", "DESC"]) * .limit(10) * .execute(); * * // Use pagination * const paginator = await statement * .select() * .from(User) * .paginate(20); // 20 users per page * * @mermaid * sequenceDiagram * participant Client * participant Statement * participant Adapter * participant Database * * Client->>Statement: select() * Client->>Statement: from(Model) * Client->>Statement: where(condition) * Client->>Statement: orderBy([field, direction]) * Client->>Statement: limit(value) * Client->>Statement: execute() * Statement->>Statement: build() * Statement->>Adapter: raw(query) * Adapter->>Database: execute query * Database-->>Adapter: return results * Adapter-->>Statement: return processed results * Statement-->>Client: return final results */ export declare abstract class Statement<Q, M extends Model, R> extends LoggedClass implements Executor<R>, RawExecutor<Q>, Paginatable<M, R, Q> { protected adapter: Adapter<any, any, Q, any, any>; protected readonly selectSelector?: SelectSelector<M>[]; protected distinctSelector?: SelectSelector<M>; protected maxSelector?: SelectSelector<M>; protected minSelector?: SelectSelector<M>; protected countSelector?: SelectSelector<M>; protected fromSelector: Constructor<M>; protected whereCondition?: Condition<M>; protected orderBySelector?: OrderBySelector<M>; protected groupBySelector?: GroupBySelector<M>; protected limitSelector?: number; protected offsetSelector?: number; protected constructor(adapter: Adapter<any, any, Q, any, any>); protected get log(): Logger; select<S extends readonly SelectSelector<M>[]>(): SelectOption<M, M[]>; select<S extends readonly SelectSelector<M>[]>(selector: readonly [...S]): SelectOption<M, Pick<M, S[number]>[]>; distinct<S extends SelectSelector<M>>(selector: S): DistinctOption<M, M[S][]>; max<S extends SelectSelector<M>>(selector: S): MaxOption<M, M[S]>; min<S extends SelectSelector<M>>(selector: S): MinOption<M, M[S]>; count<S extends SelectSelector<M>>(selector?: S): CountOption<M, number>; from(selector: FromSelector<M>): WhereOption<M, R>; where(condition: Condition<M>): OrderAndGroupOption<M, R>; orderBy(selector: OrderBySelector<M>): LimitOption<M, R> & OffsetOption<R>; groupBy(selector: GroupBySelector<M>): LimitOption<M, R>; limit(value: number): OffsetOption<R>; offset(value: number): Executor<R>; execute(): Promise<R>; raw<R>(rawInput: Q): Promise<R>; protected abstract build(): Q; protected abstract parseCondition(condition: Condition<M>, ...args: any[]): Q; abstract paginate(size: number): Promise<Paginator<M, R, Q>>; }