【GraphQL】スキーマの設計 - コネクションとリストについて
概要
GraphQLコネクションとリストについてまとめる
GraphQLのスキーマを作成するとき、フィールドにGraphQLの型のリストを指定することができる。
リストはGraphQLの型を大括弧で囲むことで表現できるので、
[String]
と記述することでString型のリストを表すことができる。
一対一の接続
カスタムオブジェクト型のフィールドを定義するときには、2つのオブジェクトを接続することになる。
例えば、PhotoはUserによって投稿されるイメージ。
この接続部分のことをエッジと呼ぶそうなので、以後この言葉を使っていきます。
Photoはその投稿者であるUserとの間にエッジがあるはずで、以下のようにスキーマを定義する。
type User {
githubLogin: ID!
name: String
avatar: String
}
type Photo {
id: ID!
name: String!
url: String!
description: String
created: Datetime!
category: PhotoCategory!
postedBy: User!
}
スキーマに新しい型を定義し、それをPhotoにpostedByフィールドを追加し、2つの型を接続する。
この場合、すべてのPhotoには必ず投稿者(User)が存在するため、末尾にビックリマークを追加した。
一対多の接続
GraphQLは基本的に向無グラフ(各枝の始点と終点がどちらであるかを気にしないグラフ)にしておくべき
これを実現するために、User型とPhoto型の間に双方向にエッジを作成する。
type User {
githubLogin: ID!
name: String
avatar: String
postedPhotos: [Photo!]!
}
※[Photo!]! → nullではないリストで中身はnullではないPhoto型
User型にpostedPhotosフィールドを追加することで、UserからPhotoに向かうエッジを形成できた。
postedPhotosフィールドはPhotoのリストを返すことになる。
多対多の接続
ノードのリストとノードのリストを接続したい場合(例:写真共有アプリで投稿された写真に写っているUserを登録する機能。いわゆるタグ付け)は、Photoは多くのUserから構成され、Userは多くのPhotoにタグ付けされるようになる。
このような接続を実現するためには、UserとPhotoの両方にお互いのリストのフィールドを追加する必要がある。
type User {
......
inPhotos: [Photo!]!
}
type Photo {
......
taggedUsers: [User!]!
}
双方向に一対多の接続を定義し、多対多の接続が表現できる。