one.tsx
function fnOne() {
var urlMap = new Map();
urlMap.put ("1",
["https://thetestrequest.com/comments/1",
"https://thetestrequest.com/comments/2", ... 100 length])
urlMap.put ("2",
["https://thetestrequest.com/comments/4",
"https://thetestrequest.com/comments/5", ... 15 length"])
urlMap.forEach((key: any, value: any) => {
console.log(key + " Loop");
const commentsXML : any = fnTwo (value);
commentsXML.then((ResponseArray: any) => {
console.log(key + " ResponseArray");
console.log(ResponseArray);
});
});
}
function fnTwo (value: any) {
console.log ("Inside fnTwo");
var d1 = fetch (value)
.then (response => response.text())
.then (data => {
console.log ("Return response.text: " + new Date() + data);
return data;
})
.catch((error) => console.error("ERROR in fetch " + error));
return d1;
}
urlMap 的 GET 与 2 次迭代同步发生时的预期控制台输出:
控制台中的实际输出是:
请注意,15 个元素的响应时间戳早于 100 个元素的响应时间戳。因此查询不会同步触发。
如何同步发送请求。也就是说,收到 urlMap[0] 的响应后,将发送 urlMap[0] 的请求。
发生您的问题是因为 forEach 的设计不是为了等待其循环中进行的任何异步调用。因此,它正在获取第一个元素,然后继续其工作,然后传递到第二个循环,而不检查第一个获取调用是否完成。 在您的情况下,您想使用 for of 循环。 您还应该将“.then”转换为 async/await,这使其更具可读性并且更容易管理异步调用。
function async fnOne() { // make the function async
for (const [key, value] of urlMap) {
console.log(key + " Loop");
const commentsXML = await fnTwo(value); // await for the fetch to finish
console.log(key + " ResponseArray");
console.log(ResponseArray);
}
}
您也有类似的问题,您也可以阅读以下内容以了解更多详细信息: 在 forEach 循环中使用 async/await