Create a useStore hook for mobx-state-tree

Mobx-state-tree?

From the mobx-state-tree docs:

MobX is a state management “engine”, and MobX-State-Tree gives it structure and common tools you need for your app.

This post will help you to create a useStore hook to use MST in functiona…


This content originally appeared on DEV Community and was authored by Colby Garland

Mobx-state-tree?

From the mobx-state-tree docs:

MobX is a state management "engine", and MobX-State-Tree gives it structure and common tools you need for your app.

This post will help you to create a useStore hook to use MST in functional components in a React project.

Note: this post will be written in TypeScript.

Let's Get Hooked

First things first, let's create our "root store" (this will be our store that will hold our of other stores - more on that later)

/// src/stores/rootStore.ts

import { types } from 'mobx-state-tree';

export const rootStore = types
  .model({})
  .create({});

Explanation

From MST, we import the types. This allows us to create a "model", which will hold our data, as well as computed data, and actions to update our data.

Context is Key

To use our hook in our React app, let's utilize React's Context API to help us do that.

/// src/stores/rootStore.ts

// Add `Instance` to our import from MST
import { type, Instance } from 'mobx-state-tree';

const RootStoreContext = createContext<null | Instance<typeof rootStore>>(null);
export const StoreProvider = RootStoreContext.Provider;
/// src/app.tsx

import { StoreProvider, rootStore } from './stores/rootStore';

export default function App(){
  return (
    <StoreProvider value={rootStore}>
      { /** rest of your app here */ }
    </StoreProvider>
  );
}

Explanation

We will wrap our app with this StoreProvider and pass as its value, our rootStore from above.

Now to create the hook

/// src/stores/rootStore.ts

export function useStore(){
  const store = React.useContext(RootStoreContext);
  if(store === null){
    throw new Error('Store cannot be null, please add a context provider');
  }
  return store;
}

Add some models

Now we can use this, but first, let us add a store into our rootStore so we can utilize this.

/// src/stores/userStore.ts

import { types } from 'mobx-state-tree';

// example store, replace this with your actual stores
export const UserStore = types
  .model('UserStore')
  .props({
    id: types.identifier,
    name: types.string,
  })
  .actions((self) => ({
    setName: (name: string) => {
      self.name = name;
    }
}));

export const UserStoreInitialState = {
  id: '',
  name: '',
}
/// src/stores/rootStore.ts

import { UserStore, UserStoreInitialState } from './userStore';

export const rootStore = types
  .model({
    userStore: UserStore,
  })
  .create({
    userStore: UserStoreInitialState,
  });

Using our new hook

/// src/components/user.ts

import { useStore } from '../stores/rootStore';

export function User(){
  const { userStore } = useStore();
  return (
    <div>
      <h1>{userStore.name}</h1>
      <button onPress={() => {
        userStore.setName('Colby');
      })>Update Name</button>
    </div>
  );
}

What about re-rendering?

If you want your component to automatically re-render when state changes, use the mobx-react-lite package.

/// src/components/user.ts

import { useStore } from '../stores/rootStore';
import { observer } from 'mobx-react-lite';

export function User observer((){
  const { userStore } = useStore();
  return (
    <div>
      <h1>{userStore.name}</h1>
      <button onPress={() => {
        userStore.setName('Colby');
      })>Update Name</button>
    </div>
  );
});

Wrapping any component that "observers" an MST model's state will automatically re-render when that state changes.

All done!

And that's it! Mobx-state-tree (combined with mobx-react-lite for re-rendering) are amazing tools to keep in your tool belt, and a nice alternative to Redux (a lot less code to write to achieve what you want).

image credit: https://unsplash.com/photos/c9FQyqIECds


This content originally appeared on DEV Community and was authored by Colby Garland


Print Share Comment Cite Upload Translate Updates
APA

Colby Garland | Sciencx (2021-07-19T20:53:56+00:00) Create a useStore hook for mobx-state-tree. Retrieved from https://www.scien.cx/2021/07/19/create-a-usestore-hook-for-mobx-state-tree/

MLA
" » Create a useStore hook for mobx-state-tree." Colby Garland | Sciencx - Monday July 19, 2021, https://www.scien.cx/2021/07/19/create-a-usestore-hook-for-mobx-state-tree/
HARVARD
Colby Garland | Sciencx Monday July 19, 2021 » Create a useStore hook for mobx-state-tree., viewed ,<https://www.scien.cx/2021/07/19/create-a-usestore-hook-for-mobx-state-tree/>
VANCOUVER
Colby Garland | Sciencx - » Create a useStore hook for mobx-state-tree. [Internet]. [Accessed ]. Available from: https://www.scien.cx/2021/07/19/create-a-usestore-hook-for-mobx-state-tree/
CHICAGO
" » Create a useStore hook for mobx-state-tree." Colby Garland | Sciencx - Accessed . https://www.scien.cx/2021/07/19/create-a-usestore-hook-for-mobx-state-tree/
IEEE
" » Create a useStore hook for mobx-state-tree." Colby Garland | Sciencx [Online]. Available: https://www.scien.cx/2021/07/19/create-a-usestore-hook-for-mobx-state-tree/. [Accessed: ]
rf:citation
» Create a useStore hook for mobx-state-tree | Colby Garland | Sciencx | https://www.scien.cx/2021/07/19/create-a-usestore-hook-for-mobx-state-tree/ |

Please log in to upload a file.




There are no updates yet.
Click the Upload button above to add an update.

You must be logged in to translate posts. Please log in or register.