js方法队列的一次实践
。
场景:
项目中有一个需求,发布故事线,发布会调用一个接口,改接口返回进度条的必要信息,进度信息由mqtt推送过来,在正常网络情况下,接口返回速度应该比mqtt推送先一步完成,但是在网络慢的情况下,接口就迟于mqtt推送的速度。
(mqtt会推送多条消息过来,执行多次)。这样会造成进度条卡死的现象。
解决办法:当有进度条实例时,直接执行进度条的方法,若没有进度条实例时,将方法存到方法队列内,待进度条实例创建时,执行队列内的方法。完美解决mqtt后接口执行顺序的问题。当然时机要把握好,我指的是执行队列还是执行方法。看情况而定。
下面是一段代码:
storyPublishQueue.js
// 故事线发布队列 export function storyPublishQueue(){ let arr = []; //入队操作 this.push = function(element){ arr.push(element); return true; } //出队操作 this.pop = function(){ return arr.shift(); } //获取队首 this.getFront = function(){ return arr[0]; } //获取队尾 this.getRear = function(){ return arr[arr.length - 1] } //清空队列 this.clear = function(){ arr = []; } //获取队长 this.size = function(){ return arr.length; } // 执行故事线发布队列 this.trigger = function(){ arr.forEach(item=>{ item(); }) arr = [];//清空队列 } }
挂在到vue实例实例上:
import {storyPublishQueue} from '@/utils/storyPublishQueue.js';//故事线发布队列 Vue.prototype.storyPublishQueue = new storyPublishQueue();//创建一个发布故事线队列实例
mqtt返回消息内调用:
let vm = this; let queue = function(){ // 为了处理 故事线页面故事线发布接口和mqtt返回时间顺序问题 将以下代码放到消息队列内 无论接口和mqtt执行顺序是怎么样的,都放在接口返回之后执行 xxx } if(vm.$aiProgress.find ('storypush')){ //如果存在了进度条弹窗实例,则执行 queue() }else{ // 如果不存在进度条实例 则加入队列 this.storyPublishQueue.push(queue);//加入消息队列 }
接口内调用:
Bus.$emit('storypush',{vm:this, storyPushTotal});//创建进度条实例 if(this.storyPublishQueue.size()){ // 如果消息队列内有队列 代表mqtt先与接口返回了进度信息,直接执行队列 this.storyPublishQueue.trigger(); }
。