flint-orm
Version:
Type-safe SQLite ORM for JavaScript
99 lines (98 loc) • 4.18 kB
TypeScript
import type { ColumnDef, DateColumnDef, DateColumnDefWithDefault } from './columns';
/** A table definition mapping column names to their `ColumnDef`s. */
export type TableDef<T> = T & {
readonly _: {
readonly name: string;
};
};
export declare function table<T extends Record<string, ColumnDef<any, any>>>(name: string, columns: T, indexFn?: (t: TableDef<T>) => (IndexBuilder | PrimaryKeyBuilder)[]): TableDef<T>;
/**
* Derive the row shape from a table's column definitions.
* DateColumnDef → Date | null (nullable unless defaultNow() was called)
* DateColumnDefWithDefault → Date (non-nullable, has a guaranteed default)
* All other columns → their _type as-is.
*
* Uses `infer C` to extract the column record from TableDef<T> so TypeScript
* evaluates the mapped type against the concrete columns, not the intersection.
* This produces cleaner hover info: { id: string; name: string } instead of
* Pick<InferRow<TableDef<{...}>>, ...>.
*/
export type InferRow<T extends TableDef<any>> = T extends TableDef<infer C> ? {
[K in keyof Omit<C, '_'>]: C[K] extends DateColumnDefWithDefault ? Date : C[K] extends DateColumnDef ? Date | null : C[K] extends ColumnDef<any, any> ? C[K]['__internal']['_type'] : never;
} : never;
/** The row type for inserts — columns with auto-defaults (integer, date) are optional. */
export type InsertRow<T extends TableDef<any>> = {
[K in keyof Omit<T, '_'> as HasAutoDefault<T[K]> extends true ? never : K]: T[K] extends ColumnDef<any, any> ? T[K]['__internal']['_type'] : never;
} & {
[K in keyof Omit<T, '_'> as HasAutoDefault<T[K]> extends true ? K : never]?: T[K] extends ColumnDef<any, any> ? T[K]['__internal']['_type'] : never;
};
/**
* Define a table with auto snake_case column names.
* Column names are inferred from object keys and converted to snake_case.
* Column constructors can be called without a name.
*
* @example
* const users = snakeCase.table("users", {
* id: text().primaryKey(),
* firstName: text(),
* });
*/
export declare function snakeCaseTable<T extends Record<string, ColumnDef<any, any>>>(tableName: string, columns: T, indexFn?: (t: TableDef<T>) => (IndexBuilder | PrimaryKeyBuilder)[]): TableDef<T>;
/** Provides `snakeCase.table()` for auto snake_case column naming. */
export declare const snakeCase: {
table: typeof snakeCaseTable;
};
/** An index definition — used internally by the migration system. */
export interface IndexDef {
name: string;
columns: string[];
unique: boolean;
}
/** Public builder returned by `index()` — chain `.on(columns)` then `.unique()`. */
export interface IndexBuilder {
/** Add one or more columns to the index. */
on(...columns: ColumnDef<any, any>[]): IndexBuilder;
/** Mark the index as unique. */
unique(): IndexBuilder;
}
/** A composite primary key definition — used internally by the migration system. */
export interface PrimaryKeyDef {
columns: string[];
}
/** Public builder returned by `primaryKey()` — chain `.on(columns)`. */
export interface PrimaryKeyBuilder {
/** Add one or more columns to the composite primary key. */
on(...columns: ColumnDef<any, any>[]): PrimaryKeyBuilder;
}
/**
* Create a composite primary key definition using a chainable API.
*
* @param name - Optional name (reserved for future use, currently unused in SQL)
* @returns A PrimaryKeyBuilder — chain `.on(columns)`
*
* @example
* const userRoles = table("user_roles", {
* userId: text("user_id"),
* roleId: text("role_id"),
* }, (t) => [
* primaryKey().on(t.userId, t.roleId),
* ]);
*/
export declare function primaryKey(): PrimaryKeyBuilderInternal;
/**
* Create an index definition using a chainable API.
*
* @param name - The index name (will be used as-is in SQL)
* @returns An IndexBuilder — chain `.on(columns)` then `.unique()`
*
* @example
* const users = table("users", {
* id: text("id").primaryKey(),
* email: text("email"),
* name: text("name"),
* }, (t) => [
* index("idx_users_email").on(t.email).unique(),
* index("idx_users_name").on(t.name),
* ]);
*/
export declare function index(name: string): IndexBuilderInternal;