![](/img/trans.png)
[英]Bluebird promise.all catch in mid promise chain and continue with promise
[英]Nodejs Promise.All with promise chain?
我不知道如何問這個問題,但我有一組承諾都需要解決,因為它們是數據 api 請求,但三個中的一個取決於另一個,我不確定如何解決。
有問題的代碼如下所示:
let dependent;
let subscriptions = getSubscriptions() //data fetch
.then((subscriptions) => {
let fieldList = subscriptions.reduce((subscription) => {
if(subscription.Threshold) {
return subscription.Threshold.Field;
}
return null;
});
dependent = getUpdatedInfo(request, body, fieldList); //Data fetch promise
return subscriptions;
});
let userInfo = getUserInformation(); //Data fetch
Promise.all([subscriptions, userInfo, dependent]).then(function(values) {
console.log({ promiseAll: values }); //Dependent is always undefined
processSubscriptions(result, body, userInfo, subscriptions, dependent);
});
基於過去 4 個小時的谷歌搜索,我已經嘗試了幾種不同的方式來使用此代碼,但還沒有完全弄清楚我在這里做錯了什么。
你可以用原始的 Promise 來做到這一點,但這有點難看。 使用 async/await 更整潔:
async function whatever() {
const subs = await getSubscriptions();
const fieldList = subs.reduce((subscription) => {
if(subscription.Threshold) {
return subscription.Threshold.Field;
}
return null;
});
const dependent = await getUpdatedInfo(request, body, fieldList);
const userInfo = await getUserInfo();
return processSubscriptions(result, body, userInfo, subscriptions, dependent);
}
非阻塞的 NodeJS。 所有行都是同步執行的,在Promise.all
調用中, dependent
肯定是 undefined 因為它在Promise.all
中設置為undefined
let dependent;
.then
回調是異步執行的,例如在所有同步代碼之后。
如果你想使用dependent
它在解決then
然后,你必須鏈then
調用。
我會用 async/await 重構。 為了實現您正在尋找的並行化,我們為(userInfo 和dependent)創建了兩個promise,然后使用promise.All 等待它們的解決。 promise.All 返回所有承諾結果的數組。
確保使用 try, catch
async function processSubscriptionsHandler(request, body) {
try {
let userInfoPromise = getUserInformation(); // async function returning a promise
let subscriptions = await getSubscriptions()
let fieldList = getFieldList(subscriptions)
let dependentPromise = getUpdatedInfo(request, body, fieldList) // async function returning a promise
let [userInfo, dependent] = await Promise.all([userInfoPromise, dependentPromise]) // await both promises to resolve and map resulting array to variables
processSubscriptions(result,
body,
userInfo,
subscriptions,
dependent);
} catch (e) {
console.error(e)
}
}
function getFieldList(subscriptions) {
subscriptions.reduce((subscription) => {
if (subscription.Threshold) {
return subscription.Threshold.Field;
}
return null;
});
}
我試圖將您的邏輯重新整合到承諾中——您可以用於一系列相關承諾的工具之一是在承諾之前聲明您的變量,然后在.then
設置它們——這樣變量就可用了對於代碼塊中的所有閉包:
let subscriptions;
let updatedInfo;
let subscriptionsPromise = getSubscriptions() //data fetch
.then((subscriptionsResults) => {
let fieldList = subscriptionsResults.reduce((subscription) => {
if(subscription.Threshold) {
return subscription.Threshold.Field;
}
return null;
});
subscriptions = subscriptionsResults
return getUpdatedInfo(request, body, fieldList); //Data fetch promise
})
.then(updatedInfoResult => {
updatedInfo = updatedInfoResult;
});
let userInfoPromise = getUserInformation(); //Data fetch
Promise.all([subscriptionsPromise, userInfoPromise]).then(function(values) {
// at this point, subscriptions should have a value,
// and so should updatedInfo,
// and values[1] should be the result from userInfoPromise
});
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.