Qiu*_*ang 7 javascript google-chrome promise async-await polyfills
我需要向多服务器发送请求,以查看哪个服务器将响应我的请求,如果其中任何一个响应,我将进一步与该服务器交互。最简单的方法是按顺序发送我的请求,像这样
async function probing(servers) {
for (const server of servers) {
const result = await fetch(server)
if (result.status == 200) {
return result
}
}
}
Run Code Online (Sandbox Code Playgroud)
但我希望加快探测过程,所以我将代码更改为
async function probing(servers) {
results = await Promise.all(
servers.map(async server => {
return await fetch(server)
})
)
for (const result of results) {
if (result.status == 200) return result
}
}
Run Code Online (Sandbox Code Playgroud)
但我仍然需要等待所有的承诺完成。我真正需要的是,如果其中一个有决心,我就从我的探测中返回()
那有可能吗?
- - 更新 - -
感谢评论promise.any是解决方案(单线箭头函数可以进一步简化如下)
result = await Promise.any(
servers.map(server => fetch(server))
)
Run Code Online (Sandbox Code Playgroud)
---- 更新 2 ----
我原以为Promise.any是要走的路,也是故事的结局。但不幸的是,事实并非如此!Promise.any仅适用于 Chrome 85+ 和 FF 79+,不像 Promise.all 可用于除 IE 之外的任何现代浏览器?在这里查看https://v8.dev/features/promise-combinators
我的客户需要我从 2020 年开始支持 Chrome 版本,即 Chrome 80+,我尝试用 Babel填充 Promise.any但我失败了。
我们使用babel6,但我未能用babel6对 Promise.any 进行 polyfill。我尝试升级到babel7 (有npx babel-upgrade --write一些曲折),现在使用 Promise.any() 的捆绑代码甚至不能用于 chrome 88。我问了另一个问题如何使用 babel 7 填充 Promise.any() ?
所以现在我只需要恢复到 Promise.all。
---- 更新 3 ----
我终于Promise.any()用 Babel 7制作了core-js@3polyfill ,关键是使用正确的 babelrc 设置(我不确定我是否全部正确),请参考我的问题和答案。
在这种情况下Promise.race()看起来很合理,但问题Promise.race()是比赛中任何拒绝承诺都会导致整个比赛崩溃。如果我们想要忽略个别拒绝并继续比赛,那么我们仍然有一个选择,在这种情况下,只有当所有承诺都被拒绝时,我们才必须执行操作来处理错误。
因此,如果我们发明Promise.invert()并将其与 Promise.all() 一起使用,那么我们就得到了我们想要的。
var invert = pr => pr.then(v => Promise.reject(v), x => Promise.resolve(x));
Run Code Online (Sandbox Code Playgroud)
让我们看看如何使用它;
var invert = pr => pr.then(v => Promise.reject(v), x => Promise.resolve(x));
Run Code Online (Sandbox Code Playgroud)
因此,由于承诺现在被颠倒了,所以现在catch是我们处理结果的地方,而这then是处理错误的地方。
我认为您可以在生产代码中安全地使用它,只要您很好地注释了此代码块以供将来阅读的任何人使用。
| 归档时间: |
|
| 查看次数: |
191 次 |
| 最近记录: |