Backport Failed
This PR was checked and could not be automatically backported to "26-x-y" cleanly
Details
Failed Diff:
diff --cc spec/api-autoupdater-darwin-spec.ts
index 28004cf1e1,373ee884b7..0000000000
--- a/spec/api-autoupdater-darwin-spec.ts
+++ b/spec/api-autoupdater-darwin-spec.ts
@@@ -1,22 -1,18 +1,23 @@@
import { expect } from 'chai';
-import * as cp from 'node:child_process';
-import * as http from 'node:http';
+import * as cp from 'child_process';
+import * as http from 'http';
import * as express from 'express';
import * as fs from 'fs-extra';
++<<<<<<< HEAD
+import * as os from 'os';
+import * as path from 'path';
++=======
+ import * as path from 'node:path';
++>>>>>>> fix: prevent node mode to be used as script runner by other apps
import * as psList from 'ps-list';
-import { AddressInfo } from 'node:net';
+import { AddressInfo } from 'net';
import { ifdescribe, ifit } from './lib/spec-helpers';
+ import { copyApp, getCodesignIdentity, shouldRunCodesignTests, signApp, spawn, withTempDirectory } from './lib/codesign-helpers';
import * as uuid from 'uuid';
-import { autoUpdater, systemPreferences } from 'electron';
+import { systemPreferences } from 'electron';
- const features = process._linkedBinding('electron_common_features');
-
- const fixturesPath = path.resolve(__dirname, 'fixtures');
-
// We can only test the auto updater on darwin non-component builds
- ifdescribe(process.platform === 'darwin' && !(process.env.CI && process.arch === 'arm64') && !process.mas && !features.isComponentBuild())('autoUpdater behavior', function () {
+ ifdescribe(shouldRunCodesignTests)('autoUpdater behavior', function () {
this.timeout(120000);
let identity = '';
@@@ -143,7 -71,13 +74,17 @@@
appPJPath,
(await fs.readFile(appPJPath, 'utf8')).replace('1.0.0', version)
);
++<<<<<<< HEAD
+ await signApp(secondAppPath);
++=======
+ const infoPath = path.resolve(secondAppPath, 'Contents', 'Info.plist');
+ await fs.writeFile(
+ infoPath,
+ (await fs.readFile(infoPath, 'utf8')).replace(/(<key>CFBundleShortVersionString<\/key>\s+<string>)[^<]+/g, `$1${version}`)
+ );
+ await mutateAppPreSign?.mutate(secondAppPath);
+ await signApp(secondAppPath, identity);
++>>>>>>> fix: prevent node mode to be used as script runner by other apps
await mutateAppPostSign?.mutate(secondAppPath);
updateZipPath = path.resolve(dir, 'update.zip');
await spawn('zip', ['-0', '-r', '--symlinks', updateZipPath, './'], {
@@@ -286,9 -218,15 +227,19 @@@
}, fn: (appPath: string, zipPath: string) => Promise<void>) => {
await withTempDirectory(async (dir) => {
const appPath = await copyApp(dir, opts.startFixture);
++<<<<<<< HEAD
+ await signApp(appPath);
++=======
+ await opts.mutateAppPreSign?.mutate(appPath);
+ const infoPath = path.resolve(appPath, 'Contents', 'Info.plist');
+ await fs.writeFile(
+ infoPath,
+ (await fs.readFile(infoPath, 'utf8')).replace(/(<key>CFBundleShortVersionString<\/key>\s+<string>)[^<]+/g, '$11.0.0')
+ );
+ await signApp(appPath, identity);
++>>>>>>> fix: prevent node mode to be used as script runner by other apps
- const updateZipPath = await getOrCreateUpdateZipPath(opts.nextVersion, opts.endFixture, opts.mutateAppPreSign, opts.mutateAppPostSign);
+ const updateZipPath = await getOrCreateUpdateZipPath(opts.nextVersion, opts.endFixture, opts.mutateAppPostSign);
await fn(appPath, updateZipPath);
});
diff --cc spec/node-spec.ts
index eac32fa0d7,0af015131a..0000000000
--- a/spec/node-spec.ts
+++ b/spec/node-spec.ts
@@@ -1,14 -1,14 +1,22 @@@
import { expect } from 'chai';
++<<<<<<< HEAD
+import * as childProcess from 'child_process';
+import * as fs from 'fs';
+import * as path from 'path';
+import * as util from 'util';
++=======
+ import * as childProcess from 'node:child_process';
+ import * as fs from 'fs-extra';
+ import * as path from 'node:path';
+ import * as util from 'node:util';
++>>>>>>> fix: prevent node mode to be used as script runner by other apps
import { getRemoteContext, ifdescribe, ifit, itremote, useRemoteContext } from './lib/spec-helpers';
+ import { copyApp, getCodesignIdentity, shouldRunCodesignTests, signApp, spawn, withTempDirectory } from './lib/codesign-helpers';
import { webContents } from 'electron/main';
-import { EventEmitter } from 'node:stream';
-import { once } from 'node:events';
+import { EventEmitter } from 'stream';
+import { once } from 'events';
+const features = process._linkedBinding('electron_common_features');
const mainFixturesPath = path.resolve(__dirname, 'fixtures');
describe('node feature', () => {
@@@ -660,7 -660,67 +668,71 @@@
});
});
++<<<<<<< HEAD
+ ifdescribe(features.isRunAsNodeEnabled())('Node.js cli flags', () => {
++=======
+ ifdescribe(shouldRunCodesignTests)('NODE_OPTIONS in signed app', function () {
+ let identity = '';
+
+ beforeEach(function () {
+ const result = getCodesignIdentity();
+ if (result === null) {
+ this.skip();
+ } else {
+ identity = result;
+ }
+ });
+
+ const script = path.join(fixtures, 'api', 'fork-with-node-options.js');
+ const nodeOptionsWarning = 'NODE_OPTIONS is disabled because this process is invoked by other apps';
+
+ it('is disabled when invoked by other apps in ELECTRON_RUN_AS_NODE mode', async () => {
+ await withTempDirectory(async (dir) => {
+ const appPath = await copyApp(dir);
+ await signApp(appPath, identity);
+ // Invoke Electron by using the system node binary as middle layer, so
+ // the check of NODE_OPTIONS will think the process is started by other
+ // apps.
+ const { code, out } = await spawn('node', [script, path.join(appPath, 'Contents/MacOS/Electron')]);
+ expect(code).to.equal(0);
+ expect(out).to.include(nodeOptionsWarning);
+ });
+ });
+
+ it('is disabled when invoked by alien binary in app bundle in ELECTRON_RUN_AS_NODE mode', async function () {
+ await withTempDirectory(async (dir) => {
+ const appPath = await copyApp(dir);
+ await signApp(appPath, identity);
+ // Find system node and copy it to app bundle.
+ const nodePath = process.env.PATH?.split(path.delimiter).find(dir => fs.existsSync(path.join(dir, 'node')));
+ if (!nodePath) {
+ this.skip();
+ return;
+ }
+ const alienBinary = path.join(appPath, 'Contents/MacOS/node');
+ await fs.copy(path.join(nodePath, 'node'), alienBinary);
+ // Try to execute electron app from the alien node in app bundle.
+ const { code, out } = await spawn(alienBinary, [script, path.join(appPath, 'Contents/MacOS/Electron')]);
+ expect(code).to.equal(0);
+ expect(out).to.include(nodeOptionsWarning);
+ });
+ });
+
+ it('is respected when invoked from self', async () => {
+ await withTempDirectory(async (dir) => {
+ const appPath = await copyApp(dir, null);
+ await signApp(appPath, identity);
+ const appExePath = path.join(appPath, 'Contents/MacOS/Electron');
+ const { code, out } = await spawn(appExePath, [script, appExePath]);
+ expect(code).to.equal(1);
+ expect(out).to.not.include(nodeOptionsWarning);
+ expect(out).to.include('NODE_OPTIONS passed to child');
+ });
+ });
+ });
+
+ describe('Node.js cli flags', () => {
++>>>>>>> fix: prevent node mode to be used as script runner by other apps
let child: childProcess.ChildProcessWithoutNullStreams;
let exitPromise: Promise<any[]>;
Annotations
Check failure on line 9 in spec/api-autoupdater-darwin-spec.ts
trop / Backportable? - 26-x-y
spec/api-autoupdater-darwin-spec.ts#L8-L9
Patch Conflict
Raw output
++<<<<<<< HEAD
+import * as os from 'os';
+import * as path from 'path';
++=======
+ import * as path from 'node:path';
++>>>>>>> fix: prevent node mode to be used as script runner by other apps
Check failure on line 77 in spec/api-autoupdater-darwin-spec.ts
trop / Backportable? - 26-x-y
spec/api-autoupdater-darwin-spec.ts#L77
Patch Conflict
Raw output
++<<<<<<< HEAD
+ await signApp(secondAppPath);
++=======
+ const infoPath = path.resolve(secondAppPath, 'Contents', 'Info.plist');
+ await fs.writeFile(
+ infoPath,
+ (await fs.readFile(infoPath, 'utf8')).replace(/(<key>CFBundleShortVersionString<\/key>\s+<string>)[^<]+/g, `$1${version}`)
+ );
+ await mutateAppPreSign?.mutate(secondAppPath);
+ await signApp(secondAppPath, identity);
++>>>>>>> fix: prevent node mode to be used as script runner by other apps
Check failure on line 230 in spec/api-autoupdater-darwin-spec.ts
trop / Backportable? - 26-x-y
spec/api-autoupdater-darwin-spec.ts#L230
Patch Conflict
Raw output
++<<<<<<< HEAD
+ await signApp(appPath);
++=======
+ await opts.mutateAppPreSign?.mutate(appPath);
+ const infoPath = path.resolve(appPath, 'Contents', 'Info.plist');
+ await fs.writeFile(
+ infoPath,
+ (await fs.readFile(infoPath, 'utf8')).replace(/(<key>CFBundleShortVersionString<\/key>\s+<string>)[^<]+/g, '$11.0.0')
+ );
+ await signApp(appPath, identity);
++>>>>>>> fix: prevent node mode to be used as script runner by other apps
Check failure on line 5 in spec/node-spec.ts
trop / Backportable? - 26-x-y
spec/node-spec.ts#L2-L5
Patch Conflict
Raw output
++<<<<<<< HEAD
+import * as childProcess from 'child_process';
+import * as fs from 'fs';
+import * as path from 'path';
+import * as util from 'util';
++=======
+ import * as childProcess from 'node:child_process';
+ import * as fs from 'fs-extra';
+ import * as path from 'node:path';
+ import * as util from 'node:util';
++>>>>>>> fix: prevent node mode to be used as script runner by other apps
Check failure on line 671 in spec/node-spec.ts
trop / Backportable? - 26-x-y
spec/node-spec.ts#L671
Patch Conflict
Raw output
++<<<<<<< HEAD
+ ifdescribe(features.isRunAsNodeEnabled())('Node.js cli flags', () => {
++=======
+ ifdescribe(shouldRunCodesignTests)('NODE_OPTIONS in signed app', function () {
+ let identity = '';
+
+ beforeEach(function () {
+ const result = getCodesignIdentity();
+ if (result === null) {
+ this.skip();
+ } else {
+ identity = result;
+ }
+ });
+
+ const script = path.join(fixtures, 'api', 'fork-with-node-options.js');
+ const nodeOptionsWarning = 'NODE_OPTIONS is disabled because this process is invoked by other apps';
+
+ it('is disabled when invoked by other apps in ELECTRON_RUN_AS_NODE mode', async () => {
+ await withTempDirectory(async (dir) => {
+ const appPath = await copyApp(dir);
+ await signApp(appPath, identity);
+ // Invoke Electron by using the system node binary as middle layer, so
+ // the check of NODE_OPTIONS will think the process is started by other
+ // apps.
+ const { code, out } = await spawn('node', [script, path.join(appPath, 'Contents/MacOS/Electron')]);
+ expect(code).to.equal(0);
+ expect(out).to.include(nodeOptionsWarning);
+ });
+ });
+
+ it('is disabled when invoked by alien binary in app bundle in ELECTRON_RUN_AS_NODE mode', async function () {
+ await withTempDirectory(async (dir) => {
+ const appPath = await copyApp(dir);
+ await signApp(appPath, identity);
+ // Find system node and copy it to app bundle.
+ const nodePath = process.env.PATH?.split(path.delimiter).find(dir => fs.existsSync(path.join(dir, 'node')));
+ if (!nodePath) {
+ this.skip();
+ return;
+ }
+ const alienBinary = path.join(appPath, 'Contents/MacOS/node');
+ await fs.copy(path.join(nodePath, 'node'), alienBinary);
+ // Try to execute electron app from the alien node in app bundle.
+ const { code, out } = await spawn(alienBinary, [script, path.join(appPath, 'Contents/MacOS/Electron')]);
+ expect(code).to.equal(0);
+ expect(out).to.include(nodeOptionsWarning);
+ });
+ });
+
+ it('is respected when invoked from self', async () => {
+ await withTempDirectory(async (dir) => {
+ const appPath = await copyApp(dir, null);
+ await signApp(appPath, identity);
+ const appExePath = path.join(appPath, 'Contents/MacOS/Electron');
+ const { code, out } = await spawn(appExePath, [script, appExePath]);
+ expect(code).to.equal(1);
+ expect(out).to.not.include(nodeOptionsWarning);
+ expect(out).to.include('NODE_OPTIONS passed to child');
+ });
+ });
+ });
+
+ describe('Node.js cli flags', () => {
++>>>>>>> fix: prevent node mode to be used as script runner by other apps