我有一个主减速器(byVideoIds),它根据action.videoId生成一个动态键名。该对象将联系评论列表。我已经标准化了子归约器,用于评论byIds(按评论ID逐个对象),allIds(与视频相关联的评论ID的数组),以及显示分页内容和isFetching。
我面临且无法追踪的问题是评论删除操作DELETE_COMMENT_SUCCESS,我的状态树未更新,并且allIds的数组不变。因此,我的UI不会重新呈现更改。
我在这里通过调用byVideos reducer内的CombineReducersComments正确地使用了CombinedReducers。我不知道状态和动作是否也需要在同一行上传递。
使用我的状态树下面的代码可以正确加载并显示每个视频的评论数据,但是在执行删除操作时,不会更新用户界面。
如果不能以这种方式使用combinedReducers。我可以为[videoId]设置初始状态的哪些选项?
const byVideoIds = (state = {}, action) => {
const { videoId } = action;
switch (action.type) {
case GET_COMMENTS_REQUEST:
return {
...state,
[videoId]: combineReducersComments(state[videoId], action)
};
case GET_COMMENTS_SUCCESS:
return {
...state,
[videoId]: combineReducersComments(state[videoId], action)
};
default:
return state;
}
};
//--------------------------------------------------------
const byIds = (state = {}, action) => {
const { comments } = action;
switch (action.type) {
case GET_COMMENTS_SUCCESS:
return {
...state,
...comments.reduce((obj, comment) => {
obj[comment.id] = comment;
return obj;
}, {})
};
default:
return state;
}
};
const allIds = (state = [], action) => {
switch (action.type) {
case GET_COMMENTS_SUCCESS:
return action.comments.map(comment => comment.id);
case DELETE_COMMENT_SUCCESS:
return state.filter(id => id !== action.commentId);
default:
return state;
}
};
const page = (state = 1, action) => {
switch (action.type) {
case GET_COMMENTS_SUCCESS:
return state + 1;
default:
return state;
}
};
const totalPages = (state = null, action) => {
switch (action.type) {
case GET_COMMENTS_SUCCESS:
return action.totalPages;
default:
return state;
}
};
const isFetching = (state = false, action) => {
switch (action.type) {
case GET_COMMENTS_REQUEST:
return true;
case GET_COMMENTS_SUCCESS:
case GET_COMMENTS_FAILURE:
return false;
default:
return state;
}
};
const combineReducersComments = combineReducers({
byIds,
allIds,
page,
totalPages,
isFetching
});