3
I’m using the Contentful GraphQL API to fetch a collection of items, in this example football clubs.
query Clubs($limit: Int!, $skip: Int!) {
clubCollection(limit: $limit, skip: $skip) {
total
items {
name
description
}
}
}
The structure of the response is:
clubCollection: {
items: [{
... array of all the clubs
}]
}
It looks like the Apollo InMemoryCache
is only caching the full query in its ROOT_QUERY object. But not each individual club. The setup for the cache looks like this:
new InMemoryCache({
typePolicies: {
Query: {
fields: {
clubCollection: concatContentfulPagination()
},
},
},
})
Does anyone know how I can target the clubs in items
so that I can cache each individual club?
EDIT:
Thanks to the answer from @xadm I realised I did not need to extend the InMemoryCache
like so:
new InMemoryCache({
typePolicies: {
Query: {
fields: {
clubCollection: {
items: {
},
...concatContentfulPagination()
}
},
},
},
})
But instead add it to the root of the typePolicies based on the type of the object, for me it is Club
. When I added that it did work!
new InMemoryCache({
typePolicies: {
Club: {
keyFields: ['name']
},
Query: {
fields: {
clubCollection: concatContentfulPagination()
},
},
},
})
0
2 Answers
Reset to default
2
Items should have an id
prop requested … to be normalized – Apollo is normalizing cache GraphQL client
It’s required to cache entries/types/subtypes properly.
https://graphql.org/learn/caching/
It, unique key can be id
, _id
or customized key per type using typePolicies
– customizing-identifier-generation-by-type.
https://www.apollographql.com/docs/react/caching/cache-configuration/#default-identifier-generation
In this case (no queryable id
prop inside items), you should check in API (docs/specs/schema or explore network response body – __typename
prop of items
object) the type of club items entries (probably Club
) and customize cache policies like:
new InMemoryCache({
typePolicies: {
Club: {
keyFields: ['name']
},
… assuming name
is unique.
3
-
Thanks for your answer. I was aware the object needs an ID, unfortunately the id of a Contentful object is in a ever deeper nested object:
graphql clubCollection(limit: $limit, skip: $skip) { total items { sys: { id } name description } }
So maybe my question was wrong… The question would be, how can I access the array of clubs in items with typePolicies to set the fieldname
for example as thekeyFields
?– LingertjeMar 12, 2021 at 11:51
-
You should see individual item entries in the cache … you can use cache API (
readFragment
) to read them … what do you mean by 'how can I access the array of clubs' ?items
array is a prop of response type (query returns some typed item? unknown? check__typename
in network response details? check api/specs, (noid
, not normalized)– xadmMar 12, 2021 at 12:49
-
Thanks again! I editted the original post with what I think is the solution. Is that indeed what you tried to tell me? 🙂
– LingertjeMar 12, 2021 at 12:55
0
For this pupose you can use reactive variables. That way you can access clubs array anywhere in your code without rerunning query and perform any array operation on it.
Visit this page for more info on it.