Отказ от обещания кукловода (селектор запросов, если класс) - PullRequest
0 голосов
/ 01 декабря 2018

Я получаю отказ от обещания, даже если я использую оператор if / else для проверки.Когда я перебираю div (const items), класс "description-main" присутствует на всех элементах.Однако класс "description-optional" не всегда присутствует.Как я могу пропустить его или назначить null для продолжения цикла без каких-либо ошибок?

// Imports: Dependencies
const puppeteer = require('puppeteer');

// Puppeteer: Generate CSV
(async () => {
    try {
       // Start Browser And Create New Page
       const browser = await puppeteer.launch({ headless: false });
       const page = await browser.newPage();

       // Go To Page
       await page.goto('http://website.com', { waitUntil: 'networkidle2' });

       const items = await page.$$('.item');

       for (let i = 0; i <= items.length; i ++) {
          const itemDescription = await items[i].$eval('.description-main', div => div.innerText.trim());
          const itemDescription2 = null | await items[i].$eval('description-optional', div => div.innerText.trim());

          console.log('Item: ' + itemDescription + itemDescription2);
       }
   }
   catch (error) {
   console.log(error);
   }
 })()

Ответы [ 2 ]

0 голосов
/ 01 декабря 2018

Вы можете использовать троичный оператор , чтобы сначала убедиться, что await items[i].$('.description-optional') является правдивым (т.е. элемент существует на странице).

Если условие истинно (т.е. не * 1006)*null), затем вы можете выполнить и назначить await items[i].$eval('.description-optional', div => div.innerText.trim()) для itemDescription2.

В противном случае присвойте null для itemDescription2:

const itemDescription2 = await items[i].$('.description-optional') ? await items[i].$eval('.description-optional', div => div.innerText.trim()) : null;

Вот полный пример:

const items = await page.$$('.item');

for (let i = 0; i < items.length; i++) {
  const itemDescription = await items[i].$eval('.description-main', div => div.innerText.trim());
  const itemDescription2 = await items[i].$('.description-optional') ? await items[i].$eval('.description-optional', div => div.innerText.trim()) : null;

  console.log('Item: ' + itemDescription + itemDescription2);
}
0 голосов
/ 01 декабря 2018

Проблема здесь в том, что $eval делает несколько вещей, которые зависят друг от друга.

$eval сначала выбирает элемент, а затем пытается оценить функцию по результату.

Вы можете решить свою проблему несколькими способами, но, возможно, проще всего просто проверить, соответствует ли селектор элементу, прежде чем делать что-либо еще:

let itemDescription2; if (await items[i].$('.description-optional')) itemDescription2 = await items[i].$eval('description-optional', div => div.innerText.trim());

В качестве альтернативы вы можете получить innerTextв браузере и верните его, не вызывая ошибки.

Примечание также:

i <= items.length; должно быть i < items.length;

, а description-optional должно быть .description-optionalкак это селектор класса.

...