refactor: use ipcMainUtils.invokeInWebContents / ipcRendererUtils.handle helpers for Chrome APIs (#17417)

This commit is contained in:
Milan Burda 2019-03-26 03:38:35 +01:00 committed by Cheng Zhao
parent 546466b209
commit 336db33d18
9 changed files with 82 additions and 99 deletions

View file

@ -3,7 +3,6 @@
const { app, webContents, BrowserWindow } = require('electron')
const { getAllWebContents } = process.electronBinding('web_contents')
const renderProcessPreferences = process.electronBinding('render_process_preferences').forAllWebContents()
const { ipcMainInternal } = require('@electron/internal/browser/ipc-main-internal')
const ipcMainUtils = require('@electron/internal/browser/ipc-main-internal-utils')
const { Buffer } = require('buffer')
@ -29,6 +28,10 @@ const isWindowOrWebView = function (webContents) {
return type === 'window' || type === 'webview'
}
const isBackgroundPage = function (webContents) {
return webContents.getType() === 'backgroundPage'
}
// Create or get manifest object from |srcDirectory|.
const getManifestFromPath = function (srcDirectory) {
let manifest
@ -94,7 +97,6 @@ const startBackgroundPages = function (manifest) {
const contents = webContents.create({
partition: 'persist:__chrome_extension',
isBackgroundPage: true,
commandLineSwitches: ['--background-page'],
sandbox: true,
enableRemoteModule: false
})
@ -156,21 +158,26 @@ const hookWebContentsEvents = function (webContents) {
// Handle the chrome.* API messages.
let nextId = 0
ipcMainInternal.on('CHROME_RUNTIME_CONNECT', function (event, extensionId, connectInfo) {
const page = backgroundPages[extensionId]
if (!page) {
console.error(`Connect to unknown extension ${extensionId}`)
return
ipcMainUtils.handle('CHROME_RUNTIME_CONNECT', function (event, extensionId, connectInfo) {
if (isBackgroundPage(event.sender)) {
throw new Error('chrome.runtime.connect is not supported in background page')
}
const page = backgroundPages[extensionId]
if (!page) {
throw new Error(`Connect to unknown extension ${extensionId}`)
}
const tabId = page.webContents.id
const portId = ++nextId
event.returnValue = { tabId: page.webContents.id, portId: portId }
event.sender.once('render-view-deleted', () => {
if (page.webContents.isDestroyed()) return
page.webContents._sendInternalToAll(`CHROME_PORT_DISCONNECT_${portId}`)
})
page.webContents._sendInternalToAll(`CHROME_RUNTIME_ONCONNECT_${extensionId}`, event.sender.id, portId, connectInfo)
return { tabId, portId }
})
ipcMainUtils.handle('CHROME_EXTENSION_MANIFEST', function (event, extensionId) {
@ -181,35 +188,28 @@ ipcMainUtils.handle('CHROME_EXTENSION_MANIFEST', function (event, extensionId) {
return manifest
})
let resultID = 1
ipcMainInternal.on('CHROME_RUNTIME_SENDMESSAGE', function (event, extensionId, message, originResultID) {
ipcMainUtils.handle('CHROME_RUNTIME_SEND_MESSAGE', async function (event, extensionId, message) {
if (isBackgroundPage(event.sender)) {
throw new Error('chrome.runtime.sendMessage is not supported in background page')
}
const page = backgroundPages[extensionId]
if (!page) {
console.error(`Connect to unknown extension ${extensionId}`)
return
throw new Error(`Connect to unknown extension ${extensionId}`)
}
page.webContents._sendInternalToAll(`CHROME_RUNTIME_ONMESSAGE_${extensionId}`, event.sender.id, message, resultID)
ipcMainInternal.once(`CHROME_RUNTIME_ONMESSAGE_RESULT_${resultID}`, (resultEvent, result) => {
event._replyInternal(`CHROME_RUNTIME_SENDMESSAGE_RESULT_${originResultID}`, result)
})
resultID++
return ipcMainUtils.invokeInWebContents(page.webContents, true, `CHROME_RUNTIME_ONMESSAGE_${extensionId}`, event.sender.id, message)
})
ipcMainInternal.on('CHROME_TABS_SEND_MESSAGE', function (event, tabId, extensionId, isBackgroundPage, message, originResultID) {
ipcMainUtils.handle('CHROME_TABS_SEND_MESSAGE', async function (event, tabId, extensionId, message) {
const contents = webContents.fromId(tabId)
if (!contents) {
console.error(`Sending message to unknown tab ${tabId}`)
return
throw new Error(`Sending message to unknown tab ${tabId}`)
}
const senderTabId = isBackgroundPage ? null : event.sender.id
const senderTabId = isBackgroundPage(event.sender) ? null : event.sender.id
contents._sendInternalToAll(`CHROME_RUNTIME_ONMESSAGE_${extensionId}`, senderTabId, message, resultID)
ipcMainInternal.once(`CHROME_RUNTIME_ONMESSAGE_RESULT_${resultID}`, (resultEvent, result) => {
event._replyInternal(`CHROME_TABS_SEND_MESSAGE_RESULT_${originResultID}`, result)
})
resultID++
return ipcMainUtils.invokeInWebContents(contents, true, `CHROME_RUNTIME_ONMESSAGE_${extensionId}`, senderTabId, message)
})
const getLanguage = () => {
@ -301,17 +301,20 @@ const isChromeExtension = function (pageURL) {
return protocol === 'chrome-extension:'
}
ipcMainInternal.on('CHROME_TABS_EXECUTESCRIPT', function (event, requestId, tabId, extensionId, details) {
const pageURL = event.sender._getURL()
const assertChromeExtension = function (contents, api) {
const pageURL = contents._getURL()
if (!isChromeExtension(pageURL)) {
console.error(`Blocked ${pageURL} from calling chrome.tabs.executeScript()`)
return
console.error(`Blocked ${pageURL} from calling ${api}`)
throw new Error(`Blocked ${api}`)
}
}
ipcMainUtils.handle('CHROME_TABS_EXECUTE_SCRIPT', async function (event, tabId, extensionId, details) {
assertChromeExtension(event.sender, 'chrome.tabs.executeScript()')
const contents = webContents.fromId(tabId)
if (!contents) {
console.error(`Sending message to unknown tab ${tabId}`)
return
throw new Error(`Sending message to unknown tab ${tabId}`)
}
let code, url
@ -324,7 +327,7 @@ ipcMainInternal.on('CHROME_TABS_EXECUTESCRIPT', function (event, requestId, tabI
url = `chrome-extension://${extensionId}/${String(Math.random()).substr(2, 8)}.js`
}
contents._sendInternal('CHROME_TABS_EXECUTESCRIPT', event.sender.id, requestId, extensionId, url, code)
return ipcMainUtils.invokeInWebContents(contents, false, 'CHROME_TABS_EXECUTE_SCRIPT', extensionId, url, code)
})
// Transfer the content scripts to renderer.