【问题标题】:Action called in componentWillReceiveProps goes in an infinite loop.在 componentWillReceiveProps 中调用的动作进入无限循环。
【发布时间】:2017-07-11 11:44:54
【问题描述】:

在我的应用程序中,有阶段和游戏对应一个阶段。我在componentDidMount中获取阶段,然后在componentWillReceiveProps中检查reducer中是否有stageId,然后为阶段获取游戏。用于获取游戏的动作舞台被无限次触发。有人可以解释为什么吗?

componentDidMount() {
  this.props.fetchCurrentStage();
}

componentWillReceiveProps(nextState) {
  if (nextState.stageReducer && nextState.stageReducer.stageId) {
    this.props.fetchGamesForStage(nextState.stageReducer.stageId);// Corresponding action is triggered infinite times.Why?
  }
}

【问题讨论】:

  • 您是否尝试过console.log nextStage.stageReducernextState.stageReducer.stageId 的值?如果在无限循环中调用该操作,则每次更新状态并触发重新渲染时,该条件都必须为真。
  • 现在,我不知道你的整个应用逻辑。但是当孩子被挂载时,您正在从父 fetchCurrentStage() 调用一个函数。直接从父级获取它并将结果作为道具传递下来不是更好吗?这不会解决您的问题 - 只是我的观察。
  • 另外,nextState 应该叫nextProps?
  • 你能分享你的mapStateToProps函数吗?
  • 不要在 componentWillReceiveProps 中触发动作。这是不正确的。触发动作时更新道具。我确定该操作需要在其他地方调用。该操作将依次更新存储,并且此事件将再次触发,从而导致无限循环。

标签: reactjs redux react-redux redux-saga


【解决方案1】:

正如你所提到的,I check if there is stageId in reducer,我假设你已经编写了类似这样的 mapStateToProps 函数:

const mapStateToProps = (state) => {
  return {
    stageReducer: state.stageReducer,
  }
}

如果你写mapStateToProps这样的东西会很棒:

const mapStateToProps = (state) => {
  return {
    stageId: state.stageReducer ? state.stageReducer.stateId : undefined,
  }
}

只需从stateReducer 传递stageId 而不是整个stateReducer,您可以将旧的stateIdcomponentWillReceiveProps 中的新stageId 进行比较,如下所示:

componentWillReceiveProps(nextProps) {
    if (nextProps.stageId && this.props.stageId !== nextProps.stageId) {
      this.props.fetchGamesForStage(nextState.stageId);// Corresponding action is triggered infinite times.Why?
    }
}

当第一次调用componentWillreceiveProps 时,this.props.stageId !== nextProps.stageId 将被评估为真。所以会触发相应的动作。

一个疑问:我认为当从服务器获取fetchGamesForStage 的结果时,您正在更改stageReducer 的引用。这就是再次调用componentWillReceiveProps 的原因。

如果正确,则从stageReducermapStateToProps 发送选定的项目

 const mapStateToProps = (state) => {
      return {
       // other things from stageReducer

        stageId: state.stageReducer ? state.stageReducer.stateId : undefined,
      }
    }

或者如果你不想改变你的结构,那么这也可能会有所帮助:

componentWillReceiveProps(newProps) {
  const oldStageId = this.props.stageReducer ? this.props.stageReducer.stageId : undefined
  const newStageId = newProps.stageReducer ? newProps.stageReducer.stageId : undefined
  if (newStageId && oldStageId !== newStageId) {
    this.props.fetchGamesForStage(newStageId);// Corresponding action is triggered infinite times.Why?
  }
}

希望,它会有所帮助。

【讨论】:

    猜你喜欢
    • 2016-07-11
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-04-15
    • 1970-01-01
    • 1970-01-01
    • 2017-01-01
    相关资源
    最近更新 更多