在React项目中,我们需要处理异步请求所出现的情况。这里我们采用Redux及其中间件。
1.整合Redux到React项目中
通过引入Provider组件将store导入到所有内部组件上。
import React from 'react'
import ReactDOM from 'react-dom'
import Router from './router'
import { Provider } from 'react-redux'
import store from './redux/store'
import './mock'
ReactDOM.render(
<Provider store={store}>
<Router />
</Provider>
, document.getElementById('root'));
store.js:
/**
* 引入createStore
*/
import { createStore, compose, applyMiddleware } from 'redux'
import reducer from './reducer'
import createSagaMiddleware from 'redux-saga'
import rootSaga from './sagas'
const sagaMiddleware = createSagaMiddleware()
const composeEnhancers = window.__REDUX_DEVTOOLS_EXTENSION_COMPOSE__ || compose
const enhancer = composeEnhancers(
applyMiddleware(sagaMiddleware),
)
const store = createStore(reducer, enhancer)
sagaMiddleware.run(rootSaga)
export default store
2.实现一个具体的异步请求任务
在需要实现的组件尾部,改造映射store。
const mapStateToProps = state => {
return {
caseQuery: state.caseQuery.caseQuerys,
pagination: state.caseQuery.pagination,
}
}
export default connect(mapStateToProps)(Form.create()(CaseQuery))
在action中,首先将type作为模块导出,然后再将具体的方法分别单独输出。
action.js:
/**
* 1. 获取查询列表
* 2. 初始化查询列表
* 3. 初始化分页组件pagination
*/
export const type = {
GET_CASE_LIST : 'GET_CASE_LIST',
ININT_CASE_LIST : 'ININT_CASE_LIST',
REFRESH_PAGINATION : 'REFRESH_PAGINATION',
}
// 1. 获取查询列表
export const getCaseList = (payload) => ({
type: type.GET_CASE_LIST,
payload
})
// 2. 初始化查询列表
export const initCaseList = (caseQuerys) => ({
type: type.ININT_CASE_LIST,
caseQuerys
})
// 3. 刷新分页组件pagination
export const refreshPagination = (pagination) => ({
type: type.REFRESH_PAGINATION,
pagination
})
当action触发以后,reducer会对action传递的数据进行处理。
reducer.js:
import { type } from './action'
const initState = {
caseQuerys: [],
pagination: {},
}
export default (state = initState, action) => {
switch(action.type) {
case type.ININT_CASE_LIST:
return {
...state,
caseQuerys: JSON.parse(JSON.stringify(action.caseQuerys))
}
case type.REFRESH_PAGINATION:
return {
...state,
pagination: JSON.parse(JSON.stringify(action.pagination))
}
default: return state
}
}
实现redux-saga中间件。引入saga后,在generator函数中我们使用yield表达式来接收返回值。
saga.js:
import { call, put } from 'redux-saga/effects'
import Http from '@/axios'
import {initCaseList, refreshPagination} from './action'
import Utils from '@/utils/utils'
// 异步获取查询列表
export function* asyncGetCaseList({ payload }) {
const res = yield call(Http.reqGetCaseList, payload.params) // $.ajax('xxx', function(res){res.data})
payload._this.switchTableLoading(false)
if(res){
const list = Utils.generateKeyIntoList(res.data.list, "uniqAcceptid") // 把列表里的每一项加一个key,key值为id字段值
const pagination = Utils.pagination(res.data) // 生成pagination
yield put(initCaseList(list))
yield put(refreshPagination(pagination))
}
}