首页 > 解决方案 > 为什么 node.js 承诺即使放在 then() 块中也不会解决?

问题描述

我想获得以下工作流程:

经过大量修改后,我的代码如下所示 -

nightmare 
    .goto(url) 
    .wait('body') 
    .evaluate( ()=>document.querySelector('body').innerHTML) 
    .end() 
    .then((response) => { 
        return getJSONData(response);
    })
    .then((data) => {
        return processJSONData(data);
    })
    .then((pages) => {
        return createFile(pages);
    }) 
    .catch(err => { 
        console.log(err);  
    });

getJSONData(data)使用cheerio解析HTML,并processJSONData(data)使用image-downloader下载图像。根据我的理解,由于这是一个承诺链,这意味着每个 then() 内部的执行将是异步的,但 then() 块本身将按顺序执行。在运行代码时,我看到即使前两个 then() 块是按顺序执行的(到目前为止),该createFile(pages)块也会立即执行,从而创建一个损坏的 PDF 文件。这可能是什么原因?如何确保then()块同步执行,即每个块then()仅在前一个 then 解决后运行?
完整的代码可以在这里找到。

标签: javascriptnode.jsasynchronouspromiseasync-await

解决方案


您不必等待所有异步操作在 内完成processJSONData(),而只是等待其中的某些部分。考虑更改如下:

function processJSONData(data){

    // map() instead of forEach() to get a promise per request
    const reqs = data.map(element => {
        // return the inner promise chain to be collected
        return download.image(element)
        .then( ({filename}) => {
            console.log("Saved to ",filename); 
            return filename;
        });
    });

    // return a promise that waits for all of them to be finished
    return Promise.all( reqs );

}

推荐阅读