apollo
apollo copied to clipboard
Vue-Apollo v4 documentation doesn't follow Apollo Client v3 documentation
In the documentation regarding pagination, it guides the user to use updateQuery. However, in ApolloClient v3 this is deprecated with a warning that it will be removed in the next major version.
https://v4.apollo.vuejs.org/guide-composable/pagination.html
The updateQuery callback for fetchMore is deprecated, and will be removed
in the next major version of Apollo Client.
Please convert updateQuery functions to field policies with appropriate
read and merge functions, or use/adapt a helper function (such as
concatPagination, offsetLimitPagination, or relayStylePagination) from
@apollo/client/utilities.
The field policy system handles pagination more effectively than a
hand-written updateQuery function, and you only need to define the policy
once, rather than every time you call fetchMore.
Removed.
Yes. Please update the documentation ASAP! Thank you!
@Gyurmatag If you're looking for help right now, you can review the Apollo Client v3 pagination documentation.
I'm not sure if @Akryum will even update his documentation to include how to handle pagination, as it now relies upon the setup of Apollo Client and is outside of his module scope. It may be best to simply have a page which directs the developer to the Apollo Client pagination documentation.
I hope it will get updated, because it is confusing and it would be so much easier to have this in the v4 documentation.
The link I provided is all you need for pagination documentation.
There isn't anything additional that Vue apollo v4 needs to document about pagination because it's all in the Apollo Client documentation.
Thanks, but I am a little bit confused about the Apollo Client documentation. So here I have this implementation (according to the docs):
setup () {
const { result: quotesResult, loading: quotesLoading, subscribeToMore, fetchMore } = useQuery(quotesQuery, { limit: 5 })
const quotes = useResult(quotesResult, null, data => data.quotes)
function loadMore () {
fetchMore({
variables: {
limit: 5,
next: quotes.value.next
},
updateQuery: (previousResult, { fetchMoreResult }) => {
return {
...previousResult,
quotes: {
...previousResult.quotes,
next: fetchMoreResult.quotes.next,
results: [
...previousResult.quotes.results,
...fetchMoreResult.quotes.results
]
}
}
}
})
}
return { quotes, quotesLoading, loadMore }
}
How should I convert this to a not deprecated solution?
Thanks for the help in advance!
@Gyurmatag
As per their Apollo Client 3 release announcement (and the console warning), we no longer want updateQuery on the fetchMore function, so you should go ahead and remove it entirely.
setup () {
const { result: quotesResult, loading: quotesLoading, subscribeToMore, fetchMore, variables } = useQuery(quotesQuery, { limit: 5 })
const quotes = useResult(quotesResult, null, data => data.quotes)
function loadMore () {
fetchMore({
variables: {
...variables,
next: quotes.value.next
},
})
}
return { quotes, quotesLoading, loadMore }
}
Note: You'll notice how I imported variables from Vue Apollo as I discovered this to be very helpful with fetchMore for pagination and refetch for searching and ordering. This will obviously be up to you if you and your use case if you find it helpful or not.
You should then read about offset pagination helpers and keyArgs to learn how to implement the new pagination methods.
If you can use Apollo Clients pagination helpers, you should. Otherwise, you will need to create the pagination logic yourself:
// ApolloConfiguration.ts
import { ApolloClient, InMemoryCache, NormalizedCacheObject, FieldPolicy } from "@apollo/client";
import { offsetLimitPagination } from "@apollo/client/utilities"
...
function customOffsetLimitPagination(): FieldPolicy {
// Your custom pagination logic should go here.
// You can have a generic pagination helper which can go with all your pagination queries
// this is the ideal solution and the reason why Apollo Client 3 did this method.
// Or you will need to write a pagination helper per query field.
...
}
export const cache: InMemoryCache = new InMemoryCache({
typePolicies: {
Query: {
fields: {
Foo: customOffsetLimitPagination(),
Bar: offsetLimitPagination(),
},
},
},
});
export const apolloClient: ApolloClient<NormalizedCacheObject> = new ApolloClient({
...
cache,
});
Thanks for your long answer! I've got cursor pagination as you can see in my implementation. So probably I should examine this: https://www.apollographql.com/docs/react/pagination/cursor-based/
@MechJosh0 Okay so here is whats happening to me: I've got quotes in the Apollo Cache, here it is:

Now I removed what you said from the loadMore() function. And then inserted this to my configs:
const cache = new InMemoryCache({
typePolicies: {
Query: {
fields: {
quotes: {
merge (existing, incoming, { readField }) {
const quotes = existing ? { ...existing.results } : {}
incoming.results.forEach(quote => {
quotes[readField('_id', quote)] = quote
})
return {
next: incoming.next,
quotes
}
},
read (existing) {
if (existing) {
return {
next: existing.next,
quotes: Object.values(existing.results)
}
}
}
}
}
}
}
})
Now whenever I am calling the loadMore() function, the graphql call gets executed, but the results not merged together and not updating the ui. Instead in the cache I've got more quotes, like this:

Maybe there is a problem with the typePolicy? It doesnt get called at all...
Thanks for your help!
@Gyurmatag I would expect your merge to look similar to that of your original merge logic from your updateQuery function. So something like:
merge (existing, incoming) {
if(!existing) return incoming;
return {
next: incoming.next,
results: [...existing.results, ...incoming.results],
}
},
@MechJosh0 My problem is that my 'quotes' typePolicy doesn't get called at all. The merge() and read() function doesnt't executes. What can be the problem?
Have you updated to Apollo Client 3 and followed it's migration?
And you will need to ensure the policy is written in the correct area depending on your graph query. This is something you'll need to work out and play around with.
query {
quotes {
..
}
}
export const cache: InMemoryCache = new InMemoryCache({
typePolicies: {
user: {
fields: {
quotes: ///
},
},
},
});
OR
query {
user {
quotes {
..
}
}
}
export const cache: InMemoryCache = new InMemoryCache({
typePolicies: {
user: {
fields: {
quotes: ///
},
},
},
});
There is a lot of documentation about type policies so I do recommend to go read everything you can.
@MechJosh0 I started the project with Apollo Client 3, and it worked great until now.

As you can see in this screenshot the quotes are PaginatedItems type, but I've tried that too, in the typePolicies like that and its not working:
typePolicies: {
Query: {
fields: {
paginatedItems: {
merge (existing, incoming, { readField }) {
console.log('asdsadasd')
if (!existing) return incoming
return {
next: incoming.next,
results: [...existing.results, ...incoming.results]
}
},
read (existing) {
console.log('asdsadasd')
if (existing) {
return {
next: existing.next,
results: Object.values(existing.results)
}
}
}
}
}
}
}
Here is my query:
query Quotes($limit: Int, $next: String) {
quotes(limit: $limit, next: $next) {
results {
_id
text
character { id }
}
previous
hasPrevious
next
hasNext
}
}
and this is what I get back:
{
"data": {
"quotes": {
"results": [
{
"_id": "5fe4df242c075a2e881d4cec",
"text": "fabian",
"character": {
"id": "5fb110ebcdb33d42188f00b8"
}
},
{
"_id": "5fe4db392c075a2e881d4ceb",
"text": "ererererer",
"character": {
"id": "5f91c4db67f18650500f1bdb"
}
},
{
"_id": "5fe4db0e2c075a2e881d4cea",
"text": "dfdf",
"character": {
"id": "5f91beb6b487003740bc0ed4"
}
},
{
"_id": "5fe21fe9ced20755500b6aa4",
"text": "AAAAAAAAAAAAAAAA",
"character": {
"id": "5fb11194cdb33d42188f00b9"
}
},
{
"_id": "5fe1f4b4799bc730d061b469",
"text": "dfsd",
"character": {
"id": "5f91c4db67f18650500f1bdb"
}
}
],
"previous": "eyIkb2lkIjoiNWZlNGRmMjQyYzA3NWEyZTg4MWQ0Y2VjIn0",
"hasPrevious": false,
"next": "eyIkb2lkIjoiNWZlMWY0YjQ3OTliYzczMGQwNjFiNDY5In0",
"hasNext": true
}
}
}
I have no idea why it is not working. Can you please help me?
Maybe I just wait till the Vue Apollo 4 docs gets into better shape... Hope I will find answers there specific to VueJS. However I started to feeling worried about this library. The last major version was months ago.. :(
@MechJosh0 I started the project with Apollo Client 3, and it worked great until now.
As you can see in this screenshot the quotes are
PaginatedItemstype, but I've tried that too, in the typePolicies like that and its not working:typePolicies: { Query: { fields: { paginatedItems: { merge (existing, incoming, { readField }) { console.log('asdsadasd') if (!existing) return incoming return { next: incoming.next, results: [...existing.results, ...incoming.results] } }, read (existing) { console.log('asdsadasd') if (existing) { return { next: existing.next, results: Object.values(existing.results) } } } } } } }Here is my query:
query Quotes($limit: Int, $next: String) { quotes(limit: $limit, next: $next) { results { _id text character { id } } previous hasPrevious next hasNext } }and this is what I get back:
{ "data": { "quotes": { "results": [ { "_id": "5fe4df242c075a2e881d4cec", "text": "fabian", "character": { "id": "5fb110ebcdb33d42188f00b8" } }, { "_id": "5fe4db392c075a2e881d4ceb", "text": "ererererer", "character": { "id": "5f91c4db67f18650500f1bdb" } }, { "_id": "5fe4db0e2c075a2e881d4cea", "text": "dfdf", "character": { "id": "5f91beb6b487003740bc0ed4" } }, { "_id": "5fe21fe9ced20755500b6aa4", "text": "AAAAAAAAAAAAAAAA", "character": { "id": "5fb11194cdb33d42188f00b9" } }, { "_id": "5fe1f4b4799bc730d061b469", "text": "dfsd", "character": { "id": "5f91c4db67f18650500f1bdb" } } ], "previous": "eyIkb2lkIjoiNWZlNGRmMjQyYzA3NWEyZTg4MWQ0Y2VjIn0", "hasPrevious": false, "next": "eyIkb2lkIjoiNWZlMWY0YjQ3OTliYzczMGQwNjFiNDY5In0", "hasNext": true } } }I have no idea why it is not working. Can you please help me?
Maybe I just wait till the Vue Apollo 4 docs gets into better shape... Hope I will find answers there specific to VueJS. However I started to feeling worried about this library. The last major version was months ago.. :(
Got same issue trying to use TypePolicies for vue-composable queries and it doesn't seem to "see" TypePolicies for my field. In contrary, I used resolvers (deprecated) with the same query and they work.
It seems I will have to use deprecated resolvers until vue-composables will be compatible with TypePolicies :(

custom posts: { page: { edges pageInfo } }
how to add typePolicies in page ?