feat: enhance PATH resolution for packaged Electron apps on macOS/Linux

Added logic to spawn the user's login shell to correctly set the PATH environment variable for packaged Electron applications, ensuring access to user-specific binaries and tools. This addresses issues with minimal environment inheritance in packaged apps.
This commit is contained in:
tusharmagar 2026-03-20 10:52:39 +05:30
parent 758a2779f4
commit 9e28c47f30

View file

@ -23,6 +23,7 @@ import { init as initInlineTasks } from "@x/core/dist/knowledge/inline_tasks.js"
import { init as initAgentRunner } from "@x/core/dist/agent-schedule/runner.js";
import { initConfigs } from "@x/core/dist/config/initConfigs.js";
import started from "electron-squirrel-startup";
import { execSync } from "node:child_process";
const __filename = fileURLToPath(import.meta.url);
const __dirname = dirname(__filename);
@ -30,6 +31,28 @@ const __dirname = dirname(__filename);
// run this as early in the main process as possible
if (started) app.quit();
// Fix PATH for packaged Electron apps on macOS/Linux.
// Packaged apps inherit a minimal environment that doesn't include paths from
// the user's shell profile (nvm, Homebrew, etc.). Spawn the user's login shell
// to resolve the full PATH, using delimiters to safely extract it from any
// surrounding shell output (motd, greeting messages, etc.).
if (process.platform !== 'win32') {
try {
const userShell = process.env.SHELL || '/bin/zsh';
const delimiter = '__ROWBOAT_PATH__';
const output = execSync(
`${userShell} -lc 'echo -n "${delimiter}$PATH${delimiter}"'`,
{ encoding: 'utf-8', timeout: 5000 },
);
const match = output.match(new RegExp(`${delimiter}(.+?)${delimiter}`));
if (match?.[1]) {
process.env.PATH = match[1];
}
} catch {
// Silently fall back to the existing PATH if shell resolution fails
}
}
// Path resolution differs between development and production:
const preloadPath = app.isPackaged
? path.join(__dirname, "../preload/dist/preload.js")