如何在 NodeJS 中使用 PhantomJS 模拟页面上的鼠标悬停或 运行 JS 功能

How to emulate mouseover or run JS function on page with PhantomJS in NodeJS

NodeJS、PhantomJS、使用 Cheerio 进行内容解析

需要解析包含动态加载的网页div(提示)。该事件可以在许多 table td 上进行,这里是一个例子

当我 'mouseover' 在特定的 td 上看到这个带有数据的橙色块时​​,它动态加载了函数,就像这样

onmouseover="page.hist(this,'P-0.00-0-0','355svxv498x0x0',417,event,0,1)"

我只能在页面加载后才能查看此信息。需要特定的行,只有 Marathonbet。

当函数 运行s 时,文本被加载到另一个 div (id='tooltip') 并显示给用户。

我使用 phantom 来解析此页面的内容,静态值一切正常,但我如何才能将这个动态生成的块接收到我在节点路由器内呈现的网页? 我看到两种方式:

  1. 在此坐标上模拟鼠标移动以显示所需的文本,但是 有问题,我怎么知道它的坐标?
  2. 在页面加载后开始模拟功能,我知道他们编码 ('355svxv498x0x0',417),但是我如何 运行 来自节点的这个函数, 来自幻影?

    这是一些代码,可以在我的路由器中接收静态页面内容

```

phantom.create(config.phantomParams).then(ph => {
    _ph = ph;
    return _ph.createPage();
}).then(page => {
    _page = page;
    return _page.on('onConsoleMessage', function (msg) {
        console.log(msg);
    });
}).then(() => {
    return _page.on('viewportSize', {width: 1920, height: 1080});
}).then(() => {
    return _page.on('dpi', 130)
}).then(() => {
    _page.setting('userAgent', config.userAgent);
    return _page.open(matchLink);
}).then(() => {
    return _page.property('content');
}).then(content => {
    let $ = cheerio.load(content);

    // working with content and get needed elements

    console.log($.html());
}).then(() => {
    _page.close();
    _ph.exit();
});

``` 我应该使用 Casper/Spooky,还是任何人都可以解释在这种情况下如何使用它?

更新。尝试使用 puppeteer,代码

```

let matchLink = 'http://www.oddsportal.com/soccer/world/club-friendly/san-carlos-guadalupe-xnsUg7zB/';

(async () => {
    const browser = await puppeteer.launch({
        args: [
            '--proxy-server=46.101.167.43:80',
        ]});
    const page = await browser.newPage();
    await browser.userAgent(config.userAgent);
    await page.setViewport({width: 1440, height: 960});
    await page.goto(matchLink);
    await page.evaluate(() => page.hist(this,'P-0.00-0-0','355svxv464x0x7omg7',381,event,0,1));

    let bodyHTML = await page.evaluate(() => document.body.innerHTML);

    console.log(bodyHTML);
    await page.screenshot({path: 'example.png'});

    await browser.close();
})();

```

得到 ```

(node:8591) UnhandledPromiseRejectionWarning: Error: Evaluation failed: TypeError: Cannot read property 'stopPropagation' of undefined
    at toolTip (http://www.oddsportal.com/res/x/global-180713073352.js:1:145511)
    at TableSet.historyTooltip (http://www.oddsportal.com/res/x/global-180713073352.js:1:631115)
    at PageEvent.PagePrototype.hist (http://www.oddsportal.com/res/x/global-180713073352.js:1:487314)
    at __puppeteer_evaluation_script__:1:13
    at ExecutionContext.evaluateHandle (/home/gil/Projects/oddsbot/node_modules/puppeteer/lib/ExecutionContext.js:97:13)
    at <anonymous>
    at process._tickCallback (internal/process/next_tick.js:188:7)

```

目标 JS 文件错误,可能与请求有关..

既然你对建议持开放态度,我建议 puppeteer 它是一个原生的 node.js 模块,可以在最新的 Chromium 中打开页面(特别有用,因为 PhantomJS 非常过时)并且接近 PhantomJS思考的条件。

如果您还使用 node.js 8.x,async/await 语法可用于处理 promises,它使使用 puppeteer 进行抓取变得轻而易举。

所以 运行 在 puppeteer 中你会 运行

await page.evaluate(() => page.hist(this,'P-0.00-0-0','355svxv498x0x0',417,event,0,1) );

更新

Puppeteer 有很多方便的助手,其中之一是 page.hover,它实际上会将指针悬停在元素上:

await page.hover('td.some_selector');

但是如果您想继续使用 Phantomjs 和出色的 phantom 模块,您可以:

_page.evaluate(function() {
    page.hist(this,'P-0.00-0-0','355svxv498x0x0',417,event,0,1)
})

page.evaluate 上的文档:http://phantomjs.org/api/webpage/method/evaluate.html