我是新来的人,面对问题。我使用Axios从API提取数据,然后必须将该数据设置为状态,并将该值作为道具传递给另一个组件。
我的问题是,在获取API后,我正在使用this.setState
更改状态,但是状态没有更改。所以我在下面分享我的代码。
constructor(props){
super(props);
this.state={
employeeData:[] // setting empty value
}
}
ComponentDidMount(){
console.log("Current State"+JSON.stringify(this.state)) ///output = []
axios.get("http://localhost:8080/hris/api/employee/get/all")
/// getting values , can see them in network
.then(response => response.data)
.then((data) => {
this.setState({ employeeData: data }) ///setting new value
console.log(this.state.employeeData) /// can see fetched data
})
.catch(err=> console.log(err))
console.log("2Nd STATE "+this.state) /// again empty state, there is no fetched data
}
然后我必须在另一个组件中传递该状态。
render(){
return(
<div className=" col-md-12" style={viewData}>
<div >
<p><b>All Employee Details</b></p>
</div>
<Table data={this.state.employeeData}/>
</div>
)
}
答案 0 :(得分:2)
setState
是一种异步功能,需要一些时间来设置新的状态值。因此,在此行之后打印新状态将只为您提供以前的状态,而不是新的状态。
您需要callback来检查更改后的状态,
this.setState({ employeeData: data }, () => console.log("2Nd STATE "+this.state))
另一件事是,axios旨在减少.then()
的数量。使用axios,您将获得直接的JSON
值。您可以删除1个.then()
。
axios.get("http://localhost:8080/hris/api/employee/get/all") /// getting values , can see them in network
.then(response => {
this.setState({ employeeData: response.data }, () => console.log("2Nd STATE "+this.state)) // This will give you new state value. Also make sure your data is in `response.data` it might be just `response`.
console.log(this.state.employeeData) // This will give you previous state only
})
.catch(err=> console.log(err))
答案 1 :(得分:1)
您的render() {
return (!this.state.employeeData.length) ?
(<div>Loading..</div>) :
(
<div className=" col-md-12" style={viewData}>
<div >
<p><b>All Employee Details</b></p>
</div>
<Table data={this.state.employeeData} />
</div>
)
}
返回的是空值,因为它可能在axios请求完成之前运行。
最初,您的render方法以空状态调用,这可能会引发错误。您需要处理处于加载状态的渲染,直到请求完成为止。
例如,您的渲染可能看起来像这样
$foo = array('a','b','c');
print_r(json_encode($foo));
unset($foo[0]);
echo "\n";
print_r(json_encode($foo));
$foo = array_values($foo);
echo "\n";
print_r(json_encode($foo));
/** Output
["a","b","c"]
{"1":"b","2":"c"}
["b","c"]
*/
答案 2 :(得分:1)
setState
是异步的,因此您无法在调用setState()
的位置立即看到更改。为了查看更改,您需要执行回调。
this.setState({ employeeData: data },()=>console.log(this.state.employeeData)) ///setting new value
将代码更改为上述格式,更改后即可看到状态更改
答案 3 :(得分:0)
我想这就是您要出问题的地方,尝试一下。它与反应无关。您使用Axios的方式是错误的。
ComponentDidMount(){
console.log("Current State" + JSON.stringify(this.state));
axios
.get("http://localhost:8080/hris/api/employee/get/all")
.then(response => {
this.setState({ employeeData: response.data });
})
.catch(err => console.log(err));
};
答案 4 :(得分:0)
好的,这两个问题都发生了,因为Axios和this.setState()是异步的。在单个StackOverflow答案中很难解释异步编程,因此我建议检查以下链接:[https://flaviocopes.com/javascript-callbacks/][1]
但是现在要使您的代码正常工作,请将其切换为此
ComponentDidMount() {
console.log(this.state); // Obviously empty state at beginning
axios.get("http://localhost:8080/hris/api/employee/get/all")
.then(res => res.data)
.then(data => {
this.setState({employeeData: data}, () => { // Notice the additional function
console.log(this.state); // You'll see your changes to state
})
})
.catch(err => console.log(err));
console.log(this.state); // This won't work because Axios is asynchronous, so the state won't change until the callback from axios is fired
}
大多数新的React开发人员不倾向于意识到的部分是this.setState()像axios是异步的,这意味着状态不会立即改变,实际执行的任务会作为后台进程传递。如果您想在状态更改后使用它,则this.setState()函数提供了用于执行此操作的第二个参数
setState(stateChange[, callback])
取自react文档。这里的第二个参数是您可以传递的回调(也称为函数),只有在状态更改发生后才会被触发
// Assuming state = {name: "nothing"}
this.setState({name: "something"}, () => {
console.log(this.state.name); // logs "something"
});
console.log(this.state.name); //logs "nothing"
希望这会有所帮助!!