diff --git a/docs/api/system-preferences.md b/docs/api/system-preferences.md index 1a4806033a14..1c4512bc6a7f 100644 --- a/docs/api/system-preferences.md +++ b/docs/api/system-preferences.md @@ -2,7 +2,7 @@ > Get system preferences. -Process: [Main](../glossary.md#main-process) +Process: [Main](../glossary.md#main-process), [Utility](../glossary.md#utility-process) ```js const { systemPreferences } = require('electron') diff --git a/filenames.auto.gni b/filenames.auto.gni index f2fd8216eb21..a9a4f6d7c09c 100644 --- a/filenames.auto.gni +++ b/filenames.auto.gni @@ -350,6 +350,7 @@ auto_filenames = { utility_bundle_deps = [ "lib/browser/api/net-fetch.ts", + "lib/browser/api/system-preferences.ts", "lib/browser/message-port-main.ts", "lib/common/api/net-client-request.ts", "lib/common/define-properties.ts", diff --git a/lib/utility/api/module-list.ts b/lib/utility/api/module-list.ts index 9d6670217e92..c501cca7ce9b 100644 --- a/lib/utility/api/module-list.ts +++ b/lib/utility/api/module-list.ts @@ -1,4 +1,5 @@ // Utility side modules, please sort alphabetically. export const utilityNodeModuleList: ElectronInternal.ModuleEntry[] = [ - { name: 'net', loader: () => require('./net') } + { name: 'net', loader: () => require('./net') }, + { name: 'systemPreferences', loader: () => require('@electron/internal/browser/api/system-preferences') } ]; diff --git a/shell/browser/api/electron_api_system_preferences_win.cc b/shell/browser/api/electron_api_system_preferences_win.cc index 3ebeea47977b..b510c9683b92 100644 --- a/shell/browser/api/electron_api_system_preferences_win.cc +++ b/shell/browser/api/electron_api_system_preferences_win.cc @@ -159,6 +159,8 @@ std::string SystemPreferences::GetMediaAccessStatus( } void SystemPreferences::InitializeWindow() { + if (electron::IsUtilityProcess()) + return; // Wait until app is ready before creating sys color listener // Creating this listener before the app is ready causes global shortcuts // to not fire diff --git a/shell/common/node_bindings.cc b/shell/common/node_bindings.cc index 25abcc205399..1abcaa0a3042 100644 --- a/shell/common/node_bindings.cc +++ b/shell/common/node_bindings.cc @@ -100,9 +100,10 @@ V(electron_renderer_ipc) \ V(electron_renderer_web_frame) -#define ELECTRON_UTILITY_BINDINGS(V) \ - V(electron_browser_event_emitter) \ - V(electron_common_net) \ +#define ELECTRON_UTILITY_BINDINGS(V) \ + V(electron_browser_event_emitter) \ + V(electron_browser_system_preferences) \ + V(electron_common_net) \ V(electron_utility_parent_port) #define ELECTRON_TESTING_BINDINGS(V) V(electron_common_testing) diff --git a/spec/api-utility-process-spec.ts b/spec/api-utility-process-spec.ts index 3694e2c1adf9..9ee9a3595ad0 100644 --- a/spec/api-utility-process-spec.ts +++ b/spec/api-utility-process-spec.ts @@ -7,6 +7,7 @@ import { closeWindow } from './lib/window-helpers'; import { once } from 'node:events'; import { pathToFileURL } from 'node:url'; import { setImmediate } from 'node:timers/promises'; +import { systemPreferences } from 'electron'; const fixturesPath = path.resolve(__dirname, 'fixtures', 'api', 'utility-process'); const isWindowsOnArm = process.platform === 'win32' && process.arch === 'arm64'; @@ -404,6 +405,18 @@ describe('utilityProcess module', () => { expect(output).to.include(result); }); + ifit(process.platform !== 'linux')('can access exposed main process modules from the utility process', async () => { + const message = 'Message from utility process'; + const child = utilityProcess.fork(path.join(fixturesPath, 'expose-main-process-module.js')); + await once(child, 'spawn'); + child.postMessage(message); + const [data] = await once(child, 'message'); + expect(data).to.equal(systemPreferences.getMediaAccessStatus('screen')); + const exit = once(child, 'exit'); + expect(child.kill()).to.be.true(); + await exit; + }); + it('can establish communication channel with sandboxed renderer', async () => { const result = 'Message from sandboxed renderer'; const w = new BrowserWindow({ diff --git a/spec/fixtures/api/utility-process/expose-main-process-module.js b/spec/fixtures/api/utility-process/expose-main-process-module.js new file mode 100644 index 000000000000..86669cb1ea19 --- /dev/null +++ b/spec/fixtures/api/utility-process/expose-main-process-module.js @@ -0,0 +1,6 @@ +const { systemPreferences } = require('electron'); + +const status = systemPreferences.getMediaAccessStatus('screen'); +process.parentPort.on('message', () => { + process.parentPort.postMessage(status); +});