SQLの外部キーをPrismaの一対多リレーションに変換する
SQLのFOREIGN KEY制約がPrismaの一対多リレーションフィールドにどのように変換されるかを学びます。@relation、references、onDelete、逆参照を解説します。
Relations
詳細な説明
一対多リレーション
最も一般的なSQLリレーションシップは一対多です:1つの親レコードが外部キーを通じて多くの子レコードを持ちます。Prismaはこれを両側のリレーションフィールドでモデル化します。
SQLの例
CREATE TABLE users (
id SERIAL PRIMARY KEY,
name VARCHAR(255) NOT NULL
);
CREATE TABLE posts (
id SERIAL PRIMARY KEY,
title VARCHAR(255) NOT NULL,
content TEXT,
author_id INTEGER NOT NULL,
CONSTRAINT fk_posts_author FOREIGN KEY (author_id) REFERENCES users(id) ON DELETE CASCADE
);
CREATE INDEX idx_posts_author_id ON posts (author_id);
生成されるPrismaスキーマ
model User {
id Int @id @default(autoincrement())
name String
posts Post[]
@@map("users")
}
model Post {
id Int @id @default(autoincrement())
title String
content String? @db.Text
authorId Int @map("author_id")
author User @relation(fields: [authorId], references: [id], onDelete: Cascade)
@@index([authorId])
@@map("posts")
}
変換の仕組み
- 外部キーカラム(
author_id)は@map付きのスカラーフィールドauthorId Intになります。 - リレーションフィールド(
author)がリンクを指定する@relation(...)付きのUser型として追加されます。 - 逆参照(
posts Post[])が親modelに追加されます。[]は一対多を示します。 - ON DELETEアクションはPrismaの
onDeleteパラメータにマッピングされます。
参照整合性アクション
| SQLアクション | Prismaアクション | 動作 |
|---|---|---|
ON DELETE CASCADE |
Cascade |
親削除時に子を削除 |
ON DELETE SET NULL |
SetNull |
外部キーをnullに設定 |
ON DELETE RESTRICT |
Restrict |
親の削除を防止 |
ON DELETE SET DEFAULT |
SetDefault |
デフォルト値にリセット |
ON DELETE NO ACTION |
NoAction |
トランザクション終了時にDBがチェック |
リレーション名
modelが同じターゲットへの複数のリレーションを持つ場合、Prismaではリレーション名が必要です:
model Post {
authorId Int
author User @relation("PostAuthor", fields: [authorId], references: [id])
reviewerId Int?
reviewer User? @relation("PostReviewer", fields: [reviewerId], references: [id])
}
コンバーターは同じテーブルへの複数の外部キーを検出し、説明的なリレーション名を自動生成します。
外部キーのインデックス
Prismaはクエリパフォーマンスのために外部キーフィールドに明示的な@@indexを推奨しています。コンバーターはFKカラムのCREATE INDEXを反映して、これを自動的に追加します。
ユースケース
ユーザーが外部キーを通じて多くの投稿を作成するブログデータベースがある場合に、コンバーターが両方のmodelにPrismaリレーションフィールドを生成し、ON DELETE CASCADEアクションをマッピングし、必要なインデックスを追加します。