在 redux 中使用 immutablejs(toJS 和 fromJS)的正确方法

IT技术 javascript reactjs redux immutable.js
2021-05-04 22:36:42

我想知道这是否是immutable.js与 redux 和reselect(也redux-saga一起使用的正确方法具体来说,我想知道如何使用它们toJS()以及从fromJS()哪里使用它们。我的想法是:

  1. toJS()在向传奇发送数据时使用
  2. 不在 fromJS()reducer 中使用,因为我认为它是通过我fromJS()用于 initialState的事实来完成的还是我错了?
  3. toJS()在选择器中使用reselect所以我可以在react组件中使用 js 数据。

例子:

1)在我的react组件中,我这样做:

// mapDispatchToProps
   function mapDispatchToProps(dispatch) {
      return {
         loginRequest: values => dispatch(loginRequest(values)),
      };
   }

// Sending values.toJS() to my redux-saga. 
   submit = values => {
      this.props.loginRequest(values.toJS());
   };

2)在我做的reducer中(应该fromJS()在这里使用还是不使用?根据redux docs你应该):

const { fromJS } = require('immutable');
const state = fromJS({
  pages: {
    usersPage: {
      loading: false,
      isFetched: false,
      list: [],
    }
  }
});
function reducer(state, action) {
  switch(action.type) {
    case 'USERS_LOADED':
      return state
        .setIn(['usersPage', 'list'], action.payload) // fromJS() here or not?
        .setIn(['usersPage', 'isFetched'], true)
        .setIn(['usersPage', 'loading'], false)
        ;
    default:
      return state;
  }
}
export default reducer;

3)在我的选择器中,我toJS()再次执行:

const selectUser = state => state.get('user', initialState);
const makeSelectList= () =>
   createSelector(selectUser, userState => userState.getIn(['usersPage', 
'list']).toJS());

// Which I then use in my react component:
const mapStateToProps = createStructuredSelector({
   list: makeSelectList(),
});

所以基本上我想知道这是否是 js 和不可变之间的正确转换流程。或者可以以某种方式进行优化(更少的转换步骤)?也许以上是一种非最佳的逻辑方式?

最好的祝福

1个回答
  1. saga——作为 redux 中间件——可以直接处理 Immutable 类型,不需要在toJS这里使用昂贵的调用

  2. 任何你转换点(例如setsetInupdate等)的纯JS非简单类型为不可变的终极版状态树,使用fromJS,以确保完全不可改变的类型制作整个状态树上不变

  3. 恕我直言,选择器(例如reselect)——通过在初始检索后提供记忆——可以是利用昂贵toJS调用的最理想的地方,如你的例子#3。我想这真的取决于人们有多不喜欢在他们的“容器/智能”组件中使用不可变的检索方法,和/或创建一大堆选择器来从 redux 状态树中检索简单的 JS 类型在任何地方使用不可变

对我来说,问题是在哪里实际使用fromJS调用,例如动作创建者,在“容器/智能”组件调度中,或者在减速器中,例如在减速器中react-boilerplate使用fromJS调用。