在我的情况下如何解决' Maximum update depth exceeded'?



我正在使用React在Ionic中开发一个应用程序,我遇到了这个错误:

Maximum update depth exceeded. This can happen when a component repeatedly calls setState inside componentWillUpdate or componentDidUpdate. React limits the number of nested updates to prevent infinite loops.

我创建了一个表单来更新一些在后台调用api请求的数据。

Request: put /xx/xx/update
Body Request: 
{
"titleId": "1",
"firstName": "Ani",  
}
Response:
{
"title": {
"1": "Dr"
},
"firstName": "Ani",
}

在功能组件MyData.tsx:内部

const MyData: React.FC = () => {
//title and firstName come from React Context, I'm using them in the whole app
const {
firstName,
setFirstName,
title,
setTitle,
iserror,
setIserror,
} = React.useContext(AuthContext);
const history = useHistory();
const authHeader = AuthHeader.getAuthHeader();
const updateData = () => {
const data = {
titleId: title,
firstName: firstName,
};
axios
.put("/xx/xx/update", data, { headers: authHeader })
.then((response) => {
setTitle(response.data.title);
setFirstName(response.data.firstName);

return response.data;
})
.catch((error) => {
setMessage(
"Please check your data and try again"
);
setIserror(true);
});
};
return (
<React.Fragment>
<IonPage className="ion-page" id="main-content">

<IonContent className="ion-padding">
<h1>Change your data</h1>
<form className="ion-padding">
<IonItem>
<IonLabel position="floating">Title</IonLabel>
<IonSelect
value={Object.keys(title)} // this row causes the problem
onIonChange={(e) => setTitle(e.detail.value!)}
>
<IonSelectOption value="0"></IonSelectOption>
<IonSelectOption value="1">Dr</IonSelectOption>
<IonSelectOption value="2">Dr.-Ing</IonSelectOption>
<IonSelectOption value="3">Professor</IonSelectOption>
<IonSelectOption value="4">Prof.-Dr</IonSelectOption>
</IonSelect>
</IonItem>

<IonItem>
<IonLabel position="floating">Name*</IonLabel>
<IonInput
required
value={firstName}
onIonChange={(e) => setFirstName(e.detail.value!)}
></IonInput>
</IonItem>

<IonButton
className="ion-margin-top"
expand="block"
onClick={(e) => {
e.preventDefault();
updateData();
history.goBack();
}}
>
Save changes
</IonButton>
</form>
</IonContent>
</IonPage>
</React.Fragment>
);
};
export default MyData;

value={Object.keys(title(}=>当我打开表单时,我需要显示所选字段"Title"的实际值,这就是为什么我需要"value"属性,但这会导致错误。如果我删除这行代码,我可以成功更新标题和名称。当我再次打开表单时,不会显示title的实际值,只显示"name"。

我真的是React/Ionial/Typescript的新手,如果有任何帮助,我将不胜感激。

谢谢!Ani

您需要将请求axios移动到useEffect react hook:中

React.useEffect(() => {
axios
.put("/xx/xx/update", data, { headers: authHeader })
.then((response) => {
setTitle(response.data.title);
setFirstName(response.data.firstName);

return response.data;
})
.catch((error) => {
setMessage(
"Please check your data and try again"
);
setIserror(true);
});
};
}, [])

问题是你的axios请求会导致重新提交,重新提交会导致axios请求,而axios请求则会导致重新发布。。。

因此,如果你将axios请求封装在useEffect中,你的请求将只发出一次。

解决方案是:Object.values(title(返回数组。使用以下技巧将Object.values(title)转换为字符串:

value={"" + Object.values(title)}

离子选择项目:

<IonItem>
<IonLabel position="floating">Title</IonLabel>
<IonSelect
value={"" + Object.values(title)}
{...register("title")}
>
<IonSelectOption value="0"></IonSelectOption>
<IonSelectOption value="1">Dr</IonSelectOption>
<IonSelectOption value="2">Ing</IonSelectOption>
<IonSelectOption value="3">Prof</IonSelectOption>
<IonSelectOption value="4">Prof.Dr</IonSelectOption>
</IonSelect>
</IonItem>
<IonItem>

Ps。我正在使用React Hook Form

相关内容

最新更新