Enforce sandbox on all spawned BrowserWindow objects

The docs (https://www.atom.pe/docs/api/sandbox-option/) say we should be using the browser-native `window.open` implementation, but in practice that appears very much false. Electron, no matter our set of options, appears to always make a hit to the ipcRenderer with `window.open` calls, causing the calling code to explode due to the sandbox making that impossible.

By using `app.enableSandbox()`, it puts the sandbox in place over all BrowserWindow objects, including the temporary ones which empirically are being created for `window.open`. We do not need to specify `sandbox: true` to the BrowserWindow with this approach, though uncommenting and therefore reintroducing the flag causes our lovely ipcRenderer error again.

As far as I can tell, the sandbox does actually get applied to the window though the fact that `sandbox: true` still does things despite the docs saying otherwise leaves me a bit uncomfortable.

Fixes https://github.com/vector-im/riot-web/issues/13719
This commit is contained in:
Travis Ralston 2020-05-20 16:16:57 -06:00
parent f9c8aa1753
commit 0269501d4f

View file

@ -615,6 +615,17 @@ protocol.registerSchemesAsPrivileged([{
}, },
}]); }]);
// Turn the sandbox on for *all* windows we might generate. Doing this means we don't
// have to specify a `sandbox: true` to each BrowserWindow.
//
// This also fixes an issue with window.open where if we only specified the sandbox
// on the main window we'd run into cryptic "ipc_renderer be broke" errors. Turns out
// it's trying to jump the sandbox and make some calls into electron, which it can't
// do when half of it is sandboxed. By turning on the sandbox for everything, the new
// window (no matter how temporary it may be) is also sandboxed, allowing for a clean
// transition into the user's browser.
app.enableSandbox();
app.on('ready', async () => { app.on('ready', async () => {
try { try {
await setupGlobals(); await setupGlobals();
@ -725,7 +736,7 @@ app.on('ready', async () => {
webPreferences: { webPreferences: {
preload: preloadScript, preload: preloadScript,
nodeIntegration: false, nodeIntegration: false,
sandbox: true, //sandbox: true, // We enable sandboxing from app.enableSandbox() above
enableRemoteModule: false, enableRemoteModule: false,
// We don't use this: it's useful for the preload script to // We don't use this: it's useful for the preload script to
// share a context with the main page so we can give select // share a context with the main page so we can give select