【问题标题】:How to fix the TypeError 'Cannot read property 'download' of undefined' from browser.downloads.download using Puppeteer如何使用 Puppeteer 从 browser.downloads.download 修复 TypeError 'Cannot read property 'download' of undefined'
【发布时间】:2021-07-10 09:16:18
【问题描述】:

我正在使用 puppeteer 登录我与之合作的内容提供商的帐户并下载大量 zip。 我可以轻松地获取包含我需要下载的所有链接的数组,然后循环遍历数组并使用 browser.downloads.download(取自 MDN 的代码)下载每个链接。问题是它甚至在开始下载之前就告诉我:

error:  TypeError: Cannot read property 'download' of undefined

这是我的代码:

const puppeteer = require('puppeteer');
require('dotenv').config();

(async () => {
  const browser = await puppeteer.launch({
    headless: false,
    args: ['--start-maximized'],
    defaultViewport: null,
  });

  const page = await browser.newPage();

  try {
    await page.goto(process.env.GROB_URL);
    page.setDefaultNavigationTimeout(0);

    await page.waitForSelector('input[name=user]', {
      visible: true,
    });
    //login
    await page.type('input[name=user]', process.env.GROB_USER);
    await page.type('input[name=pass]', process.env.GROB_PASS);
    await page.click('input#head-login');

    await page.waitForSelector('.light-highlight-row');

    const setValue = new Set();
    // get the nodelist array with all the download links
    let arr = await page.$$('.light-highlight-row td:nth-child(8) a');

    for (let item of arr) {
      const jsonValue = await item.getProperty('href');
      const value = await jsonValue.jsonValue();
      setValue.add(value);
    }
    
    const finalArray = Array.from(setValue);
    //all good till here

    function onStartedDownload(id) {
      console.log(`Started downloading: ${id}`);
    }

    function onFailed(error) {
      console.log(`Download failed: ${error}`);
    }

    //donwload all of them
    finalArray.forEach((link) => {
      var downloadUrl = link;
      var downloading = browser.downloads.download({
        url: downloadUrl,
      });
      downloading.then(onStartedDownload(link), onFailed(link));
    });
    page.waitForTimeout(500_000);

  } catch (error) {
    console.log('error: ', error);
  }
})();

它以某种方式告诉我浏览器未定义,但它是 JS API。

【问题讨论】:

    标签: javascript node.js browser typeerror puppeteer


    【解决方案1】:

    Browse 对象中没有此方法或属性下载,您可以在puppeteer docs 上查看。

    您可以尝试使用http请求来获取您的文件,例如使用下面的这种策略,我无法尝试,但我希望它对您有用=)

     const puppeteer = require('puppeteer');
        require('dotenv').config();
        
        async function downloadFile(downloadUrl) {
            
           await fetch(downloadUrl)
                .then(res => res.blob())
                .then(blob => {
                var file = window.URL.createObjectURL(blob);
                window.location.assign(file);
            });
          
        }
        
        
        (async () => {
          const browser = await puppeteer.launch({
            headless: false,
            args: ['--start-maximized'],
            defaultViewport: null,
          });
        
          const page = await browser.newPage();
        
          try {
            await page.goto(process.env.GROB_URL);
            page.setDefaultNavigationTimeout(0);
        
            await page.waitForSelector('input[name=user]', {
              visible: true,
            });
            //login
            await page.type('input[name=user]', process.env.GROB_USER);
            await page.type('input[name=pass]', process.env.GROB_PASS);
            await page.click('input#head-login');
        
            await page.waitForSelector('.light-highlight-row');
        
            const setValue = new Set();
            // get the nodelist array with all the download links
            let arr = await page.$$('.light-highlight-row td:nth-child(8) a');
        
            for (let item of arr) {
              const jsonValue = await item.getProperty('href');
              const value = await jsonValue.jsonValue();
              setValue.add(value);
            }
            
            const finalArray = Array.from(setValue);
            //all good till here
        
            function onStartedDownload(id) {
              console.log(`Started downloading: ${id}`);
            }
        
            function onFailed(error) {
              console.log(`Download failed: ${error}`);
            }
        
            //donwload all of them
            finalArray.forEach((link) => {
               //here you can call the download funcion passing link and a filename
               await downloadFile(link)
            });
            page.waitForTimeout(500_000);
        
          } catch (error) {
            console.log('error: ', error);
          }
        })()
    

    【讨论】:

    • 您好,谢谢您的回答。不幸的是,它会下载所有文件,但它们是空的。不知道为什么
    • 现在看一下,我已经改成 fetch 方法并在本地测试,它正在工作。
    猜你喜欢
    • 2020-05-02
    • 2021-06-25
    • 2021-10-31
    • 2017-04-24
    • 2023-03-15
    • 2022-11-30
    • 2022-10-18
    • 2021-09-18
    • 2021-09-25
    相关资源
    最近更新 更多