getState 函数在 action creator 中的调用总是 returns 空数组
getState function call in action creator always returns empty array
正在从组件“UserHeader”的多个实例中对操作创建者“fetchUser”进行多次调用。每次调用都应该向商店添加一个用户。在动作创建器“fetchUser”中,一个 console.log 语句用于显示使用“getState”函数添加的用户列表。第一次调用会将用户列表显示为空,但后续调用应该显示一些用户。我不知道为什么“getState”函数总是 returns 一个空数组。请帮忙解决这个问题。代码托管在 codesandbox
动作创作者
export const fetchUser = id => async (dispatch, getState) => {
console.log(getState()); // Always empty array
const response = await jsonPlaceholder.get(`/users/${id}`); // call to external API using Axios
dispatch({ type: 'FETCH_USER', payload: response.data });
};
减速器
export default (state = [], action) => {
switch (action.type) {
case 'FETCH_USER':
return [...state, action.payload];
default:
return state;
}
};
UserHeader
import React from 'react';
import { connect } from 'react-redux';
import { fetchUser } from '../actions';
class UserHeader extends React.Component {
componentDidMount() {
this.props.fetchUser(this.props.userId); // call to action creator
}
render() {
const user = this.props.users.find(user => user.id === this.props.userId);
if (!user) {
return null;
}
return <div className="header">{user.name}</div>;
}
}
const mapStateToProps = state => {
return { users: state.users };
};
export default connect( mapStateToProps, { fetchUser } )(UserHeader);
index.js
import React from 'react';
import ReactDOM from 'react-dom';
import { Provider } from 'react-redux';
import { createStore, applyMiddleware } from 'redux';
import thunk from 'redux-thunk';
import App from './components/App';
import reducers from './reducers';
const store = createStore(reducers, applyMiddleware(thunk));
ReactDOM.render(
<Provider store={store}>
<App />
</Provider>,
document.querySelector('#root')
);
Link to image that shows zero Users
您 运行 在 forEach
中创建了一个 API 请求..迭代不会等到上一次迭代完成,这就是您的商店尚未更新的原因。
如果你愿意安慰:
export const fetchUser = (id) => async (dispatch, getState) => {
console.log("before:", getState());
const response = await jsonPlaceholder.get(`/users/${id}`);
dispatch({ type: "FETCH_USER", payload: response.data });
console.log("after:", getState());
};
你会看到:
before: (->users don't contain values)
before: (->users don't contain values)
...
after: (->users contain values)
after: (users contain values
..
所以,基本上你需要在每次迭代后等待。
这是我使用 this article 实现的(我也使用 map
和 filter
func 而不是 lodash func ,但这由您决定):
async function asyncForEach(array, callback) {
for (let index = 0; index < array.length; index++) {
await callback(array[index], index, array);
}
}
export const fetchPostsAndUsers = () => async (dispatch, getState) => {
await dispatch(fetchPosts());
const postsUsersIds = getState().posts.map((ele) => ele.userId);
const uniqueVal = postsUsersIds.filter(
(t, i) => postsUsersIds.indexOf(t) === i
);
asyncForEach(uniqueVal, async (val) => {
await dispatch(fetchUser(val));
});
};
现在 fetchUser
func 中的值已更新,您也可以在 sandbox
中看到代码
正在从组件“UserHeader”的多个实例中对操作创建者“fetchUser”进行多次调用。每次调用都应该向商店添加一个用户。在动作创建器“fetchUser”中,一个 console.log 语句用于显示使用“getState”函数添加的用户列表。第一次调用会将用户列表显示为空,但后续调用应该显示一些用户。我不知道为什么“getState”函数总是 returns 一个空数组。请帮忙解决这个问题。代码托管在 codesandbox
动作创作者
export const fetchUser = id => async (dispatch, getState) => {
console.log(getState()); // Always empty array
const response = await jsonPlaceholder.get(`/users/${id}`); // call to external API using Axios
dispatch({ type: 'FETCH_USER', payload: response.data });
};
减速器
export default (state = [], action) => {
switch (action.type) {
case 'FETCH_USER':
return [...state, action.payload];
default:
return state;
}
};
UserHeader
import React from 'react';
import { connect } from 'react-redux';
import { fetchUser } from '../actions';
class UserHeader extends React.Component {
componentDidMount() {
this.props.fetchUser(this.props.userId); // call to action creator
}
render() {
const user = this.props.users.find(user => user.id === this.props.userId);
if (!user) {
return null;
}
return <div className="header">{user.name}</div>;
}
}
const mapStateToProps = state => {
return { users: state.users };
};
export default connect( mapStateToProps, { fetchUser } )(UserHeader);
index.js
import React from 'react';
import ReactDOM from 'react-dom';
import { Provider } from 'react-redux';
import { createStore, applyMiddleware } from 'redux';
import thunk from 'redux-thunk';
import App from './components/App';
import reducers from './reducers';
const store = createStore(reducers, applyMiddleware(thunk));
ReactDOM.render(
<Provider store={store}>
<App />
</Provider>,
document.querySelector('#root')
);
Link to image that shows zero Users
您 运行 在 forEach
中创建了一个 API 请求..迭代不会等到上一次迭代完成,这就是您的商店尚未更新的原因。
如果你愿意安慰:
export const fetchUser = (id) => async (dispatch, getState) => {
console.log("before:", getState());
const response = await jsonPlaceholder.get(`/users/${id}`);
dispatch({ type: "FETCH_USER", payload: response.data });
console.log("after:", getState());
};
你会看到:
before: (->users don't contain values)
before: (->users don't contain values)
...
after: (->users contain values)
after: (users contain values
..
所以,基本上你需要在每次迭代后等待。
这是我使用 this article 实现的(我也使用 map
和 filter
func 而不是 lodash func ,但这由您决定):
async function asyncForEach(array, callback) {
for (let index = 0; index < array.length; index++) {
await callback(array[index], index, array);
}
}
export const fetchPostsAndUsers = () => async (dispatch, getState) => {
await dispatch(fetchPosts());
const postsUsersIds = getState().posts.map((ele) => ele.userId);
const uniqueVal = postsUsersIds.filter(
(t, i) => postsUsersIds.indexOf(t) === i
);
asyncForEach(uniqueVal, async (val) => {
await dispatch(fetchUser(val));
});
};
现在 fetchUser
func 中的值已更新,您也可以在 sandbox