Общайтесь " вне " от Хрома через протокол DevTools

У меня есть страница, работающая в безголовом экземпляре Chromium, и я манипулирую ею через протокол DevTools, используя пакет NPM Puppeteer в узле.

я вставляю сценарий на страницу. В какой-то момент я хочу, чтобы скрипт перезвонил мне и отправил мне некоторую информацию (через какое-то событие, отображаемое протоколом DevTools или каким-то другим способом).

каков наилучший способ сделать это? Было бы здорово, если бы это можно было сделать с помощью Кукольника, но я не против получить свои руки грязный и прослушивание протокольных сообщений вручную.

Я знаю, что могу сделать это, манипулируя DOM и слушая изменения DOM, но это не звучит как хорошая идея.

2 ответов


если скрипт отправляет все свои данные в одном вызове, самым простым подходом было бы использовать page.evaluate и вернуть обещание от него:

const dataBack = page.evaluate(`new Promise((resolve, reject) => {                                                  
  setTimeout(() => resolve('some data'), 1000)                                                                      
})`)
dataBack.then(value => { console.log('got data back', value) })

это может быть обобщено для отправки данных в два раза, и т. д. Для отправки произвольного потока событий, возможно console.log было бы немного меньше взлома, чем события DOM? По крайней мере, это супер-легко сделать с кукловодом:

page.on('console', message => {
  if (message.text.startsWith('dataFromMyScript')) {
    message.args[1].jsonValue().then(value => console.log('got data back', value))
  }
})
page.evaluate(`setInterval(() => console.log('dataFromMyScript', {ts: Date.now()}), 1000)`)

(в примере используется префикс magic, чтобы отличить эти сообщения журнала от всех другие.)


хорошо, я обнаружил встроенный способ сделать это в Puppeteer. Puppeteer определяет метод, называемый exposeFunction.

page.exposeFunction(name, puppeteerFunction)

этот метод определяет функцию с заданным именем на