reactjs - 更新嵌套对象时 Redux 不重新渲染

标签 reactjs redux

此题请引用以下函数:

const mapStateToProps = (state) => {
  return {
    currentPlaylist: state.currentPlaylist,
    currentSong: state.currentSong,
    localPlaylists: state.playlistsBySource['local'],
    videoSize: state.videoSize,
  };
}

这是容器的 mapStateToProps 函数。我希望在每次更新 state.playlistsBySource['local'] 时重新呈现连接到此容器的组件。但是,即使 state.playlistsBySource['local'] 更新了,它也没有呈现,所以我将代码更改为以下内容:

const mapStateToProps = (state) => {
  return {
    currentPlaylist: state.currentPlaylist,
    currentSong: state.currentSong,
    playlists: state.playlistsBySource,
    videoSize: state.videoSize,
  };
}

然后每次更新 state.playlistsBySource['local'] 时连接的组件都会正确更新。但这是一种浪费,因为连接的组件不需要整个 playlists

为什么会发生这种情况,解决它的正确方法是什么?

更新

我这样连接组件:

export default connect(
  mapStateToProps,
  mapDispatchToProps
)(DumbComponent);

state.playlistsBySource['local'] 在全局存储中更新时,不会调用 DumbComponent 的渲染方法。

更新 2:Reducer 似乎是不可变的。我是不是漏掉了什么?

case CONSTANTS.UPDATE_LOCAL_PLAYLIST:
  var playlistUpdated = transformedPlaylist(state[action.playlist.source], action);
  return updatedPlaylists(playlistUpdated, state);

function transformedPlaylist(state=[], action) {
  var oldPlaylist = _.find(state, (pl) =>
    pl.playlistName === action.playlist.playlistName);

  switch (action.type) {
    case CONSTANTS.RECEIVE_PLAYLIST:
    case CONSTANTS.UPDATE_LOCAL_PLAYLIST:
      return Object.assign({}, oldPlaylist, action.playlist, {
        isFetching: false,
      });
    default:
      return oldPlaylist
  }
}

function updatedPlaylists(playlistUpdated, oldPlaylists) {
  const source = playlistUpdated.source;
  const idxToUpdate = _.findIndex(oldPlaylists[source], (pl) =>
    pl.playlistName === playlistUpdated.playlistName
  );
  var playlists = Object.assign({}, oldPlaylists);
  playlists[source][idxToUpdate] = playlistUpdated;
  return playlists;
}

最佳答案

如果您可以发布您的 reducer 的相关代码,将会有所帮助。然而,绝大多数时候,你的组件没有更新的原因是你直接在你的 reducer 中改变状态,而不是一成不变地返回修改后的副本。请参阅 http://redux.js.org/docs/FAQ.html#react-not-rerendering 上的 Redux 常见问题解答。获取更多信息。

更新:

这一行看起来很可疑:playlists[source][idxToUpdate] = playlistUpdated;

请记住,如果您不可变地更新嵌套数据,则必须返回复制和更新的项目,一直到数据的顶部。

如果没有在上下文中看到您的整个状态结构和操作,很难准确判断,但我认为您很可能确实在您的嵌套字段之一中进行了直接突变。

关于reactjs - 更新嵌套对象时 Redux 不重新渲染,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36458948/

相关文章:

javascript - 在触发下一行之前,使用 axios 进行 react 等待数据获取不起作用

javascript - 如何使用 JEST 对 React App 中的功能进行单元测试

reactjs - 未捕获的 TypeError : _materialUi. Styles.ThemeManager 不是函数

reactjs - 使用 react 测试实用程序测试更改选择

reactjs - 使用 Redux 分派(dispatch)与组件无关的操作的正确方法是什么?

javascript - 使用 React Hooks useReducer,如何有效地按 ID 更新对象?

reactjs - 将 React useReducer 转换为 TypeScript

javascript - 有什么方法可以检测用户是否从本地存储中删除了任何项目

javascript - 防止将重复对象添加到状态 react redux

javascript - 为什么当我解构属性时接收 props 的组件不工作,但当我使用 props.key 时它工作?