blog
blog copied to clipboard
【node实战系列】异步并发,自定义Promise.allSettled
本文首发于:https://github.com/bigo-frontend/blog/ 欢迎关注、转载。
背景
bigo前端开始推广bff,hello农场作为首个bff落地项目,历经2个月,完成了从0-1的落地实践。
【node实战系列】按照小模块拆分,从开发者的角度讲叙,如何进行bff高可用编码。
本系列文章,基于eggjs框架编码,使用ts语法,为了提升阅读体验,建议大家先了解一下eggjs。
系列文章
- 【node实战系列】编写一个重试装饰器
- 【node实战系列】自行实现应用缓存
- 【node实战系列】异步并发,自定义Promise.allSettled
- 【node实战系列】rpc与http协议通讯
- 【node实战系列】使用reqId跟踪全流程日志
- 【node实战系列】入参校验validate
- 【node实战系列】异常中断
- 【node实战系列】base64编码
- 【node实战系列】服务发现
- 【node实战系列】编码与约定
- 【node实战系列】监控告警
- 【node实战系列】单元测试
- 【node实战系列】压测
- 【node实战系列】灰度
- 【node实战系列】文档
- 【node实战系列】系列小结
欢迎大家关注我们的github blog,持续更新。 https://github.com/bigo-frontend/blog/issues
请求并发
由于nodejs事件循环的实现,让异步编程变得简单。
我们可以直接使用Promise对象进行异步调用。bff的一个核心场景就是接口聚合,自然离不开多个接口并发请求。
请求并发可以让我们把请求时间缩短为当前最长请求的时间。
举个例子:需要聚合a、b、c三个接口,对应的接口响应时间为100ms、150ms、200ms,如果是顺序请求,聚合耗时450ms, 但是使用请求并发,聚合耗时200ms,收益是十分明显的。
Promise.allSettled
Promise.all:短路特性,有一个请求错误,直接走catch,不再走then。 Promise.allSettled : 无论请求对错最终都会返回一个数组对象到then中,并切返回的数据中标识了错误跟正确数据的区别。 但是属于新的提案,有需要nodejs>=12.9.0,我们的测试环境还使用v10版本,所以需要我们手动封装一下。
自定义Promise.allSettled
实现
// 请求并发,相当于Promise.allSettled
allSettled(promises) { // 自定义 https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Promise/allSettled
return new Promise(resolve => {
const data: any = [], len = promises.length;
let count = len;
for (let i = 0; i < len; i += 1) {
const promise = promises[i];
promise.then(res => {
data[i] = res;
}, error => {
data[i] = error;
}).finally(() => { // promise has been settled
if (!--count) {
resolve(data);
}
});
}
});
}
业务使用示例
const resList = await ctx.helper.allSettled([
// 1.我的农场信息
service.accounts.getAccountInfoByUid.request(),
// 2.用户信息
service.accounts.getUserExtraInfo.requestByUid(),
// 3.是否大客户
service.accounts.getBigClient.request(),
// 4.是否显示礼包红点
service.gift.checkAppTabIsNeedShowRedPoint.request(),
// 5.今天是否签到
service.task.signHistory.isSignedToday(),
// 6.个人形象集合
service.accounts.getAccountAppearanceInfo.getAppearanceList(),
// 7.我的形象
service.accounts.getAccountAppearanceInfo.appearanceInfo(),
// 8.礼包列表
service.gift.getGiftList.request(),
// 9.任务红点
service.task.listCommonTask.isShowTaskRedPoint()
]);
小结
综上,一个简单又实用的请求并发功能就实现了。
欢迎大家留言讨论,祝工作顺利、生活愉快!
我是bigo前端,下期见。