0%

Redux入门操作详解

Redux 是 JavaScript 状态容器,提供可预测化的状态管理。随着 JavaScript 单页应用开发日趋复杂,JavaScript 需要管理比任何时候都要多的 state (状态)。 这些 state 可能包括服务器响应、缓存数据、本地生成尚未持久化到服务器的数据,也包括UI 状态,如激活的路由,被选中的标签,是否显示加载动效或者分页器等等。本次主要讲解当前针对react框架的redux,即REACT-REDUX。

React-Redux

首先,react-redux与redux的核心理念一致,只是一些API的使用上存在差异,react-redux使得在react中使用redux更为简便。

Redux的三大原则——Three Principles

单一数据源

整个应用的state被存储在一棵object tree上,并且这个object tree只存在于store,且store是唯一的,仅此一个。

State只读

唯一改变state的方法是触发action,action是一个用于描述已发生事件的对象,其形式为{type:"", data:""}

使用纯函数来执行修改

为了描述action如何改变state tree,需要编写reducers。

Reducer只是一些纯函数,它接收先前的 state 和 action,并返回新的 state。

React-Redux实际操作步骤

步骤一

在src下新建名为redux的文件,并创建好4个common JS文件,分别为store.js, reducer.js, action.js以及constant.js。其中constant.js用于存储常量,其余三个代表redux的三个核心。

注:如果不只一个action/reducer,可以分别创建action和reducer的文件夹。

index.js中引入store.js,并从react-redux中引入ProviderProvider组件用于给App下的每个需要用到redux的组件传递store。实例如下:

1
2
3
4
5
6
7
8
9
10
11
12
import React from 'react';
import ReactDOM from 'react-dom';
import App from './App'
import store from './redux/store'
import {Provider} from 'react-redux'

ReactDOM.render(
//为所有组件提供store
<Provider store={store}>
<App />
</Provider>,
document.getElementById('root'));

步骤二——编写store

在store文件中引入能创建store实例的creatStore、能修改状态的reducer和能执行异步的thunk和中间件applyMiddleware(如果需要)。

注:对于多个状态需要维护的情况,从redux中引入combineReducers方法,该方法可以通过对象{}的键值对key:value形式,维护任意多个状态(即reducer)。

实例如下:

1
2
3
4
5
6
7
8
9
import {createStore, applyMiddleware, combineReducers} from 'redux'
import countReducer from './reducers/count'
import personReducer from './reducers/person'
import thunk from 'redux-thunk'

const allReducers = combineReducers({count: countReducer, people: personReducer});

const store = createStore(allReducers, applyMiddleware(thunk))
export default store

步骤三——编写action

引入store文件,和常量文件constant(如果有)。编写action函数,其会返回一个action对象,形式为{type:"", data:""}

实例如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
import store from "../store";
import {INCREMENT, DECREMENT} from '../constant'

export const createIncrementAction = data => ({type:INCREMENT, data});
export const createDecrementAction = data => ({type:DECREMENT, data});

export const createIncrementAsyncAction = (data, time) => {
return () => {
setTimeout(() => {
store.dispatch({type:INCREMENT, data})
}, time)
}
}

步骤四——编写reducer

reducer负责维护状态。编写reducer函数,需要设置初始化的状态值,并对函数传入action参数,根据action对象的typedata对状态进行操作,并返回操作后的状态。

实例如下:

1
2
3
4
5
6
7
8
9
10
11
12
const initNumber = 0;
export default function countReducer(preState=initNumber, action) {
const {type, data} = action;
switch (type) {
case 'increment':
return preState + data;
case 'decrement':
return preState - data;
default:
return preState;
}
}

至此,redux部分的基本三大件已经写完。接下来需要编写组建模块。

步骤五——编写Container/Component

首先,引入action,并从react-redux中引入connect函数,该函数用于创建并暴露一个Container容器,同时将state和action传入组件中,并且它们都会被传入到组件自身的prorps属性中。实例如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
import React, { Component } from 'react'
// 引入connect
import { connect } from 'react-redux'
// 引入action
import {createIncrementAction, createDecrementAction, createIncrementAsyncAction} from '../../redux/actions/count'

class Count extends Component {
render() {
return (<div></div>)
}
}

export default connect(
// 传入state
state => ({count: state.count, people: state.people}),
// 传入action
{increment: createIncrementAction,
decrement: createDecrementAction,
asyncIncrement: createIncrementAsyncAction
}
)(Count)