Skip to content
VibORM
Esc
navigateopen⌘Jpreview
On this page

One-to-Many

Define one-to-many relationships connecting a single record to multiple related records

Basic Example

import { s } from "viborm";

// One user has many posts
const user = s.model({
  id: s.string().id().ulid(),
  email: s.string().unique(),
  posts: s.oneToMany(() => post),  // Array of posts
});

// Each post belongs to one user (many-to-one side)
const post = s.model({
  id: s.string().id().ulid(),
  title: s.string(),
  authorId: s.string(),
  author: s.manyToOne(() => user)
    .fields("authorId")
    .references("id"),
});

Characteristics

Aspect Value
Returns Array (Post[])
FK location On the “many” side
Can be empty Yes (empty array)
Optional modifier No (arrays are never null)

No FK on This Side

The distinctive rule of one-to-many: this side does NOT own a foreign key, so it needs almost no configuration. All FK setup lives on the many-to-one side:

// ✅ Correct - no FK configuration needed
posts: s.oneToMany(() => post)

// ❌ Wrong - oneToMany doesn't have fields/references
posts: s.oneToMany(() => post).fields("???")

The only available method is .name(relationName) for a custom relation name — see the relation method reference.

Querying One-to-Many

// Include posts, filtered and paginated
const user = await client.user.findUnique({
  where: { id: "user_123" },
  include: {
    posts: {
      where: { published: true },
      orderBy: { createdAt: "desc" },
      take: 10,
    }
  }
});
// user.posts: Post[]

// Filter users by their posts
const authors = await client.user.findMany({
  where: {
    posts: {
      some: { published: true }  // Has at least one published post
    }
  }
});

See To-Many Relation Filters for some/every/none and Nested Writes for creating related records.

Common Pattern: Blog with Categories

const category = s.model({
  id: s.string().id().ulid(),
  name: s.string().unique(),
  posts: s.oneToMany(() => post),
});

const post = s.model({
  id: s.string().id().ulid(),
  title: s.string(),
  categoryId: s.string(),
  category: s.manyToOne(() => category)
    .fields("categoryId")
    .references("id"),
});

Was this page helpful?