我有一个问题是通过元素的选择器获取元素。
我纠结的一个页面是:http://html5.haxball.com/。我成功的是登录,但这是一种黑客,因为我使用的事实,我需要填写的字段已经被选中。
在输入nick并进入大堂后,我想点击‘创建房间’按钮。其选择器:body>div>div>div>div>div>div>div.buttons>button:nth-child(3)
const puppeteer = require('puppeteer');
(async () => {
const browser = await puppeteer.launch({
args: ['--no-sandbox'], headless: false, slowMo: 10
});
const page = await browser.newPage();
await page.goto('http://html5.haxball.com/index.html');
await page.keyboard.type(name);
await page.keyboard.press('Enter');
//at this point I am logged in.
let buttonSelector = 'body > div > div > div > div > div.buttons > button:nth-child(3)';
await page.waitForSelector('body > div > div');
await page.evaluate(() => {
document.querySelector(buttonSelector).click();
});
browser.close();
})();
运行这样的代码后,我得到错误:
UnhandledPromiseRejectionWarning:错误:计算失败:TypeError:无法读取属性“Click”为null
我最初的方法是:await Page.Click(buttonSelector);而不是page.evaluate,但它也会失败。
最让我沮丧的是这样一个事实:当我在Chromium控制台中运行时:document.queryselector(buttonSelector).click();工作很好。
需要注意的几件事:
>
'button[data-hook=“create”]'
.游戏在iframe
中,因此您最好使用iframe
的document
对象调用document.QuerySelector
而不是使用包含窗口的document
传递给evaluate
的函数是在与运行节点脚本的上下文不同的上下文中执行的。因此,必须将变量从节点脚本显式传递到窗口脚本,否则buttonselector
将未定义:
进行上述更改后,您的代码将输入您的姓名并成功点击“创建房间”:
const puppeteer = require('puppeteer');
(async () => {
const browser = await puppeteer.launch({
args: ['--no-sandbox'], headless: false, slowMo: 10
});
const page = await browser.newPage();
await page.goto('http://html5.haxball.com/index.html');
await page.keyboard.type('Chris');
await page.keyboard.press('Enter');
//at this point I am logged in.
let buttonSelector = 'button[data-hook="create"]';
await page.waitForSelector('body > div > div');
await page.evaluate((buttonSelector) => {
var frame = document.querySelector('iframe');
var frameDocument = frame.contentDocument;
frameDocument.querySelector(buttonSelector).click();
}, buttonSelector);
browser.close();
})();