Skip to content

Commit

Permalink
Merge pull request #443 from valory-xyz/fix/electron-logging-process-…
Browse files Browse the repository at this point in the history
…killing

Fix electron-related process killing
  • Loading branch information
truemiller authored Nov 12, 2024
2 parents cc51de1 + a845e62 commit 24190fd
Show file tree
Hide file tree
Showing 4 changed files with 77 additions and 24 deletions.
82 changes: 68 additions & 14 deletions electron/main.js
Original file line number Diff line number Diff line change
Expand Up @@ -70,11 +70,20 @@ let splashWindow = null;
/** @type {Electron.Tray | null} */
let tray = null;

let operateDaemon, operateDaemonPid, nextAppProcess, nextAppProcessPid;
// Used in production and development
let operateDaemon;
let operateDaemonPid;

// Child processes for running next app are only used in development
// required for hot reloads and other dev features
let devNextApp;
let devNextAppPid;

// Next.js app instance for production
// requires http server wrap to work; assign port, receive requests, deliver responses
// @ts-ignore - Workaround for the missing type definitions
const nextApp = next({
dev: false, // this instance is only used for production
dev: false, // DO NOT SET TO TRUE
dir: path.join(__dirname),
});

Expand All @@ -85,28 +94,73 @@ function showNotification(title, body) {
}

async function beforeQuit() {
if (operateDaemonPid) {
// destroy all ui components for immediate feedback
tray?.destroy();
splashWindow?.destroy();
mainWindow?.destroy();

if (operateDaemon || operateDaemonPid) {
// gracefully stop running services
try {
await fetch(
`http://localhost:${appConfig.ports.prod.operate}/stop_all_services`,
);
await killProcesses(operateDaemonPid);
} catch (e) {
logger.electron(e);
logger.electron("Couldn't stop_all_services gracefully:");
logger.electron(JSON.stringify(e, null, 2));
}

// clean-up via pid first*
// may have dangling subprocesses
try {
operateDaemonPid && (await killProcesses(operateDaemonPid));
} catch (e) {
logger.electron("Couldn't kill daemon processes via pid:");
logger.electron(JSON.stringify(e, null, 2));
}

// attempt to kill the daemon process via kill
// if the pid-based cleanup fails
try {
const dead = operateDaemon?.kill();
if (!dead) {
logger.electron('Daemon process still alive after kill');
}
} catch (e) {
logger.electron("Couldn't kill operate daemon process via kill:");
logger.electron(JSON.stringify(e, null, 2));
}
}

if (nextAppProcessPid) {
if (devNextApp || devNextAppPid) {
// attempt graceful kill first with next app
try {
const dead = devNextApp?.kill();
if (!dead) {
logger.electron('Dev NextApp process still alive after kill');
}
} catch (e) {
logger.electron("Couldn't kill devNextApp process via kill:");
logger.electron(JSON.stringify(e, null, 2));
}

// attempt to kill the dev next app process via pid
try {
await killProcesses(nextAppProcessPid);
devNextAppPid && (await killProcesses(devNextAppPid));
} catch (e) {
logger.electron(e);
logger.electron("Couldn't kill devNextApp processes via pid:");
logger.electron(JSON.stringify(e, null, 2));
}
}

tray?.destroy();
splashWindow?.destroy();
mainWindow?.destroy();
if (nextApp) {
// attempt graceful close of prod next app
await nextApp.close().catch((e) => {
logger.electron("Couldn't close NextApp gracefully:");
logger.electron(JSON.stringify(e, null, 2));
});
// electron will kill next service on exit
}
}

const APP_WIDTH = 460;
Expand Down Expand Up @@ -340,7 +394,7 @@ async function launchNextApp() {
async function launchNextAppDev() {
await new Promise(function (resolve, _reject) {
process.env.NEXT_PUBLIC_BACKEND_PORT = appConfig.ports.dev.operate; // must set next env var to connect to backend
nextAppProcess = spawn(
devNextApp = spawn(
'yarn',
['dev:frontend', '--port', appConfig.ports.dev.next],
{
Expand All @@ -352,8 +406,8 @@ async function launchNextAppDev() {
},
},
);
nextAppProcessPid = nextAppProcess.pid;
nextAppProcess.stdout.on('data', (data) => {
devNextAppPid = devNextApp.pid;
devNextApp.stdout.on('data', (data) => {
logger.next(data.toString().trim());
resolve();
});
Expand Down
15 changes: 7 additions & 8 deletions electron/processes.js
Original file line number Diff line number Diff line change
Expand Up @@ -16,15 +16,16 @@ function killProcesses(pid) {

// Array of PIDs to kill, starting with the children
const pidsToKill = children.map((p) => p.PID);
logger.info("Pids to kill " + JSON.stringify(pidsToKill));
logger.electron('Pids to kill ' + JSON.stringify(pidsToKill));

const killCommand = isWindows ? windowsKillCommand : unixKillCommand;

let errors = [];
for (const ppid of pidsToKill) {
logger.info("kill: " + ppid);
exec(`${killCommand} ${ppid}`, (err) => {
logger.error("Pids to kill error:" + err);
for (const pid of pidsToKill) {
logger.electron('killing: ' + pid);
exec(`${killCommand} ${pid}`, (err) => {
err && logger.electron(`error killing pid ${pid}`);
err && logger.electron(JSON.stringify(err, null, 2));
if (
err?.message?.includes(isWindows ? 'not found' : 'No such process')
) {
Expand All @@ -36,9 +37,7 @@ function killProcesses(pid) {

if (errors.length === 0) {
reject(errors);


} else resolve();
} else resolve();
});
});
}
Expand Down
2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -63,5 +63,5 @@
"download-binaries": "sh download_binaries.sh",
"build:pearl": "sh build_pearl.sh"
},
"version": "0.1.0-rc195"
"version": "0.1.0-rc196"
}
2 changes: 1 addition & 1 deletion pyproject.toml
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
[tool.poetry]
name = "olas-operate-middleware"
version = "0.1.0-rc195"
version = "0.1.0-rc196"
description = ""
authors = ["David Vilela <[email protected]>", "Viraj Patel <[email protected]>"]
readme = "README.md"
Expand Down

0 comments on commit 24190fd

Please sign in to comment.