redux中间件执行原理?

学习过react的同窗确定都用过redux。了解redux数据流机制的action->dispatch->store->reduce->页面交互其实很好理解,但是当咱们要用到异步请求或者打印日志之类的副操做的时候,咱们没法避免的会用到中间件Middleware。中间件都是怎么执行以及如何有序的串在一块儿很使人迷惑,下面我将尝试解释这个过程:react

演变过程

假如你有个需求须要在分发dispatch先后打印不一样状态值,你确定会这么想:redux

console.log('dispatching', action)
store.dispatch(action)
console.log('next state', store.getState())
复制代码

封装成函数:bash

function dispatchAndLog(store, action) {
  console.log('dispatching', action)
  store.dispatch(action)
  console.log('next state', store.getState())
}
//执行
dispatchAndLog(store,  action)
复制代码

不妨改造store的dispatch更为直接些:app

let next = store.dispatch
store.dispatch = function dispatchAndLog(action) {
  console.log('dispatching', action)
  let result = next(action)
  console.log('next state', store.getState())
  return result
}
复制代码

Redux把这个封装的入口写成了一个函数,就叫applyMiddleware。由此咱们明白了applyMiddleware的功能:改造dispatch函数,产生真假dispatch,而中间件就是运行在假真(dispatchAndLog假和next真)之间的代码。异步

这里咱们要对applyMiddleware进行一个准确的定义,它只是一个用来加工dispatch的工厂,而要加工什么样的dispatch出来,则须要咱们传入对应的中间件函数(好比上例中的dispatchAndLog),下面咱们构造一个精简版的applyMiddleware:函数

function applyMiddleware(middleware){
  let next = store.dispatch;
  store.dispatch = middleware(store)(next);  // 这里传入store,是由于中间件中有可能会用到getState获取数据,好比打印当前用户等需求 
 }
}
applyMiddleware(dispatchAndLog)
复制代码

中间串连

中间件的功能各不相同,它们都要融入到dispatch中,在派发action的时候,按照顺序一个个的执行,这是一个费脑经的事情。在上例中middleware会返回新的dispatch,咱们须要作的也就是将产生的新的dispatch传递个下个中间件便可。以下:学习

function applyMiddleware(middleware,middleware2){
  let next = store.dispatch;
  store.dispatch = middleware2(middleware(store)(next));  
  // 这里传入store,是由于中间件中有可能会用到getState获取数据,好比打印当前用户等需求 
 }
}
applyMiddleware(dispatchAndLog,dispatchmethed)
复制代码

以此类推有大量的中间件的时候咱们能够这么干:ui

function applyMiddleware(...middlewares){
    middlewares = middlewares.slice();
    middlewares.reverse();  //执行顺序是后到前,因此得倒置
    let dispatch = store.dispatch
    //循环嵌套
    middlewares.foreach(function(middleware){
        dispatch = middleware(store)(dispatch);
    });
    return  Object.assign({}, store, { dispatch }); //合并dispatch到redux里。
}
复制代码

请注意这里是一个循环嵌套的一个过程,因此中间的顺序决定着中间件的执行顺序。spa

总结两点:日志

  1. 中间件在执行完副操做会并会返回新的dispatch
  2. applyMiddleware本质是一个循环嵌套调用的过程。

参考:zhuanlan.zhihu.com/p/34651008

相关文章
相关标签/搜索