Kadak

Column Methods

In-depth reference for Kadak shorthand types, kadak.* builders, chain methods, and SQL mappings.

Column Methods

Kadak schema has two paths:

  • Shorthand strings for speed.
  • kadak.* builders for explicit control.

Shorthand to SQL mapping

ShorthandPostgres typeNotes
'id'INTEGERprimary key, generated
'uuidId'UUIDprimary key, default gen_random_uuid()
'serialId'SERIALprimary key, generated
'text'TEXTstring
'int' / 'number'INTEGERinteger
'float'FLOAT8floating number
'decimal'NUMERICstring at runtime for precision
'boolean'BOOLEANtrue/false
'timestamp'TIMESTAMPTZdate/time
'email'TEXTemail validation + unique shortcut in shorthand
'uuid'UUIDuuid validation

Optional shorthand uses ?:

age: 'int?'

Builder constructors (kadak.*)

import { kadak } from '@shyk/kadak-orm'
  • kadak.id()
  • kadak.uuidId()
  • kadak.serialId()
  • kadak.text()
  • kadak.int() / kadak.number()
  • kadak.float()
  • kadak.decimal()
  • kadak.boolean()
  • kadak.timestamp()
  • kadak.email()
  • kadak.uuid()
  • kadak.json(zodSchema)

Chain methods (behavior)

.optional()

Marks column nullable and optional in insert/update validator contexts.

nickname: kadak.text().optional()

SQL effect:

  • allows NULL values

.unique()

Adds unique constraint intent.

email: kadak.email().unique()

SQL effect:

  • UNIQUE

.primaryKey()

Marks column as primary key.

id: kadak.int().primaryKey()

SQL effect:

  • PRIMARY KEY

.name(dbName)

Overrides default camelCase to snake_case mapping for this column.

fullName: kadak.text().name('full_name')

SQL effect:

  • column emitted as full_name

.default(value)

Sets default value. Special shortcuts:

  • timestamp: 'now' => now()
  • uuid: 'uuid' => gen_random_uuid()
createdAt: kadak.timestamp().default('now')

SQL effect:

  • DEFAULT now()

.min(n) / .max(n)

Adds validator constraints (Zod) for text/number flows.

name: kadak.text().min(2).max(120)
age: kadak.number().min(13).max(100)

Runtime effect:

  • request validation guardrails

.autoUpdate()

Auto-injects value on update paths (typically for updatedAt).

updatedAt: kadak.timestamp().default('now').autoUpdate()

.softDelete()

Marks column as soft-delete marker.

deletedAt: kadak.timestamp().softDelete()

Runtime effect:

  • delete() sets this field instead of hard deleting
  • findMany/findFirst exclude soft-deleted rows

Table options with methods

const users = table('users', {
  id: 'id',
  email: kadak.email().unique(),
  name: kadak.text().min(2).max(120),
}, {
  timestamps: true,
  softDelete: true,
})

timestamps: true injects:

  • createdAt: timestamp default now
  • updatedAt: timestamp default now + autoUpdate

softDelete: true injects:

  • deletedAt: timestamp nullable soft-delete marker

Production guidance

  • Start with shorthand for most columns.
  • Use builder chain only where you need explicit constraints/behavior.
  • Keep decimal payloads as strings to avoid float precision issues.
  • Keep DB naming consistent; override with .name() only when needed.

On this page