fix: UtilityProcess.fork crash before app ready (#46403)

fix: UtilityProcess.fork crash before app ready

Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com>
Co-authored-by: Shelley Vohr <shelley.vohr@gmail.com>
This commit is contained in:
trop[bot] 2025-04-01 14:09:16 -04:00 committed by GitHub
parent d0658ccc98
commit 13488d3c98
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
3 changed files with 42 additions and 0 deletions

View file

@ -44,6 +44,8 @@ Process: [Main](../glossary.md#main-process)<br />
Returns [`UtilityProcess`](utility-process.md#class-utilityprocess) Returns [`UtilityProcess`](utility-process.md#class-utilityprocess)
**Note:** `utilityProcess.fork` can only be called after the `ready` event has been emitted on `App`.
## Class: UtilityProcess ## Class: UtilityProcess
> Instances of the `UtilityProcess` represent the Chromium spawned child process > Instances of the `UtilityProcess` represent the Chromium spawned child process

View file

@ -21,11 +21,13 @@
#include "gin/object_template_builder.h" #include "gin/object_template_builder.h"
#include "mojo/public/cpp/bindings/pending_receiver.h" #include "mojo/public/cpp/bindings/pending_receiver.h"
#include "shell/browser/api/message_port.h" #include "shell/browser/api/message_port.h"
#include "shell/browser/browser.h"
#include "shell/browser/javascript_environment.h" #include "shell/browser/javascript_environment.h"
#include "shell/browser/net/system_network_context_manager.h" #include "shell/browser/net/system_network_context_manager.h"
#include "shell/common/gin_converters/callback_converter.h" #include "shell/common/gin_converters/callback_converter.h"
#include "shell/common/gin_converters/file_path_converter.h" #include "shell/common/gin_converters/file_path_converter.h"
#include "shell/common/gin_helper/dictionary.h" #include "shell/common/gin_helper/dictionary.h"
#include "shell/common/gin_helper/error_thrower.h"
#include "shell/common/gin_helper/object_template_builder.h" #include "shell/common/gin_helper/object_template_builder.h"
#include "shell/common/node_includes.h" #include "shell/common/node_includes.h"
#include "shell/common/v8_util.h" #include "shell/common/v8_util.h"
@ -412,6 +414,13 @@ raw_ptr<UtilityProcessWrapper> UtilityProcessWrapper::FromProcessId(
// static // static
gin::Handle<UtilityProcessWrapper> UtilityProcessWrapper::Create( gin::Handle<UtilityProcessWrapper> UtilityProcessWrapper::Create(
gin::Arguments* args) { gin::Arguments* args) {
if (!Browser::Get()->is_ready()) {
gin_helper::ErrorThrower(args->isolate())
.ThrowTypeError(
"utilityProcess cannot be created before app is ready.");
return {};
}
gin_helper::Dictionary dict; gin_helper::Dictionary dict;
if (!args->GetNext(&dict)) { if (!args->GetNext(&dict)) {
args->ThrowTypeError("Options must be an object."); args->ThrowTypeError("Options must be an object.");

View file

@ -0,0 +1,31 @@
const { app, BrowserWindow, utilityProcess } = require('electron');
const path = require('node:path');
function createWindow () {
const mainWindow = new BrowserWindow();
mainWindow.loadFile('about:blank');
}
app.whenReady().then(() => {
createWindow();
app.on('activate', function () {
if (BrowserWindow.getAllWindows().length === 0) createWindow();
});
});
app.on('window-all-closed', function () {
if (process.platform !== 'darwin') app.quit();
});
try {
utilityProcess.fork(path.join(__dirname, 'utility.js'));
} catch (e) {
if (/utilityProcess cannot be created before app is ready/.test(e.message)) {
app.exit(0);
} else {
console.error(e);
app.exit(1);
}
}