[英]Angular 7 - forEach iteration inside of a promise is executing after the promise resolves. Why?
[英]Go to the next forEach iteration after promise resolves
我将通过一些数据数组,在每次迭代中我都会处理 promise。
我想要的是 go 到下一次forEach
迭代,只有当当前迭代上的 promise 得到解决时。
我搜索了不同的解决方案,发现使用for(... of...)
而不是forEach
可以解决问题。 但还是想不通。
const data = ['apple', 'orange', 'banana'];
data.forEach((row, rowIndex) => {
let params = {
fruitIndex: rowIndex,
};
axios.post('/fruits', { ...params })
.then(response => {
// go to the next iteration of forEach only after this promise resolves
})
.catch(error => console.log(error))
});
递归有助于:
const data = ['apple', 'orange', 'banana'];
function request_fruit(n) {
let params = {
fruitIndex: n,
};
axios.post('/fruits', { ...params })
.then(response => {
// Work with recived...
// ....
// Request next
if(n+1<fruits.length) request_fruit(n+1)
})
.catch(error => console.log(error))
};
request_fruit(0)
如果可以的话,我会推荐一个易于阅读和理解的带有等待/异步的 for of 循环。 请注意,顶级 await 是最近添加的,因此您应该将其包装在一些异步 function 中(无论如何您都可能这样做)。
如果你不能使用 async/await,你可以使用reduce
和初始解析的 promise 来链接后续调用。
请注意,我使用了 function sleep
,它在一段时间后解决了 promise。 sleep
调用应该可以与 axios 调用互换。
const sleep = (ms) => new Promise(resolve => setTimeout(resolve, ms)); const data = [1000, 2000, 3000]; function withReduce() { console.log('Sequential Promises with Reduce:'); return data.reduce((previousPromise, ms) => { return previousPromise.then(() => { console.log(`sleeping for ${ms}ms`); return sleep(ms); }); }, Promise.resolve()); } async function withAsync() { console.log('Sequential Promises with for of and await:'); for (let ms of data) { console.log(`sleeping for ${ms}ms`); await sleep(ms); } } withReduce().then(withAsync);
看起来还没有人发布特定的 async/await,所以这就是你如何将它与 for...of 一起使用:
const data = ['apple', 'orange', 'banana'];
for (const [rowIndex, row] of data.entries()) {
let params = {
fruitIndex: rowIndex,
};
let response;
try {
response = await axios.post('/fruits', { ...params });
} catch (error) {
console.log(error);
continue;
}
// …
}
这一切都放在异步 function 中。 (另外, {...params }
有点奇怪。直接使用params
有什么问题?)
只需在 api 调用上使用 await 即可。
function postFruitData(){
const data = ['apple', 'orange', 'banana'];
data.forEach(async (row, rowIndex) => {
let params = {
fruitIndex: rowIndex,
};
const response = await axios.post('/fruits', { ...params })
});
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.