Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: add --enable-api-filtering-logging command-line switch #20335

Merged
merged 1 commit into from Oct 4, 2019
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
2 changes: 1 addition & 1 deletion docs/README.md
Expand Up @@ -108,7 +108,7 @@ These individual tutorials expand on topics discussed in the guide above.

* [Synopsis](api/synopsis.md)
* [Process Object](api/process.md)
* [Supported Chrome Command Line Switches](api/chrome-command-line-switches.md)
* [Supported Command Line Switches](api/command-line-switches.md)
* [Environment Variables](api/environment-variables.md)
* [Breaking API Changes](api/breaking-changes.md)

Expand Down
2 changes: 1 addition & 1 deletion docs/api/app.md
Expand Up @@ -683,7 +683,7 @@ Overrides the current application's name.

Returns `String` - The current application locale. Possible return values are documented [here](locales.md).

To set the locale, you'll want to use a command line switch at app startup, which may be found [here](https://github.com/electron/electron/blob/master/docs/api/chrome-command-line-switches.md).
To set the locale, you'll want to use a command line switch at app startup, which may be found [here](https://github.com/electron/electron/blob/master/docs/api/command-line-switches.md).

**Note:** When distributing your packaged app, you have to also ship the
`locales` folder.
Expand Down
@@ -1,4 +1,4 @@
# Supported Chrome Command Line Switches
# Supported Command Line Switches

> Command line switches supported by Electron.

Expand Down Expand Up @@ -181,6 +181,17 @@ logging level for all code in the source files under a `foo/bar` directory.

This switch only works when `--enable-logging` is also passed.

## --enable-api-filtering-logging

Enables caller stack logging for the following APIs (filtering events):
- `desktopCapturer.getSources()` / `desktop-capturer-get-sources`
- `remote.require()` / `remote-require`
- `remote.getGlobal()` / `remote-get-builtin`
- `remote.getBuiltin()` / `remote-get-global`
- `remote.getCurrentWindow()` / `remote-get-current-window`
- `remote.getCurrentWebContents()` / `remote-get-current-web-contents`
- `remote.getGuestWebContents()` / `remote-get-guest-web-contents`

## --no-sandbox

Disables Chromium sandbox, which is now enabled by default.
Expand Down
2 changes: 1 addition & 1 deletion docs/api/command-line.md
Expand Up @@ -12,7 +12,7 @@ app.commandLine.hasSwitch('disable-gpu')
```

For more information on what kinds of flags and switches you can use, check
out the [Chrome Command Line Switches](./chrome-command-line-switches.md)
out the [Command Line Switches](./command-line-switches.md)
document.

### Instance Methods
Expand Down
2 changes: 1 addition & 1 deletion docs/api/net-log.md
Expand Up @@ -15,7 +15,7 @@ app.on('ready', async () => {
})
```

See [`--log-net-log`](chrome-command-line-switches.md#--log-net-logpath) to log network events throughout the app's lifecycle.
See [`--log-net-log`](command-line-switches.md#--log-net-logpath) to log network events throughout the app's lifecycle.

**Note:** All methods unless specified can only be used after the `ready` event
of the `app` module gets emitted.
Expand Down
2 changes: 1 addition & 1 deletion filenames.auto.gni
Expand Up @@ -9,9 +9,9 @@ auto_filenames = {
"docs/api/browser-view.md",
"docs/api/browser-window-proxy.md",
"docs/api/browser-window.md",
"docs/api/chrome-command-line-switches.md",
"docs/api/client-request.md",
"docs/api/clipboard.md",
"docs/api/command-line-switches.md",
"docs/api/command-line.md",
"docs/api/content-tracing.md",
"docs/api/cookies.md",
Expand Down
26 changes: 19 additions & 7 deletions lib/browser/remote/server.ts
Expand Up @@ -383,6 +383,12 @@ const emitCustomEvent = function (contents: electron.WebContents, eventName: str
return event
}

const logStack = function (contents: electron.WebContents, code: string, stack: string | undefined) {
if (stack) {
console.warn(`WebContents (${contents.id}): ${code}`, stack)
}
}

handleRemoteCommand('ELECTRON_BROWSER_WRONG_CONTEXT_ERROR', function (event, contextId, passedContextId, id) {
const objectId = [passedContextId, id]
if (!rendererFunctions.has(objectId)) {
Expand All @@ -392,7 +398,8 @@ handleRemoteCommand('ELECTRON_BROWSER_WRONG_CONTEXT_ERROR', function (event, con
removeRemoteListenersAndLogWarning(event.sender, rendererFunctions.get(objectId))
})

handleRemoteCommand('ELECTRON_BROWSER_REQUIRE', function (event, contextId, moduleName) {
handleRemoteCommand('ELECTRON_BROWSER_REQUIRE', function (event, contextId, moduleName, stack) {
logStack(event.sender, `remote.require('${moduleName}')`, stack)
const customEvent = emitCustomEvent(event.sender, 'remote-require', moduleName)

if (customEvent.returnValue === undefined) {
Expand All @@ -406,7 +413,8 @@ handleRemoteCommand('ELECTRON_BROWSER_REQUIRE', function (event, contextId, modu
return valueToMeta(event.sender, contextId, customEvent.returnValue)
})

handleRemoteCommand('ELECTRON_BROWSER_GET_BUILTIN', function (event, contextId, moduleName) {
handleRemoteCommand('ELECTRON_BROWSER_GET_BUILTIN', function (event, contextId, moduleName, stack) {
logStack(event.sender, `remote.getBuiltin('${moduleName}')`, stack)
const customEvent = emitCustomEvent(event.sender, 'remote-get-builtin', moduleName)

if (customEvent.returnValue === undefined) {
Expand All @@ -420,7 +428,8 @@ handleRemoteCommand('ELECTRON_BROWSER_GET_BUILTIN', function (event, contextId,
return valueToMeta(event.sender, contextId, customEvent.returnValue)
})

handleRemoteCommand('ELECTRON_BROWSER_GLOBAL', function (event, contextId, globalName) {
handleRemoteCommand('ELECTRON_BROWSER_GLOBAL', function (event, contextId, globalName, stack) {
logStack(event.sender, `remote.getGlobal('${globalName}')`, stack)
const customEvent = emitCustomEvent(event.sender, 'remote-get-global', globalName)

if (customEvent.returnValue === undefined) {
Expand All @@ -434,7 +443,8 @@ handleRemoteCommand('ELECTRON_BROWSER_GLOBAL', function (event, contextId, globa
return valueToMeta(event.sender, contextId, customEvent.returnValue)
})

handleRemoteCommand('ELECTRON_BROWSER_CURRENT_WINDOW', function (event, contextId) {
handleRemoteCommand('ELECTRON_BROWSER_CURRENT_WINDOW', function (event, contextId, stack) {
logStack(event.sender, 'remote.getCurrentWindow()', stack)
const customEvent = emitCustomEvent(event.sender, 'remote-get-current-window')

if (customEvent.returnValue === undefined) {
Expand All @@ -448,7 +458,8 @@ handleRemoteCommand('ELECTRON_BROWSER_CURRENT_WINDOW', function (event, contextI
return valueToMeta(event.sender, contextId, customEvent.returnValue)
})

handleRemoteCommand('ELECTRON_BROWSER_CURRENT_WEB_CONTENTS', function (event, contextId) {
handleRemoteCommand('ELECTRON_BROWSER_CURRENT_WEB_CONTENTS', function (event, contextId, stack) {
logStack(event.sender, 'remote.getCurrentWebContents()', stack)
const customEvent = emitCustomEvent(event.sender, 'remote-get-current-web-contents')

if (customEvent.returnValue === undefined) {
Expand Down Expand Up @@ -549,14 +560,15 @@ handleRemoteCommand('ELECTRON_BROWSER_CONTEXT_RELEASE', (event, contextId) => {
return null
})

handleRemoteCommand('ELECTRON_BROWSER_GUEST_WEB_CONTENTS', function (event, contextId, guestInstanceId) {
handleRemoteCommand('ELECTRON_BROWSER_GUEST_WEB_CONTENTS', function (event, contextId, guestInstanceId, stack) {
logStack(event.sender, 'remote.getGuestWebContents()', stack)
const guest = guestViewManager.getGuestForWebContents(guestInstanceId, event.sender)

const customEvent = emitCustomEvent(event.sender, 'remote-get-guest-web-contents', guest)

if (customEvent.returnValue === undefined) {
if (customEvent.defaultPrevented) {
throw new Error(`Blocked remote.getGuestForWebContents()`)
throw new Error(`Blocked remote.getGuestWebContents()`)
} else {
customEvent.returnValue = guest
}
Expand Down
11 changes: 9 additions & 2 deletions lib/browser/rpc-server.js
Expand Up @@ -23,6 +23,12 @@ const emitCustomEvent = function (contents, eventName, ...args) {
return event
}

const logStack = function (contents, code, stack) {
if (stack) {
console.warn(`WebContents (${contents.id}): ${code}`, stack)
}
}

// Implements window.close()
ipcMainInternal.on('ELECTRON_BROWSER_WINDOW_CLOSE', function (event) {
const window = event.sender.getOwnerBrowserWindow()
Expand Down Expand Up @@ -63,15 +69,16 @@ ipcMainUtils.handleSync('ELECTRON_BROWSER_CLIPBOARD', function (event, method, .
if (features.isDesktopCapturerEnabled()) {
const desktopCapturer = require('@electron/internal/browser/desktop-capturer')

ipcMainInternal.handle('ELECTRON_BROWSER_DESKTOP_CAPTURER_GET_SOURCES', function (event, ...args) {
ipcMainInternal.handle('ELECTRON_BROWSER_DESKTOP_CAPTURER_GET_SOURCES', function (event, options, stack) {
logStack(event.sender, 'desktopCapturer.getSources()', stack)
const customEvent = emitCustomEvent(event.sender, 'desktop-capturer-get-sources')

if (customEvent.defaultPrevented) {
console.error('Blocked desktopCapturer.getSources()')
return []
}

return desktopCapturer.getSources(event, ...args)
return desktopCapturer.getSources(event, options)
})
}

Expand Down
14 changes: 13 additions & 1 deletion lib/renderer/api/desktop-capturer.ts
@@ -1,12 +1,24 @@
import { nativeImage } from 'electron'
import { ipcRendererInternal } from '@electron/internal/renderer/ipc-renderer-internal'

const { hasSwitch } = process.electronBinding('command_line')

// |options.types| can't be empty and must be an array
function isValid (options: Electron.SourcesOptions) {
const types = options ? options.types : undefined
return Array.isArray(types)
}

const enableStacks = hasSwitch('enable-api-filtering-logging')

function getCurrentStack () {
const target = {}
if (enableStacks) {
Error.captureStackTrace(target, getCurrentStack)
}
return (target as any).stack
}

export async function getSources (options: Electron.SourcesOptions) {
if (!isValid(options)) throw new Error('Invalid options')

Expand All @@ -21,7 +33,7 @@ export async function getSources (options: Electron.SourcesOptions) {
captureScreen,
thumbnailSize,
fetchWindowIcons
} as ElectronInternal.GetSourcesOptions)
} as ElectronInternal.GetSourcesOptions, getCurrentStack())

return sources.map(source => ({
id: source.id,
Expand Down
23 changes: 17 additions & 6 deletions lib/renderer/api/remote.js
@@ -1,6 +1,7 @@
'use strict'

const v8Util = process.electronBinding('v8_util')
const { hasSwitch } = process.electronBinding('command_line')

const { CallbacksRegistry } = require('@electron/internal/renderer/remote/callbacks-registry')
const bufferUtils = require('@electron/internal/common/remote/buffer-utils')
Expand Down Expand Up @@ -281,6 +282,16 @@ function handleMessage (channel, handler) {
})
}

const enableStacks = hasSwitch('enable-api-filtering-logging')

function getCurrentStack () {
const target = {}
if (enableStacks) {
Error.captureStackTrace(target, getCurrentStack)
}
return target.stack
}

// Browser calls a callback in renderer.
handleMessage('ELECTRON_RENDERER_CALLBACK', (id, args) => {
callbacksRegistry.apply(id, metaToValue(args))
Expand All @@ -293,34 +304,34 @@ handleMessage('ELECTRON_RENDERER_RELEASE_CALLBACK', (id) => {

exports.require = (module) => {
const command = 'ELECTRON_BROWSER_REQUIRE'
const meta = ipcRendererInternal.sendSync(command, contextId, module)
const meta = ipcRendererInternal.sendSync(command, contextId, module, getCurrentStack())
return metaToValue(meta)
}

// Alias to remote.require('electron').xxx.
exports.getBuiltin = (module) => {
const command = 'ELECTRON_BROWSER_GET_BUILTIN'
const meta = ipcRendererInternal.sendSync(command, contextId, module)
const meta = ipcRendererInternal.sendSync(command, contextId, module, getCurrentStack())
return metaToValue(meta)
}

exports.getCurrentWindow = () => {
const command = 'ELECTRON_BROWSER_CURRENT_WINDOW'
const meta = ipcRendererInternal.sendSync(command, contextId)
const meta = ipcRendererInternal.sendSync(command, contextId, getCurrentStack())
return metaToValue(meta)
}

// Get current WebContents object.
exports.getCurrentWebContents = () => {
const command = 'ELECTRON_BROWSER_CURRENT_WEB_CONTENTS'
const meta = ipcRendererInternal.sendSync(command, contextId)
const meta = ipcRendererInternal.sendSync(command, contextId, getCurrentStack())
return metaToValue(meta)
}

// Get a global object in browser.
exports.getGlobal = (name) => {
const command = 'ELECTRON_BROWSER_GLOBAL'
const meta = ipcRendererInternal.sendSync(command, contextId, name)
const meta = ipcRendererInternal.sendSync(command, contextId, name, getCurrentStack())
return metaToValue(meta)
}

Expand All @@ -339,7 +350,7 @@ exports.createFunctionWithReturnValue = (returnValue) => {
// Get the guest WebContents from guestInstanceId.
exports.getGuestWebContents = (guestInstanceId) => {
const command = 'ELECTRON_BROWSER_GUEST_WEB_CONTENTS'
const meta = ipcRendererInternal.sendSync(command, contextId, guestInstanceId)
const meta = ipcRendererInternal.sendSync(command, contextId, guestInstanceId, getCurrentStack())
return metaToValue(meta)
}

Expand Down
8 changes: 4 additions & 4 deletions shell/browser/atom_browser_client.cc
Expand Up @@ -533,10 +533,10 @@ void AtomBrowserClient::AppendExtraCommandLineSwitches(

// Copy following switches to child process.
static const char* const kCommonSwitchNames[] = {
switches::kStandardSchemes, switches::kEnableSandbox,
switches::kSecureSchemes, switches::kBypassCSPSchemes,
switches::kCORSSchemes, switches::kFetchSchemes,
switches::kServiceWorkerSchemes};
switches::kStandardSchemes, switches::kEnableSandbox,
switches::kSecureSchemes, switches::kBypassCSPSchemes,
switches::kCORSSchemes, switches::kFetchSchemes,
switches::kServiceWorkerSchemes, switches::kEnableApiFilteringLogging};
command_line->CopySwitchesFrom(*base::CommandLine::ForCurrentProcess(),
kCommonSwitchNames,
base::size(kCommonSwitchNames));
Expand Down
2 changes: 2 additions & 0 deletions shell/common/options_switches.cc
Expand Up @@ -220,6 +220,8 @@ const char kAppUserModelId[] = "app-user-model-id";
// The application path
const char kAppPath[] = "app-path";

const char kEnableApiFilteringLogging[] = "enable-api-filtering-logging";

// The command line switch versions of the options.
const char kBackgroundColor[] = "background-color";
const char kPreloadScript[] = "preload";
Expand Down
1 change: 1 addition & 0 deletions shell/common/options_switches.h
Expand Up @@ -107,6 +107,7 @@ extern const char kFetchSchemes[];
extern const char kCORSSchemes[];
extern const char kAppUserModelId[];
extern const char kAppPath[];
extern const char kEnableApiFilteringLogging[];

extern const char kBackgroundColor[];
extern const char kPreloadScript[];
Expand Down
4 changes: 2 additions & 2 deletions spec/ts-smoke/electron/main.ts
Expand Up @@ -356,8 +356,8 @@ app.on('ready', () => {
window.loadURL('https://github.com')
})

// Supported Chrome command line switches
// https://github.com/atom/electron/blob/master/docs/api/chrome-command-line-switches.md
// Supported command line switches
// https://github.com/atom/electron/blob/master/docs/api/command-line-switches.md

app.commandLine.appendSwitch('remote-debugging-port', '8315')
app.commandLine.appendSwitch('host-rules', 'MAP * 127.0.0.1')
Expand Down
2 changes: 1 addition & 1 deletion spec/webview-spec.js
Expand Up @@ -1052,7 +1052,7 @@ describe('<webview> tag', function () {
await loadWebView(webview, { src })

ipcRenderer.send('handle-next-remote-get-guest-web-contents')
expect(() => webview.getWebContents()).to.throw('Blocked remote.getGuestForWebContents()')
expect(() => webview.getWebContents()).to.throw('Blocked remote.getGuestWebContents()')
})
})

Expand Down