Models
A model is a plain TypeScript interface. Annotations in line comments above each field control column types, constraints, and relations. No separate schema file needed.
Basic model
src/models.ts
// src/models.ts
interface User {
// @auto;primaryKey
id: number;
// @unique
email: string;
name: string;
// @nullable
bio: string;
// @default:user
role: string;
// @json
settings: Record<string, unknown>;
// @softDelete
deletedAt: string;
createdAt: string; // injected automatically
updatedAt: string; // injected automatically
}Relations
src/models.ts
interface Post {
// @auto;primaryKey
id: number;
title: string;
// @length:5000
body: string;
// @default:false
published: boolean;
// @index
userId: number;
// @relation manytoone:User;foreignKey:userId
user?: User;
// @relation onetomany:Comment;foreignKey:postId
comments?: Comment[];
}Many-to-many
src/models.ts
interface Team {
// @auto;primaryKey
id: number;
name: string;
// @relation manytomany:User;through:team_members;foreignKey:teamId;relatedKey:userId
members?: User[];
}One-to-one
src/models.ts
interface Profile {
// @auto;primaryKey
id: number;
// @unique
userId: number;
// @nullable
avatarUrl: string;
// @relationship onetoone:User;foreignKey:userId;onDelete:CASCADE
user?: User;
}Enum fields
src/models.ts
interface Todo {
// @auto;primaryKey
id: number;
title: string;
// @enum:(pending,in_progress,done)
status: string;
// @not null
priority: number;
}Field metadata reference
Annotations go in a // comment on the line directly above the field. Both @-prefixed and bare variants are supported by the migrator.
Automatic columns
createdAt and updatedAt are injected into every table automatically.deletedAt is only added when a field is annotated with @softDelete. You don't need to declare these unless you want to customize their behavior.