【问题标题】:await fs writefile with puppeteer doesn't wait until file has written before continuing event loop带有 puppeteer 的 await fs writefile 不会等到文件写入后再继续事件循环
【发布时间】:2020-01-24 22:16:31
【问题描述】:

我正在使用 nodemon 来运行我的应用程序 nodemon index.js

在我的index.js 文件中,我使用Puppeteer 初始化我的函数

INDEX.JS

const dotenv = require("dotenv");
const reddit = require("./reddit");

(async () => {
  // ...
  await reddit.initialize();
  await reddit.login(username, password);
  const results = await reddit.getResults();
  console.log('got results');
})();

这一切都按预期工作。

在我的initialize() 函数中,我设置了Puppeteer 选项

REDDIT.JS

const puppeteer = require("puppeteer");
const fs = require("fs");

const self = {
  browser: null,
  page: null,

  initialize: async () => {
    // Select browser
    self.browser = await puppeteer.launch({
      headless: true,
      slowMo: 10,
      defaultViewport: null
    });
    //  create new page
    self.page = await self.browser.newPage();
  },
};

module.exports = self;

我遇到问题的地方是我的getResults() 函数

getResults: async () => {
    // ...
    await self.page.goto(SUBREDDIT_URL(reddit), { waitUntil: "networkidle0" });
    const elements = await self.page.$$(
      '#siteTable > div[class*="thing"]:not(.promoted)'
    );
    const results = [];
    
    await Promise.all(
      elements.map(async element => {
        // ... logic done that pushes items to results array
      })
    );
    console.log("about to write to file");

    await fs.writeFile(
      `${__dirname}/results.json`,
      JSON.stringify(results),
      err => {
        console.log("currently writing");
        if (err) return false;
        return true;
      }
    );

    console.log("finished writing to file");
    
    return await Promise.all(results);
}

当我运行它时,我会在控制台中得到以下信息

about to write to file
finished writing to file
got results
currently writing

我期待

about to write to file
currently writing
finished writing to file
got results

我的函数在写入文件之前完成,我在哪里出错了?

任何帮助将不胜感激。

【问题讨论】:

  • 尝试使用require('fs').promises 而不是require('fs')
  • @Titus 不是 100% 确定这是否有什么不同,因为我没有在控制台中登录 currently writing,但文件确实更新了

标签: javascript node.js async-await puppeteer fs


【解决方案1】:

fs.writeFile() 的常规版本不返回承诺,因此await 什么也不做。 await 仅在您等待承诺时才会做一些有用的事情。

node.js 的最新版本承诺支持 fs 模块。你可以这样做:

const fsp = require('fs').promises;

async function someFunc() {
    await fsp.writeFile('someFilename', someData);
    // other code here
}

注意,我习惯将导入的模块命名为 fsp 而不是 fs,以便更明显地表明它与普通的 fs 不同。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2021-12-27
    • 2017-09-07
    • 1970-01-01
    • 2020-07-14
    • 1970-01-01
    • 2023-03-14
    • 1970-01-01
    相关资源
    最近更新 更多