react-router-relay
アプリに 、 、 の 3 つのページ ( を使用するコンポーネント)ProductList
がありProductDetail
ますBrandList
。
問題を説明するために、フローを順を追って説明し、コードを一番下に残します。
まず、商品のリストに行き
ProductList
、それぞれにブランド名が付いています。期待どおりに動作します。次に、製品の 1 つをクリックすると、これがレンダリングされます
ProductDetail
。すべてが期待どおりに機能します。に行くと
BrandList
、問題はリレーが複数のnode(id: $id_0)
クエリをサーバーに送信することです。
何が起こるかというと、Relay のストアは のbrands
ステップ 2 の後で既にフェッチされていますProductDetail
。そしてステップ 3 で、BrandList
Relay のストアが現在持っているよりも多くのフィールドを要求します。したがって、Relay は複数のnode
クエリを送信します。私は 30 個のブランドを持っているため、30 個のクエリを送信しますが、これは非効率的であり、著しく遅いです。
([A]) と([B]) の両方で同じフィールドを尋ねることで、これを修正できます(以下のクエリを参照してください)。ただし、使用しない不要なフィールドを取得することを意味します。ProductDetail
BrandList
ProductDetail
ここで非常に明白な何かを見逃したのか、それともこの場合に複数ノードのクエリを回避するためのより良い方法があるのか はわかりません。Relay に部分的なデータがすでに保存されていて、より多くのフィールドを取得するためにクエリをbrands
送信しようとしているときに、上記の手順 3 で完全に再フェッチするように Relay に指示できれば、おそらくより良いでしょう。node
// 各コンポーネントに関連するクエリ。以下の [A] と [B] に関するコメントに注意してください。
ProductList
export default Relay.createContainer(ProductList, {
fragments: {
viewer: () => Relay.QL`
fragment on Viewer {
id
products(first: 1000) {
edges {
node {
id
localId
name
brand {
name
}
}
}
}
}
`,
},
})
ProductDetail
export default Relay.createContainer(ProductDetail, {
fragments: {
product: () => Relay.QL`
fragment on Perfume {
id
localId
name
brand {
name
}
}
`,
viewer: () => Relay.QL`
fragment on Viewer {
id
brands(first: 1000) {
edges {
node {
localId
name // <------ [A] ask only name
}
}
}
}
`,
},
})
BrandList
export default Relay.createContainer(BrandList, {
fragments: {
viewer: () => Relay.QL`
fragment on Viewer {
id
brands(first: 1000) {
edges {
node {
id
localId
name
slug // <----- [B] ask more fields than [A]
country // <----- [B] ask more fields than [A]
}
}
}
}
`,
},
})