Full Stack React Native Development using GraphCool and Apollo Subscriptions + React Navigation

Check out the repo here.

This is the first of three tutorials that I will be creating on hooking up APIs / backends with your React Native apps.

We will also be covering Serverless as well as LoopBack in the next 2 posts in this series.

The app we will be building.

If you have not heard of Graphcool, the best way I can describe is that it is something like Firebase but for GraphQL. A database as a service that you can use for free up to a certain point.

Apollo provides tooling around GraphQL that we will use to wire up our React Native application as well as our subscriptions.

The subscriptions will give us websocket connections to our data, so that if something changes, our UI will receive the new data and update without us having to manually fetch anything, or do any polling. One of the many great things about Graphcool is that they offer this functionality out of the box! The only thing we need to to is hook it into our front end!

There will be a lot going on in this post, and it will be long, so hold on to your seat! But remember, once you are done, you will have added a great new set of skills to your toolchain!

To get started building the app from scratch, you can skip to Building the App section below, or follow the next section for a quick overview of what the subscription process looks like.

Apollo + Graphcool + subscriptions

The first thing I will do is walk through what a subscription looks like.

When we create our Provider, which is how we will be wiring up the connection to Apollo, we basically add an additional set of configuration to our client.

A basic configuration would look something like this:

Once we’ve added this, we can subscribe to any changes to our data!

How would this look? Well, here is a quick look at how we will be implementing this in our final example:

  • We start off by importing gql & graphql from react-apollo
  • We then create two queries: one (MYQUERY) for the initial fetch of the data, and another (BOOKS_SUBSCRIPTION) for fetching a Book based on a mutation in our Books model. BOOKS_SUBSCRIPTION is what we will be using to listen for a CREATED mutation, and when this happens, we receive the value from the new mutation.
  • In componentWillMount we set up a subscribeToMore function which is available to us as a prop from react-apollo once subscriptions are enabled. This function will be triggered and will return new values based on the BOOKS_SUBSCRIPTION query / subscription. If we get new values, we update the previous value and just tack on the new value returned from the query:
return {
...prev,
allBooks: [...prev.allBooks, node],
}

With that quick intro out of the way, we will now start a new app from scratch and implement this functionality!

Building the App

Getting Started

The first thing we need to do is create a new React Native app! You can do this with either create-react-native-app or react-native init:

react-native init RNGraphCool

Once installed, cd into the new directory:

cd RNGraphCool

This app will have a few dependencies:

react-apollo for our Apollo Client

subscriptions-transport-ws to implement the subscriptions

react-native-elements for our UI

react-native-vector-icons as a dependency of React Native Elements

react-navigation for our navigation

Let’s install these packages then run react-native-link to get them hooked up, using either yarn or npm (I’ll be using yarn)!

yarn add react-apollo subscriptions-transport-ws react-native-elements react-native-vector-icons react-navigation

Once these are added, we’ll go ahead and link the React Native Vector Icons library:

react-native link react-native-vector-icons

Creating Graphcool project

The next thing we need to do is set up our Graphcool project, and create a Book type that we can interact with.

To do so, go to https://www.graph.cool and either login or create an account.

Once you’re in, you can either use the example project or create a new project and use it to create the Book type we will be using.

For me, I will be calling my project Book Club:

Once you are either in the example project or the new project, we can click the Add Type button at the top of the Schema to create a new Book type:

Once created, we should have the ability to add fields by clicking ADD FIELD:

We will need to be adding a few fields: title, description, author, rating, and image.

For me, I set rating as an Int and everything else as a String.

I also set title as required, which will append an ! to the type, and all of the rest of my fields as optional.

Once this is created, it should look something like this:

Something important to notice is that title has the following type:
title String!
While the others we created only have String or Int as their types. This is important to note, as this schema has to match our client schema later on in our React Native code.

Now that this type is created, we are done with Graphcool configuration. We will come back to this Graphcool page once we need to get our endpoint uris when we set up our connection to our Graphcool server.

Folder Structure

Now, we want to go ahead and create our folder structure. Let’s create an app folder, and a few files / folders within the app folder:

mkdir app
cd app
mkdir assets
touch index.js app.js Book.js Books.js AddBook.js

Next, let’s go ahead and populate the assets folder with the three images we will be needing (a logo, and two icons for our navigation tab bar).

To use the same icons I am using in the demo, go to https://github.com/react-native-training/apollo-subscriptions-book-club/tree/master/app/assets and download all of the items in this folder into your assets folder.

The first thing we want to do is create a single entry point to our app. This entry point will be app/index.js , so we will now go into both index.ios.js and index.android.js and import app/index.js:

Next, let’s go into index.js and create the main entrypoint, and wire up Apollo as well as the websocket subscription.

Wiring up the Apollo Client with Graphcool

To do so, we need to go back to the Graphcool project and be ready to reference two endpoints: simple and subscriptions (To bring up the endpoints, click the SUBSCRIPTIONS button on the Graphcool client page.)

So, let’s take a look at what’s all going on here:

  • We import everything we need from both react-apollo as well as subscriptions-transport-ws
  • We create a websocket client by calling the SubscriptionClient function provided by subscriptions-transport-ws, passing in our subscriptions uri from Graphcool
const wsClient = new
SubscriptionClient(`wss://subscriptions.graph.cool/v1/YOURID`, {
reconnect: true
});
  • We create a networkInterface using createNetworkInterface from apollo-client, passing in our simple uri from Graphcool
const networkInterface = createNetworkInterface({
uri: `https://api.graph.cool/simple/v1/YOURID`
});
  • We use addGraphQLSubscriptions, provided by subscriptions-transport-ws, to create a const called networkInterfaceWithSubscriptions which will combine our networkInterface with our websocket client
const networkInterfaceWithSubscriptions = addGraphQLSubscriptions(
networkInterface,
wsClient
);
  • Finally, we create an Apollo Client and wrap our app in the Provider, passing in the new client as the client.

Creating Navigation

Next, we will create a TabNavigation.

There’s really not a whole lot having to do with Apollo in this file, we are basically importing a few routes that have yet to be created, and using the images we downloaded earlier to be the TabBar icons.

In TabConfig, we are setting the activeTintColor so that when a tab is selected, we get the theme color of pink. This value is passed as a prop to navigationOptions.

Now, we will go ahead and open Books.js. This file has a lot going on, and I will walk through the most important parts below:

  • MYQERY is the original query to Graphcool, fetching the fields that we want for each book. This query will return every book.
  • BOOKS_SUBSCRIPTION is the subscription. This will return whenever there is a new book created, and will return the book that was created.
  • in componentWillMount we set up a subscribeToMore function which is available to us as a prop from react-apollo once subscriptions are enabled. This function will be triggered and will return new values based on the BOOKS_SUBSCRIPTION query / subscription. If we get new values, we update the previous value and just tack on the new value returned from the query.
  • In our UI, we give a loading indicator if the data is loading, and if not, map through the books once they are available to us, returning a new ListItem (from react-native-elements) for each book.
  • After our Books class is created, we wire up graphql to the Books class and then create and return a new StackNavigator, which will be set in our main tab:
const GQLBooks = graphql(MYQUERY)(Books);
const RouteConfig = {
Books: { screen: GQLBooks },
Book: { screen: Book },
}
export default StackNavigator(RouteConfig);

This is all we need to do to set up the subscription as well as our initial query to get all of the books!

Book UI

Next, we will create the screen that we will navigate to, showing the book details. There is nothing special going on here Apollo / graphql related, so I will not be going into any descriptions for this file. (Always feel free to reach out to me if you have any questions about anything though!)

Creating the Mutation (adding a new book)

The last thing we need to do is create the Add Book functionality.

In graphql, adding data is usually referred to as a mutation.

In AddBook.js, we will create a form that will allow a user to add a new book to our Graphcool database. The best thing about having subscriptions already wired up is that we will not have to do any fetching after this is hooked up, our UI is already hooked up to get this new book and add it to our book list!

  • We create an Input and Button component that we will be using in our UI.
  • We create an initial state to keep up with the form input
  • We create an updateBook class method that will take two arguments: a type and a value, updating the state with these values
  • We create an AddBook method. This method will take the values from this.state.book and use them to call this.props.addBookMutation (which we will be creating and passing down as a prop near the bottom of the file).
  • We return our UI in render
  • We create addBookMutation which will describe the mutation we will be creating, referencing two items for each argument: a value and a type ($title: String!), and returning a value of createdAt (which we will not be using).
  • Finally, we export the class, wrapping it in compose, and passing in the mutation as a prop to the component, allowing us to reference it as this.props.addBookMutation

That’s all! You should be able to run the app, adding items to your Graphcool database!

Again, the repo is located at https://github.com/react-native-training/apollo-subscriptions-book-club

If you have any questions, or issues getting this running, feel free to reach out to me at nader@reactnative.training

My Name is Nader Dabit . I am a software consultant and trainer and the founder of React Native Training where we do React Native consulting as well as teach developers at top companies around the world how to quickly get up and running with React Native.
If you like React and React Native, checkout out our podcast — React Native Radio on Devchat.tv.
Also, check out my book, React Native in Action now available from Manning Publications
If you enjoyed this article, please recommend and share it! Thanks for your time