javascript - 异步/等待同步函数改变反应状态
问题描述
我在 React 中遇到了async
/await
函数和更改状态的问题。这是我的异步功能,通过单击按钮触发:
async startNewEntry() {
this.addIssue();
let issue_id;
console.log(this.state.timeEntry, "started_timeEntry")
if (this.state.timeEntry?.issue?.id) {
issue_id = this.state.timeEntry?.issue?.id;
} else {
issue_id = (await this.issueService.list()).data[0]?.id;
}
const { data } = await this.timeEntryService.create({
comments: this.state.timeEntry.comments,
issue_id,
spent_on: moment(new Date()).format("YYYY-MM-DD"),
hours: 0.01,
activity_id: this.localStorageService.get("defaultActivityId")
});
在这个函数中,我使用this.addIssue
了,它使用this.createIssue
了,它改变了我的类组件状态:
addIssue() {
this.projectService.list([]).then(response => {
response.data = response.data.filter((x: any) => x.status === 1);
this.setState(
{
activeProjects: response.data
},
() => {
this.createIssue();
}
);
});
}
createIssue() {
this.issueAddService
.create({
project_id: this.state.activeProjects[0].id,
tracker_id: trakerId,
priority_id: priorityId,
subject: this.state.timeEntry.comments,
description: this.state.timeEntry.comments
})
.then(response => {
let timeEntry = this.state.timeEntry;
timeEntry.issue = response.data;
this.setState({
timeEntry
});
})
.catch(error => {
console.log("error", error);
});
}
如您所见,在我的异步函数中,我有了新的状态,但实际上异步函数在我的this.addIssue
函数之前工作。我知道这个问题可能有点怪异,但谢谢转发!
解决方案
如果您想startNewEntry
等到完成其工作后再addIssue
做它的工作,您需要:
- 在完成
addIssue
工作时返回一个它履行的承诺,并且 await
调用时使用:await this.addIssue();
如果您需要startNewEntry
查看更新后的状态,addIssue
则需要从状态完成处理程序回调中实现 的承诺,如下所示:
addIssue() {
// *** Return the promise chain to the caller
return this.projectService.list([]).then(response => {
response.data = response.data.filter((x: any) => x.status === 1);
// *** Create a new promise
return new Promise(resolve => {
this.setState(
{
activeProjects: response.data
},
() => {
this.createIssue();
resolve(); // *** Fulfill the promise
}
);
});
});
}
通常,new Promise
这是一种反模式,尤其是当您有另一个可以链接的承诺时。但是在这种情况下,由于您需要等待来自setState
(未启用承诺)的回调,因此它是合适的。(
请注意我对这个问题的评论。我认为你正在设置一个无限循环......
推荐阅读
- flutter - 如何在 Flutter Create 中指定本地语言?
- c - 在 C 中运行 Ruby
- python - 训练后如何使用带有 keras 的 VGG16 预测图像(外部数据集)?
- javascript - 如何将 setTimeout 添加到随机 MP3 列表
- python - 编写一个函数以使用正则表达式从字符串中提取整数
- python - Flask set_cookie 没有设置 cookie
- haskell - 如何生成使用 MVar 的数据类型?
- r - 如何在具有特定点大小的图形上制作不同的字体大小
- google-cloud-platform - 我们可以仅使用代码在 Google Cloud 中部署整个项目吗?
- c - 如何断开单个进程与共享内存对象的连接