對react中間件的理解

一、是什么?
中間件(Middleware)在計算機中,是介于應用系統(tǒng)和系統(tǒng)軟件之間的一類軟件,它使用系統(tǒng)軟件所提供的基礎服務(功能),銜接網絡應用上的各個部分或不同的應用,能夠達到資源共享、功能共享的目的
我們知道redux整個工作流程,當action發(fā)出之后,reducer立即算出state,整個過程是一個同步的操作。
那么如果要支持異步操作,或者支持錯誤處理、日志監(jiān)控,就可以使用上中間件。

Redux中,中間件就是放在就是在dispatch過程,在分發(fā)action進行攔截處理,如上圖
其本質上一個函數,對store.dispatch方法進行了改造,在發(fā)出 Action和執(zhí)行 Reducer這兩步之間,添加了其他功能
二、常用的中間件
redux-thunk:用于異步操作
redux-logger:用于日志記錄
redux-promise
redux-saga
上述的中間件都需要通過applyMiddlewares進行注冊,作用是將所有的中間件組成一個數組,依次執(zhí)行,然后作為第二個參數傳入到createStore中
import { createStore, applyMiddleware } from 'redux'
import thunk from 'redux-thunk'
import createLogger rom 'redux-logger'
const logger = createLogger()
const store = createStore(reducer, applyMiddleware(thunk, logger)) // 按順序執(zhí)行 從右到左
logger實現(xiàn)
// 自己修改dispatch,增加logger
let next = store.dispatch
store.dispatch = function dispatchAndLog(action) {
console.log('dispatching', action)
next(action)
console.log('next state', store.getState())
}
redux-thunk
添加了thunk中間件之后,就可以進行異步操作
redux-thunk是官網推薦的異步處理中間件
默認情況下的dispatch(action),action需要是一個JavaScript的對象
redux-thunk中間件會判斷你當前傳進來的數據類型,如果是一個函數,將會給函數傳入參數值(dispatch,getState)dispatch函數用于我們之后再次派發(fā)actiongetState函數考慮到我們之后的一些操作需要依賴原來的狀態(tài),用于讓我們可以獲取之前的一些狀態(tài)
所以dispatch可以寫成下述函數的形式:
const getHomeMultidataAction = () => {
return (dispatch) => {
axios.get("http://xxx.xx.xx.xx/test").then(res => {
const data = res.data.data;
dispatch(changeBannersAction(data.banner.list));
dispatch(changeRecommendsAction(data.recommend.list));
})
}
}

dispatch(addTodo(text)) dispatch(addTodoAsync(text))
redux數據流圖:

三、實現(xiàn)原理
首先看看applyMiddlewares的源碼
export default function applyMiddleware(...middlewares) {
return (createStore) => (reducer, preloadedState, enhancer) => {
var store = createStore(reducer, preloadedState, enhancer);
var dispatch = store.dispatch;
var chain = [];
var middlewareAPI = {
getState: store.getState,
dispatch: (action) => dispatch(action)
};
chain = middlewares.map(middleware => middleware(middlewareAPI));
dispatch = compose(...chain)(store.dispatch);
return {...store, dispatch}
}
}
所有中間件被放進了一個數組chain,然后嵌套執(zhí)行,最后執(zhí)行store.dispatch??梢钥吹?,中間件內部(middlewareAPI)可以拿到getState和dispatch這兩個方法
在上面的學習中,我們了解到了redux-thunk的基本使用
內部會將dispatch進行一個判斷,然后執(zhí)行對應操作,原理如下:
function patchThunk(store) {
letnext = store.dispatch;
function dispatchAndThunk(action) {
if (typeof action === "function") {
action(store.dispatch, store.getState);
} else {
next(action);
}
}
store.dispatch = dispatchAndThunk;
}
實現(xiàn)一個日志輸出的原理也非常簡單,如下:
let next = store.dispatch;
function dispatchAndLog(action) {
console.log("dispatching:", addAction(10));
next(addAction(5));
console.log("新的state:", store.getState());
}
store.dispatch = dispatchAndLog;
總結
以上為個人經驗,希望能給大家一個參考,也希望大家多多支持腳本之家。
相關文章
React-Native使用Mobx實現(xiàn)購物車功能
本篇文章主要介紹了React-Native使用Mobx實現(xiàn)購物車功能,小編覺得挺不錯的,現(xiàn)在分享給大家,也給大家做個參考。一起跟隨小編過來看看吧2017-09-09
react實現(xiàn)鼠標懸停在SVG地圖上某個區(qū)域時上方呈現(xiàn)柱形圖效果
這篇文章主要介紹了react實現(xiàn)鼠標懸停在SVG地圖上某個區(qū)域時,其上方呈現(xiàn)柱形圖,本文通過實例代碼給大家介紹的非常詳細,需要的朋友可以參考下2025-04-04
在create-react-app中使用css modules的示例代碼
這篇文章主要介紹了在create-react-app中使用css modules的示例代碼,小編覺得挺不錯的,現(xiàn)在分享給大家,也給大家做個參考。一起跟隨小編過來看看吧2018-07-07

