Error Handling
SlintORM wraps all driver errors into a unified ORMError with a typed ormCode. No more parsing raw SQLite errno or Postgres pgError codes per-driver.
Catching ORMError
// Import ORMError and ORMErrorCode
import { ORMError, ORMErrorCode } from 'slintorm';
try {
await User.insert({ email: 'duplicate@example.com', name: 'Alice' });
} catch (err) {
if (err instanceof ORMError) {
switch (err.ormCode) {
case ORMErrorCode.UNIQUE_VIOLATION:
console.log(`Duplicate value on column: ${err.column}`);
break;
case ORMErrorCode.NOT_NULL_VIOLATION:
console.log(`Required column missing: ${err.column}`);
break;
case ORMErrorCode.FOREIGN_KEY_VIOLATION:
console.log(`Foreign key broken: ${err.column}`);
break;
case ORMErrorCode.CHECK_VIOLATION:
console.log(`Check constraint failed: ${err.column}`);
break;
case ORMErrorCode.UNKNOWN_CONSTRAINT:
console.log('Unknown constraint error:', err.message);
break;
}
}
}ORMError properties
// ORMError properties
err.ormCode // ORMErrorCode — one of the 5 codes below
err.table // string | undefined — the affected table
err.column // string | undefined — the affected column
err.value // unknown — the value that caused the violation
err.sql // string | undefined — the SQL that was executed
err.params // unknown[] | undefined — bound parameters
err.message // string — human-readable error message
err.original // unknown — the original driver error (raw pg/mysql2/sqlite3 error)ORMErrorCode values
Error codes (raw)
// ORMErrorCode values
ORMErrorCode.UNIQUE_VIOLATION // Duplicate value in a UNIQUE or PRIMARY KEY column
ORMErrorCode.NOT_NULL_VIOLATION // NULL inserted into a NOT NULL column
ORMErrorCode.FOREIGN_KEY_VIOLATION // References a non-existent foreign key
ORMErrorCode.CHECK_VIOLATION // Value failed a CHECK constraint or ENUM restriction
ORMErrorCode.UNKNOWN_CONSTRAINT // Constraint error that doesn't match the known patternsPer-driver parsing
// Per-driver error parsing (done automatically by wrapExec)
// SQLite — detects by errno 19 (SQLITE_CONSTRAINT) and message parsing
// UNIQUE_VIOLATION -> "UNIQUE constraint failed: table.column"
// NOT_NULL_VIOLATION -> "NOT NULL constraint failed: table.column"
// FOREIGN_KEY_VIOLATION -> "FOREIGN KEY constraint failed"
// CHECK_VIOLATION -> "CHECK constraint failed: ..."
// PostgreSQL — detects by pgError code
// 23505 -> UNIQUE_VIOLATION
// 23502 -> NOT_NULL_VIOLATION
// 23503 -> FOREIGN_KEY_VIOLATION
// 23514 -> CHECK_VIOLATION
// MySQL — detects by mysql error code string
// ER_DUP_ENTRY -> UNIQUE_VIOLATION
// ER_BAD_NULL_ERROR -> NOT_NULL_VIOLATION
// ER_NO_REFERENCED_ROW_2 -> FOREIGN_KEY_VIOLATION
// ER_CHECK_CONSTRAINT_VIOLATED -> CHECK_VIOLATIONIn a Next.js API route
app/api/users/route.ts
// Handling ORMError in a Next.js API route
import { NextRequest, NextResponse } from 'next/server';
import { ORMError, ORMErrorCode } from 'slintorm';
import { User } from '@/db';
export async function POST(req: NextRequest) {
try {
const body = await req.json();
const user = await User.insert(body);
return NextResponse.json({ id: user.id }, { status: 201 });
} catch (err) {
if (err instanceof ORMError) {
if (err.ormCode === ORMErrorCode.UNIQUE_VIOLATION) {
return NextResponse.json(
{ error: 'Email already registered' },
{ status: 409 }
);
}
if (err.ormCode === ORMErrorCode.NOT_NULL_VIOLATION) {
return NextResponse.json(
{ error: `Missing required field: ${err.column}` },
{ status: 400 }
);
}
}
throw err; // re-throw unexpected errors
}
}