429 报错
最近在开发 LBMS 后台的图片上传时候遇到了同样的问题(大量图片同时请求时触发429限制)在这之前所使用的 valine 评论系统其中的一个 api 也是同样报错,原因很简单,leancloud 对同时发起大量查询做了限制处理,这直接导致默认请求数量过多时会返回 429 too many requests 错误,进而对操作造成一定的影响。
Error: Too many requests.
解决方案
其实早期开发后台的时候就遇到过这个问题,当时影响不大就没去考虑太多,不过现在是遇到图片并发上传限制,所以网上找了些方案,的确奏效了。
一开始打算用 promise chain,后来想试试 es7 里的 async await 来对 leancloud 发送 promise 请求进行处理,后来是各种坑,最后不了了之。
思考
既然不能从源头上解决问题,能不能简单的延迟发送请求的时间来延缓对 leancloud 请求频率?事实证明这个简单的想法是有效的!
首先我尝试了通过节流的方式对调用请求进行限制,但结果不太满意(这里的原因在后面会聊到)这之后我网上找了下,才发现了有篇《应对LeanCloud对于处理性能的限制》的文章里有对 leancloud 429 错误进行总结和解决,看了后发现思路是大同小异的,不过有部分细节需要引起注意
下面案例基于模拟 leancloud 同时发起 10 次请求,代码如下
代码语言:javascript复制 for(let i=0;i<10;i ){
doquery() //直接发起 10 次查询返回 429 too many requests 错误
setTimeOut(function(){
doquery() //在定时器内发起请求,每次请求延迟相同,异步请求时仍会触发 429 错误
},1000)
setTimeOut(function(){
doquery() //在(异步延迟)定时器内发起请求,每次请求延迟发生变化,实现了延迟请求,不会触发 429 错误
},i*100) //这里的 i 是动态发生变化的
}
这样一来解决 429 错误的思路应该很明确了,只需要给定一个定时器动态延迟发送请求即可。下面再简单聊下 valine 中的 valine-comment-count 页面评论计数所触发的 429 解决思路
老规矩,打开 valine.js 查询定位到 var R=u.findAll(document,".valine-comment-count")
修改为
var R = u.findAll(document, ".valine-comment-count"),
RLEN = R.length; //查询项目数量
u.each(R,
function(t, n) {
if (n) {
var r = u.attr(n, "data-xid");
RLEN--; //查询数量变化
//设定定时器动态查询
setTimeout(() => {
r && e.Q(r).count().then(function(e) {
n.innerText = e
}).
catch(function(e) {
n.innerText = 0
})
}, RLEN*500);
}
}),
以上修改后返回页面查询大量数据时不会触发 429 错误,唯一有点小影响的可能是动态变化的延迟时间,不过可以忽略不记。
总结
在 LBMS 的开发中其实学到了不少东西,期间在 leancloud 论坛发帖询问了浏览器环境本地文件储存方案,后续用自己的思路以另一种方式解决了问题,涉及到 valine 的时候也可以很好的融入修改,非常不错。这篇笔记有可能是发布的最后一篇静态的笔记,LBMS 应该很快就可以正式投入使用了(目前还在测试bug,因为储存在 leancloud 中的数据后续如果出问题了就不是那么方便,所以需要一段测试过渡时间)
参考链接
应对LeanCloud对于处理性能的限制
以上,有问题评论区留言。