使用Puppeteer爬取YouTube频道视频时遇Evaluation Failed错误求助
问题排查与解决
这个错误的核心原因是:你通过querySelector('h3')或querySelector('a')获取到了null,随后试图读取它的innerText或调用getAttribute方法,触发了类型错误。通常是YouTube DOM结构更新、元素未完全加载,或是选择器不够精准导致的。
具体修复步骤:
使用适配当前YouTube结构的精准选择器
当前YouTube频道视频页中,视频标题的标准选择器是#video-title,视频链接的选择器为a#thumbnail,替换你原有的h3和a选择器,避免匹配无关元素或找不到目标元素。添加空值校验
在访问元素属性前,先判断元素是否存在,防止因null触发报错。替换固定延迟为Puppeteer原生等待方法
移除await delay(5000),改用waitForSelector等待目标元素加载完成,比固定延迟更可靠。
修改后的完整代码:
async function initiate() { const browser = await puppeteer.launch({ headless: false, defaultViewport: null, userDataDir: './userdata', executablePath: 'C:\\Program Files\\Google\\Chrome\\Application\\chrome.exe' }); const page = await browser.newPage(); page.setDefaultNavigationTimeout(0); await page.goto('https://www.youtube.com/@ProthomAlo/videos', { waitUntil: 'networkidle2' }); // 等待视频元素加载完成,替换固定延迟 await page.waitForSelector('.style-scope.ytd-rich-grid-media', { timeout: 10000 }); if (!fs.existsSync('storeLink.txt')) { fs.writeFileSync("storeLink.txt", ''); } const articleLinkarr = (fs.readFileSync('storeLink.txt', { encoding: 'utf8' })).split('\n').filter(link => link.trim() !== ''); // 过滤空行 const articles = await page.evaluate((articleLinkarr) => { const arrObj = []; const videoElements = document.querySelectorAll('.style-scope.ytd-rich-grid-media'); for (const video of videoElements) { // 获取标题元素并校验 const titleElement = video.querySelector('#video-title'); if (!titleElement) continue; const headline = titleElement.innerText.trim(); // 获取链接元素并校验 const linkElement = video.querySelector('a#thumbnail'); if (!linkElement) continue; const link = 'https://www.youtube.com' + linkElement.getAttribute('href'); // 可选:过滤已爬取的链接 if (!articleLinkarr.includes(link)) { arrObj.push({ articleHeadline: headline, articleLink: link }); } } return arrObj; }, articleLinkarr); // 可选:将新爬取的链接写入文件 // fs.appendFileSync('storeLink.txt', articles.map(item => item.articleLink).join('\n') + '\n'); await browser.close(); }
额外优化建议:
- 遍历元素时使用
for...of循环,比传统for循环更简洁易读。 - 读取存储链接时过滤空行,避免后续判断出现无效值。
- 爬取完成后关闭浏览器,避免资源泄漏。
内容的提问来源于stack exchange,提问作者Lomat Haider
相关产品推荐
相关产品推荐

