DoneDeal0
DoneDeal0

Reputation: 6267

React-query: how to update the cache?

I have a very basic app that fetches a user and allows to change his name. I fetch the user with React query so I can benefit from the cache feature. It works.

However, when I want to update the user, I use a classic post request with axios. Once the user is updated in the database, I need to update the cache directly in the updateUser() function. I've seen tutorials on the web that use queryCache.setCache, but it doesn't work here. How to fix this? Or maybe there is a better way to handle such queries?

Also, I notice a huge number of rendering... (see the "user render" console.log in the app file).

For the convenience, I've made a small script on a codesandbox with the pokeapi:

https://codesandbox.io/s/api-service-syxl8?file=/src/App.js:295-306

Any help would be greatly appreciated!

Upvotes: 4

Views: 9241

Answers (1)

Daltron
Daltron

Reputation: 1866

So, I'll show you what I do:

const updateUser = async (userUpdates: User) => {
  const data = await UserService.updateUser(userUpdates); // return axios data

  return data;
}

// if you want optimistic updating:
const { mutate: mutateUser } = useMutation(updateUser, {
    onMutate: async (userUpdates) => {
      // Cancel any outgoing refetches (so they don't overwrite our optimistic update)
      await queryClient.cancelQueries(['user', userUpdates.id]);

      // Snapshot the previous value
      const previousUser = queryClient.getQueryData(['user', userUpdates.id]);

      // Optimistically update to the new value
      queryClient.setQueryData(['user', userUpdates.id], userUpdates);

      // Return a context with the previous user and updated user
      return { previousUser, userUpdates }; // context
    },
    // If the mutation fails, use the context we returned above
    onError: (err, userUpdates, context) => {
      queryClient.setQueryData(['user', context.userUpdates.id], context.previousUser);
    },
    // Always refetch after error or success:
    onSettled: (userUpdates) => {
      queryClient.invalidateQueries(['user', userUpdates.id]);
    }
  });

// then to update the user
const handleUpdateUser = (userUpdates: User) => mutateUser(userUpdates); 

This all comes from the docs: Optimistic Updates

Upvotes: 6

Related Questions