资讯详情

分批导入功能——按顺序循环执行异步请求(使用递归)

在这里插入图片描述

完成工作中遇到的完成过程: 超过50个页面导入数据会卡住,然后产品经理让我限制在只允许导入50个以内的数据,否则会报错。 将发布改为正式环境后,用户觉得将文档分成几个太麻烦了。例如,如果他们想导入300多个数据,他们必须将原始数据excel文件分成7个,一个一个导入,用户体验差。 于是这次迭代让我解除只允许导入50条的限制,想办法给导入加个进度条,让用户在等待的冗长时间里能感受到导入正在进行。

但问题是,导入是调整后端接口,只有在执行开始时才能进入pending状态,然后一直pending要求成功或失败后才会返回结果,因此制作进度条是不现实的(除非它是浏览器中永远无法读取的加载条,但仅仅提高用户体验是毫无意义的)。

那么如何才能更好地完成这一需求呢?由于导入不超过50个不会特别卡住,所以当导入超过50个数据时,我们分批进入,每50个数据调用一个接口,并在请求成功或失败时提示用户N到第一n 50条数据导入成功/失败】,就能更好的完成原定需求并提升用户体验度。

如果后端同事愿意合作,可以让他帮忙在导入前写一个数据验证接口,比如在导入200个数据之前,先验证这200个数据填写的格式是否正确,否则直接导入请求执行到一半,用户也应该抱怨(推锅)。 但是,根据项目分配,也可以编写验证前端。


回到主题:如果您想完成上述操作,即如果您不知道要传输的数据有多大,您必须在执行50个批导入请求之前不能插入下一个批导入请求,否则导入的数据将是混乱的。 但请求是异步的,我们需要解决的是按顺序执行循环导入的异步请求。for index循环执行方法不可避免地要求异步,因此写入递归执行请求不仅可以实现需求,而且比其他方法更方便。

    // 分批导入仪器     recursionMeterImport(arr, index, otherArr, otherIndex) { 
              // arr分批导入的数据数组,index是递归时导入的第几批数组。otherArr执行当前递归后执行的下一类数组,otherIndex同上。       // 首先判断arr如果是空的,则执行导入请求,如果是空的,则开始导入下一类数据        if (arr.length) { 
                this.importInfo  =           "\n"             `正在导入第${ 
         index * 50   1}条至第${ 
         (index   1) * 50}条数据...`;         ajax.post("xxxx(批量导入接口)", arr[index])           .then((res) => { 
                    this.importInfo  = "\n"   res.data.message;  // 后端返回的提示信息,【XX条数据导入成功             if (res.data.body && res.data.body.length > 0) { 
         res.data.body.forEach((item, i) => { 
         this.importInfo += "\n" + `【${ 
          index * 50 + i + 1}】:` + item; // 批量导入时每天数据的导入返回提示信息 }); } if (arr.length > index + 1) { 
         // 导入的不是最后一批数据,递归执行导入下一批数据 this.recursionMeterImport(arr, index + 1, otherArr, otherIndex); } else { 
         // 导入完数组的最后一批数据后,执行下一种类数据的递归导入 this.importInfo += "\n" + this.lang.ImportingMeterGroupStandardValue + "..."; // 提示开始导入下一种类数据 this.recursionMetergroupImport(otherArr, otherIndex); } }) .catch(() => { 
         this.$alert( "网络波动原因或未知错误导致导入失败,请重试或联系系统管理员!", this.lang.Tips ); this.btnDisabled = false; }); } else { 
         this.importInfo += "\n" + "仪表导入对标值内容为空"; this.importInfo += "\n" + this.lang.ImportingMeterGroupStandardValue + "..."; this.recursionMetergroupImport(otherArr, otherIndex); } }, // 递归分批导入仪表分组 recursionMetergroupImport(arr, index) { 
         // 下一种类的递归导入,基本同上,不再赘述 if (arr.length) { 
         this.importInfo += "\n" + `正在导入第${ 
          index * 50 + 1}条至第${ 
          (index + 1) * 50}条数据...`; ajax.post("xxxx(下一种类批量导入接口)", arr[index]) .then((res) => { 
         this.importInfo += "\n" + res.data.message; if (res.data.body && res.data.body.length > 0) { 
         res.data.body.forEach((item, i) => { 
         this.importInfo += "\n" + `【${ 
          index * 50 + i + 1}】:` + item; }); } if (arr.length > index + 1) { 
         // 导入的不是最后一批数据,继续执行递归 this.recursionMetergroupImport(arr, index + 1); } else { 
         this.importInfo += "\n" + "对标值已全部导入成功!"; this.$alert("对标值已全部导入成功!", this.lang.Tips); this.search(); this.btnDisabled = false; } }) .catch(() => { 
         this.$alert( "网络波动原因或未知错误导致导入失败,请重试或联系系统管理员!", this.lang.Tips ); this.btnDisabled = false; }); } else { 
         this.importInfo += "\n" + "仪表分组导入对标值内容为空"; this.importInfo += "\n" + "对标值已全部导入成功!"; this.$alert("对标值已全部导入成功!", this.lang.Tips); this.search(); this.btnDisabled = false; } }, 

数组切割的方法请见我上一篇文章:JS将一个数组切割成同等大小的多个数组的方法


小记:刚听到一个不合理的需求时先不要急,和产品经理说明不合理的地方并提供自己的想法,有时他会觉得你的方案更好并采用,在动手完成的过程中跟着自己的思路走就能迎刃而解,事半功倍。 THX~

标签: thx03微量程动态扭矩传感器

锐单商城拥有海量元器件数据手册IC替代型号,打造 电子元器件IC百科大全!

 锐单商城 - 一站式电子元器件采购平台  

 深圳锐单电子有限公司