apollo-client: RefetchQueries after mutation not updating UI, yet network tab shows new data

Intended outcome:

I’m trying to authenticate a user and have it update my navbar (which uses the same query) to show different options whether the user is logged in or not.

Actual outcome:

Whats actually happening is, after refetching (during the login mutation), im getting new data from my query, and the network tab is showing it, store seems updated, however the component itself is still rendering stale data (outputted via console.log). Doing a hard refresh fixes the issue (since we get new data). How to reproduce the issue: I made a little demo video: https://drive.google.com/file/d/1Zmp1nwJBYnkuO0Cr2x4jUSnY61REkD8X/view

To explain the justification, i have a user query here that checks at a high level:

  1. Enter landing page (query returns undefined here makes sense)
  2. Enter login page, and login (cache updates with new data)
  3. console.log(this.props) to see our queries response, returns user is not authorized. After looking at apollo console data is in there (new) and the network tab that new data is in there. Refreshing the page shows relevant information however that query always rerenders the components involved with stale data.
const isLoggedInQuery = gql`
  query isAuthenticated {
    currentUser {
      id
      firstName
      lastName
      gender
      location
      password
      email
      permissions {
        id
        name
        displayOrder
        description
      }
      roles {
        id
        name
        description
        displayOrder
      }
    }
  }
`;

export default graphql(isLoggedInQuery, {
  name: "isLoggedInQuery"
})(Main);

If the user isn’t authed it returns null

In my login component i have it like this:

this.props.mutate({
        variables: { token },
        refetchQueries: [
          {
            query: gql`
              query isAuthenticated {
                currentUser {
                  id
                  firstName
                  lastName
                  gender
                  location
                  password
                  email
                  permissions {
                    id
                    name
                    displayOrder
                    description
                  }
                  roles {
                    id
                    name
                    description
                    displayOrder
                  }
                }
              }
            `
          }
        ]
      });

Versions

“react-apollo”: “^2.1.4”,

About this issue

  • Original URL
  • State: closed
  • Created 6 years ago
  • Reactions: 55
  • Comments: 129 (15 by maintainers)

Commits related to this issue

Most upvoted comments

Nobody from from apollo team cares

On Tue, Sep 4, 2018, 8:38 PM sandorvasas notifications@github.com wrote:

This is a huge blocker bug for our app too.

— You are receiving this because you commented. Reply to this email directly, view it on GitHub https://github.com/apollographql/apollo-client/issues/3633#issuecomment-418351202, or mute the thread https://github.com/notifications/unsubscribe-auth/AAK0caVZuUMwL7UjM7aSkhCBocuncROcks5uXnRAgaJpZM4U8aBZ .

This is a huge blocker bug for our app too.

Edit: it DOES seem to work if i use a function. So replacing

refetchQueries: [ 'getBookings' ]

with

refetchQueries: () => [ 'getBookings' ]

does update the UI for me properly with the previous variables with which getBookings had been called.

I’m using the graphql HOC btw.

@hwillson, it’s been two months and this issue has not been closed, if you really cares, you should check it out on your testing lab and verify it, If you cannot reproduce this, then close this issue so it wont be a clutter. i dare you to close this issue… 😃

@kkotwal94 i’m seeing this same issue even though there were not any errors with the initial query

Yeah I’m not seeing an error in my queries. Basically a mutation is run and I can verify via the chrome network tab that the updated data is arriving, however even with refetchQueries set, the component is still displaying stale data.

We were rendering the mutation component with refetchQueries like so:

refetchQueries={[
    {
        query: QUERY,
        variables: { location, tags }
    }
]}

For us the issue was that the query had to be exactly the same in the refetch as when the component was first rendered. INCLUDING variables! Our variables were changing slightly between when the query was first run and on the refetch and was causing the re-render not to happen. This is definitely not the fix or a lot of the examples I’m seeing above, but hopefully it helps some people out.

This fixed the issue for me on the latest packages and react. refetchQuery MUST match the variables from when the query was last ran.

Guys,

I had the exact same issue. But as @kkotwal94 mentioned if you add fetchPolicy="cache-and-network" it works perfectly.

I set my Mutation:

Component A

<Mutation mutation={YOUR_MUTATION} refetchQueries={() => [{ query: YOUR_GUERY, variables: { whatever } }]}>

I set my Query:

Component B

<Query query={YOUR_GUERY} variables={{ whatever }} fetchPolicy="cache-and-network">

The component A redirects to Component B with the updated values.

Hope it helps.

I could not get the UI to refresh after a successful mutation-and-then-query using the <Mutation refetchQueries={['queryName']} /> render prop pattern. My <Query /> component was high up in the app structure, with the <Mutation /> as a deeply nested child component.

I fixed the issue by following the instructions above. So that included adding the fetchPolicy prop to the <Query /> AND changing the refetchQueries prop to a function returning an array instead of just an array. refetchQueries={['queryName']} became refetchQueries={() => ['queryName']}

Hope this helps! Here are my apollo versions:

├─ apollo-boost@0.1.27 ├─ apollo-cache-inmemory@1.4.2 ├─ apollo-cache@1.1.25 ├─ apollo-client@2.4.12 ├─ apollo-link-context@1.0.12 ├─ apollo-link-dedup@1.0.13 ├─ apollo-link-error@1.1.5 ├─ apollo-link-http-common@0.2.8 ├─ apollo-link-http@1.5.9 ├─ apollo-link-state@0.4.2 ├─ apollo-link@1.2.6 ├─ apollo-utilities@1.1.2 └─ react-apollo@2.4.1

EDIT: It turns out the core issue I was facing was not apollo-related at all 🤦‍♂️. I wasn’t seeing UI updates because I was copying data to React component state rather than reading it from props in a component that sits between the <Query /> and the <Mutation />, meaning the updated query response only made it through the tree down to the offending component, which did not update itsstate. Once I realized this, I was able to implement refetchQueries as follows:

<Mutation refetchQueries={['queryName']} /> (it also still works for me by passing a function that returns an array)

And then I removed the fetchPolicy prop from my <Query /> altogether, which means I am now using the default fetchPolicy, cache-first.

Hopefully @hwillson can take a look at this, once 2.5 beta is released. To me, this is either something very silly we’re missing, or a big red no-go for Apollo Client, especially when the tutorial that’s supposed to teach every one how great Apollo is, doesn’t work.

Scott

I have been having the same issue. I have spent 4 days debugging this but to no avail. The Network shows correct data, meaning the mutation is running and the refetch query is running and the correct data is coming in. However the UI is not rerendering to reflect it. I am now considering completely dumping Apollo 3.0 which has gone from Beta to official and making GraphQL queries with simply Axios or Fetch. Such a large buggy unwieldy bunch of functionality is like a prior day dinasaur reincarnated. Apollo says we need caching and so forth, yes but before that our more important need is that simple things like RefetchQueries work out of the box. Currently this thread shows, even after the release of Apollo3.0 official, they dont work. A huge amount of time is wasted on finagling a feature that should just work to work. And if it still doesnt work, the whole library has to be dumped. God knows by this thread so many people have tried to get it to work for so long. This after noon I am going to implement simple access to Graphql API using fetch or axios and bypass this whole mess.

@iamrommel The Apollo team is small (we’re hiring!). Anything the community can do to help reduce the amount of time issue triaging / bug fixing takes (like creating reproductions) goes a long way towards helping get issues resolved faster. If someone in this issue thread is able to help out, that would be awesome.

Same for me. I have a complex query (custom sorting based on several options) so updating the store manually is not an option, unfortunately. My mutation is successful, but when I run refetchQueries (or this.props.data.refetch() explicitly in the update function), my UI stays stale. If I look in the network tab I can see that the refetch actually happened and the dataset plus my new item created from my mutation was fetched.

Edit: Looks like I can get it to update the UI with an explicit call to refetch in the update function if I have the property fetchPolicy set to cache-and-network on my list. However refetchQueries still is not working as mentioned.

neither of the suggestions mentioned in https://github.com/apollographql/react-apollo/issues/2070 (changing fetchPolicy or passing variables to Query i.e {v: Math.random()}) helped with the issue.

This is a huge blocker bug for our app too.

Edit: it DOES seem to work if i use a function. So replacing

refetchQueries: [ 'getBookings' ]

with

refetchQueries: () => [ 'getBookings' ]

does update the UI for me properly with the previous variables with which getBookings had been called.

I’m using the graphql HOC btw.

Oh wow this did the trick. The docs technically do have it correct, but some practical examples would be extremely helpful.

mutations___apollo_client

Thanks all - looks like this issue has been resolved.

Is there any official word on this issue from the apollo team?

We were rendering the mutation component with refetchQueries like so:

refetchQueries={[
    {
        query: QUERY,
        variables: { location, tags }
    }
]}

For us the issue was that the query had to be exactly the same in the refetch as when the component was first rendered. INCLUDING variables! Our variables were changing slightly between when the query was first run and on the refetch and was causing the re-render not to happen. This is definitely not the fix or a lot of the examples I’m seeing above, but hopefully it helps some people out.

This is a huge blocker bug for our app too.

Edit: it DOES seem to work if i use a function. So replacing

refetchQueries: [ 'getBookings' ]

with

refetchQueries: () => [ 'getBookings' ]

does update the UI for me properly with the previous variables with which getBookings had been called.

I’m using the graphql HOC btw.

This solves my problem completely.

was able to solve by following this: https://github.com/apollographql/react-apollo/issues/2070, for anyone else who stumbles on this issue. My initial result of the query was always a error, hence refetching didnt set it back into its loading state unless you set the query you were refetching to cache-and-network.

I’ve tried following solution to solve this, but all are failed

  • add fetchPolicy="cache-and-network"
  • add errorPolicy="ignore"
  • add awaitRefetchQueries={true}
  • passing variables={{ v: Math.random() }}
  • change refetchQueries: [ 'getBookings' ] to refetchQueries: () => [ 'getBookings' ]

versions

    "apollo-boost": "^0.1.23",
    "graphql": "^14.1.0",
    "graphql-tag": "^2.10.0",
    "react": "^16.7.0",
    "react-apollo": "^2.3.3",

Guys,

I had the exact same issue. But as @kkotwal94 mentioned if you add fetchPolicy="cache-and-network" it works perfectly.

I set my Mutation:

Component A

<Mutation mutation={YOUR_MUTATION} refetchQueries={() => [{ query: YOUR_GUERY, variables: { whatever } }]}>

I set my Query:

Component B

<Query query={YOUR_GUERY} variables={{ whatever }} fetchPolicy="cache-and-network">

The component A redirects to Component B with the updated values.

Hope it helps.

Shall we assume the Apollo team have completely forgotten about this? I appreciate the effort but there hasn’t been an update for months and this is one of many important features within apollo-client…Due to this and the network-policy issues we might have to consider switching to an alternative library instead

We were rendering the mutation component with refetchQueries like so:

refetchQueries={[
    {
        query: QUERY,
        variables: { location, tags }
    }
]}

For us the issue was that the query had to be exactly the same in the refetch as when the component was first rendered. INCLUDING variables! Our variables were changing slightly between when the query was first run and on the refetch and was causing the re-render not to happen. This is definitely not the fix or a lot of the examples I’m seeing above, but hopefully it helps some people out.

Thank you so much! I spent the last 4 hours debugging this.

The majority of this thread is people not understanding how Apollo works with its cache. There IS no bug here.

If you use any form of query with a fetchPolicy that doesn’t cache (like no-cache), then refetchQueries in a mutation won’t do anything. Why? There is no cache to update from the mutation. If you want it to reload, you need to remount the component. (Yes, refetchQueries is named poorly IMO).

What SHOULD you do? Use a query with a fetchPolicy that has a cache option. If you need “always network” data, but still want this to work then use network-only (which still caches) as the fetchPolicy. It will keep a cache so it can see mutations, but it will always query the server on mount/render/cache-bust (the cache bust is what the refetchQueries is doing).

Note: you can use any fetchPolicy with a cache to cause re-renders on mutations (list of fetchPolicy options here)

The other thing people seem to be missing is that QUERIES WITH VARIABLES ARE KEYED IN THE CACHE WITH THOSE VARIABLES. So if the variables change by the time you perform your mutation, then it won’t know which key in the cache to update. Thus no re-render. If you want to use queries with changing variables, you need to customize your cache normalization behavior. See https://www.apollographql.com/docs/react/caching/cache-configuration/#data-normalization.

Read that again: if the variables change, the query won’t refresh. This is because the cache considers those different queries, as it should.

I don’t work for Apollo, but someone that does should come here, clarify what I said with more details/info, then close this issue. Also, they should update the documentation to be more clear about this subject. I get the frustration everyone has here. I felt it too until I saw the light.

Checklist when refetch queries is not working:

  • Are the variables in refetchQuery exactly the same?
  • Is the fetchPolicy in the query set to 'network-only' ?
  • is the nextFetchPolicy in the query set to 'network-only'?
const { data } = useQuery(TODOS, { 
  variables: { first: 10 }, 
  fetchPolicy: 'network-only', // Important!! Apollo will default use cache first
  nextFetchPolicy: 'network-only' // Important!! 
})
const [updateTodo] = useMutation(UPDATE_TODO, { 
  variables: { id: 1, title: 'Foo' }, 
  // The variables NEEDS to match EXACTLY! Double check!
  refetchQueries: [{ query: TODO, variables: { first: 10 } }]
})

Now, once your application is working correctly, you can start to think about reducing network requests.

ok, 2020 here is my work around guys, instead of using

refetch()
OR
refetch(DEFAULT_VARIABLES)

lets call fetchMore since fetchMore is working correctly, so we can pass the initial default variables, yeah sounds funny.

fetchMore({
      variables: DEFAULT_VARIABLES
})

thanks 😄

Here’s what I did

  1. get refetch when you call useQuery
  const { loading, error, data, refetch } = useQuery<...>(...)
  1. set fetchPolicy to cache-and-network in this useQuery invocation`

  2. call refetch(...) in the your mutation’s onCompleted callback (using useMutation)

I’ve struggled to get updates working tbh. I had to move on and just settle for refetch even though I hate the fact that it does 2 queries for a single mutation 😦

To sum it up, what works here is to first define appropriate cache policies:

{ fetchPolicy: "cache-and-network", nextFetchPolicy: "cache-first" }

Second: make sure the variables are exactly the same as in the initial query.

@julian-sf As I wrote on Feb 29th, 2019: We had the same problem (btw also with network-only), but the problem occurred only in IE. In Chrome everything was fine. So two browsers give two different outcomes and you want to tell me that it’s not a bug but a feature?

I think the people in this issue are very frustrated when they find a bug that doesn’t get fixed or even noticed and then someone tells them, they are just too stupid for the profession they do. Obviously something here went wrong, but it seems hard to reproduce.

For the people wondering how we solved this particular issue with Apollo: We don’t use it anymore. Easy as that 😉

@optimuspaul There is a refetch method supplied by Query components:

https://www.apollographql.com/docs/react/essentials/queries.html#refetching

refetchQueries are, as I understand it, basically meant to help you by not forcing you to pass that function around your app like a strand of spaghetti.

@dbertella - What if the mutation is called in a child component? The resolver is returning the new data for the parent component, but the UI isn’t getting updated. See:

https://github.com/apollographql/fullstack-tutorial/blob/7948b85d747300fd4d1596b6173b9ee783431c75/final/client/src/containers/action-button.js#L11

https://github.com/apollographql/fullstack-tutorial/blob/7948b85d747300fd4d1596b6173b9ee783431c75/final/client/src/resolvers.js#L27

of the full-stack tutorial as an example of what I mean. If you run the app and server in the tutorial, add a space flight/ mission to your shopping cart, then go to the cart and remove it, the mission and the remove button stay instead of the mission being removed from the cart. (in the background, the mission is removed from the cart).

Scott

Hey guys. It seems that I’ve found the trick to reproduce the issue. Here is my code:

const GET_VEHICLES = gql`
  query getAllVehicles {
    getVehicle {
      id
      ...
    }
  }
`;
...
<VehiclesQuery query={GET_VEHICLES}>
  {({ data, loading, error }) => {
     const list = _.get(data, 'getVehicle');
    if (loading || error || (!list || list.length < 1)) {
      return <VehicleSlideView list={[]} />;
    }
     return <VehicleSlideView list={list as Vehicle[]} showAddCard={false} />;
    }}
</VehiclesQuery>

The first time when entering this page and if not signed in, the query will fail due to 401. After that If I signed in and add a vehicle via a mutation like this:

<MutationAddVehicle
   mutation={ADD_VEHICLE}
   variables={{ vehicle: this.state.carData }}
   onCompleted={this.addVehicleSuccess}
   refetchQueries={[{ query: GET_VEHICLES }]}
>
...</MutationAddVehicle>

When user trigger the mutation the expected behavior is in the VehiclesQuery the list will rerender due to the refetchQueries in mutation. However nothing happened.

The magic thing happens when I set the default state of the apollo-link-state into this:

const defaultState = {
  getVehicle: []
};

instead of this:

const defaultState = {};

It seems that if the first time the query is not successfully fired and no default state in link-state is provided for this query, all the refetchQueries and writeCache that associated with it will not work as expected.

Hope it will be helpful.

I was running into a similar issue - documenting my fix here although it looks like this wouldn’t fix it for the original poster.

TL;DR:

Switching from

 refetchQueries: ['namedQuery']

to

 refetchQueries: [{ query: NAMED_QUERY_DOCUMENT }]

fixed the issue for me. See this issue comment for more details.


Longer description of issue to hopefully help someone fix this:

In my case, we had a list query (groups) that took no variables. When we deleted an item from the list, we would refetch the query instead of updating the cache directly:

const [deleteGroup] = useDeleteGroupMutation({
  variables: { id: group.id },
  refetchQueries: ['groups'],
  awaitRefetchQueries: true,
});

Worked with no issues. We also added an option to “undo” the group deletion. We’d store the group info, and on undo, would just create a new group with all the old info:

const [createSiteGroup] = useCreateSiteGroupMutation({
  refetchQueries: ['groups'],
  awaitRefetchQueries: true,
});

// Actually deleting group
deleteSiteGroup().then(({ data: deleteData }) => {
  const deletedGroup = deleteData!.deleteGroup;

  const undo = async () => (
    await createGroup({
      variables: {
        name: deletedGroup?.name,
      },
    })
  );

// Call the undo somewhere conditionally, like in a toast notification
  await undo();
})

That worked fine too. The old group got recreated (with all the same data except a new id field), UI updated perfectly.

The issue was when we tried to delete that restored group - exact same code as above should have fired, and it did. A network request to delete the group was successful, and another followup to refetch the groups query returned the correct data - but the cache and UI did not update.

If we deleted a group, undid the delete, navigated away and came back (i.e. unmounted and remounted the observable query in the restored group), we could successfully delete the restored group and the UI would update. This definitely feels like an Apollo bug related to the string option of the refetchQueries array, given that switching to the object syntax fixes the issue.

The documentation is also lacking around this point. It fails to mention that a named query string will only refetch if it exists in mounted, observable queries, whereas passing an object with a query document will always run the query.

This also fixed a separate, unrelated issue where we ran the undo and related refetchQueries asynchronously, after navigating away from the original observable query. Again, it’s not well-documented.

I have to add that none of the solutions mentioned here worked - fetchPolicy, variables ordering etc

I ended up moving the logic from onCompleted to a useEffect with data as dependency, which is working as expected. I got the solution from here

Thanks for the response @Ruslan @Johnny. However, please note the following points:

  1. The query that is being refetched is a simple list of items after a delete mutation has run. There are no variables. If there are no variables being passed to the query where is the question of there being same or different variables.
  2. I have even done an update method to evict the deleted item from the local cache. The item is deleted from the local cache, however the query is not refetched.
  3. In my network requests, the refetched data shows correctly, with the deleted item removed. I see 2 network requests, the first to delete and item and the 2nd to show the revised list minus the deleted item, however the UI does not update

So the refetch is working at the network request level, but it is most strangely not updating the UI.

I have been stuck on this for many days. I am at a loss. Dont know what to do further.

Best regards, arjuna

On Wed, Jul 22, 2020 at 8:57 AM Johnny Bell notifications@github.com wrote:

I have been having the same issue. I have spent 4 days debugging this but to no avail…

This also took me a long time to figure out, but as long as you call it with the same variables then it will work. It can be super frustrating but I don’t think thats a reason to ditch apollo-client, it has a lot of other amazing features.

— You are receiving this because you commented. Reply to this email directly, view it on GitHub https://github.com/apollographql/apollo-client/issues/3633#issuecomment-662220206, or unsubscribe https://github.com/notifications/unsubscribe-auth/AEVWN4TDPM22WG5VW3SZK63R4ZMBNANCNFSM4FHRUBMQ .

I have been having the same issue. I have spent 4 days debugging this but to no avail…

This also took me a long time to figure out, but as long as you call it with the same variables then it will work. It can be super frustrating but I don’t think thats a reason to ditch apollo-client, it has a lot of other amazing features.

And when it comes to matching the variables, it appears that the types also matter. I was passing an int (42) for my refetch query while the initial query has a string ("42") and that was preventing it from working.

I am having same issue. As workaround I am manually changing the state of the component to force the component to re-render on refetch

Solved my issue. My data connection was timing out, always leaving me with an empty array of savedItems. cache-first can’t work because it doesn’t know what the new cache is, cache-and-network can’t work because the network call on the end returning [] (timeout default) was wiping out the good data.

TL;DR use update. refetchQueries is only as reliable as your data connection, probably why it’s not recommended for in place UI updates.

@madisonbullard that helps! My issue was that I was not passing the variables into the refetchQueries array object, your syntax helped me find that.

refetchQueries={() => [{ query: YOUR_QUERY, variables: { whatever } }]}

I think Apollo could in general put more emphasis on the fact that whenever you call a query, whether through refetch or through cache, the variables need to be re-specified.

Hi all,

I think I figured out how the refetchQueries works with HOC. As you pass down in the variables that need to be assigned to your components, you need to pass also the gql that contains your queries that you want to be refetched.

(yes it can contain many queries. They are distinguished with their names:

const MY_QUERIES = gql`
      query QueryName1 {
             // attributes to query
}
      query QueryName2 {
             // attributes to query
}
` ) ;

BUT this is not enough to trigger a refetch. You know that within your component you need to mutate the variables that you passed down from the HOC right? OK, then you need ALSO to specify, with their names which queries within the gql you want to be refetched.

So, in your component, you need to specify it like below:

this.props.mutate({
	variables: {
_// assign your passed down variables here_            
},
refetchQueries: ['QueryName1', 'QueryName2']
});

Btw, in my case, it works independent of the fetchPolicy.

I hope it will help some of you guys.

Cheers!

@hutber I have had some success by setting partialRefetch={true} on the <Query /> component. Maybe worth a shot.

It returns the whole cart object, either with the new mission added, or the mission deleted. The logic is based off of ids, so the ids are there. It’s just not one id, but possibly none or more than one.

I guess the question should be, if the Apollo cache is updated, will the UI displaying that data be updated automatically too? Or does something else need to be triggered? I’m far from an Apollo expert and even farther from a Apollo React expert. 😁

Scott

@iamrommel We care! If someone here can provide a small, runnable reproduction that clearly demonstrates this issue, that would greatly help with getting this resolved.

We were rendering the mutation component with refetchQueries like so:

refetchQueries={[
    {
        query: QUERY,
        variables: { location, tags }
    }
]}

For us the issue was that the query had to be exactly the same in the refetch as when the component was first rendered. INCLUDING variables! Our variables were changing slightly between when the query was first run and on the refetch and was causing the re-render not to happen. This is definitely not the fix or a lot of the examples I’m seeing above, but hopefully it helps some people out.

This fixed the issue for me on the latest packages and react. refetchQuery MUST match the variables from when the query was last ran.

On my side, variables are matching 100% but still, UI is not updating! 😐

OK, refetchQueries fixed. Below is a sample of what I updated in my case, and steps that could help you identify what you need to update in your particular case.

// This change helped in my case. Please use the below steps to identify what you
// need to change in your case.
const variables = {
  first,
  - sortBy: [{ key, dir }], // removed
  + sortBy: { key, dir }, // added
};

Troubleshooting steps for your situation:

  1. Make sure you provide the absolute same variables both to the original and to the refetch query as outlined in other posts above.

  2. If (1) did not solve it, then you need to reveal what inconsistency you may have between your variables and how your data is stored in Apollo’s cache, because Apollo converts your variables into a JSON string and makes it a part of the key at which your data is stored in its cache:

A. Familiarize yourself with Apollo’s Making all other cache updates, specifically the update method.

B. Make sure to include your original variables in the ‘update’ method in every place you are using the original query used to get data. This stackoverflow answer was helpful.

C. Try mutating your data while using the update method. In my case it immediately threw an error, which revealed the solution:

Invariant Violation: Can't find field books({"first":10,"sortBy":[{"dir":"ASC","key":"NAME"}]}) on object {
  ... // Other data
  "books({\"first\":10,\"sortBy\":{\"dir\":\"ASC\",\"key\":\"NAME\"}})": {
    "type": "id",
    "generated": true,
    "id": "$ROOT_QUERY.books({\"first\":10,\"sortBy\":{\"dir\":\"ASC\",\"key\":\"NAME\"}})",
    "typename": "BookConnection"
  },
  ... // Other data
}.

Notice the data structure difference between these 2 lines:

"books({\"first\":10,\"sortBy\":{\"dir\":\"ASC\",\"key\":\"NAME\"}})"
books({"first":10,"sortBy":[{"dir":"ASC","key":"NAME"}]}) // Array with an object

As soon as I eliminated that difference in the original variables, the refetchQueries began to update the UI as expected.

I’m in the process of safely migrating all of our render prop components to Apollo hooks, however once that’s done I will definitely upgrade to 3, grazie 😃

I am not sure that is the only issue. I am using network-only for one of my queries, and I see it fire in the network inspector (as in the original post) but the page doesn’t (always) re-render.

In one case, I found that adding a useState(false) and flipping it after awaiting the refetch does re-render consistently, which smells very much like a React context state propagation bug.

The majority of this thread is people not understanding how Apollo works with its cache. There IS no bug here.

If you use any form of query with a fetchPolicy that doesn’t cache (like no-cache), then refetchQueries in a mutation won’t do anything. Why? There is no cache to update from the mutation. If you want it to reload, you need to remount the component.

What SHOULD you do? Use a query with a fetchPolicy that has a cache option. If you need “always network” data, but still want this to work then use network-only as the fetchPolicy. It will keep a cache so it can see mutations, but it will always query the server on mount/render/cache-bust (the cache bust is what the refetchQueries is doing).

This is what I just discovered last week to. I had to change my fetchPolicy to network-only to make it work.

I go with that @JustDoItSascha resolution, i turned away from using apollo because there are several issues that are not getting fixed which are reported for a very long time. I dont want to specify it one by one here as nobody listens. What happens is not a “issue tab on github” but rather “ranting tab” just like what i did. Hahaha

On Sat, Feb 15, 2020, 12:26 AM JustDoItSascha, notifications@github.com wrote:

@julian-sf https://github.com/julian-sf As I wrote on Feb 29th, 2019: We had the same problem (btw also with network-only), but the problem occurred only in IE. In Chrome everything was fine. So two browsers give two different outcomes and you want to tell me that it’s not a bug but a feature?

I think the people in this issue are very frustrated when they find a bug that doesn’t get fixed or even noticed and then someone tells them, they are just too stupid for the profession they do. Obviously something here went wrong, but it seems hard to reproduce.

For the people wondering how we solved this particular issue with Apollo: We don’t use it anymore. Easy as that 😉

— You are receiving this because you were mentioned. Reply to this email directly, view it on GitHub https://github.com/apollographql/apollo-client/issues/3633?email_source=notifications&email_token=AABLI4M7PS4GSFFHSLL52YLRC3AZ5A5CNFSM4FHRUBM2YY3PNVWWK3TUL52HS4DFVREXG43VMVBW63LNMVXHJKTDN5WW2ZLOORPWSZGOELZS3RY#issuecomment-586362311, or unsubscribe https://github.com/notifications/unsubscribe-auth/AABLI4NDL7BCFITEIR7HWLTRC3AZ5ANCNFSM4FHRUBMQ .

In regarding to the refresh issue. I have the same trouble but with Angular 5 & 6 using Apollo Client 2.3. I think that is a sync issue.

No matter how do you write the refresh query, this works nice, but the mutation arrives first & the refresh milliseconds later without possibility to catch it: there is no an observable, or promise, of the refresh query to sync with it.

I resolve this issue with a separate query, changing the fetchPolicy to network-only. Its work like a charm.

Why isn’t there just a reload method that we can call or trigger on the Query objects? Why all the complexity?

and the query thats being refetched has this option?

graphql(userQuery, {
    name: "user",
    options: { fetchPolicy: "cache-and-network" }
  }),