Apollo client and React
“🚀 A fully-featured, production ready caching GraphQL client for every UI framework and GraphQL server” — Apollo Client github repository
Why do we need a GraphQL client?
As GraphQL backends expose their API over a single HTTP endpoint, we could just use fetch to interact with it. The problem is this doesn’t scale well because we would need to reimplement backend agnostic features on every project, such as caching data, updating the local cache after a mutation, UI framework integration, and more!
A GraphQL client should have those kinds of functionalities so that you don’t have to reimplement these behaviors yourself. Instead, you can completely focus on your application domain and on implementing the specific requirements of your app.
As we should expect, there is a multitude of GraphQL clients to choose from, in this article we’ll go over Apollo Client.
Why Apollo Client?
“Apollo Client is a complete state management library for JavaScript apps. Simply write a GraphQL query, and Apollo Client will take care of requesting and caching your data, as well as updating your UI.” — Apollo Client docs
Apollo provides a lightweight and flexible approach that works in any environment. Many tasks such as keeping the local cache consistent can also be achieved with Apollo Client, but require more manual work and bookkeeping.
Since Apollo Client is framework agnostic, it’s a great option to learn and use in your applications. Everything you learn can be used on React, Vue, and even on native apps!
In this article, we’ll see how to use Apollo Client with React.
Setup
First, we need to add the required dependencies to use Apollo Client on a React application, using either npm or yarn.
Dependencies required to use Apollo Client on a React app:
Once we’ve successfully installed the dependencies, we have to set up the Apollo Client. To do so, we only need to let it know our GraphQL endpoint. Note that we are also using an in-memory cache, we’ll cover this later.
Basic Apollo Client configuration:
Now that we’ve created our client, we need to wrap our application in the ApolloProvider
tag, so that our app has access to our newly created client.
As you should know by now (if you don’t, check out this awesome article), in GraphQL we use Queries
to retrieve data and Mutations
to mutate data.
In our React app, there are two ways to do either of them, by using components or hooks. We’ll cover the latter as they are much cleaner and more pleasant to work with.
Queries
Let’s say we want to get the id
and name
of all the Users on our imaginary GraphQL backend. This is easily done by writing the following query.
Now, we can use this query to actually fetch some users by using the useQuery
hook. In order to run a query, we need to call useQuery
and pass a GraphQL query string to it. This hook returns a result object that contains the following properties:
loading
: whether the request is in flight or not.data
: the result of your GraphQL query (defaults toundefined
).error
: a runtime error withgraphQLErrors
andnetworkError
properties.- …and more.
Usage example of useQuery
:
Mutations
As an example, we may want to create a Post
with a title
and a body
. To do this, we must write a mutation:
Here, CreatPostInput
is a GraphQL type defined in our backend, that has title
and body
fields.
To use this mutation we can use the useMutation
hook. This hook returns an array where this first item is the mutation itself and the second item is pretty similar to the one returned by useQuery
.
Usage example of useMutation:
Apollo Cache
“Apollo Client stores the results of its GraphQL queries in a normalized, in-memory cache. This enables your client to respond to future queries for the same data without sending unnecessary network requests.” — Apollo Client docs
What does this mean? It means that we can use this in-memory cache as our global state, no need to use Redux or Context!
Apollo exposes a handful of functions to read and write the cache. To keep this post short we won’t cover it, but you can read about it in Apollo’s documentation.
To sum up, by using Apollo we get a way to use GraphQL queries and mutations and an included global state manager! The latter was the main selling point for me.
Look at an example project here!