注入用于按需组件的减速器,该组件最初不在商店或组合减速器中

时间:2017-05-13 16:12:08

标签: javascript reactjs redux redux-saga

我正在尝试构建一些模块化SAP,因此很多团队可以单独工作。

基本上,我希望我的容器在容器,商店,减速器,传奇方面是独立的。

实际问题是(示例代码):

  1. 我渲染一个基本模板:
  2. <div> <a onClick={emitLoadUserListAction}>Load user list</a> <UserList/> </div>

    此时,我为UserList使用了1个reducer来保留用户数组(开头为空)。

    让我们假设我有一个传奇,等待这些数据作为json中的用户列表。

    商店: { UserList: [] }

    1. 一旦saga获取数据,就会发布修改当前商店的操作:
    2. 商店: { UserList: [{name:"john",counter:0},{name:"pepe",counter:0}] }

      1. 现在我的UserList组件可以列出这个,因为我们有mapStateToProps指向商店的这一部分。
      2. this.props.userList.map ( (userData,i) => { return <User data={userData}> } ))

        所以现在如果User组件只是一个普通的组件,一切都像魅力一样。

        但是,如果User实际上是一个容器,它希望能够独立工作,并且有自己的状态,我还没有通过它自己的reducer连接。我不希望他的父母管理它。我希望用户是独立的,因为我可以使用重新选择器或类似物传递它在商店中的位置,或者我可以将数组中的索引作为prop传递,因此我可以成为选择器。这样我会把商店注入道具,但我不会有减速器。

        我很确定你们中的许多人已经通过了这个但我找不到合适的答案。

        正如你所看到的那样,想法是有一个按需加载的组件,而不是在初始的combineReducers中,不是由其父级处理的,只是渲染,并且注入的reducer是独立工作的。

        如果我只能按需加载其reducer,那么我不会将数据存储在UserList中,但它将是reducers的组合。

        提前多多感谢。

2 个答案:

答案 0 :(得分:1)

我继续my commentquestion that followed,因此我可以在不受评论部分限制的情况下进行扩展。

是的,我的库在商店上调用replaceReducer,以便用新的包含替换reducer。为此,我提供了一个Higher-Order Component (HOC),它将组件与其关联的减速器捆绑在一起,并在安装时执行替换。

界面如下所示:

export const MyBundledComponent = bundle(MyComponent, myReducer)

该工作的唯一要求是该组件安装在Provider react-redux内。这使得HOC在React's context上以connect HOC的方式访问商店。但这并不是一个非常严格的限制,因为大多数redux应用程序已经在树的顶部有Provider

希望这有帮助。

答案 1 :(得分:0)

到目前为止,我找到了这样的资源:

https://medium.com/@jimmy_shen/inject-reducer-arbitrarily-rather-than-top-level-for-redux-store-to-replace-reducer-fdc1060a6a7

允许您通过使用Redux商店API store.replaceReducer(nextReducer)

替换主reducer来按需注入Reducer

此解决方案的问题是需要从应该封装的子组件访问主存储对象。

目前工作不理想的解决方案是我发现带有“多个组件减速器”的封装组件意味着减速器假设在同一个父组件下可能有多个组件,每个组件具有不同的ID。 / p>

因此,每个操作都应该检查有效负载ID,以便从商店对象中获取状态。

这意味着层次结构会发生微小的变化,因为组件不是孩子而是兄弟。

按照前面的示例,假设我们列出了用户列表的浅版本,然后在您点击任何用户后显示更多数据:

`
Store:  {
   UserList: [], // basic info, id plus minimal data
   users: {} --> userReducer // listing each user by key
}
`

这样,用户组件只会暴露multiUserReducer而不是逻辑。

这显然意味着即使您从未加载任何用户组件,也会提前加载reducer。