How to Persist Your MobX State

Image for post
Image for post
Photo by Kaitlyn Baker on Unsplash

When I started my latest side-project half a year ago I had to choose how to manage and persist the state of Avocation a React Native App I built.

I decided to use MobX for its simplicity and my experience with it. Setting up MobX and managing my apps state was easy like always, but at some point I needed some intuitive way of persisting my stores.

After some research I found mobx-persist, a great library to solve my problem with a simple API which was easy to integrate into my existing code base.

mobx-persist works for React Native, as well as for Web.

First I will explain how to set-up mobx-persist in your existing application and afterwards how to persist your data with it.

I will assume you already have your MobX app configured and running. If not, make sure to check out the following article about how to get started with MobX and React.

First, we install the npm package in our application

npm install -s mobx-persist

Now let’s assume we have three stores in our application

  • AuthStore
  • UserStore
  • SettingsStore

We need to create what is called a hydrate function. This function tells
mobx-persist which stores you want to persist and how to save them. All of the observables will be restored, once the user re-opens the app or refreshes your web application.

If you are using React Native, you need to make sure to set the storage to AsyncStorage and jsonify:true in the create function, to let mobx-persist know what to use for persisting the observables locally. If you are developing a web application, you can skip these parameters to use localStorage or use a custom local storage library like localForage.

The hydrate function accepts the following parameters

  • key - This will be the key used by AsyncStorage for the serialised store
  • store - The store you want to persist
  • initialState - An optional initial state
  • customArgs - Custom arguments for serializr (See documentation)

Make sure to display some loading UI while the state hydration is running, because you want to avoid to render your application with faulty data.
That’s why I combined all the hydrate promises and called the finishLoading() function after all of them are resolved. In this function you can set the loading state to “finished” and start rendering your application content.

In the example above you can see, that I combined all of the stores into a single class. In your index.js you can then spread this class into props for your <Provider> ,and your application will just work like before.

After we finished the configuration, we can start persisting our stores!
In our AuthStore we want to save the authToken to keep the user logged in. So we create the store and add the observable:

This works fine, until the user restarts your app or refreshes your web application. If you do not persist the authToken ,the user will need to log in again, which we wanted to avoid.

To persist this observable we simply add a persist to it:

When you update the observable variable, which is marked with persist, mobx-persist will automatically save the change using AsyncStorage.

That’s it!

If the application got closed and the user opens it again later, the state will be restored after the hydration is finished.

For all primitive JS types a simple persist will be sufficient. For more complex types like objects, arrays, and maps you need to give mobx-persist more information about the observable.

You can even add some time delay between updating the observable and persisting these updates.

This can be configured when you create your hydrate method.

I used mobx-persist with great success in my latest side-project, even though the library is unmaintained for some time now. There is also another library which is a bit more active called mobx-sync. In my opinion, mobx-persist has the most convenient API and is very simple to set up.

Try both libraries and see what works best for you!

Thanks for reading this article! If you liked it, make sure to follow me on Medium for more content about React and React Native. I also sometimes tweet interesting stuff.

Co-Founder of 🎈 Working on 🥑

Get the Medium app

A button that says 'Download on the App Store', and if clicked it will lead you to the iOS App store
A button that says 'Get it on, Google Play', and if clicked it will lead you to the Google Play store