State management is a very important issue for large front-end projects. Processing data is not difficult, the difficulty is how to deal with so much data in the project beautiful, simple, easy to understand. When different pages get the same data, make sure that the data on both sides is the same and that the data on both sides is not different because of the delay in the request. Therefore, a unified state management tool is necessary. The main React state management solutions are Redux and Mobx. Mobx-state-tree is another State management tool developed by Mobx developers. While retaining the basic design concept of Mobx, Mobx State Tree combines the advantages of Redux having only one store and immutable data.
The installation
// Install yarn add mobx mobx-react-lite mobx-state-tree. // Install yarn add mobx mobx-react-lite mobx-state-treeCopy the code
Basic concept
core idea
The tree Root. The tree consists of mutable but tightly protected objects that are rich in runtime type information. In other words; Each tree has a shape (type information) and a state (data). From this living tree, snapshots of shared immutable structures are automatically generated.
As you can see, the state of the entire project is similar to that of a tree, with Root as the trunk of the tree and other branches (other state data) attached to the Root tree. That is, different branches process different data and eventually mount the data to the Root tree, so that all data mounted on the Root can be accessed, updated, and modified.
Basic Concepts:
Tree = type + state
// type
const Todo = types.model({
title: types.string
})
//state
const coffeeTodo = Todo.create({
title: "Get coffee"
})
Copy the code
Hands type
Define the model
Import {types} from mobx - state - "tree" / / define a List of the "branches" structure, which is a const object contains the title attribute List = types. The model ({title: types.string })Copy the code
Create the Root tree and initialize the data
Model ({lists: List}) // Initialize data const rootStore = rootModel.create ({lists: { title: 'hello world' } })Copy the code
Modify the state of
const Todo = types.model({ title: Types.string}).actions(self => {return {setNewTitle(newTitle){self.title = newTitle}}) // use rootStore.lists.setNewTitle('hello ccc')Copy the code
Adds data to an object
const RootModel = types .model({ userList: types.map(List) }).actions(self => { return { addUser(id: string, title:string, done: boolean){ self.userList.set(id, List.create({title, done})) } } }); let initialState = RootModel.create({ userList: {} }); // Call rootStore.adduser ('1', 'CCC ', false) rootStore.userlist.get ('1').toggle()Copy the code
Adds data to an array
const RootModel = types .model({ listArray: types.array(List) }) .actions(self => { return { addArray(title: string, done: boolean){ self.listArray.push({title, done}) } } }); // Call rootStore.addArray('dog', false)Copy the code
Asynchronous operations
const RootModel = types .model({ data: types.string }) .actions(self => ( { getData: flow(function* getData(){ const data = yield axios('http://xxxx') self.data = JSON.strinfy(data) }) } )); / / call rootStore. GetData ()Copy the code
Listen on the Store in the UI
import {observer} from 'mobx-react-lite';
const User = observer(() => {
const store = useRootStore()
return(
<div>
<p>{JSON.stringify(store)}</p>
</div>
)
})
export default User
Copy the code
Update by snapshot
OnSnapshot (rootStore, snapshot => {console.log(' snapshot: ', snapshot); });Copy the code
Summary of the type
The base type
types.string
– String typetypes.number
– Number typetypes.integer
– Integer typetypes.boolean
– Boolean typetypes.Date
– Date typetypes.custom
– Creates a custom base type
The complex type
types.model()
– Used to describe the shape of an objecttypes.array(type)
– Declares an array of the specified type.types.map(type)
– Declares the mapping of the specified type.types.model()
– Creates a linkable model type where each linked method produces a new type.named(name)
– Clone the current type, but give it a new name.props(props)
– Generates a new type based on the current type, and adds or overwrites the specified attributes.actions(self => ...)
– Provides a series of operations on the current data.views(self => ..)
– Calculate attributes