问题描述
我有一个 this
,它一个接一个地执行两个查询。在 Object.create
的结果中,我想使用第二个查询的结果执行第三个查询。
如何创建一个可以在 Promise.all()
中干净使用的 Promise.all()
?
function()
我想不通的是我怎样才能听到这第三个查询的结果和
返回一个 Promise()
或错误。
Promise
.all([upsertdeviceid,createEndpoint])
.then((values) => {
const upsertdeviceidResult = values[0];
const createEndpoint = values[1];
if(upsertdeviceidResult.upsertedCount > 0){
//Perform third query here
//performThirdQuery(createEndpoint.EndpointArn);
}
return res.status(200).send({ success: true });
})
.catch((err) => {
console.log(err);
return res.status(400).send({ reason: 'unkNown' });
});
});
return res.status(200).send({ success: true });
解决方法
我有一个 Promise.all()
一个接一个执行两个查询
这不是 Promise.all
所做的。这两个操作并行运行,都在您获得 upsertDeviceId
和 createEndpoint
(这可能是您从其他地方获得的承诺)时开始,并且 Promise.all
等待它们都完成之前履行其承诺(或在拒绝承诺之前等待其中一个拒绝)。
但假设您确实想并行运行它们,您通常会返回第三个查询的结果(在前两个查询完成之前不会运行):
Promise
.all([upsertDeviceId,createEndpoint])
.then((values) => {
const upsertDeviceIdResult = values[0];
const createEndpoint = values[1];
if(upsertDeviceIdResult.upsertedCount > 0){
return performThirdQuery(createEndpoint.EndpointArn);
}
})
.then(() => {
res.status(200).send({ success: true });
})
.catch((err) => {
console.log(err);
res.status(400).send({ reason: 'unknown' });
});
});
注意 return
之前的 performThirdQuery
。假设 performThirdQuery
返回一个承诺,这会将来自第一个履行处理程序的承诺解析为来自 performThirdQuery
的承诺(当您将一个承诺解析为另一个承诺时,它使前者的结果由后者的结果决定)。在另一种情况下(upsertDeviceIdResult.upsertedCount > 0
不是真的),处理程序只是隐式返回 undefined
。当第一个处理程序的承诺得到履行时,第二个履行处理程序运行,要么立即使用 undefined
,要么当 upsertDeviceIdResult.upsertedCount > 0
is 为真时,当该承诺得到履行时。
在现代环境中(包括任何模糊的最新版本的 Node.js),您可以改用 async
函数和 await
:
// (In an `async` function)
const [upsertDeviceIdResult,createEndpoint] = await Promise.all([upsertDeviceId,createEndpoint]);
try {
if (upsertDeviceIdResult.upsertedCount > 0) {
await performThirdQuery(createEndpoint.EndpointArn);
}
res.status(200).send({ success: true });
} catch (err) {
console.log(err);
res.status(400).send({ reason: 'unknown' });
}
旁注 - 而不是:
.then((values) => {
const upsertDeviceIdResult = values[0];
const createEndpoint = values[1];
// ...
你可以在参数列表中使用解构:
.then(([upsertDeviceIdResult,createEndpoint]) => {
// ...