フィールドの選択
概要
デフォルトでは、クエリがレコードを返す場合(カウントとは対照的に)、結果には以下が含まれます
- モデルのすべてのスカラフィールド(enumを含む)
- モデルに定義されたリレーションは含まれません
例として、このスキーマを考えてみましょう
model User {
id Int @id @default(autoincrement())
email String @unique
name String?
role Role @default(USER)
posts Post[]
}
model Post {
id Int @id @default(autoincrement())
published Boolean @default(false)
title String
author User? @relation(fields: [authorId], references: [id])
authorId Int?
}
enum Role {
USER
ADMIN
}
`User`モデルへのクエリには、`id`、`email`、`name`、`role`フィールドが含まれます(これらはスカラフィールドであるため)が、`posts`フィールドは含まれません(これはリレーションフィールドであるため)
const users = await prisma.user.findFirst()
{
id: 42,
name: "Sabelle",
email: "sabelle@prisma.io",
role: "ADMIN"
}
結果をカスタマイズして、異なるフィールドの組み合わせを返したい場合は、以下を使用できます
select
を使用して、特定のフィールドを返します。また、リレーションフィールドを選択することで、ネストされたselect
を使用します。omit
を使用して、結果から特定のフィールドを除外します。omit
はselect
の「反対」と見なすことができます。include
を使用して、さらにリレーションを含めます。
どの場合でも、クエリ結果は静的に型付けされ、データベースから実際にクエリしなかったフィールドに誤ってアクセスすることがないようにします。
デフォルトの選択セットに頼るのではなく、必要なフィールドとリレーションのみを選択すると、レスポンスのサイズを縮小し、クエリ速度を向上させることができます。
バージョン 5.9.0 以降、リレーションクエリを include
で行う場合、またはリレーションフィールドで select
を使用する場合、relationLoadStrategy
を指定して、データベースレベルの結合を使用するか、複数のクエリを実行してアプリケーションレベルでデータをマージするかを決定できます。この機能は現在 プレビュー にあります。詳細についてはこちらをご覧ください。
スキーマ例
このページの以降の例はすべて、次のスキーマに基づいています
model User {
id Int @id
name String?
email String @unique
password String
role Role @default(USER)
coinflips Boolean[]
posts Post[]
profile Profile?
}
model Post {
id Int @id
title String
published Boolean @default(true)
author User @relation(fields: [authorId], references: [id])
authorId Int
}
model Profile {
id Int @id
biography String
user User @relation(fields: [userId], references: [id])
userId Int @unique
}
enum Role {
USER
ADMIN
}
デフォルトフィールドを返す
次のクエリは、デフォルトフィールド(すべてのスカラフィールド、リレーションなし)を返します
const user = await prisma.user.findFirst()
{
id: 22,
name: "Alice",
email: "alice@prisma.io",
password: "mySecretPassword42"
role: "ADMIN",
coinflips: [true, false],
}
特定のフィールドを選択
select
を使用して、すべてのフィールドではなく、フィールドのサブセットを返します。次の例では、email
フィールドと name
フィールドのみを返します
const user = await prisma.user.findFirst({
select: {
email: true,
name: true,
},
})
{
name: "Alice",
email: "alice@prisma.io",
}
リレーションフィールドを選択してネストされたオブジェクトを返す
また、リレーションフィールドで select
を複数回ネストすることでリレーションを返すこともできます。
次のクエリは、ネストされた select
を使用して、各ユーザーの name
と、関連する各投稿の title
を選択します
const usersWithPostTitles = await prisma.user.findFirst({
select: {
name: true,
posts: {
select: { title: true },
},
},
})
{
"name":"Sabelle",
"posts":[
{ "title":"Getting started with Azure Functions" },
{ "title":"All about databases" }
]
}
次のクエリは、include
内で select
を使用し、すべてのユーザーフィールドと各投稿の title
フィールドを返します
const usersWithPostTitles = await prisma.user.findFirst({
include: {
posts: {
select: { title: true },
},
},
})
{
id: 9
name: "Sabelle",
email: "sabelle@prisma.io",
password: "mySecretPassword42",
role: "USER",
coinflips: [],
posts:[
{ title:"Getting started with Azure Functions" },
{ title:"All about databases" }
]
}
クエリは任意に深くネストできます。次のクエリはフェッチします
Post
のtitle
- 関連する
User
のname
- 関連する
Profile
のbiography
const postsWithAuthorsAndProfiles = await prisma.post.findFirst({
select: {
title: true,
author: {
select: {
name: true,
profile: {
select: { biography: true }
}
},
},
},
})
{
id: 9
title:"All about databases",
author: {
name: "Sabelle",.
profile: {
biography: "I like turtles"
}
}
}
リレーションを深くネストする場合は注意してください。基盤となるデータベースクエリが、多数の異なるテーブルにアクセスする必要があるために遅くなる可能性があります。クエリが常に最適な速度を持つようにするには、Prisma Accelerate でキャッシュレイヤーを追加するか、Prisma Optimize を使用して、クエリの洞察とパフォーマンス最適化の推奨事項を取得することを検討してください。
リレーションのクエリの詳細については、次のドキュメントを参照してください
特定のフィールドを省略
モデルのほとんどのフィールドを返したいが、小さなサブセットのみを除外したい状況があるかもしれません。これの一般的な例は、User
をクエリするが、セキュリティ上の理由から password
フィールドを除外したい場合です。
このような場合、omit
を使用できます。これは select
の対応物と見なすことができます
const users = await prisma.user.findFirst({
omit: {
password: true
}
})
{
id: 9
name: "Sabelle",
email: "sabelle@prisma.io",
profileViews: 90,
role: "USER",
coinflips: [],
}
返されたオブジェクトに password
フィールドが含まれていないことに注意してください。
リレーション数
3.0.1 以降では、include
または select
を使用してリレーションのカウントをフィールドとともにカウントできます。たとえば、ユーザーの投稿数などです。