詳解在React里使用"Vuex"
一直是Redux的死忠黨,但使用過Vuex后,感嘆于Vuex上手之快,于是萌生了寫一個能在React里使用的類Vuex庫,暫時取名 Ruex 。
如何使用
一:創(chuàng)建Store實例:
與vuex一樣,使用單一狀態(tài)樹(一個對象)包含全部的應用層級狀態(tài)(store)。
store可配置state,mutations,actions和modules屬性:
- state :存放數(shù)據(jù)
- mutations :更改state的唯一方法是提交 mutation
- actions :Action 提交的是 mutation,而不是直接變更狀態(tài)。Action 可以包含任意異步操作,觸發(fā)mutation,觸發(fā)其他actions。
支持中間件:中間件會在每次mutation觸發(fā)前后執(zhí)行。
store.js:
import {createStore} from 'ruex'
const state = {
total_num:1111,
}
const mutations = {
add(state,payload){
state.total_num += payload
},
double(state,payload){
state.total_num = state.total_num*payload
},
}
const actions = {
addAsync({state,commit,rootState,dispatch},payload){
setTimeout(()=>{
commit('add',payload)
},1000)
},
addPromise({state,commit,rootState,dispatch},payload){
return fetch('https://api.github.com/search/users?q=haha').then(res=>res.json())
.then(res=>{
commit('add',1)
dispatch('addAsync',1)
})
},
doubleAsync({state,commit,rootState,dispatch},payload){
setTimeout(()=>{
commit('double',2)
},1000)
},
doublePromise({state,commit,rootState,dispatch},payload){
return fetch('https://api.github.com/search/users?q=haha').then(res=>res.json())
.then(res=>{
commit('double',2)
dispatch('doubleAsync',2)
})
},
}
// middleware
const logger = (store) => (next) => (mutation,payload) =>{
console.group('before emit mutation ',store.getState())
let result = next(mutation,payload)
console.log('after emit mutation', store.getState())
console.groupEnd()
}
// create store instance
const store = createStore({
state,
mutations,
actions,
},[logger])
export default store
將Store實例綁定到組件上
ruex提供Provider方便store實例注冊到全局context上。類似react-redux的方式。
App.js:
import React from 'react'
import {Provider} from 'ruex'
import store from './store.js'
class App extends React.Component{
render(){
return (
<Provider store={store} >
<Child1/>
</Provider>
)
}
}
使用或修改store上數(shù)據(jù)
store綁定完成后,在組件中就可以使用state上的數(shù)據(jù),并且可以通過觸發(fā)mutation或action修改state。具體的方式參考react-redux的綁定方式:使用connect高階組件。
Child1.js:
import React, {PureComponent} from 'react'
import {connect} from 'ruex'
class Chlid1 extends PureComponent {
state = {}
constructor(props) {
super(props);
}
render() {
const {
total_num,
} = this.props
return (
<div className=''>
<div className="">
total_num: {total_num}
</div>
<button onClick={this.props.add.bind(this,1)}>mutation:add</button>
<button onClick={this.props.addAsync.bind(this,1)}>action:addAsync</button>
<button onClick={this.props.addPromise.bind(this,1)}>action:addPromise</button>
<br />
<button onClick={this.props.double.bind(this,2)}>mutation:double</button>
<button onClick={this.props.doubleAsync.bind(this,2)}>action:doubleAsync</button>
<button onClick={this.props.doublePromise.bind(this,2)}>action:doublePromise</button>
</div>)
}
}
const mapStateToProps = (state) => ({
total_num:state.total_num,
})
const mapMutationsToProps = ['add','double']
const mapActionsToProps = ['addAsync','addPromise','doubleAsync','doublePromise']
export default connect(
mapStateToProps,
mapMutationsToProps,
mapActionsToProps,
)(Chlid1)
API:
- mapStateToProps :將state上的數(shù)據(jù)綁定到當前組件的props上。
- mapMutationsToProps : 將mutation綁定到props上。例如:調(diào)用時通過this.props.add(data)的方式即可觸發(fā)mutation,data參數(shù)會被mutaion的payload參數(shù)接收。
- mapActionsToProps : 將action綁定到props上。
內(nèi)部實現(xiàn)
ruex內(nèi)部使用immer維護store狀態(tài)更新,因此在mutation中,可以通過直接修改對象的屬性更改狀態(tài),而不需要返回一個新的對象。例如:
const state = {
obj:{
name:'aaaa'
}
}
const mutations = {
changeName(state,payload){
state.obj.name = 'bbbb'
// instead of
// state.obj = {name:'bbbb'}
},
}
支持modules(暫不支持namespace)
支持中間件。注:actions已實現(xiàn)類似redux-thunk的功能
以上就是本文的全部內(nèi)容,希望對大家的學習有所幫助,也希望大家多多支持腳本之家。
相關文章
React避坑指南之useEffect 依賴引用類型問題分析
這篇文章主要介紹了React避坑指南之useEffect 依賴引用類型問題分析,本文通過實例代碼給大家介紹的非常詳細,對大家的學習或工作具有一定的參考借鑒價值,需要的朋友可以參考下2023-03-03
React路由規(guī)則定義與聲明式導航及編程式導航分別介紹
這篇文章主要介紹了React路由規(guī)則的定義、聲明式導航、編程式導航,文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友們下面隨著小編來一起學習吧2022-09-09

