//源码使用方法 import {createStore, applyMiddleWare} from 'redux'; //createStore.js的源码 export default function createStore(reducer, preloadState, enhancer) { //... if(typeof enhancer !== 'undefined'){ if(typeof enhancer !== 'function'){ throw new Error('...') } }
//enhancer是一个增加强器,是可选参数。是applyMiddelWare的返回值即一个函数
return enhancer(createStore)(reducer, preloadState); }
//顾名思义, applyMiddleWare就是对各个需要应用的中间件进行糅合,并作为createStore的 //第二个或者第三个参数传入,用于增强store。源码如下: export default function applyMiddleWare(...middlewares){ return (next) => (reducer, initialState) => { var store = next(reducer, initialState); 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 } } } //分析: export default function applyMiddleware(...middlewares); //这里使用了扩展运算符,使得applyMiddleware可以接收任意个数的中间件。接下来, //applyMiddleware会返回一个函数,这个函数接收了一个next参数: return (next) => (reducer, initialState) => { //... } //对应于createStore.js代码,applyMiddelware作为一个三级柯里化的函数,它的执行相当于: applyMiddleware(...middlewares)(store)(reducer, initialState); //这样做的目的是借用原始的createStore方法,创建一个增强版store,具体看其内容实现: var store = createStore(reducer, initialState); var dispatch = store.dispatch; var chain = [] //这里记录了原始的store和store.dispatch方法,并准备了一个chain数组 var middlewareAPI = { getState: store.getState, dispatch: (action) => dispatch(action) } var chain = middlewares.map(middleware => middleware(middlewareAPI)); //middlewareAPI是第三方中间件需要使用的参数,即原始的store.getState 和dispatch方法, //这些参数在中间件中是否会全部应用到,自然要看每个中间件的应用场景和需求。 //可以想象chain数组中每一项都是对原始dispatch的增强,并进行控制权转移。所以就有了 dispatch = compose(...chain, store.dispatch) //这里的dispatch函数就是增强后的dispatch。因此,compose 方法接收了chain数组和原始的store.dispatch方法。 export default function compose (...funcs) { if(funcs.length === 0){ return arg => arg; } if(funcs.length === 1){ return funcs[0]; } return funcs.reduce((a, b) => (...args) => a(b(...args))); } //实际上,compose方法就像是把多个中间件串联起来,就像 // middlewareA( middlewareB( middlewareC(store.dispatch) ) )