【问题标题】:Wait for actions to finish before executing again in puppeteer等待动作完成,然后在 puppeteer 中再次执行
【发布时间】:2018-09-12 20:42:20
【问题描述】:

我有一个 puppeteer 脚本,可以将一些文本输入到字段中,提交查询并处理结果。

目前,该脚本一次只处理 1 个搜索词,但我需要它能够连续处理一组项目。

我想我只是将代码放在一个循环中(参见下面的代码),但是,它只是一次将数组中的所有项目输入到字段中,并且不会为每个搜索词执行代码块:

  for (const search of searchTerms) {
    await Promise.all([
      page.type('input[name="q"]', 'in:spam ' + search + String.fromCharCode(13)),
      page.waitForNavigation({
          waitUntil: 'networkidle2'
        })
    ]);

    const count = await page.evaluate((sel) => {
      return document.querySelectorAll(sel)[1].querySelectorAll('tr').length;
    }, 'table[id^=":"]');

    if (count > 0) {
      const more = await page.$x('//span[contains(@class, "asa") and contains(@class, "bjy")]');
      await more[1].click();

      await page.waitFor(1250);
      const markRead = await page.$x('//div[text()="Mark all as read"]');
      await markRead[0].click();

      const selectAll = await page.$x('//span[@role="checkbox"]');
      await selectAll[1].click();

      const move = await page.$x('//div[@act="8"]');
      await move[0].click();

      await page.waitFor(5000);
    }
  }

我尝试使用来自Nodejs Synchronous For each loop 的递归函数

我还尝试使用带有 yield 和 promise 的函数生成器,甚至尝试了这篇文章 Nodejs Puppeteer Wait to finish all code from loopasync 包中的 eachSeries 函数@

我尝试过的都没有成功。任何帮助将不胜感激,谢谢!

【问题讨论】:

  • >目前,该脚本一次只处理 1 个搜索词,但我需要它能够连续处理一组项目。你的意思是……并行?连续的意思是一个接一个,按顺序。

标签: javascript node.js automation puppeteer


【解决方案1】:

无法使用相同的标签同时访问两个网站。您可以在浏览器上试一试以确保。

除了笑话,如果你想搜索多个项目,你必须为此创建一个pagetab

for (const search of searchTerms) {
  const newTab = await browser.newPage()
  // other modified code here
}

...等等,仍然会一一搜索。但是如果你使用有并发限制的地图,它会很好地工作。

我们可以为此使用p-all

const pAll = require('p-all');
const actions = []
for (const search of searchTerms) {
  actions.push(async()=>{
    const newTab = await browser.newPage()
    // other modified code here
  })
}
pAll(actions, {concurrency: 2}) // <-- set how many to search at once

所以我们循环遍历每个术语,并在操作列表中添加一个新的承诺。添加功能不会花费太多时间。然后我们可以运行承诺链。

您仍然需要修改上面的代码以获得您想要的。 和平!

【讨论】:

  • 这根本不是我想要做的。我只打开了 1 个选项卡,并且想在同一页面内执行代码块 x 次。
  • @NativeCoder 我相信您发布的代码应该已经这样做了。 for (const search of searchTerms) 表示将按顺序处理条款。如果您需要并行执行此操作,则需要此答案中建议的内容。
  • 实际上,你是对的,它确实工作得很好,哈哈,没有返回任何结果,所以它会执行下一次搜索。我只需要清除该字段,现在它可以完美运行。谢谢你们的帮助,哈哈,对我的错误深表歉意!
  • @NativeCoder 如果你返回数据,你可以在所有操作完成后得到一个结果。 ;) pAll 本身返回一个承诺。
猜你喜欢
  • 2011-02-12
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-07-20
  • 1970-01-01
  • 1970-01-01
  • 2020-09-14
  • 1970-01-01
相关资源
最近更新 更多