我有一个带有多个减速器/状态的组合减速器。看起来如下
const reducer = combineReducers({
blogs: blogReducer,
notification: notificationReducer,
search: searchReducer,
filter: filterReducer,
users: userReducer,
loggedUser: loginReducer
});
const store = createStore(reducer, composeWithDevTools(applyMiddleware(thunk)));
在我的userReducer文件中,我想从一个函数中访问博客状态
这是为了在保存新博客帖子时更新我的用户状态。
我已经尝试过了:
import store from "../store";
const { blogs } = store.getState().blogReducer.blogs;
还有这个
const { blogs } = store.getState().blogs;
但都不起作用
最终,在发布新博客后,我将调用createBlog操作创建者和updateUser操作创建者。我的用户与我的博客模型具有一对多的关系。我认为我需要更新用户状态以包括新创建的博客,并且认为我可以只采用当前博客状态,找到用户,然后用更新后的状态替换他们的博客。
类似这样的东西,但也有部分困难。
const userReducer = (state = [], action) => {
switch (action.type) {
case "NEW_USER":
return [...state, action.data];
case "UPDATE_USER":
const { blogs } = state;
console.log("Blogs", blogs);
const username = action.data.id.username;
const userBlogs = blogs.filter(b => b.user.username === username);
const userToChange = state.find(a => a.username === username);
const changedUser = userToChange.blogs.replace(userBlogs);
return state.map(user =>
user.username !== username ? user : changedUser
);
export const updateUser = (id, blog) => {
return async (dispatch, getState) => {
const { blogs } = getState();
dispatch({
type: "UPDATE_USER",
data: {
id: id,
data: blog,
blogs
}
});
};
};
答案 0 :(得分:1)
Redux文档中有一个关于此问题的FAQ部分: https://redux.js.org/faq/reducers#how-do-i-share-state-between-two-reducers-do-i-have-to-use-combinereducers
您可以使用reduce-reducers例如
/* Below isn't correct web.xml syntax and will not work but is a sketch of what I am looking for. */
<error-page>
<exception-type>*</exception-type>
<location>/MyServlet?exctype=$exception-type$</location>
</error-page>
<error-page>
<error-code>*</error-code>
<location>/MyOtherServlet?errcode=$error-code$</location>
</error-page>
答案 1 :(得分:1)
所以,正如我怀疑的那样,我使事情变得过于复杂。感谢这里的来回,我意识到我可以从另一个reducer调用另一个监听器。因此,这就是我解决问题的方式。
在我的用户简化器中,我添加了一个案例“ USER_POSTED_BLOG”
case "USER_POSTED_BLOG":
return [...action.data];
然后在我的Blog Reducer中,我向该新创建的案例添加了一个额外的调度,它将捕获所有用户并在创建新博客后更新状态
export const createBlog = content => {
return async dispatch => {
const newBlog = await blogService.create(content);
dispatch({
type: "NEW_BLOG",
data: newBlog
});
const updatedUsers = await userService.getAll();
dispatch({
type: "USER_POSTED_BLOG",
data: updatedUsers
});
};
};
答案 2 :(得分:0)
如果要在化简器中获取状态值,则不需要getState()。状态值是化简器中的第一个参数。因此,您只需要在化简器中调用状态即可。如果要在操作中获取状态值,则可以使用getState。另外,如果您想从状态对象中提取博客对象,那也就太过分了。
您正在这样做:
const { blogs } = store.getState().blogs;
应该是这样:
const { blogs } = store.getState();
这里是一个例子。
减速器:
const initialState = {
//your initial state
}
export default (state = initialState, action) => {
switch(action.type){
case "UPDATE_USER":
// just use the state object
const { blogs } = state;
const username = action.data.id.username;
const userToChange = blogs.find(a => a.username === username);
const blogsNeedToChange = userToChange.blogs
const changedUserBlogs = ?????????????
return state.map(user =>
user.username !== username ? user : changedUserBlogs
);
}
}
操作:
export const updateUser = (id, blog) => {
return async (dispatch, getState) => {
const { blogs } = getState();
dispatch({
type: "UPDATE_USER",
data: {
id: id,
data: blog,
}
});
};
};