add better 403 screens and start with bun dev mode. (going to rewrite to fit the bun standard in a bit).

This commit is contained in:
KingKDot
2026-07-23 13:29:32 -05:00
parent 49bf1438a8
commit a68172538d
10 changed files with 487 additions and 22 deletions
+2 -2
View File
@@ -8,7 +8,7 @@
"test:e2e": "bun run test:e2e:prepare && playwright test", "test:e2e": "bun run test:e2e:prepare && playwright test",
"test:e2e:prepare": "bun run build:css && bun run vendor", "test:e2e:prepare": "bun run build:css && bun run vendor",
"test:e2e:install": "playwright install chromium", "test:e2e:install": "playwright install chromium",
"dev": "bun --watch src/index.ts", "dev": "bun run scripts/dev.ts",
"start": "bun run build && bun dist/index.js", "start": "bun run build && bun dist/index.js",
"build": "bun run build:css && bun run vendor && bun run build:bundle", "build": "bun run build:css && bun run vendor && bun run build:bundle",
"build:public:prod": "bun run build:css && bun run vendor && bun run minify", "build:public:prod": "bun run build:css && bun run vendor && bun run minify",
@@ -17,7 +17,7 @@
"build:prod:win": "bun run build:public:prod && bun build --production src/index.ts --compile --target bun-windows-x64 --outfile dist/overlord-server.exe", "build:prod:win": "bun run build:public:prod && bun build --production src/index.ts --compile --target bun-windows-x64 --outfile dist/overlord-server.exe",
"build:prod:linux": "bun run build:public:prod && bun build --production src/index.ts --compile --target bun-linux-x64 --outfile dist/overlord-server-linux-x64", "build:prod:linux": "bun run build:public:prod && bun build --production src/index.ts --compile --target bun-linux-x64 --outfile dist/overlord-server-linux-x64",
"build:css": "tailwindcss -i ./src/styles.css -o ./public/assets/tailwind.css --minify", "build:css": "tailwindcss -i ./src/styles.css -o ./public/assets/tailwind.css --minify",
"watch:css": "tailwindcss -i ./src/styles.css -o ./public/assets/tailwind.css --watch", "watch:css": "tailwindcss -i ./src/styles.css -o ./public/assets/tailwind.css --watch=always",
"minify": "bun run scripts/minify-public.ts", "minify": "bun run scripts/minify-public.ts",
"bench:client-db": "bun run scripts/client-db-stress.ts", "bench:client-db": "bun run scripts/client-db-stress.ts",
"typecheck": "tsc --noEmit" "typecheck": "tsc --noEmit"
@@ -0,0 +1,201 @@
:root {
color-scheme: dark;
font-family: "Inter", system-ui, sans-serif;
background: #05070f;
color: #eef2ff;
}
* {
box-sizing: border-box;
}
body {
min-width: 320px;
min-height: 100vh;
margin: 0;
background:
radial-gradient(circle at 18% 16%, rgba(37, 99, 235, 0.22), transparent 32rem),
radial-gradient(circle at 82% 84%, rgba(124, 58, 237, 0.16), transparent 30rem),
#05070f;
}
body::before {
position: fixed;
inset: 0;
background-image:
linear-gradient(rgba(148, 163, 184, 0.025) 1px, transparent 1px),
linear-gradient(90deg, rgba(148, 163, 184, 0.025) 1px, transparent 1px);
background-size: 40px 40px;
content: "";
pointer-events: none;
mask-image: radial-gradient(circle at center, black, transparent 80%);
}
.access-shell {
position: relative;
display: grid;
min-height: 100vh;
place-content: center;
justify-items: center;
padding: 32px 20px;
}
.access-card {
width: min(100%, 590px);
padding: clamp(28px, 6vw, 48px);
overflow: hidden;
text-align: center;
background: linear-gradient(145deg, rgba(24, 32, 52, 0.96), rgba(11, 15, 27, 0.98));
border: 1px solid rgba(148, 163, 184, 0.16);
border-radius: 24px;
box-shadow: 0 28px 90px rgba(0, 0, 0, 0.48), 0 0 80px rgba(59, 130, 246, 0.08);
}
.access-status {
display: inline-flex;
padding: 7px 11px;
margin-bottom: 28px;
color: #fbbf24;
font-size: 0.72rem;
font-weight: 700;
letter-spacing: 0.1em;
text-transform: uppercase;
background: rgba(245, 158, 11, 0.09);
border: 1px solid rgba(245, 158, 11, 0.2);
border-radius: 999px;
}
.access-icon {
display: grid;
width: 76px;
height: 76px;
margin: 0 auto 22px;
place-items: center;
color: #a5b4fc;
font-size: 1.8rem;
background: linear-gradient(145deg, rgba(79, 70, 229, 0.25), rgba(37, 99, 235, 0.12));
border: 1px solid rgba(129, 140, 248, 0.24);
border-radius: 22px;
box-shadow: inset 0 1px rgba(255, 255, 255, 0.08), 0 14px 35px rgba(37, 99, 235, 0.14);
}
h1 {
margin: 0;
font-size: clamp(1.7rem, 5vw, 2.35rem);
line-height: 1.12;
letter-spacing: -0.035em;
}
.access-message {
max-width: 460px;
margin: 14px auto 0;
color: #aebbd0;
font-size: 1rem;
line-height: 1.65;
}
.access-detail {
display: flex;
gap: 12px;
align-items: center;
justify-content: space-between;
margin-top: 26px;
padding: 14px 16px;
text-align: left;
background: rgba(2, 6, 23, 0.58);
border: 1px solid rgba(100, 116, 139, 0.2);
border-radius: 12px;
}
.access-detail span {
color: #8593aa;
font-size: 0.78rem;
font-weight: 600;
}
.access-detail code {
padding: 4px 7px;
color: #c7d2fe;
font-family: ui-monospace, "Cascadia Code", monospace;
font-size: 0.78rem;
background: rgba(99, 102, 241, 0.1);
border-radius: 6px;
}
.access-help {
margin: 17px auto 0;
color: #708097;
font-size: 0.8rem;
line-height: 1.5;
}
.access-actions {
display: flex;
gap: 10px;
justify-content: center;
margin-top: 30px;
}
.access-actions a {
display: inline-flex;
gap: 9px;
align-items: center;
justify-content: center;
min-height: 44px;
padding: 0 17px;
color: #dbe7f7;
font-size: 0.86rem;
font-weight: 600;
text-decoration: none;
border-radius: 10px;
transition: transform 150ms ease, border-color 150ms ease, background 150ms ease;
}
.access-actions a:hover {
transform: translateY(-1px);
}
.access-primary {
background: linear-gradient(135deg, #4f46e5, #2563eb);
border: 1px solid rgba(165, 180, 252, 0.24);
box-shadow: 0 10px 24px rgba(37, 99, 235, 0.2);
}
.access-primary:hover {
background: linear-gradient(135deg, #5b52ee, #3472ec);
}
.access-secondary {
background: rgba(30, 41, 59, 0.6);
border: 1px solid rgba(148, 163, 184, 0.16);
}
.access-secondary:hover {
background: rgba(51, 65, 85, 0.66);
border-color: rgba(148, 163, 184, 0.3);
}
.access-footer {
margin: 22px 0 0;
color: #536077;
font-size: 0.76rem;
font-weight: 600;
letter-spacing: 0.08em;
text-transform: uppercase;
}
.access-footer i {
margin-right: 6px;
color: #6776a5;
}
@media (max-width: 520px) {
.access-actions {
flex-direction: column;
}
.access-detail {
align-items: flex-start;
flex-direction: column;
}
}
+70
View File
@@ -0,0 +1,70 @@
/**
* Development supervisor.
*
* Keeps the backend and generated Tailwind stylesheet up to date while
* preserving a single foreground process for the repository launchers.
*/
const cwd = import.meta.dir.replace(/[\\/]scripts$/, "");
const env = {
...process.env,
NODE_ENV: "development",
};
function runPreparation(command: string): void {
const result = Bun.spawnSync(["bun", "run", command], {
cwd,
env,
stdin: "inherit",
stdout: "inherit",
stderr: "inherit",
});
if (!result.success) {
process.exit(result.exitCode || 1);
}
}
runPreparation("build:css");
runPreparation("vendor");
const backend = Bun.spawn(["bun", "--watch", "src/index.ts"], {
cwd,
env,
stdin: "inherit",
stdout: "inherit",
stderr: "inherit",
});
const styles = Bun.spawn(["bun", "run", "watch:css"], {
cwd,
env,
stdin: "inherit",
stdout: "inherit",
stderr: "inherit",
});
let stopping = false;
function stop(exitCode = 0): void {
if (stopping) return;
stopping = true;
backend.kill();
styles.kill();
process.exitCode = exitCode;
}
process.on("SIGINT", () => stop(130));
process.on("SIGTERM", () => stop(143));
const result = await Promise.race([
backend.exited.then((exitCode) => ({ process: "backend", exitCode })),
styles.exited.then((exitCode) => ({ process: "Tailwind watcher", exitCode })),
]);
if (!stopping) {
console.error(`[dev] ${result.process} exited with code ${result.exitCode}`);
stop(result.exitCode || 1);
}
await Promise.allSettled([backend.exited, styles.exited]);
+8
View File
@@ -278,6 +278,7 @@ function parseMaxHttpBodyBytes(): number {
} }
const MAX_HTTP_BODY_BYTES = parseMaxHttpBodyBytes(); const MAX_HTTP_BODY_BYTES = parseMaxHttpBodyBytes();
const IS_DEVELOPMENT = String(process.env.NODE_ENV || "").trim().toLowerCase() === "development";
const pluginLoadedByClient = new Map<string, Set<string>>(); const pluginLoadedByClient = new Map<string, Set<string>>();
const pendingPluginEvents = new Map<string, Array<{ event: string; payload: any }>>(); const pendingPluginEvents = new Map<string, Array<{ event: string; payload: any }>>();
@@ -710,6 +711,13 @@ async function startServer() {
port: PORT, port: PORT,
hostname: HOST, hostname: HOST,
...(tls ? { tls: tls.tlsOptions } : {}), ...(tls ? { tls: tls.tlsOptions } : {}),
development: IS_DEVELOPMENT
? {
hmr: true,
console: true,
chromeDevToolsAutomaticWorkspaceFolders: true,
}
: false,
idleTimeout: 255, idleTimeout: 255,
maxRequestBodySize: MAX_HTTP_BODY_BYTES, maxRequestBodySize: MAX_HTTP_BODY_BYTES,
fetch: createHttpFetchHandler({ fetch: createHttpFetchHandler({
@@ -1,8 +1,10 @@
import { authenticateRequest } from "../../auth"; import { authenticateRequest } from "../../auth";
import { getConfig } from "../../config"; import { getConfig } from "../../config";
import { consumeLoginPageRateLimit } from "../../rateLimit"; import { consumeLoginPageRateLimit } from "../../rateLimit";
import { requirePermission, type Permission } from "../../rbac"; import { getPermissionDescription, requirePermission, type Permission } from "../../rbac";
import { canUserAccessClient, canUserAccessFeature, getUserById, type FeatureName, type UserRole } from "../../users"; import { canUserAccessClient, canUserAccessFeature, getUserById, type FeatureName, type UserRole } from "../../users";
import { renderAccessDeniedPage, type AccessDeniedKind } from "../ui/access-denied-view";
import { htmlResponse } from "../ui/html";
type PageRouteDeps = { type PageRouteDeps = {
PUBLIC_ROOT: string; PUBLIC_ROOT: string;
@@ -120,23 +122,60 @@ const PATH_CLIENT_PAGES: ClientPageDef[] = [
{ pattern: /^\/(.+)\/keylogger$/, file: "keylogger.html", clientIdGroup: 1, feature: "keylogger" }, { pattern: /^\/(.+)\/keylogger$/, file: "keylogger.html", clientIdGroup: 1, feature: "keylogger" },
]; ];
function checkAccess(role: UserRole, access: AccessLevel): Response | null { function accessDeniedResponse(
deps: PageRouteDeps,
options: {
kind: AccessDeniedKind;
title?: string;
message: string;
detail?: string;
detailLabel?: string;
},
): Response {
return htmlResponse(renderAccessDeniedPage(options), {
status: 403,
headers: deps.secureHeaders("text/html; charset=utf-8"),
});
}
function permissionDeniedResponse(deps: PageRouteDeps, permission: Permission): Response {
return accessDeniedResponse(deps, {
kind: "permission",
message: `This page requires permission to ${getPermissionDescription(permission).toLowerCase()}.`,
detail: permission,
detailLabel: "Missing permission",
});
}
function checkAccess(deps: PageRouteDeps, role: UserRole, access: AccessLevel): Response | null {
switch (access) { switch (access) {
case "any": case "any":
return null; return null;
case "no-viewer": case "no-viewer":
if (role === "viewer") { if (role === "viewer") {
return new Response("Forbidden: Viewers cannot access interactive features", { status: 403 }); return accessDeniedResponse(deps, {
kind: "role",
message: "Viewer accounts can inspect data, but cannot open interactive control features.",
detail: "Operator or administrator role",
});
} }
return null; return null;
case "admin": case "admin":
if (role !== "admin") { if (role !== "admin") {
return new Response("Forbidden: Admin access required", { status: 403 }); return accessDeniedResponse(deps, {
kind: "role",
message: "This area is reserved for administrators.",
detail: "Administrator role",
});
} }
return null; return null;
case "admin-or-operator": case "admin-or-operator":
if (role !== "admin" && role !== "operator") { if (role !== "admin" && role !== "operator") {
return new Response("Forbidden: Admin or operator access required", { status: 403 }); return accessDeniedResponse(deps, {
kind: "role",
message: "This interactive area is available to operators and administrators.",
detail: "Operator or administrator role",
});
} }
return null; return null;
} }
@@ -195,7 +234,12 @@ export async function handlePageRoutes(
if (!user) return serveLoginOrUnauthorized(req, deps); if (!user) return serveLoginOrUnauthorized(req, deps);
if (page.path === "/screenshots" && !getConfig().thumbnails.wallEnabled) { if (page.path === "/screenshots" && !getConfig().thumbnails.wallEnabled) {
return new Response("Screenshot wall is disabled by the administrator", { status: 403 }); return accessDeniedResponse(deps, {
kind: "unavailable",
message: "The screenshot wall has been disabled in server settings.",
detail: "Screenshot wall disabled",
detailLabel: "Current status",
});
} }
if (page.checkPasswordChange) { if (page.checkPasswordChange) {
@@ -203,14 +247,16 @@ export async function handlePageRoutes(
if (maybeChange) return maybeChange; if (maybeChange) return maybeChange;
} }
const accessDenied = checkAccess(user.role, page.access); const accessDenied = checkAccess(deps, user.role, page.access);
if (accessDenied) return accessDenied; if (accessDenied) return accessDenied;
if (page.permission) { if (page.permission) {
try { try {
requirePermission(user, page.permission); requirePermission(user, page.permission);
} catch (error) { } catch (error) {
if (error instanceof Response) return error; if (error instanceof Response && error.status === 403) {
return permissionDeniedResponse(deps, page.permission);
}
return new Response("Forbidden", { status: 403 }); return new Response("Forbidden", { status: 403 });
} }
} }
@@ -232,18 +278,34 @@ export async function handlePageRoutes(
try { try {
requirePermission(user, page.permission); requirePermission(user, page.permission);
} catch (error) { } catch (error) {
if (error instanceof Response) return error; if (error instanceof Response && error.status === 403) {
return permissionDeniedResponse(deps, page.permission);
}
return new Response("Forbidden", { status: 403 }); return new Response("Forbidden", { status: 403 });
} }
} }
if (page.feature && !canUserAccessFeature(user.userId, user.role, page.feature)) { if (page.feature && !canUserAccessFeature(user.userId, user.role, page.feature)) {
return new Response(`Forbidden: feature access denied for ${page.feature}`, { status: 403 }); return accessDeniedResponse(deps, {
kind: "feature",
title: "This feature isn't enabled for you",
message: "Your account's feature access does not include this client tool.",
detail: page.feature,
detailLabel: "Restricted feature",
});
} }
const clientId = (url.searchParams.get("clientId") || "").trim(); const clientId = (url.searchParams.get("clientId") || "").trim();
if (!canAccessClientPage(user.userId, user.role, clientId)) { if (!canAccessClientPage(user.userId, user.role, clientId)) {
return new Response("Forbidden: Client access denied", { status: 403 }); return accessDeniedResponse(deps, {
kind: "client",
title: "Client access restricted",
message: clientId
? "This client is outside the scope assigned to your account."
: "Choose a client from the dashboard before opening this tool.",
detail: clientId || "No client selected",
detailLabel: "Client",
});
} }
return serveFile(deps, page.file); return serveFile(deps, page.file);
@@ -261,18 +323,32 @@ export async function handlePageRoutes(
try { try {
requirePermission(user, page.permission); requirePermission(user, page.permission);
} catch (error) { } catch (error) {
if (error instanceof Response) return error; if (error instanceof Response && error.status === 403) {
return permissionDeniedResponse(deps, page.permission);
}
return new Response("Forbidden", { status: 403 }); return new Response("Forbidden", { status: 403 });
} }
} }
if (page.feature && !canUserAccessFeature(user.userId, user.role, page.feature)) { if (page.feature && !canUserAccessFeature(user.userId, user.role, page.feature)) {
return new Response(`Forbidden: feature access denied for ${page.feature}`, { status: 403 }); return accessDeniedResponse(deps, {
kind: "feature",
title: "This feature isn't enabled for you",
message: "Your account's feature access does not include this client tool.",
detail: page.feature,
detailLabel: "Restricted feature",
});
} }
const clientId = match[page.clientIdGroup]; const clientId = match[page.clientIdGroup];
if (!canAccessClientPage(user.userId, user.role, clientId)) { if (!canAccessClientPage(user.userId, user.role, clientId)) {
return new Response("Forbidden: Client access denied", { status: 403 }); return accessDeniedResponse(deps, {
kind: "client",
title: "Client access restricted",
message: "This client is outside the scope assigned to your account.",
detail: clientId,
detailLabel: "Client",
});
} }
return serveFile(deps, page.file); return serveFile(deps, page.file);
@@ -0,0 +1,33 @@
import { describe, expect, test } from "bun:test";
import { renderAccessDeniedPage } from "./access-denied-view";
describe("renderAccessDeniedPage", () => {
test("renders a complete permission screen with recovery actions", () => {
const html = renderAccessDeniedPage({
kind: "permission",
message: "This page requires additional access.",
detail: "users:manage",
detailLabel: "Missing permission",
});
expect(html).toContain("<!doctype html>");
expect(html).toContain("You don&#39;t have access");
expect(html).toContain("users:manage");
expect(html).toContain('href="/"');
expect(html).toContain('href="/settings"');
});
test("escapes dynamic denial details", () => {
const html = renderAccessDeniedPage({
kind: "client",
title: "<script>bad()</script>",
message: "Client <not-allowed>",
detail: '"><img src=x onerror=bad()>',
});
expect(html).not.toContain("<script>bad()</script>");
expect(html).not.toContain("<img src=x");
expect(html).toContain("&lt;script&gt;bad()&lt;/script&gt;");
expect(html).toContain("&lt;not-allowed&gt;");
});
});
@@ -0,0 +1,78 @@
import { escapeHtml } from "./html";
export type AccessDeniedKind =
| "permission"
| "role"
| "feature"
| "client"
| "unavailable";
type AccessDeniedViewOptions = {
kind: AccessDeniedKind;
title?: string;
message: string;
detail?: string;
detailLabel?: string;
};
const ICONS: Record<AccessDeniedKind, string> = {
permission: "fa-user-lock",
role: "fa-shield-halved",
feature: "fa-toggle-off",
client: "fa-desktop",
unavailable: "fa-circle-pause",
};
export function renderAccessDeniedPage(options: AccessDeniedViewOptions): string {
const title = options.title || (
options.kind === "unavailable" ? "This feature is unavailable" : "You don't have access"
);
const detail = options.detail
? `
<div class="access-detail">
<span>${escapeHtml(options.detailLabel || "Required access")}</span>
<code>${escapeHtml(options.detail)}</code>
</div>`
: "";
return `<!doctype html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<meta name="turbo-visit-control" content="reload" />
<title>${escapeHtml(title)} · Overlord</title>
<link rel="icon" type="image/x-icon" href="/assets/favicon.ico" />
<link rel="stylesheet" href="/vendor/inter/400.css" />
<link rel="stylesheet" href="/vendor/inter/600.css" />
<link rel="stylesheet" href="/vendor/inter/700.css" />
<link rel="stylesheet" href="/vendor/fontawesome/css/all.min.css" />
<link rel="stylesheet" href="/assets/access-denied.css" />
</head>
<body>
<main class="access-shell">
<section class="access-card" aria-labelledby="access-title">
<div class="access-status">403 · Access restricted</div>
<div class="access-icon" aria-hidden="true">
<i class="fa-solid ${ICONS[options.kind]}"></i>
</div>
<h1 id="access-title">${escapeHtml(title)}</h1>
<p class="access-message">${escapeHtml(options.message)}</p>
${detail}
<p class="access-help">If you believe you should have access, ask an administrator to update your account.</p>
<div class="access-actions">
<a class="access-primary" href="/">
<i class="fa-solid fa-border-all" aria-hidden="true"></i>
Return to dashboard
</a>
<a class="access-secondary" href="/settings">
<i class="fa-solid fa-gear" aria-hidden="true"></i>
Account settings
</a>
</div>
</section>
<p class="access-footer"><i class="fa-solid fa-crown" aria-hidden="true"></i> Overlord</p>
</main>
</body>
</html>`;
}
+3 -1
View File
@@ -56,7 +56,9 @@ test.describe("authentication and authorization", () => {
const denied = await page.goto("/users"); const denied = await page.goto("/users");
expect(denied?.status()).toBe(403); expect(denied?.status()).toBe(403);
await expect(page.locator("body")).toContainText("missing permission users:manage"); await expect(page.getByRole("heading", { name: "You don't have access" })).toBeVisible();
await expect(page.locator(".access-detail")).toContainText("users:manage");
await expect(page.getByRole("link", { name: "Return to dashboard" })).toBeVisible();
const allowed = await page.goto("/metrics"); const allowed = await page.goto("/metrics");
expect(allowed?.status()).toBe(200); expect(allowed?.status()).toBe(200);
+1 -4
View File
@@ -23,12 +23,9 @@ fi
echo "[server] using bun at: $(command -v $BUN_BIN)" echo "[server] using bun at: $(command -v $BUN_BIN)"
echo "[server] bun install..." echo "[server] bun install..."
"$BUN_BIN" install "$BUN_BIN" install
echo "[server] building Tailwind CSS..."
"$BUN_BIN" run build:css
echo "[server] building vendor assets..."
"$BUN_BIN" run vendor
echo "[server] starting bun dev (foreground)" echo "[server] starting bun dev (foreground)"
# Use exec so the script process is replaced by the bun process. This keeps the # Use exec so the script process is replaced by the bun process. This keeps the
# bun process as a child of the dispatcher so the dispatcher can kill it. # bun process as a child of the dispatcher so the dispatcher can kill it.
export OVERLORD_AGENT_TOKEN="dev-token-insecure-local-only" export OVERLORD_AGENT_TOKEN="dev-token-insecure-local-only"
export NODE_ENV="development"
exec "$BUN_BIN" run dev exec "$BUN_BIN" run dev
+1 -1
View File
@@ -37,7 +37,7 @@ set OVERLORD_DISABLE_AGENT_AUTH=true
set LOG_LEVEL=debug set LOG_LEVEL=debug
set CGO_ENABLED=1 set CGO_ENABLED=1
start "Overlord-Server" cmd /k "cd /d ""%ROOT%Overlord-Server"" && set OVERLORD_DISABLE_AGENT_AUTH=true && set OVERLORD_AGENT_TOKEN=dev-token-insecure-local-only && set LOG_LEVEL=debug && set NODE_ENV=development && bun install && bun run start" start "Overlord-Server" cmd /k "cd /d ""%ROOT%Overlord-Server"" && set OVERLORD_DISABLE_AGENT_AUTH=true && set OVERLORD_AGENT_TOKEN=dev-token-insecure-local-only && set LOG_LEVEL=debug && set NODE_ENV=development && bun run dev"
timeout /t 3 /nobreak >nul timeout /t 3 /nobreak >nul
start "Overlord-Client" cmd /k "cd /d ""%ROOT%Overlord-Client"" && set CGO_ENABLED=1 && set OVERLORD_SERVER=wss://localhost:5173 && set OVERLORD_AGENT_TOKEN=dev-token-insecure-local-only && set OVERLORD_TLS_INSECURE_SKIP_VERIFY=true && set OVERLORD_MODE=dev && set OVERLORD_CAPTURE_METRICS=true && set GOINSECURE=* && set GOSUMDB=off && set GOPROXY=https://proxy.golang.org,direct && go mod tidy && go run ./cmd/agent" start "Overlord-Client" cmd /k "cd /d ""%ROOT%Overlord-Client"" && set CGO_ENABLED=1 && set OVERLORD_SERVER=wss://localhost:5173 && set OVERLORD_AGENT_TOKEN=dev-token-insecure-local-only && set OVERLORD_TLS_INSECURE_SKIP_VERIFY=true && set OVERLORD_MODE=dev && set OVERLORD_CAPTURE_METRICS=true && set GOINSECURE=* && set GOSUMDB=off && set GOPROXY=https://proxy.golang.org,direct && go mod tidy && go run ./cmd/agent"