PrismaとSQLのリレーションシップをマスターする

Prismaが接続をどのように処理するかを理解すれば、データベースの操作は非常にシンプルになります。ここでは、スキーマ、リレーションシップ、およびクエリに関するガイドを紹介します。

スキーマとリレーションシップ

リレーションシップは、データがどのように接続されるかを定義します。

  • 一対多 (One-to-Many): 1人のユーザーが複数の投稿を持つ場合。Postモデルが外部キー (authorId) を保持し、Userモデルは単に参照を保持します。
  • 多対多 (Many-to-Many): 1人のユーザーが複数のプロジェクトに所属し、1つのプロジェクトに複数のユーザーがいる場合。間に中間テーブル (ProjectMember) が必要です。このテーブルは両方の側の外部キーを保持します。
  • 自己参照リレーション (Self-Relations): あるユーザーが別のユーザーをフォローする場合。「Follower」や「Following」のような名前付きのリレーションを使用することで、Prismaはどちらの側が何であるかを識別できます。

主要なクエリメソッド

  • findUnique: @id または @unique フィールドを持つレコードに使用します。見つからない場合は null を返します。
  • findMany: リストを取得するために使用します。フィルタリング、ソート、ページネーションが可能です。
  • findFirst: 1つのレコードが必要だが、フィルタリングに使用するフィールドがユニークではない場合に使用します。

where によるフィルタリング

where 句は SQL に直接マッピングされます。

  • 比較: gt (より大きい)、lt (より小さい)、または gte (以上) を使用します。
  • テキスト検索: 大文字小文字を区別しない検索を行うには、"contains""mode: insensitive" を使用します。
  • 論理演算子: ORAND、または NOT を使用して条件を組み合わせます。
  • リレーションフィルタ: 接続されたデータに基づいてフィルタリングするには、"some""every"、または "none" を使用します。"some" は、少なくとも1つのリレーションが一致するレコードを見つけます。

データ制御: select vs include

  • select: 返却するフィールドを正確に選択します。これにより、データを軽量かつ安全に保つことができます。
  • include: 関連データを結果に結合します。これにより、ネストされたオブジェクトを取得できます。
  • 注意: 同じレベルで selectinclude を同時に使用することはできません。どちらか一方を選択する必要があります。ただし、include の中で select を使用して、結合されたリレーションから特定のフィールドを選択することは可能です。

操作と安全性

  • createMany: 複数の行を一度に作成します。高速ですが、ネストされた書き込みはサポートされていません。
  • upsert: レコードが存在する場合は更新し、存在しない場合は作成します。ショッピングカートの実装などに最適です。
  • update: 数値をエラーなく変更するために、incrementdecrement などのアトミックな操作を使用します。
  • $transaction: 複数の書き込みをグループ化します。一部が失敗した場合、グループ全体がロールバックされます。これにより、データの不整合を防ぐことができます。

ページネーション

「take」と「skip」を組み合わせてページを作成します。

  • take: 表示するレコード数
  • skip: スキップするレコード数

出典: https://dev.to/chinwuba_jeffrey/understanding-prisma-and-sql-relationships-schema-and-querying-l7k