Most modern web applications are dependent on some external data source. And in React, we generally use fetch or axios to get the data from the remote endpoints.
However, these 2 libraries only do so much. We still need to implement the loading state, error handling, caching, pagination, re-validation all of these things ourselves.
But there are 2 popular libraries for solving these problems. They are:
React Query
According to the documentation what this library offers are
Fetch, cache and update data in your React and React Native applications all without touching any “global state”.
Another library is
SWR
This library recognize itself as
React Hooks for Data Fetching
Today we will compare these 2 solutions and see which one is better in which scenarios.
The common things
Let's first talk about the common features. Both of these libraries can perform common tasks like
-
Query
-
Caching
-
Polling
-
Parallel Queries
-
Initial Data
-
Window focus re-fetching
-
Network status re-fetching
Now let's talk about the differences between them
Dev tools
This is a big one. React query offers Devtools which is just awesome. We have to pass it inside the root.
import { ReactQueryDevtools } from "react-query/devtools";
function App() {
return (
<QueryClientProvider client={queryClient}>
{/* The rest of your application */}
<ReactQueryDevtools initialIsOpen={false} />
</QueryClientProvider>
);
}
Unfortunately, SWR doesn't have any dev tools. There are some 3rd party packages that can do that though.
So this is a big win for react-query.
Global Error Handler
We can enable Global error handling on SWR taking the help of SWRConfig .
To enable it we wrap our root like the following
<SWRConfig
value={{
onError: (error, key) => {
if (error.status !== 403 && error.status !== 404) {
// We can send the error to Sentry,
// or show a notification UI.
}
},
}}
>
<MyApp />
</SWRConfig>
But for some weird reason React query doesn't have this feature. We can achieve something like that by creating a special hook by ourselves but having official support would be awesome.
Update
Apparently, react-query does have official support for global error handling. You have to use the onError of query cache in your global configuration. Like the following.
const queryClient = new QueryClient({
queryCache: new QueryCache({
onError: (error, query) => {
console.log(`Something went wrong: ${error.message}`);
},
}),
});
So that's a draw for this round :P
Thank you Dominik Dorfmeister for the correction. You can check his article on this topic here
Mutation Hooks
In React query we have mutation hooks by default. They are something like this
const mutation = useMutation(newTodo => axios.post('/todos', newTodo))
But in SWR we don't have any mutation hook rather we have the option to manipulate the data manually which is not convenient as mutation hooks.
import useSWR, { useSWRConfig } from "swr";
function App() {
const { mutate } = useSWRConfig();
const onClickHandler = () => {
logout();
mutate("/api/user"); // invalidate the user data
};
return <button> Logout </button>;
}
So this is obviously a huge win for React Query
Bundle Size
According to BundlePhobia the bundle size for SWR is 15kb where the bundle size for React Query is 50kb. Which is more than 3 times!
So if you consider the size then obviously SWR wins by a large margin here!
Garbage Collection
According to react-query documentation, all of the data that is cached is garbage collected if any query remains inactive for 5 minutes.
Also, we have the ability to configure this according to our needs by changing the cacheTime in the configuration option.
But in SWR there is no garbage collection. SO you have to manipulate the cache manually if you want.
So this is a win for React Query
Final Verdict
In my opinion, both of these libraries are very good and can make the developer's life easy with improvement in the performance of the application.
However, it's clear that react-query has some very powerful features that SWR doesn't have. But that comes with the cost of increased bundle size.
So if you are building a simple application and want a ready-to-go simple solution then SWR should be your choice.
But if you need more control and customization and want to get the most out of the developer tools then definitely go for react-query.
That's it for today. Hopefully, now you have a better understanding of how these 2 libraries compare to each other.
Have a wonderful day!