美文网首页
Redux中间件(三):中间件

Redux中间件(三):中间件

作者: Viewwei | 来源:发表于2021-01-08 14:41 被阅读0次

redux中的reducer函数主要目的是制定更新规则,如果reduce中的action是一个异步的或者是一个函数的时候就会报错实例如下
调用方法

   const delayed = ()=>{
        store.dispatch(()=>{
            setTimeout(() => {
                store.dispath({type:"ADD"})    
            }, 1000);
        })
    }

执行结果


image.png

报错原因说action必须使用明确的action,你可以使用带中间件的异步action

  • 使用中间件
    需要安装3个中间件
    • 第一步
yarn add redux-logger redux-promise redux-thunk
  • 第二步修改createStore方法
import {createStore, applyMiddleware, combineReducers} from "redux";
 import thunk from "redux-thunk";
 import logger from "redux-logger";
import promise from "redux-promise";
function countReducer(state=0,action) {
  debugger
    switch(action.type){
        case "ADD":
            return state+=1
        case "MINUS":
            return state -=1
        default:
            return state
    }
}
const store = createStore(countReducer,applyMiddleware(promise,thunk,logger))
export default store

修改完成,在执行dispatch为函数或者为promise都可以

  • 注意 logger最好写在最后,不然不能很好的捕捉日志

仿写中间件 logger thunk 和promise

  • 代码思路:所谓的中间件其实就是对现有的createStore进行增强,返回的结果也应该和createStore保持一致。增强只是说对dispatch进行增强。同时也需要执行一遍中间件(函数)
  1. 修改createStore函数
export default function createStore(reducer,enhancer){
//enhancer 表示applyMiddleware 执行结果
    if (enhancer){
        //enhancer(createStore) 返回一个函数,相当于把createStore函数传递到函数中,在此执行这个函数,参数为reducer
        return enhancer(createStore)(reducer)
    }
    // reducer 表示一个函数
    let currentState;
    let currentListeners =[]
    function getState() {
        return currentState
    }
    function  dispatch(action) {
        currentState = reducer(currentState,action)
        currentListeners.forEach(listener =>listener())
    }

    function subscribe(listener) {
        currentListeners.push(listener)
        return () =>{
            const index = currentListeners.indexOf(listener)
            currentListeners.splice(index,1)
        }
    }
    dispatch({type:"REDXXXXXXXX"})
    return {
        getState,
        subscribe,
        dispatch
    }

}
  1. 创建 applyMiddleware文件并导出
export default function applyMiddleware(...middlewares) {
//这个地方可以改为  createStore  =>reducer =>{} 函数样式
    return createStore => {
        return reducer => {
            const store = createStore(reducer) //调用createStore函数,返回值为
        // store  = {getState, subscribe,dispatch}
            let dispatch = store.dispatch //取出store中的dispath函数,主要目的是传递给中间件(函数使用)
            const midApi = { //定义一个中间件使用的对象
                getState: store.getState,
                dispatch: action => dispatch(action)
            }
            // 把midApi 传递给中间件
            const middlewareChain = middlewares.map(middleware => middleware(midApi)) //注意,这个地方需要结合中间件函数一起看, 返回next => action =>{}函数总数为2 一个为thunk的返回值一个为logger返回值
            let res = compose(...middlewareChain) //返回一个函数,logger的
         dispatch =res(store.dispatch)//执行compose函数 dispatch 返回的就是thunk中的 action =>{} 函数
            // 返回增强的store,其实把dispatch增强就行了 
            return {
                ...store,
                dispatch
            };
        }
    }
}
function compose(...funs) {
    // 这个空数组的兼容情况
    if (funs.length === 0) {
        return arg => arg;
    }
    if (funs.length === 1) {
        return funs[0];
    }
    // 这个返回值是个函数
    let r=  funs.reduce((a, b) => (...args) => a(b(...args)));
    return r
}
  1. 中间件(函数)的创建
import {createStore, applyMiddleware, combineReducers} from "redux";
// import thunk from "redux-thunk";
// import logger from "redux-logger";
// import promise from "redux-promise";
// import  {createStore,applyMiddleware} from '../vRedux/index'
function countReducer(state=0,action) {
  debugger
    switch(action.type){
        case "ADD":
            return state+=1
        case "MINUS":
            return state -=1
        default:
            return state
    }
}
// ,
const store = createStore(countReducer,applyMiddleware(thunk,logger))
// thunk处理异步
function thunk({dispatch, getState}) {
    // next 通过comose函数,next其实就是logger函数,action函数就是dispatch中的函数dispatch(A) A =action,首先要判断action是对象还是函数,如果是函数的话,首先执行函数,因为在action(dispatch, getState);函数体重,仍然有dispatch函数的调用,它会再次进入这个函数,只不过这个参数为对象,因为next =logger函数返回的action=>{}函数,所以进入logger函数
    return next => action => {
      if (typeof action === "function") {
        return action(dispatch, getState);
      }
      return next(action);
    };
  }
  
  // ! 注意了: logger一定要放在applyMiddleware最后一个参数,因为放在前面的话,可能或没有type值,
  // ! 比如说thunk处理的函数也是’action‘,但是就没有type值
  function logger({dispatch, getState}) {
    return next => action => {
       //logger函数中 next为createStore 方法中dispatch函数,这是因为在compose函数调用的时候传递的为store.dispatch函数,action 表示操作类型action={type:XXX}
      console.log("start *************************************");
      console.log(action.type + "执行啦"); //sy-log
      // dispatch执行前的state
      const prevState = getState(); //这表示当前的state状态
      console.log("prev state" + prevState, JSON.stringify(prevState)); //sy-log
  
      // 相当于dispatch执行完了,数据已经发生变化
      const returnValue = next(action); //正式执行了dispatch(action)函数,state发生了变化
      const nextState = getState(); //最新的状态
      console.log("next state" + nextState, JSON.stringify(nextState)); //sy-log
  
      console.log("end *************************************");
  
      return returnValue;
    };
  }
export default store

相关文章

  • 2-Redux中间件

    Redux 中间件 [toc] Redux 中间件的作用 Reudx 中的中间件是通过对 dispatch 进行的...

  • react 面试

    react redux (所有数据都放入redux管理) 1、redux中间件原理(middleware) 中间件...

  • Redux 中间件源码清源

    网上的Redux中间件原理解释多有疏漏,譬如我在多篇blog上看到Redux中间件解释以及Redux中间件深入浅出...

  • 关于redux中的Middleware

    什么是Redux中间件 ? redux 提供了类似后端 Express 的中间件概念,本质的目的是提供第三方插件的...

  • [源码] Redux React-Redux01

    redux中间件洋葱模型imageimage redux中间件注意点image 导航 [深入01] 执行上下文[h...

  • react技术栈

    关于 Redux 中间件 Redux 的中间件是定义一个函数,对 dispatch 进行改造,在发出 action...

  • 使用中间件加强store

    Time: 2019-08-18 什么是中间件 redux的插件通常称之为中间件。 中间件并不神奇,因为中间件就是...

  • 如何在 Redux 中使用中间件

    目录 中间件介绍 自定义 logger 中间件 概括 中间件介绍 Redux 是 React 最流行的状态管理库之...

  • Day17. Redux深入

    如何使用redux-thunk 中间件的使用, redux-thunk redux-devtools redux开...

  • js中不同框架中间件实现的区别

      用过express,koa,react(redux)的都会知道中间件,那么在这三个框架的中间件的实现有什么不同...

网友评论

      本文标题:Redux中间件(三):中间件

      本文链接:https://www.haomeiwen.com/subject/tlgwoktx.html