Кукловод получает элемент из elementHandle, вызывая ошибку протокола - PullRequest
1 голос
/ 08 июня 2019

Я пытаюсь почистить определенную страницу на Facebook для сообщений, написанных определенным пользователем и начинающихся с определенного слова.

const puppeteer = require('puppeteer');

async function findPosts(page) {
    const USERNAME = 'test123';
    const posts = await page.$$('.userContentWrapper');
    return posts.filter(async post => {
        try {
            let usernameElement = await post.$('.fwb');
            let username = await page.evaluate(element => element.textContent, usernameElement);
            if (username === USERNAME) {
                let postElement = await post.$('[data-testid="post_message"] p');
                let postContent = page.evaluate(element => element.textContent, postElement);
                return /\[test \d+\]/.test(postContent);
            }
            return false;
        } catch(e) {
            console.log(e);
            return false;
        }
    });
}


(async () => {
    const browser = await puppeteer.launch({
        headless: false
    });
    const page = await browser.newPage();
    await page.goto('https://www.facebook.com/groups/groupid/');
    const pageTitle = await page.title();
    console.log(pageTitle);
    const posts = await findPosts(page);
    console.log(posts);
    await browser.close();
})();

Я получаю

Ошибка: ошибка протокола (Runtime.callFunctionOn): цель закрыта. когда Я пытаюсь получить usernameElement

в этой строке:

let usernameElement = ждать сообщения. $ ('. Fwb');

Не уверен, что здесь происходит, какие-либо предложения?

1 Ответ

1 голос
/ 08 июня 2019

Проблема в том, что функция filter не работает с Promises. Таким образом, return posts.filter(...) немедленно вернется, и после этого браузер закроется. Поэтому, когда вы пытаетесь запустить функцию $ на странице, страница больше не существует, и вы получаете ошибку Target closed.

Чтобы заставить его работать с синтаксисом async / await, вы можете вместо этого использовать простой цикл:

async function findPosts(page) {
    const USERNAME = 'test123';
    const posts = await page.$$('.userContentWrapper');
    const postsToReturn = [];
    for (let post of posts) {
        /* ... if else logic */
        postsToReturn.push(post); // instead of return true
    }
    return postsToReturn;
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...