揭秘React-redux神秘面纱

一. 完整的 Redux 数据流:

 

一脸懵逼?那么请按照如下顺序捋一捋 Redux 的数据流:

  1. 从 View 出发, 视图层调用 action 方法。当前视图层是允许有多个Actions的。
import warning from'./utils/warning'

function bindActionCreator (actionCreator, dispatch) {
    return (...args) => dispatch(actionCreator(...args))
}

export default function bindActionCreators (actionCreators, dispatch) {
    if (typeof actionCreators ==='function') {
        return bindActionCreator(actionCreators, dispatch)
    }
    if (typeof actionCreators !=='object'|| actionCreators ===null) {
        throw new Error(`bindActionCreators expected an object or a function, instead received ${actionCreators === null ? 'null' : typeof actionCreators}. ` + `Did you write "import ActionCreators from" instead of "import * as ActionCreators from"?`)
    }
    const keys = Object.keys(actionCreators)
    const boundActionCreators ={}
    for (let i =0; i < keys.length; i++) {
        const key = keys[i]
        const actionCreator = actionCreators[key]
        if (typeof actionCreator ==='function') {
            boundActionCreators[key] = bindActionCreator(actionCreator, dispatch)
        } else {
            warning(`bindActionCreators expected a function actionCreator for key '${key}', instead received type '${typeof actionCreator}'.`)
        }
    }
    return boundActionCreators
}

  从代码中可以感受到,当存在多个 Actions 的时候,会出现一个重名覆盖的问题。

  2. 从 View 出发, 视图层调用 action 方法。当前视图层是允许有多个Actions的。

  3. action 主要为了提交触发事件,上报到 reduce 里面去处理具体的数据更新,这一部分属于 react-redux 内部的实现范畴。

  4. 外层当接收到了 action 信号,会根据 action ID 去处理对应的数据逻辑,combineReducers 会把众多的 Reduces 给整合到一起。这里注意,reduce 必须是一个纯函数,所谓的 Promise 返回是不可以的。

二. Redux 设计模式:

  

 

 

  store 相当于一个全局的大对象(PS: 对象还真的是 javascript 一个很重要的东西)。设计模式我觉得是发布-订阅的一个设计模式。全局 store 相当于被观察对象,当你的 React 自定义组件订阅了Store 的信息, 各个 action dispatch 相当于一个发布的过程,那么 Store 的变化自然会通知到已订阅该信息的所有自定义组件。那么我们会有一个问题。就算知道了对象的变化,我们又怎么促使 React Compoents 更新呢? 接下来,让我们看一看神奇的 Connect 方法。

import React from 'react';

export default function Connect (props, ChildComponents) {
  return function (ChildComponents) {
    console.log(props, ChildComponents);
    return class extends React.Component {
      render() {
          return (
            // that renders your component
            <ChildComponents />
          )
        }
    }
  }
}

  我写了一个简单的 DEMO 来阐述我的观点,其实,Connect 就是一个高阶组件( HOC )。它接收到了之后,进行了一次浅对比,利用了一个 this.forceUpdate(来强制被传组件重新 Render 。

 

  

  

  

posted @ 2020-05-09 17:35  JockerM  阅读(223)  评论(0)    收藏  举报