Files
hermes-agent/apps/gui/scripts/start-dashboard.mjs
Brooklyn Nicholson 648da6a8d1 feat(gui): make desktop setup flow real and testable
Add a GUI-first setup gate and runtime state API so desktop onboarding is safe, iterative, and works with isolated fresh-mode installs. Scaffold and wire the desktop shell/runtime pieces so this branch runs end-to-end without disturbing existing user installs.
2026-04-25 19:48:02 -05:00

96 lines
2.1 KiB
JavaScript

import { spawn } from "node:child_process";
import { dirname, resolve } from "node:path";
import { fileURLToPath } from "node:url";
const here = dirname(fileURLToPath(import.meta.url));
const repoRoot = resolve(here, "../../..");
const python = process.env.HERMES_PYTHON || "python";
const port = process.env.HERMES_GUI_PORT || "9120";
const url = `http://127.0.0.1:${port}`;
async function isHealthy() {
try {
const res = await fetch(`${url}/api/health`, {
signal: AbortSignal.timeout(1000),
});
const data = await res.json();
return res.ok && data.status === "ok";
} catch {
return false;
}
}
function wslRepoRoot() {
const normalized = repoRoot.replaceAll("\\", "/");
const parts = normalized.split("/");
const host = parts[2]?.toLowerCase();
if (process.platform !== "win32") return null;
if (host !== "wsl$" && host !== "wsl.localhost") return null;
const distro = parts[3];
const path = `/${parts.slice(4).join("/")}`;
return distro && path !== "/" ? { distro, path } : null;
}
function spawnDashboard() {
const wsl = wslRepoRoot();
if (wsl) {
return spawn(
"wsl.exe",
[
"-d",
wsl.distro,
"--cd",
wsl.path,
"env",
"HERMES_GUI=1",
process.env.HERMES_WSL_PYTHON || "python",
"-m",
"hermes_cli.main",
"dashboard",
"--gui",
"--no-open",
"--host",
"127.0.0.1",
"--port",
port,
],
{ stdio: "inherit" },
);
}
return spawn(
python,
[
"-m",
"hermes_cli.main",
"dashboard",
"--gui",
"--no-open",
"--host",
"127.0.0.1",
"--port",
port,
],
{
cwd: repoRoot,
env: {
...process.env,
HERMES_GUI: "1",
},
stdio: "inherit",
},
);
}
if (await isHealthy()) {
console.log(`Hermes GUI already running -> ${url}`);
process.exit(0);
}
const child = spawnDashboard();
child.on("exit", (code, signal) => {
if (signal) process.kill(process.pid, signal);
process.exit(code ?? 0);
});