Javascript React-Axios/Fetch/Ajax在新道具传递给子组件后请求
我有两个组件,App和Child。我的目标是,应用程序将id传递给Child,当Child作为道具接收到id时,我希望Child执行Axios/Fetch请求,然后用结果数据更新自己。我将接受任何为我提供示例应用程序/子源代码的答案,这些示例应用程序/子源代码将完成我的示例,或者提供我的见解,如果这确实可能是我试图实现的 我是一个新的反应 //App.jsJavascript React-Axios/Fetch/Ajax在新道具传递给子组件后请求,javascript,reactjs,components,Javascript,Reactjs,Components,我有两个组件,App和Child。我的目标是,应用程序将id传递给Child,当Child作为道具接收到id时,我希望Child执行Axios/Fetch请求,然后用结果数据更新自己。我将接受任何为我提供示例应用程序/子源代码的答案,这些示例应用程序/子源代码将完成我的示例,或者提供我的见解,如果这确实可能是我试图实现的 我是一个新的反应 //App.js import React, { Component } from 'react'; import Child from './Child.j
import React, { Component } from 'react';
import Child from './Child.js';
import './App.css';
class App extends Component {
state = {
id: 0
};
handleClick() {
this.setState({
id: this.state.id + 1
});
}
render() {
return (
<div>
<Child id={this.state.id} />
<div>
<button onClick={this.handleClick.bind(this)}>Pass new id down to Child component</button>
</div>
</div>
);
}
}
export default App;
import React,{Component}来自'React';
从“/Child.js”导入子项;
导入“/App.css”;
类应用程序扩展组件{
状态={
身份证号码:0
};
handleClick(){
这是我的国家({
id:this.state.id+1
});
}
render(){
返回(
将新id向下传递给子组件
);
}
}
导出默认应用程序;
//Child.js
import React, { Component } from 'react';
import axios from 'axios';
class Child extends Component {
state = {
data: null,
id: 0
};
loadData(q, cb) {
axios.get('http://localhost:3000/foo?q='+this.state.id)
.then(result => {
// ?
// this.setState would retrigger update and create an infinite updating loop
})
.catch(error => {
console.log('error: ' + error);
});
}
shouldComponentUpdate(nextProps, prevState) {
console.log('shouldComponentUpdate: nextProps = ' + JSON.stringify(nextProps) + ', prevState = ' + JSON.stringify(prevState));
// ??
}
getSnapshotBeforeUpdate(nextProps, prevState) {
console.log('getSnapshotBeforeUpdate: nextProps = ' + JSON.stringify(nextProps) + ', prevState = ' + JSON.stringify(prevState));
// ??
}
static getDerivedStateFromProps(nextProps, prevState) {
console.log('getDerivedStateFromProps: nextProps = ' + JSON.stringify(nextProps) + ', prevState = ' + JSON.stringify(prevState));
return {
id: nextProps.id
};
// ??
}
componentDidUpdate() {
console.log('componentDidUpdate');
}
render() {
return (
<div>
<div>data = {this.state.data}</div>
</div>
);
}
}
export default Child;
import React,{Component}来自'React';
从“axios”导入axios;
类子扩展组件{
状态={
数据:空,
身份证号码:0
};
负载数据(q,cb){
axios.get()http://localhost:3000/foo?q=“+this.state.id)
。然后(结果=>{
// ?
//this.setState将重新触发更新并创建无限更新循环
})
.catch(错误=>{
console.log('错误:'+错误);
});
}
shouldComponentUpdate(下一步,上一步状态){
log('shouldComponentUpdate:nextProps='+JSON.stringify(nextProps)+',prevState='+JSON.stringify(prevState));
// ??
}
更新前获取快照(下一步,前一步){
log('getSnapshotBeforeUpdate:nextProps='+JSON.stringify(nextProps)+',prevState='+JSON.stringify(prevState));
// ??
}
静态getDerivedStateFromProps(下一步,上一步){
log('getDerivedStateFromProps:nextProps='+JSON.stringify(nextProps)+',prevState='+JSON.stringify(prevState));
返回{
id:nextrops.id
};
// ??
}
componentDidUpdate(){
log('componentdiddupdate');
}
render(){
返回(
data={this.state.data}
);
}
}
导出默认子对象;
您应该使用当前Id调用check prev Id以避免递归更新。你只需要确保只有当你的道具发生变化时,你才能从道具中获得状态
static getDerivedStateFromProps(nextProps, prevState) {
if (nextProps.id !== prevState.id) {
return {
id: nextProps.id
};
}
return null;
}
如果您的问题仍然存在,请告诉我这可能是解决您问题的一种方法,
首先,您必须更新getDerivedStateFromProps中的所有状态数据
对于loadData
方法中的api调用,您可以使用aync/await从api调用返回数据
注:
- 这不是完整的解决方案,因为在
中的api调用捕获任何错误时,您可能不想更新状态loadData
- 此外,由于您使用的是api调用,您可能希望限制向子级传递道具的时间,因为它们都会触发不同的api调用,并且您将进入不可预测的状态。试试去抖
在
componentdiddupdate()
中,比较prevProps.id
和this.state.id
。如果它们不同,请调用loadData()
。(我也不知道你的电流怎么会产生无限循环?)。为了使其成为循环,componentdiddupdate()
必须始终调用loadData()
。但是,只有当id
发生更改时,才会发生这种情况。这已经有7周了,你还在坚持这一点,甚至没有尝试我的建议吗?如果道具改变,状态得到更新,你会在ComponentDidUpdate中调用loadData为什么?它将调用setState,它将一次又一次地更新componentDidUpdate。不,您可以在componentDidUpdate中进行检查,以避免不必要的setState调用
static getDerivedStateFromProps(nextProps, prevState) {
if (nextProps.id !== prevState.id) {
// Returning this object is equivalent to setting state using this.setState
return {
id: nextProps.id
data: loadData(nextProps.id) // Something like this
};
}
return null; // Indicates no state change
}
async loadData(id) {
try {
// Make your api call here
let response = await axios.get('http://localhost:3000/foo?q='+id);
return await response.json();
} catch(err) {
// catches errors both in axios.get and response.json
// Make sure to not update state in case of any error
alert(err);
return null;
}
}