上文我们说到redux的状态管理API的基本用法,state,reducer,store,dispatch,subscribe之间的基本关系,但是在实际的使用中引入扩展包与组件拆分开,让组件无污染,可复用性更强,更方便对状态进行管理。
- react-redux认识
1.1 react-redux将组件分为两大类,UI组件和容器组件。简单的理解就是UI负责UI的呈现,容器组件负责管理数据和逻辑。UI组件由用户提供,容器组件则是由react-redux自动生成,负责状态管理。
1.2 connect()方法 用于从UI组件中生成容器组件,connect就是将两种组件连接起来
1.3 mapStateToProps()方法 建立一个state对象到UI组件对象的props对象映射关系。import { connect } from 'react-redux'; import DemoUI from 'UI'; //ui组件 const Demo = connect()(DemoUI)
1.4 mapDispatchToProps()方法 建立UI组件参数到store.dispatch方法的映射,定义了UI 组件发出的action。function mapStateToProps(state){ return { //state 对象 }}
1.5 Provider组件 Provider在根目录组件包装已成,让容器拿到state状态function mapDispatchToProps(dispatch){ return { //action } }
import { Provider } from 'react-redux'; import counter from './reducer'; import { createStore } from 'react'; let store = createStore(counter); import App from './app'; //组件 render(){ return ( <Provider store={store}> <App/> </Provider> )}
npm i react-redux -S
import React from 'react';
import ReactDom from 'react-dom';
import { createStore } from 'redux';
import {Provider, connect} from 'react-redux';
const reducer = (state={sum:0}, action)=>{
switch(action.type){
case 'INCREMENT':
const incre = state.sum + action.value;
return {
sum: incre
}
case 'DECREMENT':
const decre = state.sum - action.value;
return {
sum: decre
}
default:
return state;
}
}
const store = createStore(reducer);
class Main extends React.Component{
render(){
const {state, increment, decrement} = this.props;
return (
<div>
<div>{ state.sum }</div>
<input type="button" value="+" onClick={increment}/>
<input type="button" value="-" onClick={decrement}/>
</div>
)
}
}
const mapStateToProps = (state) => {
return { state }
}
const mapDispatchToProps = (dispatch) => {
return {
increment: ()=>dispatch({type:'INCREMENT',value:1}),
decrement: ()=>dispatch({type:'DECREMENT',value:2})
}
}
const App = connect(mapStateToProps, mapDispatchToProps)(Main);
ReactDom.render(
<Provider store={store}>
<App/>
</Provider>,
document.getElementById('app')
);
2. redux-thunk. 异步操作
一个常见的ajax请求成功后触发dispatch,最简单的就是将这个操作封装成函数。
decrement: ()=>{
dispatch({type:'DECREMENT',value:1});
setTimeout(()=>{
dispatch({type:'DECREMENT',value:2})
}, 1000);
}
但是更好的做法是redux-thunk这样的中间件,在 actionCreator 中生成一个包含异步操作的action。
redux-thunk的使用方法
import { createStore, applyMiddleware } from 'redux';
import thunk from 'thunk';
......
const sore = createStore(reducer, applyMiddleware(thunk));
actionCreator返回一个函数,在这个函数中可以做任意事情,触发任意次的dispatch和异步函数。
const laoder = () => {
console.log('loader...');
return {type:'DECREMENT',value:2}
}
decrement: ()=>dispatch((dispatch, getState)=>{
dispatch(laoder());
setTimeout(()=>{
dispatch({type:'DECREMENT',value:2})
}, 1000);
})
以上就是redux扩展的基本使用方式,使用扩展主要也就是为了状态管理更加方便。