@rubytech/create-maxy-code 0.1.198 → 0.1.200
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/package.json +2 -2
- package/payload/platform/plugins/admin/skills/platform-architecture/SKILL.md +3736 -0
- package/payload/platform/plugins/docs/references/admin-ui.md +3 -1
- package/payload/platform/scripts/check-architecture-skill-no-drift.mjs +67 -0
- package/payload/platform/services/claude-session-manager/dist/http-server.d.ts.map +1 -1
- package/payload/platform/services/claude-session-manager/dist/http-server.js +56 -0
- package/payload/platform/services/claude-session-manager/dist/http-server.js.map +1 -1
- package/payload/platform/services/claude-session-manager/dist/rc-daemon.d.ts +18 -0
- package/payload/platform/services/claude-session-manager/dist/rc-daemon.d.ts.map +1 -1
- package/payload/platform/services/claude-session-manager/dist/rc-daemon.js +25 -15
- package/payload/platform/services/claude-session-manager/dist/rc-daemon.js.map +1 -1
- package/payload/platform/templates/agents/admin/IDENTITY.md +4 -0
- package/payload/platform/templates/agents/public/IDENTITY.md +1 -1
- package/payload/server/public/assets/AdminShell-OJlDJakR.js +1 -0
- package/payload/server/public/assets/{Checkbox-Bh3kwzxP.js → Checkbox-DE_tsDq_.js} +1 -1
- package/payload/server/public/assets/{admin-BWzKAudL.js → admin-DbQw1TyC.js} +1 -1
- package/payload/server/public/assets/{architectureDiagram-Q4EWVU46-Boys2mT1.js → architectureDiagram-Q4EWVU46-DfZVWJVr.js} +1 -1
- package/payload/server/public/assets/{blockDiagram-DXYQGD6D-CvHqp46r.js → blockDiagram-DXYQGD6D-Cd9vcTYg.js} +1 -1
- package/payload/server/public/assets/{brand-VQtREmts.css → brand-Ed5R2W5J.css} +1 -1
- package/payload/server/public/assets/{c4Diagram-AHTNJAMY-DiNQ95F6.js → c4Diagram-AHTNJAMY-zmNCfJ5F.js} +1 -1
- package/payload/server/public/assets/channel-DCJza6li.js +1 -0
- package/payload/server/public/assets/{chunk-336JU56O-9nS9-05M.js → chunk-336JU56O-DvHeoV7B.js} +2 -2
- package/payload/server/public/assets/{chunk-426QAEUC-B2__9lRY.js → chunk-426QAEUC-IZknbXMM.js} +1 -1
- package/payload/server/public/assets/{chunk-4TB4RGXK-R5F8rS0Z.js → chunk-4TB4RGXK-DN_qw6Oi.js} +1 -1
- package/payload/server/public/assets/{chunk-5FUZZQ4R-B8HhJce-.js → chunk-5FUZZQ4R-tt-46Rcq.js} +1 -1
- package/payload/server/public/assets/{chunk-5PVQY5BW-Bjb08lbL.js → chunk-5PVQY5BW-Bl0mxmQP.js} +1 -1
- package/payload/server/public/assets/{chunk-EDXVE4YY-he0qCF3s.js → chunk-EDXVE4YY-v31HwKDb.js} +1 -1
- package/payload/server/public/assets/{chunk-ENJZ2VHE-BTArFW5l.js → chunk-ENJZ2VHE-D6T1RStj.js} +1 -1
- package/payload/server/public/assets/{chunk-ICPOFSXX-CoyIL4q_.js → chunk-ICPOFSXX-DVnIs_5A.js} +1 -1
- package/payload/server/public/assets/{chunk-OYMX7WX6-DjLEhNFe.js → chunk-OYMX7WX6-DiZNprr1.js} +1 -1
- package/payload/server/public/assets/{chunk-U2HBQHQK-tac2uvW1.js → chunk-U2HBQHQK-Cy0qH3H0.js} +1 -1
- package/payload/server/public/assets/{chunk-X2U36JSP-DIWD9i88.js → chunk-X2U36JSP-wR3wBPyu.js} +1 -1
- package/payload/server/public/assets/{chunk-YZCP3GAM-Ac7ogADz.js → chunk-YZCP3GAM-BGOVJLky.js} +1 -1
- package/payload/server/public/assets/{chunk-ZZ45TVLE-QgqDaY9-.js → chunk-ZZ45TVLE-14vtIjRh.js} +1 -1
- package/payload/server/public/assets/classDiagram-6PBFFD2Q-DEo4goqG.js +1 -0
- package/payload/server/public/assets/classDiagram-v2-HSJHXN6E-CoAVCeH7.js +1 -0
- package/payload/server/public/assets/clone-CLnBlH9n.js +1 -0
- package/payload/server/public/assets/{dagre-D6qN4nkK.js → dagre-CG1l6rfK.js} +1 -1
- package/payload/server/public/assets/{dagre-KV5264BT-C6TRKOg0.js → dagre-KV5264BT-DKFDl1Nz.js} +1 -1
- package/payload/server/public/assets/{data-CaZbNF-j.js → data-b1v7Pjly.js} +1 -1
- package/payload/server/public/assets/{diagram-5BDNPKRD-BVk_J8Pt.js → diagram-5BDNPKRD-PJd29fkg.js} +1 -1
- package/payload/server/public/assets/{diagram-G4DWMVQ6-BdV1IgwS.js → diagram-G4DWMVQ6-Bz7_SWJH.js} +1 -1
- package/payload/server/public/assets/{diagram-MMDJMWI5-OsvBkN6u.js → diagram-MMDJMWI5-CmWknm9v.js} +1 -1
- package/payload/server/public/assets/{diagram-TYMM5635-BQmKPyrb.js → diagram-TYMM5635-CLYRluM2.js} +1 -1
- package/payload/server/public/assets/{erDiagram-SMLLAGMA-ChEx5_3C.js → erDiagram-SMLLAGMA-EWVKGrgT.js} +1 -1
- package/payload/server/public/assets/{flowDiagram-DWJPFMVM-B7sf6AG3.js → flowDiagram-DWJPFMVM-CNtfJIG7.js} +1 -1
- package/payload/server/public/assets/{ganttDiagram-T4ZO3ILL-DbpSraax.js → ganttDiagram-T4ZO3ILL-SIlymJ6A.js} +1 -1
- package/payload/server/public/assets/{gitGraphDiagram-UUTBAWPF-BnxDElDh.js → gitGraphDiagram-UUTBAWPF-DWVl6CUl.js} +1 -1
- package/payload/server/public/assets/{graph-CBP5yppq.js → graph-BOcblKu9.js} +1 -1
- package/payload/server/public/assets/{graph-labels-BsZNScfa.js → graph-labels-CH-Tffon.js} +1 -1
- package/payload/server/public/assets/{graphlib-Dux06enE.js → graphlib-i-qJjJM7.js} +1 -1
- package/payload/server/public/assets/{infoDiagram-42DDH7IO-BLWb6oKx.js → infoDiagram-42DDH7IO-D66Yr_7b.js} +1 -1
- package/payload/server/public/assets/{ishikawaDiagram-UXIWVN3A-AFiRuE6G.js → ishikawaDiagram-UXIWVN3A-C4mQi7AB.js} +1 -1
- package/payload/server/public/assets/{journeyDiagram-VCZTEJTY-CxHBRGGu.js → journeyDiagram-VCZTEJTY-7Vp2UBlF.js} +1 -1
- package/payload/server/public/assets/{kanban-definition-6JOO6SKY-CGugF0N8.js → kanban-definition-6JOO6SKY-nEDANSe9.js} +1 -1
- package/payload/server/public/assets/{line-COFloj-X.js → line-BxGbTwly.js} +1 -1
- package/payload/server/public/assets/{mermaid-parser.core-CxXuCDQf.js → mermaid-parser.core-CAG4AdDd.js} +1 -1
- package/payload/server/public/assets/{mermaid.core-BRBNvNup.js → mermaid.core-prtUaAsI.js} +3 -3
- package/payload/server/public/assets/{mindmap-definition-QFDTVHPH-DarW5Wwq.js → mindmap-definition-QFDTVHPH-Dvcph8zi.js} +1 -1
- package/payload/server/public/assets/{pieDiagram-DEJITSTG-CTokFAkN.js → pieDiagram-DEJITSTG-C4qHs6Vb.js} +1 -1
- package/payload/server/public/assets/{public-Bq-eOUu9.js → public-DIyn-De4.js} +3 -3
- package/payload/server/public/assets/{quadrantDiagram-34T5L4WZ-BNawkg3I.js → quadrantDiagram-34T5L4WZ-I9Et2l2H.js} +1 -1
- package/payload/server/public/assets/{requirementDiagram-MS252O5E-CWnO56oR.js → requirementDiagram-MS252O5E-DLKlY81v.js} +1 -1
- package/payload/server/public/assets/{sankeyDiagram-XADWPNL6-D9c-EZfV.js → sankeyDiagram-XADWPNL6-dX3pgMv_.js} +1 -1
- package/payload/server/public/assets/{sequenceDiagram-FGHM5R23-In5lxCT5.js → sequenceDiagram-FGHM5R23-C4qTAl3F.js} +1 -1
- package/payload/server/public/assets/{stateDiagram-FHFEXIEX-CYb5js-u.js → stateDiagram-FHFEXIEX-DzA0NObk.js} +1 -1
- package/payload/server/public/assets/stateDiagram-v2-QKLJ7IA2-Dsgd5hEe.js +1 -0
- package/payload/server/public/assets/{timeline-definition-GMOUNBTQ-Cje-BY9v.js → timeline-definition-GMOUNBTQ-D-DPUQCU.js} +1 -1
- package/payload/server/public/assets/{useSelectionMode-B_2EQ2CC.js → useSelectionMode-C4HDuwDT.js} +1 -1
- package/payload/server/public/assets/{vennDiagram-DHZGUBPP-BqeuoPr1.js → vennDiagram-DHZGUBPP-C_RwTsUi.js} +1 -1
- package/payload/server/public/assets/{wardleyDiagram-NUSXRM2D-DE7xAnoq.js → wardleyDiagram-NUSXRM2D-BAftlsC2.js} +1 -1
- package/payload/server/public/assets/{xychartDiagram-5P7HB3ND-JE4x8YEZ.js → xychartDiagram-5P7HB3ND-C_tKMCMd.js} +1 -1
- package/payload/server/public/data.html +5 -5
- package/payload/server/public/graph.html +6 -6
- package/payload/server/public/index.html +6 -6
- package/payload/server/public/public.html +5 -5
- package/payload/server/server.js +399 -245
- package/payload/server/public/assets/AdminShell-DPk5UgEJ.js +0 -1
- package/payload/server/public/assets/channel-BgwH_qhE.js +0 -1
- package/payload/server/public/assets/classDiagram-6PBFFD2Q-CwdV1-c8.js +0 -1
- package/payload/server/public/assets/classDiagram-v2-HSJHXN6E-CS_jtevB.js +0 -1
- package/payload/server/public/assets/clone-BTishuSs.js +0 -1
- package/payload/server/public/assets/stateDiagram-v2-QKLJ7IA2-z-TVJfRt.js +0 -1
- /package/payload/server/public/assets/{brand-CzeO4m4J.js → brand-CCOPpjM4.js} +0 -0
package/payload/server/server.js
CHANGED
|
@@ -816,8 +816,8 @@ var serveStatic = (options = { root: "" }) => {
|
|
|
816
816
|
};
|
|
817
817
|
|
|
818
818
|
// server/index.ts
|
|
819
|
-
import { readFileSync as
|
|
820
|
-
import { resolve as
|
|
819
|
+
import { readFileSync as readFileSync22, existsSync as existsSync22, watchFile } from "fs";
|
|
820
|
+
import { resolve as resolve23, join as join17, basename as basename6 } from "path";
|
|
821
821
|
import { homedir as homedir2 } from "os";
|
|
822
822
|
import { monitorEventLoopDelay } from "perf_hooks";
|
|
823
823
|
|
|
@@ -1275,7 +1275,7 @@ var credsSaveQueue = Promise.resolve();
|
|
|
1275
1275
|
async function drainCredsSaveQueue(timeoutMs = 5e3) {
|
|
1276
1276
|
console.error(`${TAG2} draining credential save queue\u2026`);
|
|
1277
1277
|
const timer2 = new Promise(
|
|
1278
|
-
(
|
|
1278
|
+
(resolve24) => setTimeout(() => resolve24("timeout"), timeoutMs)
|
|
1279
1279
|
);
|
|
1280
1280
|
const result = await Promise.race([
|
|
1281
1281
|
credsSaveQueue.then(() => "drained"),
|
|
@@ -1403,11 +1403,11 @@ async function createWaSocket(opts) {
|
|
|
1403
1403
|
return sock;
|
|
1404
1404
|
}
|
|
1405
1405
|
async function waitForConnection(sock) {
|
|
1406
|
-
return new Promise((
|
|
1406
|
+
return new Promise((resolve24, reject) => {
|
|
1407
1407
|
const handler = (update) => {
|
|
1408
1408
|
if (update.connection === "open") {
|
|
1409
1409
|
sock.ev.off("connection.update", handler);
|
|
1410
|
-
|
|
1410
|
+
resolve24();
|
|
1411
1411
|
}
|
|
1412
1412
|
if (update.connection === "close") {
|
|
1413
1413
|
sock.ev.off("connection.update", handler);
|
|
@@ -1521,14 +1521,14 @@ ${inspected}`;
|
|
|
1521
1521
|
return inspect2(err, INSPECT_OPTS2);
|
|
1522
1522
|
}
|
|
1523
1523
|
function withTimeout(label, promise, timeoutMs) {
|
|
1524
|
-
return new Promise((
|
|
1524
|
+
return new Promise((resolve24, reject) => {
|
|
1525
1525
|
const timer2 = setTimeout(() => {
|
|
1526
1526
|
reject(new Error(`${label} timed out after ${timeoutMs}ms`));
|
|
1527
1527
|
}, timeoutMs);
|
|
1528
1528
|
promise.then(
|
|
1529
1529
|
(value) => {
|
|
1530
1530
|
clearTimeout(timer2);
|
|
1531
|
-
|
|
1531
|
+
resolve24(value);
|
|
1532
1532
|
},
|
|
1533
1533
|
(err) => {
|
|
1534
1534
|
clearTimeout(timer2);
|
|
@@ -2063,8 +2063,8 @@ async function persistWhatsAppMessage(input) {
|
|
|
2063
2063
|
const { givenName, familyName } = splitName(input.pushName);
|
|
2064
2064
|
const prev = sessionWriteLocks.get(input.cacheKey);
|
|
2065
2065
|
let release;
|
|
2066
|
-
const mine = new Promise((
|
|
2067
|
-
release =
|
|
2066
|
+
const mine = new Promise((resolve24) => {
|
|
2067
|
+
release = resolve24;
|
|
2068
2068
|
});
|
|
2069
2069
|
const chained = (prev ?? Promise.resolve()).then(() => mine);
|
|
2070
2070
|
sessionWriteLocks.set(input.cacheKey, chained);
|
|
@@ -3100,11 +3100,11 @@ async function connectWithReconnect(conn) {
|
|
|
3100
3100
|
console.error(
|
|
3101
3101
|
`${TAG12} reconnecting account=${conn.accountId} in ${delay}ms (attempt ${decision.nextAttempts}/${maxAttempts})`
|
|
3102
3102
|
);
|
|
3103
|
-
await new Promise((
|
|
3104
|
-
const timer2 = setTimeout(
|
|
3103
|
+
await new Promise((resolve24) => {
|
|
3104
|
+
const timer2 = setTimeout(resolve24, delay);
|
|
3105
3105
|
conn.abortController.signal.addEventListener("abort", () => {
|
|
3106
3106
|
clearTimeout(timer2);
|
|
3107
|
-
|
|
3107
|
+
resolve24();
|
|
3108
3108
|
}, { once: true });
|
|
3109
3109
|
});
|
|
3110
3110
|
}
|
|
@@ -3112,16 +3112,16 @@ async function connectWithReconnect(conn) {
|
|
|
3112
3112
|
}
|
|
3113
3113
|
}
|
|
3114
3114
|
function waitForDisconnectEvent(conn) {
|
|
3115
|
-
return new Promise((
|
|
3115
|
+
return new Promise((resolve24) => {
|
|
3116
3116
|
if (!conn.sock) {
|
|
3117
|
-
|
|
3117
|
+
resolve24();
|
|
3118
3118
|
return;
|
|
3119
3119
|
}
|
|
3120
3120
|
const sock = conn.sock;
|
|
3121
3121
|
const handler = (update) => {
|
|
3122
3122
|
if (update.connection === "close") {
|
|
3123
3123
|
sock.ev.off("connection.update", handler);
|
|
3124
|
-
|
|
3124
|
+
resolve24();
|
|
3125
3125
|
}
|
|
3126
3126
|
};
|
|
3127
3127
|
sock.ev.on("connection.update", handler);
|
|
@@ -3383,8 +3383,8 @@ async function handleInboundMessage(conn, msg) {
|
|
|
3383
3383
|
const conversationKey = isGroup ? remoteJid : senderPhone;
|
|
3384
3384
|
const debounceKey = `${conn.accountId}:${conversationKey}:${senderPhone}`;
|
|
3385
3385
|
let resolvePending;
|
|
3386
|
-
const sttPending = new Promise((
|
|
3387
|
-
resolvePending =
|
|
3386
|
+
const sttPending = new Promise((resolve24) => {
|
|
3387
|
+
resolvePending = resolve24;
|
|
3388
3388
|
});
|
|
3389
3389
|
if (conn.debouncer) conn.debouncer.registerPending(debounceKey, sttPending);
|
|
3390
3390
|
try {
|
|
@@ -3788,20 +3788,20 @@ function buildX11Env(chromiumWrapperPath, transport = "vnc") {
|
|
|
3788
3788
|
|
|
3789
3789
|
// server/routes/health.ts
|
|
3790
3790
|
function checkPort(port2, timeoutMs = 500) {
|
|
3791
|
-
return new Promise((
|
|
3791
|
+
return new Promise((resolve24) => {
|
|
3792
3792
|
const socket = createConnection2(port2, "127.0.0.1");
|
|
3793
3793
|
socket.setTimeout(timeoutMs);
|
|
3794
3794
|
socket.once("connect", () => {
|
|
3795
3795
|
socket.destroy();
|
|
3796
|
-
|
|
3796
|
+
resolve24(true);
|
|
3797
3797
|
});
|
|
3798
3798
|
socket.once("error", () => {
|
|
3799
3799
|
socket.destroy();
|
|
3800
|
-
|
|
3800
|
+
resolve24(false);
|
|
3801
3801
|
});
|
|
3802
3802
|
socket.once("timeout", () => {
|
|
3803
3803
|
socket.destroy();
|
|
3804
|
-
|
|
3804
|
+
resolve24(false);
|
|
3805
3805
|
});
|
|
3806
3806
|
});
|
|
3807
3807
|
}
|
|
@@ -4537,12 +4537,12 @@ async function dispatchOnce(input) {
|
|
|
4537
4537
|
});
|
|
4538
4538
|
if (!entry) return { error: "spawn-failed" };
|
|
4539
4539
|
entry.lastInboundAt = Date.now();
|
|
4540
|
-
let
|
|
4540
|
+
let resolve24;
|
|
4541
4541
|
const turnPromise = new Promise((r) => {
|
|
4542
|
-
|
|
4542
|
+
resolve24 = r;
|
|
4543
4543
|
});
|
|
4544
4544
|
const listener = (text) => {
|
|
4545
|
-
|
|
4545
|
+
resolve24(text);
|
|
4546
4546
|
};
|
|
4547
4547
|
entry.subscribers.add(listener);
|
|
4548
4548
|
const writeOk = await writeInput(entry, input.text);
|
|
@@ -4984,8 +4984,8 @@ async function startLogin(opts) {
|
|
|
4984
4984
|
resetActiveLogin(accountId);
|
|
4985
4985
|
let resolveQr = null;
|
|
4986
4986
|
let rejectQr = null;
|
|
4987
|
-
const qrPromise = new Promise((
|
|
4988
|
-
resolveQr =
|
|
4987
|
+
const qrPromise = new Promise((resolve24, reject) => {
|
|
4988
|
+
resolveQr = resolve24;
|
|
4989
4989
|
rejectQr = reject;
|
|
4990
4990
|
});
|
|
4991
4991
|
const qrTimer = setTimeout(
|
|
@@ -7458,11 +7458,11 @@ app11.delete("/:id", requireAdminSession, async (c) => {
|
|
|
7458
7458
|
const owned = await verifyConversationOwnership(sessionId, accountId);
|
|
7459
7459
|
if (!owned) return c.json({ error: "Conversation not found" }, 404);
|
|
7460
7460
|
const managerPort = requirePortEnv("CLAUDE_SESSION_MANAGER_PORT", { tag: "admin-conversation-delete" });
|
|
7461
|
-
const
|
|
7461
|
+
const managerBase5 = `http://127.0.0.1:${managerPort}`;
|
|
7462
7462
|
const outcome = await cascadeAdminConversationDelete({
|
|
7463
7463
|
sessionId,
|
|
7464
7464
|
accountId,
|
|
7465
|
-
managerBase:
|
|
7465
|
+
managerBase: managerBase5
|
|
7466
7466
|
});
|
|
7467
7467
|
if (outcome.ok) return c.json({ ok: true, claudeSessionIds: outcome.claudeSessionIds });
|
|
7468
7468
|
if (outcome.reason === "pty-still-alive") {
|
|
@@ -11159,7 +11159,7 @@ app18.post("/", requireAdminSession, async (c) => {
|
|
|
11159
11159
|
return c.json({ error: "AdminConversation node is missing sessionId" }, 500);
|
|
11160
11160
|
}
|
|
11161
11161
|
const managerPort = requirePortEnv("CLAUDE_SESSION_MANAGER_PORT", { tag: "graph-page-cascade" });
|
|
11162
|
-
const
|
|
11162
|
+
const managerBase5 = `http://127.0.0.1:${managerPort}`;
|
|
11163
11163
|
try {
|
|
11164
11164
|
await session.close();
|
|
11165
11165
|
} catch {
|
|
@@ -11167,7 +11167,7 @@ app18.post("/", requireAdminSession, async (c) => {
|
|
|
11167
11167
|
const outcome = await cascadeAdminConversationDelete({
|
|
11168
11168
|
sessionId,
|
|
11169
11169
|
accountId,
|
|
11170
|
-
managerBase:
|
|
11170
|
+
managerBase: managerBase5
|
|
11171
11171
|
});
|
|
11172
11172
|
const elapsed2 = Date.now() - started;
|
|
11173
11173
|
const labelSummary2 = preflightLabels.join(",");
|
|
@@ -11723,8 +11723,8 @@ var sidebar_artefacts_default = app22;
|
|
|
11723
11723
|
// server/routes/admin/sidebar-sessions.ts
|
|
11724
11724
|
import { readdirSync as readdirSync8, readFileSync as readFileSync14, statSync as statSync7 } from "fs";
|
|
11725
11725
|
import { join as join13 } from "path";
|
|
11726
|
-
var RC_URL_RE = /https:\/\/claude\.ai\/code\/session_[A-Za-z0-9_-]+/;
|
|
11727
11726
|
var SESSION_ID_RE = /^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}\.jsonl$/i;
|
|
11727
|
+
var PID_FILE_RE = /^([0-9]+)\.json$/;
|
|
11728
11728
|
var TITLE_MAX = 80;
|
|
11729
11729
|
var app23 = new Hono();
|
|
11730
11730
|
function claudeConfigDir() {
|
|
@@ -11772,8 +11772,8 @@ function enumerateJsonls(projectsRoot) {
|
|
|
11772
11772
|
}
|
|
11773
11773
|
return out;
|
|
11774
11774
|
}
|
|
11775
|
-
function
|
|
11776
|
-
const out = /* @__PURE__ */ new
|
|
11775
|
+
function sessionIdToPidMap(configDir2) {
|
|
11776
|
+
const out = /* @__PURE__ */ new Map();
|
|
11777
11777
|
const sessionsDir = join13(configDir2, "sessions");
|
|
11778
11778
|
let entries;
|
|
11779
11779
|
try {
|
|
@@ -11782,7 +11782,11 @@ function liveSessionIdSet(configDir2) {
|
|
|
11782
11782
|
return out;
|
|
11783
11783
|
}
|
|
11784
11784
|
for (const entry of entries) {
|
|
11785
|
-
if (!entry.isFile()
|
|
11785
|
+
if (!entry.isFile()) continue;
|
|
11786
|
+
const m = entry.name.match(PID_FILE_RE);
|
|
11787
|
+
if (!m) continue;
|
|
11788
|
+
const pid = Number(m[1]);
|
|
11789
|
+
if (!Number.isFinite(pid) || pid <= 0) continue;
|
|
11786
11790
|
let body;
|
|
11787
11791
|
try {
|
|
11788
11792
|
body = readFileSync14(join13(sessionsDir, entry.name), "utf8");
|
|
@@ -11797,7 +11801,7 @@ function liveSessionIdSet(configDir2) {
|
|
|
11797
11801
|
}
|
|
11798
11802
|
if (!parsed || typeof parsed !== "object") continue;
|
|
11799
11803
|
const sid = parsed.sessionId;
|
|
11800
|
-
if (typeof sid === "string" && sid.length > 0) out.
|
|
11804
|
+
if (typeof sid === "string" && sid.length > 0) out.set(sid, pid);
|
|
11801
11805
|
}
|
|
11802
11806
|
return out;
|
|
11803
11807
|
}
|
|
@@ -11822,21 +11826,23 @@ function firstUserMessage(body) {
|
|
|
11822
11826
|
return null;
|
|
11823
11827
|
}
|
|
11824
11828
|
app23.get("/", requireAdminSession, async (c) => {
|
|
11829
|
+
const accountId = process.env.ACCOUNT_ID ?? null;
|
|
11825
11830
|
const configDir2 = claudeConfigDir();
|
|
11826
11831
|
if (!configDir2) {
|
|
11827
11832
|
console.error("[admin-sessions-list] CLAUDE_CONFIG_DIR not set; returning empty list");
|
|
11828
|
-
return c.json({ sessions: [] });
|
|
11833
|
+
return c.json({ sessions: [], accountId });
|
|
11829
11834
|
}
|
|
11830
11835
|
const projectsRoot = join13(configDir2, "projects");
|
|
11831
11836
|
const jsonls = enumerateJsonls(projectsRoot);
|
|
11832
|
-
const
|
|
11837
|
+
const pidsBySession = sessionIdToPidMap(configDir2);
|
|
11833
11838
|
const rows = [];
|
|
11834
11839
|
const seenIds = /* @__PURE__ */ new Set();
|
|
11835
11840
|
let liveCount = 0;
|
|
11836
|
-
let rcCount = 0;
|
|
11837
11841
|
let subagentCount = 0;
|
|
11838
11842
|
for (const { path: path2, isSubagent } of jsonls) {
|
|
11839
|
-
const
|
|
11843
|
+
const lastSlash = path2.lastIndexOf("/");
|
|
11844
|
+
const base = path2.slice(lastSlash + 1);
|
|
11845
|
+
const projectDir = path2.slice(0, lastSlash);
|
|
11840
11846
|
const sessionId = base.slice(0, -".jsonl".length);
|
|
11841
11847
|
if (seenIds.has(sessionId)) {
|
|
11842
11848
|
console.error(`[admin-sessions-list] duplicate-sessionId sessionId=${sessionId} path=${path2}`);
|
|
@@ -11851,30 +11857,176 @@ app23.get("/", requireAdminSession, async (c) => {
|
|
|
11851
11857
|
} catch {
|
|
11852
11858
|
continue;
|
|
11853
11859
|
}
|
|
11854
|
-
const
|
|
11855
|
-
const live =
|
|
11860
|
+
const pid = pidsBySession.get(sessionId) ?? null;
|
|
11861
|
+
const live = pid !== null;
|
|
11856
11862
|
const title = firstUserMessage(body) ?? sessionId.slice(0, 8);
|
|
11857
|
-
|
|
11863
|
+
rows.push({
|
|
11858
11864
|
sessionId,
|
|
11859
11865
|
title,
|
|
11860
11866
|
startedAt: new Date(mtimeMs).toISOString(),
|
|
11861
11867
|
live,
|
|
11862
|
-
isSubagent
|
|
11863
|
-
|
|
11864
|
-
|
|
11865
|
-
|
|
11868
|
+
isSubagent,
|
|
11869
|
+
pid,
|
|
11870
|
+
projectDir
|
|
11871
|
+
});
|
|
11866
11872
|
if (live) liveCount += 1;
|
|
11867
|
-
if (urlMatch) rcCount += 1;
|
|
11868
11873
|
if (isSubagent) subagentCount += 1;
|
|
11869
11874
|
}
|
|
11870
11875
|
rows.sort((a, b) => a.startedAt < b.startedAt ? 1 : -1);
|
|
11871
11876
|
console.log(
|
|
11872
|
-
`[admin-sessions-list] rows=${rows.length} live=${liveCount}
|
|
11877
|
+
`[admin-sessions-list] rows=${rows.length} live=${liveCount} subagents=${subagentCount} accountId=${accountId ? accountId.slice(0, 8) : "unset"}`
|
|
11873
11878
|
);
|
|
11874
|
-
return c.json({ sessions: rows });
|
|
11879
|
+
return c.json({ sessions: rows, accountId });
|
|
11875
11880
|
});
|
|
11876
11881
|
var sidebar_sessions_default = app23;
|
|
11877
11882
|
|
|
11883
|
+
// server/routes/admin/session-delete.ts
|
|
11884
|
+
import { existsSync as existsSync17, readdirSync as readdirSync9, readFileSync as readFileSync15, unlinkSync as unlinkSync2 } from "fs";
|
|
11885
|
+
import { join as join14, resolve as resolve16 } from "path";
|
|
11886
|
+
var app24 = new Hono();
|
|
11887
|
+
var SESSION_ID_RE2 = /^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$/i;
|
|
11888
|
+
var PID_FILE_RE2 = /^([0-9]+)\.json$/;
|
|
11889
|
+
function findPidForSession(configDir2, sessionId) {
|
|
11890
|
+
const sessionsDir = join14(configDir2, "sessions");
|
|
11891
|
+
let entries;
|
|
11892
|
+
try {
|
|
11893
|
+
entries = readdirSync9(sessionsDir, { withFileTypes: true });
|
|
11894
|
+
} catch {
|
|
11895
|
+
return null;
|
|
11896
|
+
}
|
|
11897
|
+
for (const entry of entries) {
|
|
11898
|
+
if (!entry.isFile()) continue;
|
|
11899
|
+
const m = entry.name.match(PID_FILE_RE2);
|
|
11900
|
+
if (!m) continue;
|
|
11901
|
+
const pid = Number(m[1]);
|
|
11902
|
+
if (!Number.isFinite(pid) || pid <= 0) continue;
|
|
11903
|
+
let body;
|
|
11904
|
+
try {
|
|
11905
|
+
body = readFileSync15(join14(sessionsDir, entry.name), "utf8");
|
|
11906
|
+
} catch {
|
|
11907
|
+
continue;
|
|
11908
|
+
}
|
|
11909
|
+
let parsed;
|
|
11910
|
+
try {
|
|
11911
|
+
parsed = JSON.parse(body);
|
|
11912
|
+
} catch {
|
|
11913
|
+
continue;
|
|
11914
|
+
}
|
|
11915
|
+
if (!parsed || typeof parsed !== "object") continue;
|
|
11916
|
+
if (parsed.sessionId === sessionId) return pid;
|
|
11917
|
+
}
|
|
11918
|
+
return null;
|
|
11919
|
+
}
|
|
11920
|
+
function killBestEffort(pid) {
|
|
11921
|
+
try {
|
|
11922
|
+
process.kill(pid, "SIGTERM");
|
|
11923
|
+
return true;
|
|
11924
|
+
} catch {
|
|
11925
|
+
return false;
|
|
11926
|
+
}
|
|
11927
|
+
}
|
|
11928
|
+
app24.post("/", requireAdminSession, async (c) => {
|
|
11929
|
+
let body;
|
|
11930
|
+
try {
|
|
11931
|
+
body = await c.req.json();
|
|
11932
|
+
} catch {
|
|
11933
|
+
return c.json({ error: "invalid JSON body" }, 400);
|
|
11934
|
+
}
|
|
11935
|
+
const sessionId = typeof body.sessionId === "string" ? body.sessionId : "";
|
|
11936
|
+
const projectDir = typeof body.projectDir === "string" ? body.projectDir : "";
|
|
11937
|
+
if (!SESSION_ID_RE2.test(sessionId)) {
|
|
11938
|
+
return c.json({ error: "sessionId must be a v4 UUID" }, 400);
|
|
11939
|
+
}
|
|
11940
|
+
if (!projectDir) {
|
|
11941
|
+
return c.json({ error: "projectDir is required" }, 400);
|
|
11942
|
+
}
|
|
11943
|
+
const configDir2 = process.env.CLAUDE_CONFIG_DIR;
|
|
11944
|
+
if (!configDir2) {
|
|
11945
|
+
return c.json({ error: "CLAUDE_CONFIG_DIR not set" }, 500);
|
|
11946
|
+
}
|
|
11947
|
+
const projectsRoot = resolve16(join14(configDir2, "projects")) + "/";
|
|
11948
|
+
const resolvedProject = resolve16(projectDir) + "/";
|
|
11949
|
+
if (!resolvedProject.startsWith(projectsRoot)) {
|
|
11950
|
+
console.error(`[sessions-delete] reject reason=projectDir-outside-tree projectDir=${projectDir}`);
|
|
11951
|
+
return c.json({ error: "projectDir is not under CLAUDE_CONFIG_DIR/projects/" }, 400);
|
|
11952
|
+
}
|
|
11953
|
+
const jsonlPath = join14(projectDir, `${sessionId}.jsonl`);
|
|
11954
|
+
const sidecarPath = join14(projectDir, `${sessionId}.meta.json`);
|
|
11955
|
+
const pid = findPidForSession(configDir2, sessionId);
|
|
11956
|
+
let pidKilled;
|
|
11957
|
+
if (pid === null) {
|
|
11958
|
+
pidKilled = "absent";
|
|
11959
|
+
} else {
|
|
11960
|
+
pidKilled = killBestEffort(pid) ? "true" : "false";
|
|
11961
|
+
}
|
|
11962
|
+
let deleted = false;
|
|
11963
|
+
try {
|
|
11964
|
+
if (existsSync17(jsonlPath)) {
|
|
11965
|
+
unlinkSync2(jsonlPath);
|
|
11966
|
+
deleted = true;
|
|
11967
|
+
}
|
|
11968
|
+
} catch (err) {
|
|
11969
|
+
const msg = err instanceof Error ? err.message : String(err);
|
|
11970
|
+
console.error(`[sessions-delete] unlink-failed path=${jsonlPath} err=${msg}`);
|
|
11971
|
+
console.log(
|
|
11972
|
+
`[sessions-delete] sessionId=${sessionId} pidKilled=${pidKilled} jsonlPath=${jsonlPath} deleted=false`
|
|
11973
|
+
);
|
|
11974
|
+
return c.json({ error: `unlink failed: ${msg}` }, 500);
|
|
11975
|
+
}
|
|
11976
|
+
try {
|
|
11977
|
+
if (existsSync17(sidecarPath)) unlinkSync2(sidecarPath);
|
|
11978
|
+
} catch {
|
|
11979
|
+
}
|
|
11980
|
+
console.log(
|
|
11981
|
+
`[sessions-delete] sessionId=${sessionId} pidKilled=${pidKilled} jsonlPath=${jsonlPath} deleted=${deleted}`
|
|
11982
|
+
);
|
|
11983
|
+
return c.json({ deleted, pidKilled, jsonlPath });
|
|
11984
|
+
});
|
|
11985
|
+
var session_delete_default = app24;
|
|
11986
|
+
|
|
11987
|
+
// server/routes/admin/session-rc-spawn.ts
|
|
11988
|
+
var app25 = new Hono();
|
|
11989
|
+
function managerBase4() {
|
|
11990
|
+
const port2 = process.env.CLAUDE_SESSION_MANAGER_PORT;
|
|
11991
|
+
if (!port2) throw new Error("CLAUDE_SESSION_MANAGER_PORT is not set");
|
|
11992
|
+
return `http://127.0.0.1:${port2}`;
|
|
11993
|
+
}
|
|
11994
|
+
app25.post("/", requireAdminSession, async (c) => {
|
|
11995
|
+
let body;
|
|
11996
|
+
try {
|
|
11997
|
+
body = await c.req.json();
|
|
11998
|
+
} catch {
|
|
11999
|
+
body = {};
|
|
12000
|
+
}
|
|
12001
|
+
const payload = {};
|
|
12002
|
+
if (typeof body.sessionId === "string" && body.sessionId.length > 0) payload.sessionId = body.sessionId;
|
|
12003
|
+
if (typeof body.name === "string" && body.name.length > 0) payload.name = body.name;
|
|
12004
|
+
let res;
|
|
12005
|
+
try {
|
|
12006
|
+
res = await fetch(`${managerBase4()}/rc-spawn`, {
|
|
12007
|
+
method: "POST",
|
|
12008
|
+
headers: { "content-type": "application/json" },
|
|
12009
|
+
body: JSON.stringify(payload)
|
|
12010
|
+
});
|
|
12011
|
+
} catch (err) {
|
|
12012
|
+
const msg = err instanceof Error ? err.message : String(err);
|
|
12013
|
+
console.error(`[session-rc-spawn] manager-unreachable err=${msg}`);
|
|
12014
|
+
return c.json({ error: `session manager unreachable: ${msg}` }, 502);
|
|
12015
|
+
}
|
|
12016
|
+
const text = await res.text();
|
|
12017
|
+
let parsed = null;
|
|
12018
|
+
try {
|
|
12019
|
+
parsed = JSON.parse(text);
|
|
12020
|
+
} catch {
|
|
12021
|
+
}
|
|
12022
|
+
if (!res.ok) {
|
|
12023
|
+
console.error(`[session-rc-spawn] manager-error status=${res.status} body=${text.slice(0, 200)}`);
|
|
12024
|
+
return c.json(parsed ?? { error: text }, res.status);
|
|
12025
|
+
}
|
|
12026
|
+
return c.json(parsed ?? {});
|
|
12027
|
+
});
|
|
12028
|
+
var session_rc_spawn_default = app25;
|
|
12029
|
+
|
|
11878
12030
|
// server/routes/admin/system-stats.ts
|
|
11879
12031
|
import { readFile as readFile5 } from "fs/promises";
|
|
11880
12032
|
import { cpus, loadavg, totalmem, freemem } from "os";
|
|
@@ -11970,8 +12122,8 @@ async function sample() {
|
|
|
11970
12122
|
if (process.platform === "linux") return sampleLinux();
|
|
11971
12123
|
return sampleOsFallback();
|
|
11972
12124
|
}
|
|
11973
|
-
var
|
|
11974
|
-
|
|
12125
|
+
var app26 = new Hono();
|
|
12126
|
+
app26.get("/", async (c) => {
|
|
11975
12127
|
const started = Date.now();
|
|
11976
12128
|
if (!inflight) {
|
|
11977
12129
|
inflight = sample().finally(() => {
|
|
@@ -11994,27 +12146,27 @@ app24.get("/", async (c) => {
|
|
|
11994
12146
|
return c.json({ degraded: true, reason, sampledAtMs: Date.now() });
|
|
11995
12147
|
}
|
|
11996
12148
|
});
|
|
11997
|
-
var system_stats_default =
|
|
12149
|
+
var system_stats_default = app26;
|
|
11998
12150
|
|
|
11999
12151
|
// server/routes/admin/health.ts
|
|
12000
|
-
import { existsSync as
|
|
12001
|
-
import { resolve as
|
|
12002
|
-
var PLATFORM_ROOT6 = process.env.MAXY_PLATFORM_ROOT ??
|
|
12152
|
+
import { existsSync as existsSync18, readFileSync as readFileSync16 } from "fs";
|
|
12153
|
+
import { resolve as resolve17, join as join15 } from "path";
|
|
12154
|
+
var PLATFORM_ROOT6 = process.env.MAXY_PLATFORM_ROOT ?? resolve17(process.cwd(), "..");
|
|
12003
12155
|
var brandHostname = "maxy";
|
|
12004
|
-
var brandJsonPath =
|
|
12005
|
-
if (
|
|
12156
|
+
var brandJsonPath = join15(PLATFORM_ROOT6, "config", "brand.json");
|
|
12157
|
+
if (existsSync18(brandJsonPath)) {
|
|
12006
12158
|
try {
|
|
12007
|
-
const brand = JSON.parse(
|
|
12159
|
+
const brand = JSON.parse(readFileSync16(brandJsonPath, "utf-8"));
|
|
12008
12160
|
if (brand.hostname) brandHostname = brand.hostname;
|
|
12009
12161
|
} catch {
|
|
12010
12162
|
}
|
|
12011
12163
|
}
|
|
12012
|
-
var VERSION_FILE =
|
|
12164
|
+
var VERSION_FILE = resolve17(PLATFORM_ROOT6, `config/.${brandHostname}-version`);
|
|
12013
12165
|
var PROCESS_STARTED_AT = (/* @__PURE__ */ new Date()).toISOString();
|
|
12014
12166
|
var PROBE_TIMEOUT_MS = 1e3;
|
|
12015
12167
|
function readVersion() {
|
|
12016
|
-
if (!
|
|
12017
|
-
return
|
|
12168
|
+
if (!existsSync18(VERSION_FILE)) return "unknown";
|
|
12169
|
+
return readFileSync16(VERSION_FILE, "utf-8").trim() || "unknown";
|
|
12018
12170
|
}
|
|
12019
12171
|
async function probeConversationDb() {
|
|
12020
12172
|
let session;
|
|
@@ -12039,8 +12191,8 @@ async function probeConversationDb() {
|
|
|
12039
12191
|
});
|
|
12040
12192
|
}
|
|
12041
12193
|
}
|
|
12042
|
-
var
|
|
12043
|
-
|
|
12194
|
+
var app27 = new Hono();
|
|
12195
|
+
app27.get("/", async (c) => {
|
|
12044
12196
|
const version = readVersion();
|
|
12045
12197
|
const probe = await probeConversationDb();
|
|
12046
12198
|
const uptimeMs = Date.now() - new Date(PROCESS_STARTED_AT).getTime();
|
|
@@ -12062,7 +12214,7 @@ app25.get("/", async (c) => {
|
|
|
12062
12214
|
uptimeMs
|
|
12063
12215
|
});
|
|
12064
12216
|
});
|
|
12065
|
-
var health_default2 =
|
|
12217
|
+
var health_default2 = app27;
|
|
12066
12218
|
|
|
12067
12219
|
// server/routes/admin/linkedin-ingest.ts
|
|
12068
12220
|
var TAG20 = "[linkedin-ingest-route]";
|
|
@@ -12158,8 +12310,8 @@ function buildInitialMessage(env) {
|
|
|
12158
12310
|
}
|
|
12159
12311
|
return header;
|
|
12160
12312
|
}
|
|
12161
|
-
var
|
|
12162
|
-
|
|
12313
|
+
var app28 = new Hono();
|
|
12314
|
+
app28.post("/", requireAdminSession, async (c) => {
|
|
12163
12315
|
let body;
|
|
12164
12316
|
try {
|
|
12165
12317
|
body = await c.req.json();
|
|
@@ -12213,7 +12365,7 @@ app26.post("/", requireAdminSession, async (c) => {
|
|
|
12213
12365
|
);
|
|
12214
12366
|
return c.json({ ok: true, dispatchId: envelope.dispatchId, taskId: claudeSessionId }, 202);
|
|
12215
12367
|
});
|
|
12216
|
-
var linkedin_ingest_default =
|
|
12368
|
+
var linkedin_ingest_default = app28;
|
|
12217
12369
|
|
|
12218
12370
|
// server/routes/admin/post-turn-context.ts
|
|
12219
12371
|
import neo4j2 from "neo4j-driver";
|
|
@@ -12255,8 +12407,8 @@ function pruneProperties(raw) {
|
|
|
12255
12407
|
}
|
|
12256
12408
|
return out;
|
|
12257
12409
|
}
|
|
12258
|
-
var
|
|
12259
|
-
|
|
12410
|
+
var app29 = new Hono();
|
|
12411
|
+
app29.get("/", async (c) => {
|
|
12260
12412
|
const remoteAddr = c.env?.incoming?.socket?.remoteAddress ?? "";
|
|
12261
12413
|
if (!isLoopbackAddr2(remoteAddr)) {
|
|
12262
12414
|
console.error(`${TAG21} reject reason=non-loopback remoteAddr=${remoteAddr}`);
|
|
@@ -12316,7 +12468,7 @@ app27.get("/", async (c) => {
|
|
|
12316
12468
|
await session.close();
|
|
12317
12469
|
}
|
|
12318
12470
|
});
|
|
12319
|
-
var post_turn_context_default =
|
|
12471
|
+
var post_turn_context_default = app29;
|
|
12320
12472
|
|
|
12321
12473
|
// server/routes/admin/public-session-context.ts
|
|
12322
12474
|
import neo4j3 from "neo4j-driver";
|
|
@@ -12358,8 +12510,8 @@ function pruneProperties2(raw) {
|
|
|
12358
12510
|
}
|
|
12359
12511
|
return out;
|
|
12360
12512
|
}
|
|
12361
|
-
var
|
|
12362
|
-
|
|
12513
|
+
var app30 = new Hono();
|
|
12514
|
+
app30.get("/", async (c) => {
|
|
12363
12515
|
const remoteAddr = c.env?.incoming?.socket?.remoteAddress ?? "";
|
|
12364
12516
|
if (!isLoopbackAddr3(remoteAddr)) {
|
|
12365
12517
|
console.error(`${TAG22} reject reason=non-loopback remoteAddr=${remoteAddr}`);
|
|
@@ -12418,15 +12570,15 @@ app28.get("/", async (c) => {
|
|
|
12418
12570
|
await session.close();
|
|
12419
12571
|
}
|
|
12420
12572
|
});
|
|
12421
|
-
var public_session_context_default =
|
|
12573
|
+
var public_session_context_default = app30;
|
|
12422
12574
|
|
|
12423
12575
|
// server/routes/admin/public-session-exit.ts
|
|
12424
12576
|
var TAG23 = "[public-session-exit-route]";
|
|
12425
12577
|
function isLoopbackAddr4(addr) {
|
|
12426
12578
|
return addr === "127.0.0.1" || addr === "::1" || addr === "::ffff:127.0.0.1";
|
|
12427
12579
|
}
|
|
12428
|
-
var
|
|
12429
|
-
|
|
12580
|
+
var app31 = new Hono();
|
|
12581
|
+
app31.post("/", async (c) => {
|
|
12430
12582
|
const remoteAddr = c.env?.incoming?.socket?.remoteAddress ?? "";
|
|
12431
12583
|
if (!isLoopbackAddr4(remoteAddr)) {
|
|
12432
12584
|
console.error(`${TAG23} reject reason=non-loopback remoteAddr=${remoteAddr}`);
|
|
@@ -12453,15 +12605,15 @@ app29.post("/", async (c) => {
|
|
|
12453
12605
|
handlePublicSessionExit(sessionId);
|
|
12454
12606
|
return c.json({ ok: true });
|
|
12455
12607
|
});
|
|
12456
|
-
var public_session_exit_default =
|
|
12608
|
+
var public_session_exit_default = app31;
|
|
12457
12609
|
|
|
12458
12610
|
// server/routes/admin/access-session-evict.ts
|
|
12459
12611
|
var TAG24 = "[access-session-evict]";
|
|
12460
12612
|
function isLoopbackAddr5(addr) {
|
|
12461
12613
|
return addr === "127.0.0.1" || addr === "::1" || addr === "::ffff:127.0.0.1";
|
|
12462
12614
|
}
|
|
12463
|
-
var
|
|
12464
|
-
|
|
12615
|
+
var app32 = new Hono();
|
|
12616
|
+
app32.post("/", async (c) => {
|
|
12465
12617
|
const remoteAddr = c.env?.incoming?.socket?.remoteAddress ?? "";
|
|
12466
12618
|
if (!isLoopbackAddr5(remoteAddr)) {
|
|
12467
12619
|
console.error(`${TAG24} reject reason=non-loopback remoteAddr=${remoteAddr}`);
|
|
@@ -12489,49 +12641,51 @@ app30.post("/", async (c) => {
|
|
|
12489
12641
|
console.log(`${TAG24} grantId=${grantId} dropped=${dropped}`);
|
|
12490
12642
|
return c.json({ ok: true, dropped });
|
|
12491
12643
|
});
|
|
12492
|
-
var access_session_evict_default =
|
|
12644
|
+
var access_session_evict_default = app32;
|
|
12493
12645
|
|
|
12494
12646
|
// server/routes/admin/index.ts
|
|
12495
|
-
var
|
|
12496
|
-
|
|
12497
|
-
|
|
12498
|
-
|
|
12499
|
-
|
|
12500
|
-
|
|
12501
|
-
|
|
12502
|
-
|
|
12503
|
-
|
|
12504
|
-
|
|
12505
|
-
|
|
12506
|
-
|
|
12507
|
-
|
|
12508
|
-
|
|
12509
|
-
|
|
12510
|
-
|
|
12511
|
-
|
|
12512
|
-
|
|
12513
|
-
|
|
12514
|
-
|
|
12515
|
-
|
|
12516
|
-
|
|
12517
|
-
|
|
12518
|
-
|
|
12519
|
-
|
|
12520
|
-
|
|
12521
|
-
|
|
12647
|
+
var app33 = new Hono();
|
|
12648
|
+
app33.route("/session", session_default);
|
|
12649
|
+
app33.route("/logs", logs_default);
|
|
12650
|
+
app33.route("/claude-info", claude_info_default);
|
|
12651
|
+
app33.route("/attachment", attachment_default);
|
|
12652
|
+
app33.route("/agents", agents_default);
|
|
12653
|
+
app33.route("/sessions", sessions_default);
|
|
12654
|
+
app33.route("/claude-sessions", claude_sessions_default);
|
|
12655
|
+
app33.route("/log-ingest", log_ingest_default);
|
|
12656
|
+
app33.route("/events", events_default);
|
|
12657
|
+
app33.route("/files", files_default);
|
|
12658
|
+
app33.route("/graph-search", graph_search_default);
|
|
12659
|
+
app33.route("/graph-subgraph", graph_subgraph_default);
|
|
12660
|
+
app33.route("/graph-delete", graph_delete_default);
|
|
12661
|
+
app33.route("/graph-restore", graph_restore_default);
|
|
12662
|
+
app33.route("/graph-labels-in-graph", graph_labels_in_graph_default);
|
|
12663
|
+
app33.route("/graph-default-view", graph_default_view_default);
|
|
12664
|
+
app33.route("/sidebar-artefacts", sidebar_artefacts_default);
|
|
12665
|
+
app33.route("/sidebar-sessions", sidebar_sessions_default);
|
|
12666
|
+
app33.route("/session-delete", session_delete_default);
|
|
12667
|
+
app33.route("/session-rc-spawn", session_rc_spawn_default);
|
|
12668
|
+
app33.route("/system-stats", system_stats_default);
|
|
12669
|
+
app33.route("/health-brand", health_default2);
|
|
12670
|
+
app33.route("/linkedin-ingest", linkedin_ingest_default);
|
|
12671
|
+
app33.route("/post-turn-context", post_turn_context_default);
|
|
12672
|
+
app33.route("/public-session-context", public_session_context_default);
|
|
12673
|
+
app33.route("/public-session-exit", public_session_exit_default);
|
|
12674
|
+
app33.route("/access-session-evict", access_session_evict_default);
|
|
12675
|
+
var admin_default = app33;
|
|
12522
12676
|
|
|
12523
12677
|
// app/lib/access-gate.ts
|
|
12524
12678
|
import neo4j4 from "neo4j-driver";
|
|
12525
|
-
import { readFileSync as
|
|
12526
|
-
import { resolve as
|
|
12679
|
+
import { readFileSync as readFileSync17 } from "fs";
|
|
12680
|
+
import { resolve as resolve18 } from "path";
|
|
12527
12681
|
import { randomUUID as randomUUID8 } from "crypto";
|
|
12528
|
-
var PLATFORM_ROOT7 = process.env.MAXY_PLATFORM_ROOT ??
|
|
12682
|
+
var PLATFORM_ROOT7 = process.env.MAXY_PLATFORM_ROOT ?? resolve18(process.cwd(), "..");
|
|
12529
12683
|
var driver = null;
|
|
12530
12684
|
function readPassword() {
|
|
12531
12685
|
if (process.env.NEO4J_PASSWORD) return process.env.NEO4J_PASSWORD;
|
|
12532
|
-
const passwordFile =
|
|
12686
|
+
const passwordFile = resolve18(PLATFORM_ROOT7, "config/.neo4j-password");
|
|
12533
12687
|
try {
|
|
12534
|
-
return
|
|
12688
|
+
return readFileSync17(passwordFile, "utf-8").trim();
|
|
12535
12689
|
} catch {
|
|
12536
12690
|
throw new Error(
|
|
12537
12691
|
`Neo4j password not found. Expected at ${passwordFile} or in NEO4J_PASSWORD env var.`
|
|
@@ -12732,8 +12886,8 @@ async function generateNewMagicToken(grantId) {
|
|
|
12732
12886
|
var TAG25 = "[access-verify]";
|
|
12733
12887
|
var MINT_TAG = "[access-session-mint]";
|
|
12734
12888
|
var COOKIE_NAME = "__access_session";
|
|
12735
|
-
var
|
|
12736
|
-
|
|
12889
|
+
var app34 = new Hono();
|
|
12890
|
+
app34.post("/", async (c) => {
|
|
12737
12891
|
const ip = c.var.clientIp || "unknown";
|
|
12738
12892
|
let body;
|
|
12739
12893
|
try {
|
|
@@ -12815,13 +12969,13 @@ app32.post("/", async (c) => {
|
|
|
12815
12969
|
displayName: grant.displayName
|
|
12816
12970
|
});
|
|
12817
12971
|
});
|
|
12818
|
-
var verify_token_default =
|
|
12972
|
+
var verify_token_default = app34;
|
|
12819
12973
|
|
|
12820
12974
|
// app/lib/access-email.ts
|
|
12821
12975
|
import { spawn as spawn2 } from "child_process";
|
|
12822
|
-
import { resolve as
|
|
12823
|
-
var PLATFORM_ROOT8 = process.env.MAXY_PLATFORM_ROOT ??
|
|
12824
|
-
var SEND_SCRIPT =
|
|
12976
|
+
import { resolve as resolve19 } from "path";
|
|
12977
|
+
var PLATFORM_ROOT8 = process.env.MAXY_PLATFORM_ROOT ?? resolve19(process.cwd(), "..");
|
|
12978
|
+
var SEND_SCRIPT = resolve19(
|
|
12825
12979
|
PLATFORM_ROOT8,
|
|
12826
12980
|
"plugins",
|
|
12827
12981
|
"email",
|
|
@@ -12878,9 +13032,9 @@ async function sendMagicLinkEmail(payload) {
|
|
|
12878
13032
|
|
|
12879
13033
|
// server/routes/access/request-magic-link.ts
|
|
12880
13034
|
var TAG26 = "[access-request-link]";
|
|
12881
|
-
var
|
|
13035
|
+
var app35 = new Hono();
|
|
12882
13036
|
var VISITOR_MESSAGE = "If that email is on the invite list, a fresh link is on the way.";
|
|
12883
|
-
|
|
13037
|
+
app35.post("/", async (c) => {
|
|
12884
13038
|
let body;
|
|
12885
13039
|
try {
|
|
12886
13040
|
body = await c.req.json();
|
|
@@ -12954,17 +13108,17 @@ app33.post("/", async (c) => {
|
|
|
12954
13108
|
);
|
|
12955
13109
|
return c.json({ message: VISITOR_MESSAGE }, 200);
|
|
12956
13110
|
});
|
|
12957
|
-
var request_magic_link_default =
|
|
13111
|
+
var request_magic_link_default = app35;
|
|
12958
13112
|
|
|
12959
13113
|
// server/routes/access/index.ts
|
|
12960
|
-
var
|
|
12961
|
-
|
|
12962
|
-
|
|
12963
|
-
var access_default =
|
|
13114
|
+
var app36 = new Hono();
|
|
13115
|
+
app36.route("/verify-token", verify_token_default);
|
|
13116
|
+
app36.route("/request-magic-link", request_magic_link_default);
|
|
13117
|
+
var access_default = app36;
|
|
12964
13118
|
|
|
12965
13119
|
// server/routes/sites.ts
|
|
12966
|
-
import { existsSync as
|
|
12967
|
-
import { resolve as
|
|
13120
|
+
import { existsSync as existsSync19, readFileSync as readFileSync18, realpathSync as realpathSync5, statSync as statSync8 } from "fs";
|
|
13121
|
+
import { resolve as resolve20 } from "path";
|
|
12968
13122
|
var SAFE_SEG_RE = /^[a-z0-9_][a-z0-9_.-]{0,99}$/i;
|
|
12969
13123
|
var MIME = {
|
|
12970
13124
|
".html": "text/html; charset=utf-8",
|
|
@@ -12995,8 +13149,8 @@ function getExt(p) {
|
|
|
12995
13149
|
if (idx < p.lastIndexOf("/")) return "";
|
|
12996
13150
|
return p.slice(idx).toLowerCase();
|
|
12997
13151
|
}
|
|
12998
|
-
var
|
|
12999
|
-
|
|
13152
|
+
var app37 = new Hono();
|
|
13153
|
+
app37.get("/:rel{.*}", (c) => {
|
|
13000
13154
|
const reqPath = c.req.path;
|
|
13001
13155
|
const rawRel = c.req.param("rel") ?? "";
|
|
13002
13156
|
const trimmed = rawRel.replace(/^\/+/, "").replace(/\/+$/, "");
|
|
@@ -13021,15 +13175,15 @@ app35.get("/:rel{.*}", (c) => {
|
|
|
13021
13175
|
}
|
|
13022
13176
|
segments.push(seg);
|
|
13023
13177
|
}
|
|
13024
|
-
const rootDir =
|
|
13025
|
-
let filePath = segments.length === 0 ? rootDir :
|
|
13178
|
+
const rootDir = resolve20(account.accountDir, "sites");
|
|
13179
|
+
let filePath = segments.length === 0 ? rootDir : resolve20(rootDir, ...segments);
|
|
13026
13180
|
if (filePath !== rootDir && !filePath.startsWith(rootDir + "/")) {
|
|
13027
13181
|
console.error(`[sites] path-traversal-rejected path=${reqPath} reason=escape status=403`);
|
|
13028
13182
|
return c.text("Forbidden", 403);
|
|
13029
13183
|
}
|
|
13030
13184
|
let stat7;
|
|
13031
13185
|
try {
|
|
13032
|
-
stat7 =
|
|
13186
|
+
stat7 = existsSync19(filePath) ? statSync8(filePath) : null;
|
|
13033
13187
|
} catch {
|
|
13034
13188
|
stat7 = null;
|
|
13035
13189
|
}
|
|
@@ -13042,13 +13196,13 @@ app35.get("/:rel{.*}", (c) => {
|
|
|
13042
13196
|
return c.redirect(target, 301);
|
|
13043
13197
|
}
|
|
13044
13198
|
if (stat7?.isDirectory()) {
|
|
13045
|
-
filePath =
|
|
13199
|
+
filePath = resolve20(filePath, "index.html");
|
|
13046
13200
|
}
|
|
13047
13201
|
if (!filePath.startsWith(rootDir + "/")) {
|
|
13048
13202
|
console.error(`[sites] path-traversal-rejected path=${reqPath} reason=escape status=403`);
|
|
13049
13203
|
return c.text("Forbidden", 403);
|
|
13050
13204
|
}
|
|
13051
|
-
if (!
|
|
13205
|
+
if (!existsSync19(filePath)) {
|
|
13052
13206
|
console.error(`[sites] not-found path=${reqPath} status=404`);
|
|
13053
13207
|
return c.text("Not found", 404);
|
|
13054
13208
|
}
|
|
@@ -13067,7 +13221,7 @@ app35.get("/:rel{.*}", (c) => {
|
|
|
13067
13221
|
}
|
|
13068
13222
|
let body;
|
|
13069
13223
|
try {
|
|
13070
|
-
body =
|
|
13224
|
+
body = readFileSync18(realPath);
|
|
13071
13225
|
} catch (err) {
|
|
13072
13226
|
const code = err?.code;
|
|
13073
13227
|
if (code === "EISDIR") {
|
|
@@ -13099,11 +13253,11 @@ app35.get("/:rel{.*}", (c) => {
|
|
|
13099
13253
|
"X-Content-Type-Options": "nosniff"
|
|
13100
13254
|
});
|
|
13101
13255
|
});
|
|
13102
|
-
var sites_default =
|
|
13256
|
+
var sites_default = app37;
|
|
13103
13257
|
|
|
13104
13258
|
// app/lib/visitor-token.ts
|
|
13105
13259
|
import { createHmac, randomBytes, timingSafeEqual } from "crypto";
|
|
13106
|
-
import { mkdirSync as mkdirSync4, readFileSync as
|
|
13260
|
+
import { mkdirSync as mkdirSync4, readFileSync as readFileSync19, writeFileSync as writeFileSync6 } from "fs";
|
|
13107
13261
|
import { dirname as dirname4 } from "path";
|
|
13108
13262
|
var TOKEN_PREFIX = "v1.";
|
|
13109
13263
|
var SECRET_BYTES = 32;
|
|
@@ -13112,7 +13266,7 @@ var cachedSecret = null;
|
|
|
13112
13266
|
function getSecret() {
|
|
13113
13267
|
if (cachedSecret) return cachedSecret;
|
|
13114
13268
|
try {
|
|
13115
|
-
const hex2 =
|
|
13269
|
+
const hex2 = readFileSync19(VISITOR_TOKEN_SECRET_FILE, "utf-8").trim();
|
|
13116
13270
|
if (hex2.length === SECRET_BYTES * 2) {
|
|
13117
13271
|
cachedSecret = Buffer.from(hex2, "hex");
|
|
13118
13272
|
return cachedSecret;
|
|
@@ -13126,7 +13280,7 @@ function getSecret() {
|
|
|
13126
13280
|
console.log(`[visitor-token] secret minted path=${VISITOR_TOKEN_SECRET_FILE}`);
|
|
13127
13281
|
} catch {
|
|
13128
13282
|
}
|
|
13129
|
-
const hex =
|
|
13283
|
+
const hex = readFileSync19(VISITOR_TOKEN_SECRET_FILE, "utf-8").trim();
|
|
13130
13284
|
cachedSecret = Buffer.from(hex, "hex");
|
|
13131
13285
|
return cachedSecret;
|
|
13132
13286
|
}
|
|
@@ -13179,8 +13333,8 @@ var VISITOR_COOKIE_NAME = "mxy_v";
|
|
|
13179
13333
|
var VISITOR_COOKIE_MAX_AGE_SECONDS = Math.floor(DEFAULT_TTL_MS / 1e3);
|
|
13180
13334
|
|
|
13181
13335
|
// app/lib/brand-config.ts
|
|
13182
|
-
import { existsSync as
|
|
13183
|
-
import { join as
|
|
13336
|
+
import { existsSync as existsSync20, readFileSync as readFileSync20 } from "fs";
|
|
13337
|
+
import { join as join16 } from "path";
|
|
13184
13338
|
var cached2 = null;
|
|
13185
13339
|
var cachedAttempted = false;
|
|
13186
13340
|
function readBrandConfig() {
|
|
@@ -13188,10 +13342,10 @@ function readBrandConfig() {
|
|
|
13188
13342
|
cachedAttempted = true;
|
|
13189
13343
|
const platformRoot = process.env.MAXY_PLATFORM_ROOT;
|
|
13190
13344
|
if (!platformRoot) return null;
|
|
13191
|
-
const brandPath =
|
|
13192
|
-
if (!
|
|
13345
|
+
const brandPath = join16(platformRoot, "config", "brand.json");
|
|
13346
|
+
if (!existsSync20(brandPath)) return null;
|
|
13193
13347
|
try {
|
|
13194
|
-
cached2 = JSON.parse(
|
|
13348
|
+
cached2 = JSON.parse(readFileSync20(brandPath, "utf-8"));
|
|
13195
13349
|
return cached2;
|
|
13196
13350
|
} catch {
|
|
13197
13351
|
return null;
|
|
@@ -13199,7 +13353,7 @@ function readBrandConfig() {
|
|
|
13199
13353
|
}
|
|
13200
13354
|
|
|
13201
13355
|
// server/routes/visitor-consent.ts
|
|
13202
|
-
var
|
|
13356
|
+
var app38 = new Hono();
|
|
13203
13357
|
var CONSENT_COOKIE_NAME = "mxy_consent";
|
|
13204
13358
|
var CONSENT_COOKIE_MAX_AGE_SECONDS = 60 * 60 * 24 * 365;
|
|
13205
13359
|
var DEFAULT_CONSENT_COPY = {
|
|
@@ -13244,17 +13398,17 @@ function siteSlugFromReferer(referer) {
|
|
|
13244
13398
|
return "";
|
|
13245
13399
|
}
|
|
13246
13400
|
}
|
|
13247
|
-
|
|
13401
|
+
app38.options("/consent", (c) => {
|
|
13248
13402
|
const origin = getOrigin(c);
|
|
13249
13403
|
setCorsHeaders(c, origin);
|
|
13250
13404
|
return c.body(null, 204);
|
|
13251
13405
|
});
|
|
13252
|
-
|
|
13406
|
+
app38.options("/brand-config", (c) => {
|
|
13253
13407
|
const origin = getOrigin(c);
|
|
13254
13408
|
setCorsHeaders(c, origin);
|
|
13255
13409
|
return c.body(null, 204);
|
|
13256
13410
|
});
|
|
13257
|
-
|
|
13411
|
+
app38.post("/consent", async (c) => {
|
|
13258
13412
|
const origin = getOrigin(c);
|
|
13259
13413
|
setCorsHeaders(c, origin);
|
|
13260
13414
|
let raw;
|
|
@@ -13294,7 +13448,7 @@ app36.post("/consent", async (c) => {
|
|
|
13294
13448
|
console.log(`[consent] ${parsed.decision} site=${site} brand=${brandName} tokenBound=${tokenBound}`);
|
|
13295
13449
|
return c.body(null, 204);
|
|
13296
13450
|
});
|
|
13297
|
-
|
|
13451
|
+
app38.get("/brand-config", (c) => {
|
|
13298
13452
|
const origin = getOrigin(c);
|
|
13299
13453
|
setCorsHeaders(c, origin);
|
|
13300
13454
|
const brand = readBrandConfig();
|
|
@@ -13304,7 +13458,7 @@ app36.get("/brand-config", (c) => {
|
|
|
13304
13458
|
c.header("Cache-Control", "public, max-age=300");
|
|
13305
13459
|
return c.json({ consent: { copy, palette } });
|
|
13306
13460
|
});
|
|
13307
|
-
var visitor_consent_default =
|
|
13461
|
+
var visitor_consent_default = app38;
|
|
13308
13462
|
|
|
13309
13463
|
// server/routes/listings.ts
|
|
13310
13464
|
function getCookie(headerValue, name) {
|
|
@@ -13331,8 +13485,8 @@ function appendConsentParams(pageUrl, token) {
|
|
|
13331
13485
|
}
|
|
13332
13486
|
var SAFE_SLUG_RE = /^[a-z0-9](?:[a-z0-9-]{0,118}[a-z0-9])?$/;
|
|
13333
13487
|
var CHAT_SESSION_KEY_RE = /^[A-Za-z0-9][A-Za-z0-9_-]{7,127}$/;
|
|
13334
|
-
var
|
|
13335
|
-
|
|
13488
|
+
var app39 = new Hono();
|
|
13489
|
+
app39.get("/:slug/click", async (c) => {
|
|
13336
13490
|
const slug = c.req.param("slug") ?? "";
|
|
13337
13491
|
const rawSession = c.req.query("session") ?? "";
|
|
13338
13492
|
const sessionKey = CHAT_SESSION_KEY_RE.test(rawSession) ? rawSession : "invalid";
|
|
@@ -13396,10 +13550,10 @@ app37.get("/:slug/click", async (c) => {
|
|
|
13396
13550
|
console.log(`[property-card-click] sessionKey=${sessionKey} listingSlug=${slug} consent=${consentCookie ?? "absent"} ts=${(/* @__PURE__ */ new Date()).toISOString()}`);
|
|
13397
13551
|
return c.redirect(redirectUrl, 302);
|
|
13398
13552
|
});
|
|
13399
|
-
var listings_default =
|
|
13553
|
+
var listings_default = app39;
|
|
13400
13554
|
|
|
13401
13555
|
// server/routes/visitor-event.ts
|
|
13402
|
-
var
|
|
13556
|
+
var app40 = new Hono();
|
|
13403
13557
|
var BOT_UA_RE = /\b(bot|crawl|spider|slurp|headlesschrome|phantomjs|googlebot|bingbot|yandex|baiduspider|ahrefsbot|semrushbot|mj12bot|dotbot|petalbot)\b/i;
|
|
13404
13558
|
var buckets = /* @__PURE__ */ new Map();
|
|
13405
13559
|
var RATE_LIMIT = 60;
|
|
@@ -13466,12 +13620,12 @@ function originAllowed(origin, allowlist) {
|
|
|
13466
13620
|
return false;
|
|
13467
13621
|
}
|
|
13468
13622
|
}
|
|
13469
|
-
|
|
13623
|
+
app40.options("/event", (c) => {
|
|
13470
13624
|
const origin = getOrigin2(c);
|
|
13471
13625
|
setCorsHeaders2(c, origin);
|
|
13472
13626
|
return c.body(null, 204);
|
|
13473
13627
|
});
|
|
13474
|
-
|
|
13628
|
+
app40.post("/event", async (c) => {
|
|
13475
13629
|
const origin = getOrigin2(c);
|
|
13476
13630
|
setCorsHeaders2(c, origin);
|
|
13477
13631
|
const ua = c.req.header("user-agent") ?? "";
|
|
@@ -13676,7 +13830,7 @@ async function writeEvent(opts) {
|
|
|
13676
13830
|
);
|
|
13677
13831
|
}
|
|
13678
13832
|
}
|
|
13679
|
-
var visitor_event_default =
|
|
13833
|
+
var visitor_event_default = app40;
|
|
13680
13834
|
|
|
13681
13835
|
// app/lib/graph-health.ts
|
|
13682
13836
|
var HOUR_MS = 60 * 60 * 1e3;
|
|
@@ -13761,7 +13915,7 @@ function startGraphHealthTimer() {
|
|
|
13761
13915
|
|
|
13762
13916
|
// app/lib/file-watcher.ts
|
|
13763
13917
|
import * as fsp2 from "fs/promises";
|
|
13764
|
-
import { resolve as
|
|
13918
|
+
import { resolve as resolve21, sep as sep6 } from "path";
|
|
13765
13919
|
var ACCOUNT_UUID_RE2 = /^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$/i;
|
|
13766
13920
|
var DEFAULT_COALESCE_MS = 500;
|
|
13767
13921
|
var ROOTS = ["uploads", "accounts"];
|
|
@@ -13780,7 +13934,7 @@ async function startFileWatcher(opts = {}) {
|
|
|
13780
13934
|
const dropFn = opts.drop ?? dropFileIndex;
|
|
13781
13935
|
for (const r of ROOTS) {
|
|
13782
13936
|
try {
|
|
13783
|
-
await fsp2.mkdir(
|
|
13937
|
+
await fsp2.mkdir(resolve21(dataRoot, r), { recursive: true });
|
|
13784
13938
|
} catch (err) {
|
|
13785
13939
|
console.error(
|
|
13786
13940
|
`[file-watcher] start-failed root="${r}" err="${err.message}" \u2014 index will be maintained by the 5-min reconcile backstop only`
|
|
@@ -13801,7 +13955,7 @@ async function startFileWatcher(opts = {}) {
|
|
|
13801
13955
|
timers.set(relativePath, t);
|
|
13802
13956
|
}
|
|
13803
13957
|
async function runHook(relativePath, accountId) {
|
|
13804
|
-
const absolute =
|
|
13958
|
+
const absolute = resolve21(dataRoot, relativePath);
|
|
13805
13959
|
let exists = false;
|
|
13806
13960
|
try {
|
|
13807
13961
|
const st = await fsp2.stat(absolute);
|
|
@@ -13825,7 +13979,7 @@ async function startFileWatcher(opts = {}) {
|
|
|
13825
13979
|
}
|
|
13826
13980
|
}
|
|
13827
13981
|
async function watchRoot(rootName) {
|
|
13828
|
-
const absRoot =
|
|
13982
|
+
const absRoot = resolve21(dataRoot, rootName);
|
|
13829
13983
|
try {
|
|
13830
13984
|
const iter = fsp2.watch(absRoot, { recursive: true, signal: controller.signal });
|
|
13831
13985
|
for await (const event of iter) {
|
|
@@ -13923,8 +14077,8 @@ function broadcastAdminShutdown(reason) {
|
|
|
13923
14077
|
|
|
13924
14078
|
// ../lib/entitlement/src/index.ts
|
|
13925
14079
|
import { createPublicKey, createHash as createHash4, verify as cryptoVerify } from "crypto";
|
|
13926
|
-
import { existsSync as
|
|
13927
|
-
import { resolve as
|
|
14080
|
+
import { existsSync as existsSync21, readFileSync as readFileSync21, statSync as statSync9 } from "fs";
|
|
14081
|
+
import { resolve as resolve22 } from "path";
|
|
13928
14082
|
|
|
13929
14083
|
// ../lib/entitlement/src/canonicalize.ts
|
|
13930
14084
|
function canonicalize(value) {
|
|
@@ -13959,7 +14113,7 @@ var PUBKEY_SHA256 = "8eee6bcb33545fd13b16d3199a5735ca5db5062834c7b49dfe4f23801d9
|
|
|
13959
14113
|
var GRACE_DAYS = 7;
|
|
13960
14114
|
var GRACE_MS = GRACE_DAYS * 24 * 60 * 60 * 1e3;
|
|
13961
14115
|
function pubkeyPath(brand) {
|
|
13962
|
-
return
|
|
14116
|
+
return resolve22(brand.platformRoot, "lib", "entitlement", "rubytech-pubkey.pem");
|
|
13963
14117
|
}
|
|
13964
14118
|
var memo = null;
|
|
13965
14119
|
function memoKey(mtimeMs, account) {
|
|
@@ -13971,8 +14125,8 @@ function resolveEntitlement(brand, account) {
|
|
|
13971
14125
|
if (brand.commercialMode !== true) {
|
|
13972
14126
|
return logResolved(implicitTrust(account), null);
|
|
13973
14127
|
}
|
|
13974
|
-
const entitlementPath =
|
|
13975
|
-
if (!
|
|
14128
|
+
const entitlementPath = resolve22(brand.configDir, "entitlement.json");
|
|
14129
|
+
if (!existsSync21(entitlementPath)) {
|
|
13976
14130
|
return logResolved(anonymousFallback("missing"), { reason: "missing" });
|
|
13977
14131
|
}
|
|
13978
14132
|
const stat7 = statSync9(entitlementPath);
|
|
@@ -13987,7 +14141,7 @@ function resolveEntitlement(brand, account) {
|
|
|
13987
14141
|
function verifyAndResolve(brand, entitlementPath, account) {
|
|
13988
14142
|
let pubkeyPem;
|
|
13989
14143
|
try {
|
|
13990
|
-
pubkeyPem =
|
|
14144
|
+
pubkeyPem = readFileSync21(pubkeyPath(brand), "utf-8");
|
|
13991
14145
|
} catch (err) {
|
|
13992
14146
|
return logResolved(anonymousFallback("pubkey-missing"), {
|
|
13993
14147
|
reason: "pubkey-missing"
|
|
@@ -14001,7 +14155,7 @@ function verifyAndResolve(brand, entitlementPath, account) {
|
|
|
14001
14155
|
}
|
|
14002
14156
|
let envelope;
|
|
14003
14157
|
try {
|
|
14004
|
-
envelope = JSON.parse(
|
|
14158
|
+
envelope = JSON.parse(readFileSync21(entitlementPath, "utf-8"));
|
|
14005
14159
|
} catch {
|
|
14006
14160
|
return logResolved(anonymousFallback("malformed"), { reason: "malformed" });
|
|
14007
14161
|
}
|
|
@@ -14162,14 +14316,14 @@ function clientFrom(c) {
|
|
|
14162
14316
|
);
|
|
14163
14317
|
}
|
|
14164
14318
|
var PLATFORM_ROOT9 = process.env.MAXY_PLATFORM_ROOT || "";
|
|
14165
|
-
var BRAND_JSON_PATH = PLATFORM_ROOT9 ?
|
|
14319
|
+
var BRAND_JSON_PATH = PLATFORM_ROOT9 ? join17(PLATFORM_ROOT9, "config", "brand.json") : "";
|
|
14166
14320
|
var BRAND = { productName: "Maxy", hostname: "maxy", configDir: ".maxy", marketingUrl: "https://getmaxy.com" };
|
|
14167
|
-
if (BRAND_JSON_PATH && !
|
|
14321
|
+
if (BRAND_JSON_PATH && !existsSync22(BRAND_JSON_PATH)) {
|
|
14168
14322
|
console.error(`[brand] WARNING: brand.json not found at ${BRAND_JSON_PATH} \u2014 using Maxy defaults`);
|
|
14169
14323
|
}
|
|
14170
|
-
if (BRAND_JSON_PATH &&
|
|
14324
|
+
if (BRAND_JSON_PATH && existsSync22(BRAND_JSON_PATH)) {
|
|
14171
14325
|
try {
|
|
14172
|
-
const parsed = JSON.parse(
|
|
14326
|
+
const parsed = JSON.parse(readFileSync22(BRAND_JSON_PATH, "utf-8"));
|
|
14173
14327
|
BRAND = { ...BRAND, ...parsed };
|
|
14174
14328
|
} catch (err) {
|
|
14175
14329
|
console.error(`[brand] Failed to parse brand.json: ${err.message}`);
|
|
@@ -14188,11 +14342,11 @@ var brandLoginOpts = {
|
|
|
14188
14342
|
bodyFont: BRAND.defaultFonts?.body,
|
|
14189
14343
|
logoContainsName: !!BRAND.logoContainsName
|
|
14190
14344
|
};
|
|
14191
|
-
var ALIAS_DOMAINS_PATH =
|
|
14345
|
+
var ALIAS_DOMAINS_PATH = join17(homedir2(), BRAND.configDir, "alias-domains.json");
|
|
14192
14346
|
function loadAliasDomains() {
|
|
14193
14347
|
try {
|
|
14194
|
-
if (!
|
|
14195
|
-
const parsed = JSON.parse(
|
|
14348
|
+
if (!existsSync22(ALIAS_DOMAINS_PATH)) return null;
|
|
14349
|
+
const parsed = JSON.parse(readFileSync22(ALIAS_DOMAINS_PATH, "utf-8"));
|
|
14196
14350
|
if (!Array.isArray(parsed)) {
|
|
14197
14351
|
console.error("[alias-domains] malformed alias-domains.json \u2014 expected array");
|
|
14198
14352
|
return null;
|
|
@@ -14216,9 +14370,9 @@ watchFile(ALIAS_DOMAINS_PATH, { interval: 2e3 }, () => {
|
|
|
14216
14370
|
function isPublicHost(host) {
|
|
14217
14371
|
return host.startsWith("public.") || aliasDomains.has(host);
|
|
14218
14372
|
}
|
|
14219
|
-
var
|
|
14220
|
-
|
|
14221
|
-
|
|
14373
|
+
var app41 = new Hono();
|
|
14374
|
+
app41.use("*", clientIpMiddleware);
|
|
14375
|
+
app41.use("*", async (c, next) => {
|
|
14222
14376
|
await next();
|
|
14223
14377
|
c.header("X-Content-Type-Options", "nosniff");
|
|
14224
14378
|
c.header("Referrer-Policy", "strict-origin-when-cross-origin");
|
|
@@ -14228,7 +14382,7 @@ app39.use("*", async (c, next) => {
|
|
|
14228
14382
|
);
|
|
14229
14383
|
});
|
|
14230
14384
|
var HTTP_LOG_PATHS = /* @__PURE__ */ new Set(["/vnc-viewer.html", "/vnc-popout.html"]);
|
|
14231
|
-
|
|
14385
|
+
app41.use("*", async (c, next) => {
|
|
14232
14386
|
if (!HTTP_LOG_PATHS.has(c.req.path)) {
|
|
14233
14387
|
await next();
|
|
14234
14388
|
return;
|
|
@@ -14261,7 +14415,7 @@ var PUBLIC_ALLOWED_PREFIXES = [
|
|
|
14261
14415
|
"/sites/"
|
|
14262
14416
|
];
|
|
14263
14417
|
var PUBLIC_ALLOWED_EXACT = ["/favicon.ico"];
|
|
14264
|
-
|
|
14418
|
+
app41.use("*", async (c, next) => {
|
|
14265
14419
|
const host = (c.req.header("host") ?? "").split(":")[0];
|
|
14266
14420
|
if (!isPublicHost(host)) {
|
|
14267
14421
|
await next();
|
|
@@ -14301,7 +14455,7 @@ function resolveRemoteAuthOpts() {
|
|
|
14301
14455
|
return brandLoginOpts;
|
|
14302
14456
|
}
|
|
14303
14457
|
var MAX_LOGIN_BODY = 8 * 1024;
|
|
14304
|
-
|
|
14458
|
+
app41.post("/__remote-auth/login", async (c) => {
|
|
14305
14459
|
const client = clientFrom(c);
|
|
14306
14460
|
const clientIp = client.ip || "unknown";
|
|
14307
14461
|
if (!requestIsTlsTerminated(c)) {
|
|
@@ -14346,7 +14500,7 @@ app39.post("/__remote-auth/login", async (c) => {
|
|
|
14346
14500
|
}
|
|
14347
14501
|
});
|
|
14348
14502
|
});
|
|
14349
|
-
|
|
14503
|
+
app41.get("/__remote-auth/logout", (c) => {
|
|
14350
14504
|
const client = clientFrom(c);
|
|
14351
14505
|
const clientIp = client.ip || "unknown";
|
|
14352
14506
|
console.error(`[remote-auth] logout ip=${clientIp}`);
|
|
@@ -14359,7 +14513,7 @@ app39.get("/__remote-auth/logout", (c) => {
|
|
|
14359
14513
|
}
|
|
14360
14514
|
});
|
|
14361
14515
|
});
|
|
14362
|
-
|
|
14516
|
+
app41.post("/__remote-auth/change-password", async (c) => {
|
|
14363
14517
|
const client = clientFrom(c);
|
|
14364
14518
|
const clientIp = client.ip || "unknown";
|
|
14365
14519
|
const rateLimited = checkRateLimit(client);
|
|
@@ -14410,13 +14564,13 @@ app39.post("/__remote-auth/change-password", async (c) => {
|
|
|
14410
14564
|
return c.html(renderLoginPage({ ...resolveRemoteAuthOpts(), mode: "change", changeError: "Failed to save password", redirect }), 200);
|
|
14411
14565
|
}
|
|
14412
14566
|
});
|
|
14413
|
-
|
|
14567
|
+
app41.get("/__remote-auth/setup", (c) => {
|
|
14414
14568
|
if (isRemoteAuthConfigured()) {
|
|
14415
14569
|
return c.redirect("/");
|
|
14416
14570
|
}
|
|
14417
14571
|
return c.html(renderLoginPage({ ...resolveRemoteAuthOpts(), mode: "setup" }), 200);
|
|
14418
14572
|
});
|
|
14419
|
-
|
|
14573
|
+
app41.post("/__remote-auth/set-initial-password", async (c) => {
|
|
14420
14574
|
if (isRemoteAuthConfigured()) {
|
|
14421
14575
|
return c.redirect("/");
|
|
14422
14576
|
}
|
|
@@ -14454,10 +14608,10 @@ app39.post("/__remote-auth/set-initial-password", async (c) => {
|
|
|
14454
14608
|
return c.html(renderLoginPage({ ...resolveRemoteAuthOpts(), mode: "setup", setupError: "Failed to save password. Please try again." }), 200);
|
|
14455
14609
|
}
|
|
14456
14610
|
});
|
|
14457
|
-
|
|
14611
|
+
app41.get("/api/remote-auth/status", (c) => {
|
|
14458
14612
|
return c.json({ configured: isRemoteAuthConfigured() });
|
|
14459
14613
|
});
|
|
14460
|
-
|
|
14614
|
+
app41.post("/api/remote-auth/set-password", async (c) => {
|
|
14461
14615
|
let body;
|
|
14462
14616
|
try {
|
|
14463
14617
|
body = await c.req.json();
|
|
@@ -14488,9 +14642,9 @@ app39.post("/api/remote-auth/set-password", async (c) => {
|
|
|
14488
14642
|
return c.json({ error: "Failed to save password" }, 500);
|
|
14489
14643
|
}
|
|
14490
14644
|
});
|
|
14491
|
-
|
|
14645
|
+
app41.route("/api/_client-error", client_error_default);
|
|
14492
14646
|
console.log("[client-error-route] mounted");
|
|
14493
|
-
|
|
14647
|
+
app41.use("*", async (c, next) => {
|
|
14494
14648
|
const host = (c.req.header("host") ?? "").split(":")[0];
|
|
14495
14649
|
const path2 = c.req.path;
|
|
14496
14650
|
if (path2 === "/favicon.ico" || path2.startsWith("/assets/") || path2.startsWith("/brand/")) {
|
|
@@ -14523,12 +14677,12 @@ app39.use("*", async (c, next) => {
|
|
|
14523
14677
|
console.error(`[remote-auth] login required ip=${clientIp} path=${path2} ${disambig}`);
|
|
14524
14678
|
return c.html(renderLoginPage({ ...resolveRemoteAuthOpts(), redirect: path2 }), 200);
|
|
14525
14679
|
});
|
|
14526
|
-
|
|
14527
|
-
|
|
14528
|
-
|
|
14529
|
-
|
|
14530
|
-
|
|
14531
|
-
|
|
14680
|
+
app41.route("/api/health", health_default);
|
|
14681
|
+
app41.route("/api/chat", chat_default);
|
|
14682
|
+
app41.route("/api/whatsapp", whatsapp_default);
|
|
14683
|
+
app41.route("/api/onboarding", onboarding_default);
|
|
14684
|
+
app41.route("/api/admin", admin_default);
|
|
14685
|
+
app41.route("/api/access", access_default);
|
|
14532
14686
|
var SAFE_SLUG_RE2 = /^[a-z][a-z0-9-]{2,49}$/;
|
|
14533
14687
|
var SAFE_FILENAME_RE = /^[a-z0-9_][a-z0-9_.-]{0,99}$/i;
|
|
14534
14688
|
var IMAGE_MIME = {
|
|
@@ -14540,7 +14694,7 @@ var IMAGE_MIME = {
|
|
|
14540
14694
|
".svg": "image/svg+xml",
|
|
14541
14695
|
".ico": "image/x-icon"
|
|
14542
14696
|
};
|
|
14543
|
-
|
|
14697
|
+
app41.get("/agent-assets/:slug/:filename", (c) => {
|
|
14544
14698
|
const slug = c.req.param("slug");
|
|
14545
14699
|
const filename = c.req.param("filename");
|
|
14546
14700
|
if (!SAFE_SLUG_RE2.test(slug)) {
|
|
@@ -14556,26 +14710,26 @@ app39.get("/agent-assets/:slug/:filename", (c) => {
|
|
|
14556
14710
|
console.error(`[agent-assets] no-account slug=${slug} file=${filename}`);
|
|
14557
14711
|
return c.text("Not found", 404);
|
|
14558
14712
|
}
|
|
14559
|
-
const filePath =
|
|
14560
|
-
const expectedDir =
|
|
14713
|
+
const filePath = resolve23(account.accountDir, "agents", slug, "assets", filename);
|
|
14714
|
+
const expectedDir = resolve23(account.accountDir, "agents", slug, "assets");
|
|
14561
14715
|
if (!filePath.startsWith(expectedDir + "/")) {
|
|
14562
14716
|
console.error(`[agent-assets] path-traversal-rejected slug=${slug} file=${filename}`);
|
|
14563
14717
|
return c.text("Forbidden", 403);
|
|
14564
14718
|
}
|
|
14565
|
-
if (!
|
|
14719
|
+
if (!existsSync22(filePath)) {
|
|
14566
14720
|
console.error(`[agent-assets] serve slug=${slug} file=${filename} status=404`);
|
|
14567
14721
|
return c.text("Not found", 404);
|
|
14568
14722
|
}
|
|
14569
14723
|
const ext = "." + filename.split(".").pop()?.toLowerCase();
|
|
14570
14724
|
const contentType = IMAGE_MIME[ext] || "application/octet-stream";
|
|
14571
14725
|
console.log(`[agent-assets] serve slug=${slug} file=${filename} status=200`);
|
|
14572
|
-
const body =
|
|
14726
|
+
const body = readFileSync22(filePath);
|
|
14573
14727
|
return c.body(body, 200, {
|
|
14574
14728
|
"Content-Type": contentType,
|
|
14575
14729
|
"Cache-Control": "public, max-age=3600"
|
|
14576
14730
|
});
|
|
14577
14731
|
});
|
|
14578
|
-
|
|
14732
|
+
app41.get("/generated/:filename", (c) => {
|
|
14579
14733
|
const filename = c.req.param("filename");
|
|
14580
14734
|
if (!SAFE_FILENAME_RE.test(filename) || filename.includes("..")) {
|
|
14581
14735
|
console.error(`[generated] serve file=${filename} status=403`);
|
|
@@ -14586,35 +14740,35 @@ app39.get("/generated/:filename", (c) => {
|
|
|
14586
14740
|
console.error(`[generated] serve file=${filename} status=404`);
|
|
14587
14741
|
return c.text("Not found", 404);
|
|
14588
14742
|
}
|
|
14589
|
-
const filePath =
|
|
14590
|
-
const expectedDir =
|
|
14743
|
+
const filePath = resolve23(account.accountDir, "generated", filename);
|
|
14744
|
+
const expectedDir = resolve23(account.accountDir, "generated");
|
|
14591
14745
|
if (!filePath.startsWith(expectedDir + "/")) {
|
|
14592
14746
|
console.error(`[generated] serve file=${filename} status=403`);
|
|
14593
14747
|
return c.text("Forbidden", 403);
|
|
14594
14748
|
}
|
|
14595
|
-
if (!
|
|
14749
|
+
if (!existsSync22(filePath)) {
|
|
14596
14750
|
console.error(`[generated] serve file=${filename} status=404`);
|
|
14597
14751
|
return c.text("Not found", 404);
|
|
14598
14752
|
}
|
|
14599
14753
|
const ext = "." + filename.split(".").pop()?.toLowerCase();
|
|
14600
14754
|
const contentType = IMAGE_MIME[ext] || "application/octet-stream";
|
|
14601
14755
|
console.log(`[generated] serve file=${filename} status=200`);
|
|
14602
|
-
const body =
|
|
14756
|
+
const body = readFileSync22(filePath);
|
|
14603
14757
|
return c.body(body, 200, {
|
|
14604
14758
|
"Content-Type": contentType,
|
|
14605
14759
|
"Cache-Control": "public, max-age=86400"
|
|
14606
14760
|
});
|
|
14607
14761
|
});
|
|
14608
|
-
|
|
14609
|
-
|
|
14610
|
-
|
|
14611
|
-
|
|
14762
|
+
app41.route("/sites", sites_default);
|
|
14763
|
+
app41.route("/listings", listings_default);
|
|
14764
|
+
app41.route("/v", visitor_event_default);
|
|
14765
|
+
app41.route("/v", visitor_consent_default);
|
|
14612
14766
|
var htmlCache = /* @__PURE__ */ new Map();
|
|
14613
14767
|
var brandLogoPath = "/brand/maxy-monochrome.png";
|
|
14614
14768
|
var brandIconPath = "/brand/maxy-monochrome.png";
|
|
14615
|
-
if (BRAND_JSON_PATH &&
|
|
14769
|
+
if (BRAND_JSON_PATH && existsSync22(BRAND_JSON_PATH)) {
|
|
14616
14770
|
try {
|
|
14617
|
-
const fullBrand = JSON.parse(
|
|
14771
|
+
const fullBrand = JSON.parse(readFileSync22(BRAND_JSON_PATH, "utf-8"));
|
|
14618
14772
|
if (fullBrand.assets?.logo) brandLogoPath = `/brand/${fullBrand.assets.logo}`;
|
|
14619
14773
|
brandIconPath = fullBrand.assets?.icon ? `/brand/${fullBrand.assets.icon}` : brandLogoPath;
|
|
14620
14774
|
} catch {
|
|
@@ -14631,9 +14785,9 @@ var brandScript = `<script>window.__BRAND__=${JSON.stringify({
|
|
|
14631
14785
|
function readInstalledVersion() {
|
|
14632
14786
|
try {
|
|
14633
14787
|
if (!PLATFORM_ROOT9) return "unknown";
|
|
14634
|
-
const versionFile =
|
|
14635
|
-
if (!
|
|
14636
|
-
const content =
|
|
14788
|
+
const versionFile = join17(PLATFORM_ROOT9, "config", `.${BRAND.hostname}-version`);
|
|
14789
|
+
if (!existsSync22(versionFile)) return "unknown";
|
|
14790
|
+
const content = readFileSync22(versionFile, "utf-8").trim();
|
|
14637
14791
|
return content || "unknown";
|
|
14638
14792
|
} catch {
|
|
14639
14793
|
return "unknown";
|
|
@@ -14674,7 +14828,7 @@ var clientErrorReporterScript = `<script>
|
|
|
14674
14828
|
function cachedHtml(file) {
|
|
14675
14829
|
let html = htmlCache.get(file);
|
|
14676
14830
|
if (!html) {
|
|
14677
|
-
html =
|
|
14831
|
+
html = readFileSync22(resolve23(process.cwd(), "public", file), "utf-8");
|
|
14678
14832
|
const productNameEsc = escapeHtml(BRAND.productName);
|
|
14679
14833
|
html = html.replace(/<title>([^<]*)<\/title>/, (_match, inner) => `<title>${escapeHtml(inner).replace(/Maxy/g, productNameEsc)}</title>`);
|
|
14680
14834
|
html = html.replace('href="/favicon.ico"', `href="${escapeHtml(brandFaviconPath)}"`);
|
|
@@ -14690,26 +14844,26 @@ ${clientErrorReporterScript}
|
|
|
14690
14844
|
}
|
|
14691
14845
|
var brandedHtmlCache = /* @__PURE__ */ new Map();
|
|
14692
14846
|
function loadBrandingCache(agentSlug) {
|
|
14693
|
-
const configDir2 =
|
|
14847
|
+
const configDir2 = join17(homedir2(), BRAND.configDir);
|
|
14694
14848
|
try {
|
|
14695
|
-
const accountJsonPath =
|
|
14696
|
-
if (!
|
|
14697
|
-
const account = JSON.parse(
|
|
14849
|
+
const accountJsonPath = join17(configDir2, "account.json");
|
|
14850
|
+
if (!existsSync22(accountJsonPath)) return null;
|
|
14851
|
+
const account = JSON.parse(readFileSync22(accountJsonPath, "utf-8"));
|
|
14698
14852
|
const accountId = account.accountId;
|
|
14699
14853
|
if (!accountId) return null;
|
|
14700
|
-
const cachePath =
|
|
14701
|
-
if (!
|
|
14702
|
-
return JSON.parse(
|
|
14854
|
+
const cachePath = join17(configDir2, "branding-cache", accountId, `${agentSlug}.json`);
|
|
14855
|
+
if (!existsSync22(cachePath)) return null;
|
|
14856
|
+
return JSON.parse(readFileSync22(cachePath, "utf-8"));
|
|
14703
14857
|
} catch {
|
|
14704
14858
|
return null;
|
|
14705
14859
|
}
|
|
14706
14860
|
}
|
|
14707
14861
|
function resolveDefaultSlug() {
|
|
14708
14862
|
try {
|
|
14709
|
-
const configDir2 =
|
|
14710
|
-
const accountJsonPath =
|
|
14711
|
-
if (!
|
|
14712
|
-
const account = JSON.parse(
|
|
14863
|
+
const configDir2 = join17(homedir2(), BRAND.configDir);
|
|
14864
|
+
const accountJsonPath = join17(configDir2, "account.json");
|
|
14865
|
+
if (!existsSync22(accountJsonPath)) return null;
|
|
14866
|
+
const account = JSON.parse(readFileSync22(accountJsonPath, "utf-8"));
|
|
14713
14867
|
return account.defaultAgent || null;
|
|
14714
14868
|
} catch {
|
|
14715
14869
|
return null;
|
|
@@ -14745,7 +14899,7 @@ function brandedPublicHtml(agentSlug) {
|
|
|
14745
14899
|
function escapeHtml(s) {
|
|
14746
14900
|
return s.replace(/&/g, "&").replace(/"/g, """).replace(/</g, "<").replace(/>/g, ">");
|
|
14747
14901
|
}
|
|
14748
|
-
|
|
14902
|
+
app41.get("/", (c) => {
|
|
14749
14903
|
const host = (c.req.header("host") ?? "").split(":")[0];
|
|
14750
14904
|
if (isPublicHost(host)) {
|
|
14751
14905
|
const defaultSlug = resolveDefaultSlug();
|
|
@@ -14753,12 +14907,12 @@ app39.get("/", (c) => {
|
|
|
14753
14907
|
}
|
|
14754
14908
|
return c.html(cachedHtml("index.html"));
|
|
14755
14909
|
});
|
|
14756
|
-
|
|
14910
|
+
app41.get("/public", (c) => {
|
|
14757
14911
|
const host = (c.req.header("host") ?? "").split(":")[0];
|
|
14758
14912
|
if (isPublicHost(host)) return c.text("Not found", 404);
|
|
14759
14913
|
return c.html(cachedHtml("public.html"));
|
|
14760
14914
|
});
|
|
14761
|
-
|
|
14915
|
+
app41.get("/chat", (c) => {
|
|
14762
14916
|
const host = (c.req.header("host") ?? "").split(":")[0];
|
|
14763
14917
|
if (isPublicHost(host)) return c.text("Not found", 404);
|
|
14764
14918
|
return c.html(cachedHtml("public.html"));
|
|
@@ -14777,12 +14931,12 @@ async function logViewerFetch(c, next) {
|
|
|
14777
14931
|
duration_ms: Date.now() - start
|
|
14778
14932
|
});
|
|
14779
14933
|
}
|
|
14780
|
-
|
|
14781
|
-
|
|
14782
|
-
|
|
14934
|
+
app41.use("/vnc-viewer.html", logViewerFetch);
|
|
14935
|
+
app41.use("/vnc-popout.html", logViewerFetch);
|
|
14936
|
+
app41.get("/vnc-popout.html", (c) => {
|
|
14783
14937
|
let html = htmlCache.get("vnc-popout.html");
|
|
14784
14938
|
if (!html) {
|
|
14785
|
-
html =
|
|
14939
|
+
html = readFileSync22(resolve23(process.cwd(), "public", "vnc-popout.html"), "utf-8");
|
|
14786
14940
|
const name = escapeHtml(BRAND.productName);
|
|
14787
14941
|
html = html.replace("<title>Browser \u2014 Maxy</title>", `<title>${name}</title>`);
|
|
14788
14942
|
html = html.replace("</head>", ` ${brandScript}
|
|
@@ -14792,7 +14946,7 @@ app39.get("/vnc-popout.html", (c) => {
|
|
|
14792
14946
|
}
|
|
14793
14947
|
return c.html(html);
|
|
14794
14948
|
});
|
|
14795
|
-
|
|
14949
|
+
app41.post("/api/vnc/client-event", async (c) => {
|
|
14796
14950
|
let body;
|
|
14797
14951
|
try {
|
|
14798
14952
|
body = await c.req.json();
|
|
@@ -14813,25 +14967,25 @@ app39.post("/api/vnc/client-event", async (c) => {
|
|
|
14813
14967
|
});
|
|
14814
14968
|
return c.json({ ok: true });
|
|
14815
14969
|
});
|
|
14816
|
-
|
|
14970
|
+
app41.get("/g/:slug", (c) => {
|
|
14817
14971
|
return c.html(brandedPublicHtml());
|
|
14818
14972
|
});
|
|
14819
|
-
|
|
14973
|
+
app41.get("/graph", (c) => {
|
|
14820
14974
|
const host = (c.req.header("host") ?? "").split(":")[0];
|
|
14821
14975
|
if (isPublicHost(host)) return c.text("Not found", 404);
|
|
14822
14976
|
return c.html(cachedHtml("graph.html"));
|
|
14823
14977
|
});
|
|
14824
|
-
|
|
14978
|
+
app41.get("/sessions", (c) => {
|
|
14825
14979
|
const host = (c.req.header("host") ?? "").split(":")[0];
|
|
14826
14980
|
if (isPublicHost(host)) return c.text("Not found", 404);
|
|
14827
14981
|
return c.html(cachedHtml("sessions.html"));
|
|
14828
14982
|
});
|
|
14829
|
-
|
|
14983
|
+
app41.get("/data", (c) => {
|
|
14830
14984
|
const host = (c.req.header("host") ?? "").split(":")[0];
|
|
14831
14985
|
if (isPublicHost(host)) return c.text("Not found", 404);
|
|
14832
14986
|
return c.html(cachedHtml("data.html"));
|
|
14833
14987
|
});
|
|
14834
|
-
|
|
14988
|
+
app41.get("/:slug", async (c, next) => {
|
|
14835
14989
|
const slug = c.req.param("slug");
|
|
14836
14990
|
if (AGENT_SLUG_PATTERN.test(`/${slug}`)) {
|
|
14837
14991
|
const branding = loadBrandingCache(slug);
|
|
@@ -14841,15 +14995,15 @@ app39.get("/:slug", async (c, next) => {
|
|
|
14841
14995
|
await next();
|
|
14842
14996
|
});
|
|
14843
14997
|
if (brandFaviconPath !== "/favicon.ico") {
|
|
14844
|
-
|
|
14998
|
+
app41.get("/favicon.ico", (c) => {
|
|
14845
14999
|
c.header("Cache-Control", "public, max-age=300");
|
|
14846
15000
|
return c.redirect(brandFaviconPath, 302);
|
|
14847
15001
|
});
|
|
14848
15002
|
}
|
|
14849
|
-
|
|
15003
|
+
app41.use("/*", serveStatic({ root: "./public" }));
|
|
14850
15004
|
var port = requirePortEnv("MAXY_UI_INTERNAL_PORT", { tag: "ui-server" });
|
|
14851
15005
|
var hostname = process.env.HOSTNAME ?? "127.0.0.1";
|
|
14852
|
-
var httpServer = serve({ fetch:
|
|
15006
|
+
var httpServer = serve({ fetch: app41.fetch, port, hostname });
|
|
14853
15007
|
console.log(`${BRAND.productName} listening on http://${hostname}:${port}`);
|
|
14854
15008
|
{
|
|
14855
15009
|
const loopHist = monitorEventLoopDelay({ resolution: 50 });
|
|
@@ -14885,7 +15039,7 @@ for (const m of SUBAPP_MANIFEST) {
|
|
|
14885
15039
|
}
|
|
14886
15040
|
try {
|
|
14887
15041
|
const registered = [];
|
|
14888
|
-
for (const r of
|
|
15042
|
+
for (const r of app41.routes ?? []) {
|
|
14889
15043
|
if (typeof r.path !== "string" || r.path.includes(":") || r.path.includes("*")) continue;
|
|
14890
15044
|
if (AGENT_SLUG_PATTERN.test(r.path)) {
|
|
14891
15045
|
registered.push({ method: (r.method ?? "ALL").toUpperCase(), path: r.path });
|
|
@@ -14907,8 +15061,8 @@ try {
|
|
|
14907
15061
|
}
|
|
14908
15062
|
(async () => {
|
|
14909
15063
|
try {
|
|
14910
|
-
if (!
|
|
14911
|
-
const usersRaw =
|
|
15064
|
+
if (!existsSync22(USERS_FILE)) return;
|
|
15065
|
+
const usersRaw = readFileSync22(USERS_FILE, "utf-8").trim();
|
|
14912
15066
|
if (!usersRaw) return;
|
|
14913
15067
|
const users = JSON.parse(usersRaw);
|
|
14914
15068
|
const userId = users[0]?.userId;
|
|
@@ -15003,7 +15157,7 @@ if (bootAccountConfig?.whatsapp) {
|
|
|
15003
15157
|
}
|
|
15004
15158
|
init({
|
|
15005
15159
|
configDir: configDirForWhatsApp,
|
|
15006
|
-
platformRoot:
|
|
15160
|
+
platformRoot: resolve23(process.env.MAXY_PLATFORM_ROOT ?? join17(__dirname, "..")),
|
|
15007
15161
|
accountConfig: bootAccountConfig,
|
|
15008
15162
|
onMessage: async (msg) => {
|
|
15009
15163
|
if (process.env.WHATSAPP_PTY_BRIDGE_ENABLED === "true" && msg.text && !msg.isOwnerMirror) {
|