李恒道 发表于 2022-1-24 17:19:24

ThisAV 发表于 2022-1-24 15:59
感谢大佬回帖,是我的描述有问题,现有的代码就是这个操作方法

startDownload 函数里


cxxjackie给的代码就是我描述的了

ThisAV 发表于 2022-1-25 13:56:43

cxxjackie 发表于 2022-1-24 19:44
感觉你对async/await的理解有问题,虽然强行异步后返回值变成了Promise,但代码实际还是同步的,这个down ...

function requestUrlBlob(url) {
      return new Promise((resolve, reject) => {
            GM_xmlhttpRequest({
                url: url,
                method: 'get',
                responseType : 'blob',
                onload :res => resolve(res.response),
                onerror : e => reject(e)
            });
      })
    }

    async function downloadAndPackFile(zipPack, url, filename, extname) {
      if (!extname) {
            const urlExt = url.split('.').pop();
            extname = urlExt ? `.${urlExt}` : '';
      }

      console.log(`正在下载`, url, filename);
      await requestUrlBlob(url).then((blob) => {
            console.log(`下载完成`, url, blob, filename);
            zipPack.file(`${filename}${extname}`, blob);
      })
    }

对不起,downloadAndPackFile 是我复制了错误代码,完整的是上面这个

asyncPool 的效果和 downloadAll 是基本上一致的,downloadAndPackFile 在上面的例子得到的返回是一个 Promise。


我现在遇到的问题是 zipPack.generateAsync 的执行时机

GM_xhr 是异步的,downloadAndPackFile 并没有等待 GM_xhr 返回结果就执行结束了


ThisAV 发表于 2022-1-25 14:09:25

李恒道 发表于 2022-1-24 17:19
cxxjackie给的代码就是我描述的了

我的代码原型就是这样,之前的代码是复制错了

论坛里即时所得视图下 code 标签里的东西在发表时会出现丢失情况,导致我多次编辑帖子贴错了代码

对了,论坛里加的灯笼,对1440以下的分辨率有点不友好,会遮挡屏幕内容,还影响帖子编辑

李恒道 发表于 2022-1-25 15:17:05

ThisAV 发表于 2022-1-25 14:09
我的代码原型就是这样,之前的代码是复制错了

论坛里即时所得视图下 code 标签里的东西在发表时会出现丢 ...

499买的编辑器....
作者根本不维护
钱打水漂了,唉,没办法
后期如果人多一点会考虑自己搞编辑器的
灯笼的话,哥哥干他妈的!

李恒道 发表于 2022-1-25 15:17:35

ThisAV 发表于 2022-1-25 13:56
对不起,downloadAndPackFile 是我复制了错误代码,完整的是上面这个

asyncPool 的效果和 downloadAl ...

      await requestUrlBlob(url).then((blob) => {
            console.log(`下载完成`, url, blob, filename);
            zipPack.file(`${filename}${extname}`, blob);
      })
这里的await是等待返回
直接let result= await requestUrlBlob(url)就可以了

cxxjackie 发表于 2022-1-25 19:45:26

ThisAV 发表于 2022-1-25 13:56
对不起,downloadAndPackFile 是我复制了错误代码,完整的是上面这个

asyncPool 的效果和 downloadAl ...

async/await和.then是调用Promise的两种不同方案,不应该同时使用,改成这样试试:const blob = await requestUrlBlob(url);
console.log(`下载完成`, url, blob, filename);
zipPack.file(`${filename}${extname}`, blob);
我不太确定问题是否出在这里,没用过zipPack,你最好自己debugger跑一下看看。

ThisAV 发表于 2022-1-26 01:26:35

cxxjackie 发表于 2022-1-25 19:45
async/await和.then是调用Promise的两种不同方案,不应该同时使用,改成这样试试:
我不太确定问题是否出 ...

async/await和.then 这个,await 还是要等待 then 完成,然后才 await 返回结果吧?
我想这个应该是不冲突的

和大佬交流后,对 Promise 有更深的认识

另外我发现,我的原始代码是没问题的,因为对 Promise 的理解问题,在论坛发帖时越改越乱,导致了后面我误以为是下载打包文件时,没有等待文件添加

asyncPool 的作用是限制并发数量,从而提升下载的效率。结果因为测试时某些文件比较大而本末倒置,因此导致了卡死的假象,使得找问题的方向错了。另外还有一个就是打包效率实在低的感人,也是罪魁祸首之一。

cxxjackie 发表于 2022-1-26 11:31:20

ThisAV 发表于 2022-1-26 01:26
async/await和.then 这个,await 还是要等待 then 完成,然后才 await 返回结果吧?
我想这个应该是不冲 ...

我也觉得你这样写虽然很怪,但不影响结果,所以不确定问题是否出在这里。asyncPool一般用于每个线程耗时大致相同的情况,比如把一个大文件分割下载,限制数量可以控制线程数,耗时不一的话直接Promise.all是最快的。其实现代浏览器都会自己做这些优化,我测试过在chrome开启多线程下载的前提下,GM_xhr下载单个大文件和分割成多个小的下载,结论是效率基本一样,所以asyncPool就有点画蛇添足了。
还有不要叫大佬,搞得我压力很大哈哈。

ThisAV 发表于 2022-1-27 14:55:18

cxxjackie 发表于 2022-1-26 11:31
我也觉得你这样写虽然很怪,但不影响结果,所以不确定问题是否出在这里。asyncPool一般用于每个线程耗时 ...

嗯?~GM_xhr 可以受到多线程下载影响?又涨知识了

GG说得对,asyncPool 从测试结果来看,效率不仅没有提高,反而下降了,实现效果和我预想的作用不一致。{:4_98:}
不过以后应该可以应用在有并发限制的地方。

GG 不要有压力,和 GG 交流受益匪浅,获益良多。{:4_110:}

现在想想自己这样走了好多弯路,当作涨经验了 {:4_115:}

ozon 发表于 2022-3-14 10:03:57

看懵了{:4_115:}
页: 1 [2]
查看完整版本: 怎么用 Promise 让所有 GM_xmlhttpRequest 完成再进行下一步操作?