@lob-ox/core-darwin-x64 0.0.15 → 0.0.17

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.
Files changed (2) hide show
  1. package/core.cjs +449 -309
  2. package/package.json +1 -1
package/core.cjs CHANGED
@@ -917,29 +917,29 @@ var require_brand = __commonJS({
917
917
  "src/shared/brand.js"(exports2, module2) {
918
918
  "use strict";
919
919
  var path2 = require("node:path");
920
- var SHARED = require_shared_constants2();
921
- var PRODUCT_NAME = SHARED.product.name;
922
- var CLI_NAME = SHARED.product.cliName;
923
- var GUI_BIN_NAME = SHARED.product.guiBinName;
924
- var GUI_CRATE_NAME = SHARED.product.guiCrateName;
920
+ var SHARED2 = require_shared_constants2();
921
+ var PRODUCT_NAME = SHARED2.product.name;
922
+ var CLI_NAME = SHARED2.product.cliName;
923
+ var GUI_BIN_NAME = SHARED2.product.guiBinName;
924
+ var GUI_CRATE_NAME = SHARED2.product.guiCrateName;
925
925
  var NPM_SCOPE = "@lob-ox";
926
926
  var CORE_PKG_PREFIX = "core-";
927
927
  var CORE_PKG_TAGS = ["linux-x64", "darwin-arm64", "darwin-x64", "win-x64"];
928
928
  var SHELL_RELEASE_PKG = "@lob-ox/shell-release";
929
929
  var TAURI_IDENTIFIER = "dev.bowen.lobox";
930
930
  var TAURI_PRODUCT_NAME = "lobox";
931
- var STATE_DIR_NAME = SHARED.state.dirName;
932
- var STATE_SUPERVISOR_SUBDIR = SHARED.state.supervisorSubdir;
933
- var STATE_SHELL_SUBDIR = SHARED.state.shellSubdir;
931
+ var STATE_DIR_NAME = SHARED2.state.dirName;
932
+ var STATE_SUPERVISOR_SUBDIR = SHARED2.state.supervisorSubdir;
933
+ var STATE_SHELL_SUBDIR = SHARED2.state.shellSubdir;
934
934
  var LEGACY_PRODUCT_NAME = "dsh-supervisor";
935
- var STATE_ROOT_WIN_BASE_ENV = SHARED.state.winBaseEnv;
935
+ var STATE_ROOT_WIN_BASE_ENV = SHARED2.state.winBaseEnv;
936
936
  var STATE_ROOT_WIN_BASE_FALLBACK_SEGMENTS = ["AppData", "Local"];
937
937
  var STATE_ROOT_MACOS_SEGMENTS = ["Library", "Application Support"];
938
- var STATE_ROOT_LINUX_XDG_ENV = SHARED.state.linuxXdgEnv;
938
+ var STATE_ROOT_LINUX_XDG_ENV = SHARED2.state.linuxXdgEnv;
939
939
  var STATE_ROOT_LINUX_FALLBACK_SEGMENTS = [".local", "state"];
940
- var LEGACY_HARNESS_DIR = SHARED.state.legacyHarnessDir;
941
- var ENV_STATE_ROOT = SHARED.env.stateRoot;
942
- var ENV_CONFIG = SHARED.env.config;
940
+ var LEGACY_HARNESS_DIR = SHARED2.state.legacyHarnessDir;
941
+ var ENV_STATE_ROOT = SHARED2.env.stateRoot;
942
+ var ENV_CONFIG = SHARED2.env.config;
943
943
  var ENV_LOCK_FILE = "DSH_SUPERVISOR_LOCK_FILE";
944
944
  var ENV_DAEMON = "DSH_SUPERVISOR_DAEMON";
945
945
  var ENV_TRAY_PORT = "DSH_SUPERVISOR_TRAY_PORT";
@@ -972,8 +972,6 @@ var require_brand = __commonJS({
972
972
  var ENV_PLATFORM_OVERRIDE = "DSH_PLATFORM_OVERRIDE";
973
973
  var ENV_ESBUILD_VERSION = "DSH_ESBUILD_VERSION";
974
974
  var ENV_VERSION_LIB = "DSH_VERSION_LIB";
975
- var WINDOWS_GUARD_TASK = "Lobox";
976
- var WINDOWS_WATCHDOG_TASK = "Lobox-Watchdog";
977
975
  var WINDOWS_GUI_TASK = "Lobox-Shell";
978
976
  var WINDOWS_RUN_VALUE = "Lobox";
979
977
  var SYSTEMD_UNIT_NAME = "lobox";
@@ -997,10 +995,10 @@ var require_brand = __commonJS({
997
995
  var CLI_BIN_NAMES = ["lobox.exe", "lobox.cmd", "lobox"];
998
996
  var CLI_SHIM_NAMES = ["lobox", "lobox.cmd", "lobox.ps1"];
999
997
  var GUI_BIN_NAMES = ["lobox-shell", "lobox-shell.exe"];
1000
- var PROC_MATCH_GUARD = SHARED.proc.matchGuard;
1001
- var BRIDGE_MSG_KERNEL_UPDATE_REQUEST = SHARED.bridge.msgKernelUpdateRequest;
1002
- var BRIDGE_MSG_KERNEL_UPDATE_RESULT = SHARED.bridge.msgKernelUpdateResult;
1003
- var BRIDGE_MSG_KERNEL_UPDATE_PROGRESS = SHARED.bridge.msgKernelUpdateProgress;
998
+ var PROC_MATCH_GUARD = SHARED2.proc.matchGuard;
999
+ var BRIDGE_MSG_KERNEL_UPDATE_REQUEST = SHARED2.bridge.msgKernelUpdateRequest;
1000
+ var BRIDGE_MSG_KERNEL_UPDATE_RESULT = SHARED2.bridge.msgKernelUpdateResult;
1001
+ var BRIDGE_MSG_KERNEL_UPDATE_PROGRESS = SHARED2.bridge.msgKernelUpdateProgress;
1004
1002
  var STORE_KEY_API_ACCESS = "lobox.apiAccessKey";
1005
1003
  var COOKIE_LAN_TOKEN = "lobox_lan_token";
1006
1004
  var EVENT_HARNESS_EXITED = "harness_exited";
@@ -1094,8 +1092,6 @@ var require_brand = __commonJS({
1094
1092
  ENV_PLATFORM_OVERRIDE,
1095
1093
  ENV_ESBUILD_VERSION,
1096
1094
  ENV_VERSION_LIB,
1097
- WINDOWS_GUARD_TASK,
1098
- WINDOWS_WATCHDOG_TASK,
1099
1095
  WINDOWS_GUI_TASK,
1100
1096
  WINDOWS_RUN_VALUE,
1101
1097
  SYSTEMD_UNIT_NAME,
@@ -1287,7 +1283,7 @@ var require_config = __commonJS({
1287
1283
  "use strict";
1288
1284
  var os2 = require("node:os");
1289
1285
  var path2 = require("node:path");
1290
- var SHARED = require_shared_constants2();
1286
+ var SHARED2 = require_shared_constants2();
1291
1287
  function expandHome(p) {
1292
1288
  if (typeof p !== "string") return p;
1293
1289
  if (p === "~") return os2.homedir();
@@ -1312,7 +1308,7 @@ var require_config = __commonJS({
1312
1308
  stopGraceMs: 1e4,
1313
1309
  portReleaseWaitMs: 1e4,
1314
1310
  apiHost: "127.0.0.1",
1315
- apiPort: SHARED.net.apiPort,
1311
+ apiPort: SHARED2.net.apiPort,
1316
1312
  portPools: null,
1317
1313
  stateFile: path2.join(SUP, "state.json"),
1318
1314
  logFile: path2.join(SUP, "events", "guard.events.log"),
@@ -1359,7 +1355,7 @@ var require_config = __commonJS({
1359
1355
  return out;
1360
1356
  }
1361
1357
  var DEFAULTS = buildDefaults2(null);
1362
- var DEPRECATED_API_PORTS = SHARED.net.deprecatedApiPorts.slice();
1358
+ var DEPRECATED_API_PORTS = SHARED2.net.deprecatedApiPorts.slice();
1363
1359
  function isDeprecatedApiPort(v) {
1364
1360
  const n = Number(v);
1365
1361
  return Number.isInteger(n) && DEPRECATED_API_PORTS.includes(n);
@@ -1435,13 +1431,13 @@ var require_config = __commonJS({
1435
1431
  var require_domain_config = __commonJS({
1436
1432
  "src/app/settings/domain-config.js"(exports2, module2) {
1437
1433
  "use strict";
1438
- var SHARED = require_shared_constants2();
1434
+ var SHARED2 = require_shared_constants2();
1439
1435
  var defaults = [
1440
1436
  {
1441
1437
  at: "portPools",
1442
1438
  values: {
1443
- routerCtlPort: SHARED.net.routerCtlPort,
1444
- lanCtlPort: SHARED.net.lanCtlPort
1439
+ routerCtlPort: SHARED2.net.routerCtlPort,
1440
+ lanCtlPort: SHARED2.net.lanCtlPort
1445
1441
  }
1446
1442
  },
1447
1443
  {
@@ -1471,7 +1467,7 @@ var require_version = __commonJS({
1471
1467
  var fs2 = require("node:fs");
1472
1468
  var path2 = require("node:path");
1473
1469
  function guardVersion() {
1474
- if (true) return String("0.0.15");
1470
+ if (true) return String("0.0.17");
1475
1471
  try {
1476
1472
  return JSON.parse(fs2.readFileSync(path2.join(__dirname, "..", "..", "package.json"), "utf8")).version || "unknown";
1477
1473
  } catch {
@@ -3362,15 +3358,15 @@ var require_client = __commonJS({
3362
3358
  "src/app/ctl/client.js"(exports2, module2) {
3363
3359
  "use strict";
3364
3360
  var hub = require_hub();
3365
- var SHARED = require_shared_constants2();
3361
+ var SHARED2 = require_shared_constants2();
3366
3362
  function ctlCall(port, method, args, timeoutMs) {
3367
3363
  return hub.ctlCall(port, method, args, timeoutMs || 12e4, { withErrorFields: true });
3368
3364
  }
3369
3365
  function routerCtlPort(config) {
3370
- return Number(config && config.routerCtlPort) || SHARED.net.routerCtlPort;
3366
+ return Number(config && config.routerCtlPort) || SHARED2.net.routerCtlPort;
3371
3367
  }
3372
3368
  function lanCtlPort(config) {
3373
- return Number(config && config.lanCtlPort) || SHARED.net.lanCtlPort;
3369
+ return Number(config && config.lanCtlPort) || SHARED2.net.lanCtlPort;
3374
3370
  }
3375
3371
  function createCtlClient(deps) {
3376
3372
  const g = deps || {};
@@ -3922,8 +3918,7 @@ var require_alloc = __commonJS({
3922
3918
  await new Promise((res) => setTimeout(res, 10));
3923
3919
  waited += 10;
3924
3920
  if (waited >= XLOCK_TIMEOUT_MS) {
3925
- r._allocLock = true;
3926
- break;
3921
+ throw new Error("ports.claimSlot: \u8FDB\u7A0B\u5185\u5206\u914D\u9501\u7B49\u5F85\u8D85\u65F6\uFF08" + XLOCK_TIMEOUT_MS + "ms\uFF09\uFF0C\u62D2\u7EDD\u5728\u65E0\u9501\u72B6\u6001\u4E0B\u5206\u914D");
3927
3922
  }
3928
3923
  }
3929
3924
  this._xrel = await this._acquireXLock();
@@ -3983,9 +3978,9 @@ var require_alloc = __commonJS({
3983
3978
  await new Promise((res) => setTimeout(res, 25));
3984
3979
  continue;
3985
3980
  }
3986
- return null;
3981
+ throw new Error("ports.claimSlot: \u8DE8\u8FDB\u7A0B\u5206\u914D\u9501\u7B49\u5F85\u8D85\u65F6\uFF08" + XLOCK_TIMEOUT_MS + "ms\uFF09\uFF0C\u62D2\u7EDD\u5728\u65E0\u9501\u72B6\u6001\u4E0B\u5206\u914D");
3987
3982
  }
3988
- return null;
3983
+ throw new Error("ports.claimSlot: \u8DE8\u8FDB\u7A0B\u5206\u914D\u9501\u83B7\u53D6\u5931\u8D25\uFF08" + (e && e.code ? e.code : e) + "\uFF09\uFF0C\u62D2\u7EDD\u5728\u65E0\u9501\u72B6\u6001\u4E0B\u5206\u914D");
3989
3984
  }
3990
3985
  }
3991
3986
  }
@@ -4512,6 +4507,19 @@ var require_collaborators = __commonJS({
4512
4507
  ui: { notify: "notify" }
4513
4508
  };
4514
4509
  var THIN_NAMES = Object.keys(THIN_SPEC);
4510
+ function collaboratorSurface(host, name) {
4511
+ const obj = host[name];
4512
+ if (!obj || typeof obj !== "object") return [];
4513
+ return Object.keys(obj).sort();
4514
+ }
4515
+ function requireThin(host, name, prop) {
4516
+ const obj = host[name];
4517
+ if (!obj || typeof obj[prop] !== "function") {
4518
+ const have = collaboratorSurface(host, name);
4519
+ throw new Error("app/assembly/collaborators: " + name + "." + prop + " \u4E0D\u5B58\u5728\uFF08\u5F53\u524D\u63A5\u53E3\u9762: " + (have.join(", ") || "\u7A7A") + "\uFF09");
4520
+ }
4521
+ return obj[prop];
4522
+ }
4515
4523
  function assertCollaboratorTargets(host) {
4516
4524
  const missing = [];
4517
4525
  for (const name of THIN_NAMES) {
@@ -4520,6 +4528,8 @@ var require_collaborators = __commonJS({
4520
4528
  }
4521
4529
  }
4522
4530
  if (missing.length) throw new Error("app/assembly/collaborators: \u63A5\u53E3\u8868\u6307\u5411\u7F3A\u5931\u65B9\u6CD5: " + missing.join(", "));
4531
+ const empty = THIN_NAMES.filter((n) => collaboratorSurface(host, n).length === 0);
4532
+ if (empty.length) throw new Error("app/assembly/collaborators: \u63A5\u53E3\u9762\u4E3A\u7A7A: " + empty.join(", "));
4523
4533
  }
4524
4534
  function installFieldHelpers(host, state) {
4525
4535
  for (const [suf, field] of ENTRY_FIELDS) {
@@ -4685,7 +4695,7 @@ var require_collaborators = __commonJS({
4685
4695
  if (options && options.validate) assertCollaboratorTargets(host);
4686
4696
  return host;
4687
4697
  }
4688
- module2.exports = { THIN_SPEC, assertCollaboratorTargets, installCollaborators };
4698
+ module2.exports = { THIN_SPEC, assertCollaboratorTargets, installCollaborators, collaboratorSurface, requireThin };
4689
4699
  }
4690
4700
  });
4691
4701
 
@@ -6604,6 +6614,71 @@ var require_file_protect = __commonJS({
6604
6614
  }
6605
6615
  });
6606
6616
 
6617
+ // src/platform/os/liveness.js
6618
+ var require_liveness = __commonJS({
6619
+ "src/platform/os/liveness.js"(exports2, module2) {
6620
+ "use strict";
6621
+ var fs2 = require("node:fs");
6622
+ var pidlook = require_pidlookup();
6623
+ function readPidFile(f) {
6624
+ if (!f) return null;
6625
+ try {
6626
+ const t = fs2.readFileSync(f, "utf8").trim();
6627
+ const n = Number.parseInt(t, 10);
6628
+ return Number.isInteger(n) && n > 0 ? n : null;
6629
+ } catch {
6630
+ return null;
6631
+ }
6632
+ }
6633
+ function anchorsHit(pid, anchors) {
6634
+ if (!Array.isArray(anchors) || !anchors.length) return null;
6635
+ const cmd2 = pidlook.readCmdline(pid);
6636
+ if (!cmd2) return null;
6637
+ return anchors.every((a) => a && cmd2.indexOf(String(a)) !== -1);
6638
+ }
6639
+ function judge(identity) {
6640
+ const q = identity || {};
6641
+ const anchors = Array.isArray(q.anchors) ? q.anchors : [];
6642
+ const evidence = [];
6643
+ let pid = Number.isInteger(q.pid) && q.pid > 0 ? q.pid : null;
6644
+ let via = null;
6645
+ if (!pid) {
6646
+ pid = readPidFile(q.pidFile);
6647
+ if (pid) {
6648
+ via = "pidfile";
6649
+ evidence.push("pid \u6765\u81EA pid \u6587\u4EF6");
6650
+ }
6651
+ }
6652
+ const port = Number.isInteger(q.port) && q.port > 0 ? q.port : null;
6653
+ if (!pid && port) {
6654
+ pid = pidlook.findListeningPid(port);
6655
+ if (pid) {
6656
+ via = "port";
6657
+ evidence.push("pid \u6765\u81EA\u7AEF\u53E3\u76D1\u542C\u8005");
6658
+ }
6659
+ }
6660
+ if (!pid) return { state: "dead", pid: null, via: null, evidence: ["\u65E0 pid \u8BC1\u636E"] };
6661
+ const alive = pidlook.probeAlive(pid);
6662
+ if (alive === "dead") return { state: "dead", pid, via, evidence: evidence.concat(["pid \u5DF2\u9000\u51FA"]) };
6663
+ if (alive === "unknown") return { state: "unknown", pid, via, evidence: evidence.concat(["pid \u5B58\u6D3B\u4E0D\u53EF\u5224\u5B9A"]) };
6664
+ const cmd2 = pidlook.readCmdline(pid);
6665
+ if (anchors.length) {
6666
+ if (!cmd2) return { state: "unknown", pid, via, evidence: evidence.concat(["cmdline \u4E0D\u53EF\u8BFB\uFF0C\u951A\u70B9\u65E0\u6CD5\u6821\u9A8C"]) };
6667
+ const hit = anchorsHit(pid, anchors);
6668
+ if (hit === true) return { state: "ours", pid, via, evidence: evidence.concat(["\u951A\u70B9\u5168\u90E8\u547D\u4E2D"]) };
6669
+ return { state: "foreign", pid, via, evidence: evidence.concat(["\u951A\u70B9\u672A\u5168\u90E8\u547D\u4E2D"]) };
6670
+ }
6671
+ if (cmd2) {
6672
+ const known = pidlook.isDshCmdlineText(cmd2);
6673
+ if (known) return { state: "ours", pid, via, evidence: evidence.concat(["cmdline \u547D\u4E2D dsh"]) };
6674
+ return { state: "foreign", pid, via, evidence: evidence.concat(["cmdline \u975E dsh"]) };
6675
+ }
6676
+ return { state: "unknown", pid, via, evidence: evidence.concat(["cmdline \u4E0D\u53EF\u8BFB\uFF0C\u8EAB\u4EFD\u4E0D\u53EF\u5224\u5B9A"]) };
6677
+ }
6678
+ module2.exports = { judge, readPidFile, anchorsHit };
6679
+ }
6680
+ });
6681
+
6607
6682
  // src/platform/os/spawn.js
6608
6683
  var require_spawn = __commonJS({
6609
6684
  "src/platform/os/spawn.js"(exports2, module2) {
@@ -6643,6 +6718,7 @@ var require_portable = __commonJS({
6643
6718
  "use strict";
6644
6719
  var fs2 = require("node:fs");
6645
6720
  var pidlookup = require_pidlookup();
6721
+ var { judge: judgeIdentity } = require_liveness();
6646
6722
  var spawner = require_spawn();
6647
6723
  var procOS = require_process();
6648
6724
  var OUTCOME = require_outcome();
@@ -6658,10 +6734,7 @@ var require_portable = __commonJS({
6658
6734
  }
6659
6735
  }
6660
6736
  function matchesAnchors(pid, anchors) {
6661
- if (!pid || !Array.isArray(anchors) || !anchors.length) return false;
6662
- const cmd2 = pidlookup.readCmdline(pid);
6663
- if (!cmd2) return false;
6664
- return anchors.some((a) => a && cmd2.indexOf(String(a)) !== -1);
6737
+ return judgeIdentity({ pid, anchors }).state === "ours";
6665
6738
  }
6666
6739
  var portOf = (o) => {
6667
6740
  const p = Number(o && o.port);
@@ -7362,10 +7435,8 @@ var require_win32 = __commonJS({
7362
7435
  }
7363
7436
  }
7364
7437
  function status() {
7365
- const guard = hasTask(BRAND2.WINDOWS_GUARD_TASK);
7366
7438
  const gui = hasTask(BRAND2.WINDOWS_GUI_TASK);
7367
- const watchdog = hasTask(BRAND2.WINDOWS_WATCHDOG_TASK);
7368
- return { kind: "schtasks", on: guard || gui || watchdog, gui, watchdog, guard };
7439
+ return { kind: "schtasks", on: gui, gui };
7369
7440
  }
7370
7441
  function setAutostart(on, deps) {
7371
7442
  const errors = [];
@@ -7658,13 +7729,7 @@ var require_autostart = __commonJS({
7658
7729
  var isLinux = process.platform === "linux";
7659
7730
  var isMac = process.platform === "darwin";
7660
7731
  var isWindows = process.platform === "win32";
7661
- var CLI_EXE = isWindows ? BRAND2.CLI_NAME + ".exe" : BRAND2.CLI_NAME;
7662
7732
  var GUI_EXE = isWindows ? BRAND2.GUI_BIN_NAME + ".exe" : BRAND2.GUI_BIN_NAME;
7663
- function daemonCommand() {
7664
- const hit = resolveExecutable(BRAND2.CLI_NAME, { envVar: BRAND2.ENV_DAEMON });
7665
- if (hit) return hit;
7666
- return path2.join(os2.homedir(), ".local", "bin", CLI_EXE);
7667
- }
7668
7733
  function guiCommand() {
7669
7734
  const hit = resolveExecutable(BRAND2.GUI_BIN_NAME, { envVar: BRAND2.ENV_SHELL_EXE });
7670
7735
  if (hit) return hit;
@@ -7702,7 +7767,7 @@ var require_autostart = __commonJS({
7702
7767
  if (pl !== "linux") return { ok: false, unsupported: true, platform: pl, enabled: false, error: "\u672A\u77E5\u5E73\u53F0" };
7703
7768
  return linux.setGuiAutostart(on, DEPS);
7704
7769
  }
7705
- module2.exports = { status, setAutostart, setGuiAutostart, daemonCommand, guiCommand };
7770
+ module2.exports = { status, setAutostart, setGuiAutostart, guiCommand };
7706
7771
  }
7707
7772
  });
7708
7773
 
@@ -8917,6 +8982,39 @@ var require_registry3 = __commonJS({
8917
8982
  }
8918
8983
  return info;
8919
8984
  }
8985
+ var http2 = require("node:http");
8986
+ var https = require("node:https");
8987
+ function probeOriginHttp(origin, timeoutMs) {
8988
+ return new Promise((resolve) => {
8989
+ let u;
8990
+ try {
8991
+ u = new URL(origin);
8992
+ } catch {
8993
+ return resolve({ ok: false, latencyMs: null, error: "origin \u975E\u6CD5" });
8994
+ }
8995
+ const mod = u.protocol === "https:" ? https : http2;
8996
+ const t0 = Date.now();
8997
+ const req = mod.get(u, (res) => {
8998
+ res.resume();
8999
+ resolve({ ok: res.statusCode < 500, latencyMs: Date.now() - t0, status: res.statusCode });
9000
+ });
9001
+ req.setTimeout(Math.max(200, Number(timeoutMs) || 5e3), () => {
9002
+ try {
9003
+ req.destroy();
9004
+ } catch {
9005
+ }
9006
+ resolve({ ok: false, latencyMs: null, error: "\u8D85\u65F6" });
9007
+ });
9008
+ req.on("error", (e) => resolve({ ok: false, latencyMs: null, error: e.message }));
9009
+ });
9010
+ }
9011
+ function probeRegistry(state, origin, opts) {
9012
+ const o = opts || {};
9013
+ return probeOriginHttp(origin, o.timeoutMs);
9014
+ }
9015
+ function probeOrigin(state, origin, opts) {
9016
+ return probeRegistry(state, origin, opts);
9017
+ }
8920
9018
  module2.exports = {
8921
9019
  platformTag,
8922
9020
  registryOrigins,
@@ -8924,7 +9022,9 @@ var require_registry3 = __commonJS({
8924
9022
  selectRegistry,
8925
9023
  registryOrigin,
8926
9024
  registryInfo,
8927
- setRegistryConfig
9025
+ setRegistryConfig,
9026
+ probeOrigin,
9027
+ probeRegistry
8928
9028
  };
8929
9029
  }
8930
9030
  });
@@ -9870,6 +9970,7 @@ var require_monitor = __commonJS({
9870
9970
  "src/platform/service/monitor.js"(exports2, module2) {
9871
9971
  "use strict";
9872
9972
  var pidlook = require_pidlookup();
9973
+ var { judge: judgeIdentity } = require_liveness();
9873
9974
  var probeModule = require_probe2();
9874
9975
  function isPortListening(host, port, timeoutMs) {
9875
9976
  return probeModule.portListening(host, port, timeoutMs || 1e3);
@@ -9889,10 +9990,7 @@ var require_monitor = __commonJS({
9889
9990
  return { up: pid !== null, pid, isDsh };
9890
9991
  }
9891
9992
  function matchesAnchors(pid, anchors) {
9892
- if (!pid || !Array.isArray(anchors) || !anchors.length) return false;
9893
- const cmd2 = pidlook.readCmdline(pid);
9894
- if (!cmd2) return false;
9895
- return anchors.every((a) => a && cmd2.indexOf(String(a)) !== -1);
9993
+ return judgeIdentity({ pid, anchors }).state === "ours";
9896
9994
  }
9897
9995
  function probeInstance(inst, opts) {
9898
9996
  const o = opts || {};
@@ -10377,6 +10475,58 @@ var require_command = __commonJS({
10377
10475
  }
10378
10476
  });
10379
10477
 
10478
+ // src/shared/guardian.js
10479
+ var require_guardian = __commonJS({
10480
+ "src/shared/guardian.js"(exports2, module2) {
10481
+ "use strict";
10482
+ function shouldGuard(inst) {
10483
+ return !!(inst && inst.guardian === true);
10484
+ }
10485
+ function bumpStartupFailure(w, now, cfg) {
10486
+ const windowMs = cfg && Number(cfg.windowMs) > 0 ? Number(cfg.windowMs) : 6e4;
10487
+ const burst = cfg && Number(cfg.burst) >= 1 ? Number(cfg.burst) : 5;
10488
+ let start = w.start;
10489
+ let count = w.count;
10490
+ if (start === null || start === void 0 || now - start > windowMs) {
10491
+ start = now;
10492
+ count = 1;
10493
+ } else {
10494
+ count += 1;
10495
+ }
10496
+ return { start, count, tripped: count >= burst };
10497
+ }
10498
+ function makeBudget(cfg) {
10499
+ const windowMs = cfg && Number(cfg.windowMs) > 0 ? Number(cfg.windowMs) : 6e4;
10500
+ const burst = cfg && Number(cfg.burst) >= 1 ? Number(cfg.burst) : 5;
10501
+ let state = { start: null, count: 0 };
10502
+ const self = {
10503
+ windowMs,
10504
+ burst,
10505
+ get count() {
10506
+ return state.count;
10507
+ },
10508
+ get tripped() {
10509
+ return state.count >= burst;
10510
+ },
10511
+ note(startupFailure) {
10512
+ if (startupFailure === false || startupFailure == null) {
10513
+ return { tripped: false, count: state.count, halted: false };
10514
+ }
10515
+ const dec = bumpStartupFailure(state, Date.now(), { windowMs, burst });
10516
+ state.start = dec.start;
10517
+ state.count = dec.count;
10518
+ return { tripped: dec.tripped, count: state.count, halted: dec.tripped };
10519
+ },
10520
+ reset() {
10521
+ state = { start: null, count: 0 };
10522
+ }
10523
+ };
10524
+ return self;
10525
+ }
10526
+ module2.exports = { shouldGuard, bumpStartupFailure, makeBudget };
10527
+ }
10528
+ });
10529
+
10380
10530
  // src/app/main/port-rederive.js
10381
10531
  var require_port_rederive = __commonJS({
10382
10532
  "src/app/main/port-rederive.js"(exports2, module2) {
@@ -10468,6 +10618,7 @@ var require_process2 = __commonJS({
10468
10618
  var { LineBuffer } = require_log();
10469
10619
  var native = require_command();
10470
10620
  var BRAND2 = require_brand();
10621
+ var guardian = require_guardian();
10471
10622
  var { findManagedDshPort, applyMainPort } = require_port_rederive();
10472
10623
  var DEPS = /* @__PURE__ */ new WeakMap();
10473
10624
  var HELPERS = [
@@ -10482,7 +10633,9 @@ var require_process2 = __commonJS({
10482
10633
  "SetObservedOnly",
10483
10634
  "StartDeadline",
10484
10635
  "SetStartDeadline",
10636
+ "StartupFailWindowStart",
10485
10637
  "SetStartupFailWindowStart",
10638
+ "StartupFailCount",
10486
10639
  "SetStartupFailCount",
10487
10640
  "SetLastFailure",
10488
10641
  "SetLastRestartAt",
@@ -10513,6 +10666,10 @@ var require_process2 = __commonJS({
10513
10666
  beginRestart: (reason, opts) => host._beginRestart(reason, opts),
10514
10667
  writeMainOwner: (pid, port) => host._writeMainOwner(pid, port)
10515
10668
  };
10669
+ const unresolved = HELPERS.filter((n) => typeof host["_m" + n] !== "function");
10670
+ if (unresolved.length) {
10671
+ throw new Error("app/main/process: HELPERS \u6307\u5411\u4E0D\u5B58\u5728\u7684\u65B9\u6CD5: " + unresolved.map((n) => "_m" + n).join(", "));
10672
+ }
10516
10673
  for (const n of HELPERS) d["m" + n] = (...a) => host["_m" + n](...a);
10517
10674
  DEPS.set(host, d);
10518
10675
  }
@@ -10700,13 +10857,31 @@ var require_process2 = __commonJS({
10700
10857
  d.logger().warn("restart triggered: " + reason + (startupFailure ? "\uFF08\u542F\u52A8\u7A97\u53E3\u5185\u9000\u51FA\uFF0C\u8BA1\u4E00\u6B21\u542F\u52A8\u5931\u8D25\uFF09" : "\uFF08\u6B63\u5E38\u91CD\u542F\uFF09"));
10701
10858
  d.tokenService().clear("main");
10702
10859
  if (!manual) d.mSetRestartCount(d.mRestartCount() + 1);
10703
- const throttle = null;
10704
- if (throttle && throttle.failed) {
10860
+ let throttle = null;
10861
+ if (startupFailure) {
10862
+ throttle = guardian.bumpStartupFailure(
10863
+ { start: d.mStartupFailWindowStart(), count: d.mStartupFailCount() },
10864
+ Date.now(),
10865
+ {
10866
+ windowMs: d.config().startupFailWindowMs || 6e4,
10867
+ burst: d.config().startupFailBurst || 5
10868
+ }
10869
+ );
10870
+ d.mSetStartupFailWindowStart(throttle.start);
10871
+ d.mSetStartupFailCount(throttle.count);
10872
+ }
10873
+ if (throttle && throttle.tripped) {
10874
+ d.state().setPhase("FAILED");
10875
+ d.mSetStartDeadline(null);
10705
10876
  d.mSetRestartAt(null);
10706
- } else {
10707
- d.state().setPhase("STARTING");
10708
- d.mSetRestartAt(Date.now() + d.config().portReleaseWaitMs);
10877
+ d.writeCrashHalted(true);
10878
+ d.events().append("main_startup_failed", { reason, count: throttle.count });
10879
+ d.logger().error("\u4E3B\u8FDB\u7A0B\u542F\u52A8\u53CD\u590D\u5931\u8D25\uFF08" + throttle.count + " \u6B21\uFF09\uFF0C\u5DF2\u505C\u6B62\u81EA\u52A8\u91CD\u542F");
10880
+ d.state().write();
10881
+ return;
10709
10882
  }
10883
+ d.state().setPhase("STARTING");
10884
+ d.mSetRestartAt(Date.now() + d.config().portReleaseWaitMs);
10710
10885
  d.mSetStartDeadline(null);
10711
10886
  const child = d.mChild();
10712
10887
  if (child && child.exitCode === null) d.main().killSequence(child);
@@ -12638,7 +12813,7 @@ var require_env_catalog = __commonJS({
12638
12813
  "src/platform/service/env-catalog.js"(exports2, module2) {
12639
12814
  "use strict";
12640
12815
  var runtime = require_runtime();
12641
- var SHARED = require_shared_constants2();
12816
+ var SHARED2 = require_shared_constants2();
12642
12817
  var ex2 = require_exec();
12643
12818
  var BRAND2 = require_brand();
12644
12819
  function whichVersion(bin, args) {
@@ -12676,7 +12851,7 @@ var require_env_catalog = __commonJS({
12676
12851
  if (hit && Date.now() - hit.at < CACHE_TTL) return Promise.resolve(hit.v);
12677
12852
  return whichVersionAsync(bin, args).then((v) => cacheSet(key, v));
12678
12853
  }
12679
- var MIN_NODE_DEFAULT = SHARED.runtime.minNode;
12854
+ var MIN_NODE_DEFAULT = SHARED2.runtime.minNode;
12680
12855
  var _runtimeMetaCache = null;
12681
12856
  var _runtimeMetaAt = 0;
12682
12857
  function runtimeMeta() {
@@ -16253,58 +16428,6 @@ var require_instance_lifecycle = __commonJS({
16253
16428
  }
16254
16429
  });
16255
16430
 
16256
- // src/shared/guardian.js
16257
- var require_guardian = __commonJS({
16258
- "src/shared/guardian.js"(exports2, module2) {
16259
- "use strict";
16260
- function shouldGuard(inst) {
16261
- return !!(inst && inst.guardian === true);
16262
- }
16263
- function bumpStartupFailure(w, now, cfg) {
16264
- const windowMs = cfg && Number(cfg.windowMs) > 0 ? Number(cfg.windowMs) : 6e4;
16265
- const burst = cfg && Number(cfg.burst) >= 1 ? Number(cfg.burst) : 5;
16266
- let start = w.start;
16267
- let count = w.count;
16268
- if (start === null || start === void 0 || now - start > windowMs) {
16269
- start = now;
16270
- count = 1;
16271
- } else {
16272
- count += 1;
16273
- }
16274
- return { start, count, tripped: count >= burst };
16275
- }
16276
- function makeBudget(cfg) {
16277
- const windowMs = cfg && Number(cfg.windowMs) > 0 ? Number(cfg.windowMs) : 6e4;
16278
- const burst = cfg && Number(cfg.burst) >= 1 ? Number(cfg.burst) : 5;
16279
- let state = { start: null, count: 0 };
16280
- const self = {
16281
- windowMs,
16282
- burst,
16283
- get count() {
16284
- return state.count;
16285
- },
16286
- get tripped() {
16287
- return state.count >= burst;
16288
- },
16289
- note(startupFailure) {
16290
- if (startupFailure === false || startupFailure == null) {
16291
- return { tripped: false, count: state.count, halted: false };
16292
- }
16293
- const dec = bumpStartupFailure(state, Date.now(), { windowMs, burst });
16294
- state.start = dec.start;
16295
- state.count = dec.count;
16296
- return { tripped: dec.tripped, count: state.count, halted: dec.tripped };
16297
- },
16298
- reset() {
16299
- state = { start: null, count: 0 };
16300
- }
16301
- };
16302
- return self;
16303
- }
16304
- module2.exports = { shouldGuard, bumpStartupFailure, makeBudget };
16305
- }
16306
- });
16307
-
16308
16431
  // src/domains/router/providers/restart.js
16309
16432
  var require_restart = __commonJS({
16310
16433
  "src/domains/router/providers/restart.js"(exports2, module2) {
@@ -16454,9 +16577,9 @@ var require_restart = __commonJS({
16454
16577
  }
16455
16578
  });
16456
16579
 
16457
- // src/app/control/process-lifecycle.js
16580
+ // src/platform/os/process-lifecycle.js
16458
16581
  var require_process_lifecycle = __commonJS({
16459
- "src/app/control/process-lifecycle.js"(exports2, module2) {
16582
+ "src/platform/os/process-lifecycle.js"(exports2, module2) {
16460
16583
  "use strict";
16461
16584
  var procOS = require_process();
16462
16585
  var pidlook = require_pidlookup();
@@ -24233,7 +24356,9 @@ var require_pm_client = __commonJS({
24233
24356
  const port = Number(j.port);
24234
24357
  if (!Number.isInteger(port) || port <= 0 || port > 65535) return null;
24235
24358
  if (!pidAlive2(Number(j.pid))) return null;
24236
- return { port, host: typeof j.host === "string" && j.host ? j.host : HOST };
24359
+ const token = typeof j.token === "string" ? j.token : "";
24360
+ if (!token) return null;
24361
+ return { port, host: typeof j.host === "string" && j.host ? j.host : HOST, token };
24237
24362
  }
24238
24363
  function post(route, payload) {
24239
24364
  const ep = endpoint();
@@ -24258,7 +24383,7 @@ var require_pm_client = __commonJS({
24258
24383
  port: ep.port,
24259
24384
  path: route,
24260
24385
  method: "POST",
24261
- headers: { "content-type": "application/json", "content-length": Buffer.byteLength(body) },
24386
+ headers: { "content-type": "application/json", "content-length": Buffer.byteLength(body), "x-lobox-mgmt-token": ep.token },
24262
24387
  timeout: TIMEOUT_MS
24263
24388
  },
24264
24389
  (res) => {
@@ -25133,7 +25258,7 @@ var require_upgrade2 = __commonJS({
25133
25258
  host._activeTaskId = null;
25134
25259
  return { ok: true, result: "up-to-date", from: oldV, to: target };
25135
25260
  }
25136
- function finishStopped(host, oldV, target, task) {
25261
+ async function finishStopped(host, oldV, target, task) {
25137
25262
  host.upgradeState = "done";
25138
25263
  host.upgradeFinishedAt = (/* @__PURE__ */ new Date()).toISOString();
25139
25264
  log(host, "DSH \u671F\u671B\u72B6\u6001\u4E3A stopped\uFF1B\u4E0B\u6B21 start \u5C06\u4F7F\u7528\u65B0\u7248\u672C\u3002");
@@ -25143,7 +25268,7 @@ var require_upgrade2 = __commonJS({
25143
25268
  host.tasks.succeed(task.id);
25144
25269
  }
25145
25270
  host._activeTaskId = null;
25146
- if (host.hooks.resumeAfterUpgrade) host.hooks.resumeAfterUpgrade();
25271
+ if (host.hooks.resumeAfterUpgrade) await host.hooks.resumeAfterUpgrade();
25147
25272
  return { ok: true, result: "installed", from: oldV, to: target };
25148
25273
  }
25149
25274
  function finishVerified(host, oldV, target, task) {
@@ -25164,7 +25289,7 @@ var require_upgrade2 = __commonJS({
25164
25289
  markStep(host, task, "\u62C9\u8D77\u5E76\u9A8C\u8BC1");
25165
25290
  log(host, "\u91CD\u65B0\u62C9\u8D77 DSH\uFF0C\u7B49\u5F85\u5065\u5EB7\u9A8C\u8BC1\u2026");
25166
25291
  taskLog(host, task, "\u91CD\u65B0\u62C9\u8D77 DSH\uFF0C\u7B49\u5F85\u5065\u5EB7\u9A8C\u8BC1\u2026");
25167
- if (host.hooks.resumeAfterUpgrade) host.hooks.resumeAfterUpgrade();
25292
+ if (host.hooks.resumeAfterUpgrade) await host.hooks.resumeAfterUpgrade();
25168
25293
  const port = host._targetPort();
25169
25294
  if (!port) {
25170
25295
  const msg = "\u65E0\u6CD5\u786E\u5B9A\u539F\u751F DSH \u7AEF\u53E3\uFF08healthUrl \u7F3A\u5931\uFF09";
@@ -25220,7 +25345,7 @@ var require_upgrade2 = __commonJS({
25220
25345
  } catch (e2) {
25221
25346
  tlog("manifest \u66F4\u65B0\u5931\u8D25: " + e2.message);
25222
25347
  }
25223
- if (host.hooks.resumeAfterUpgrade) host.hooks.resumeAfterUpgrade();
25348
+ if (host.hooks.resumeAfterUpgrade) await host.hooks.resumeAfterUpgrade();
25224
25349
  const port = host._targetPort();
25225
25350
  if (port) {
25226
25351
  const healthy = await host._waitNativeHealthy(port, host._mainUnit(), 6e4);
@@ -25288,7 +25413,7 @@ var require_upgrade2 = __commonJS({
25288
25413
  if (taskId && host.tasks) host.tasks.fail(taskId, err.message, { meta: { rolledBack: false } });
25289
25414
  }
25290
25415
  if (host.hooks.desiredRunning && host.hooks.desiredRunning()) log(host, "\u6062\u590D\u542F\u52A8 DSH\uFF08\u5F53\u524D\u78C1\u76D8\u7248\u672C\uFF09\u3002");
25291
- if (host.hooks.resumeAfterUpgrade) host.hooks.resumeAfterUpgrade();
25416
+ if (host.hooks.resumeAfterUpgrade) await host.hooks.resumeAfterUpgrade();
25292
25417
  host._activeTaskId = null;
25293
25418
  }
25294
25419
  async function upgrade(host, requestedVersion) {
@@ -25803,7 +25928,25 @@ var require_domains = __commonJS({
25803
25928
  isDshActive: () => ["STARTING", "RUNNING"].includes(host._mPhase()),
25804
25929
  desiredRunning: () => host._mDesired() === "running",
25805
25930
  verifyDeadlineMs: () => Math.max(2 * host.config.startsecs * 1e3, 12e4),
25806
- notify: (t, b) => host.notify(t, b)
25931
+ notify: (t, b) => host.notify(t, b),
25932
+ stopForUpgrade: async () => {
25933
+ const want = host._mDesired();
25934
+ if (want !== "stopped") host.setDesired("stopped");
25935
+ host.stopProcess("upgrade-stop");
25936
+ const deadline = Date.now() + Math.max(2 * host.config.startsecs * 1e3, 12e4);
25937
+ while (Date.now() < deadline) {
25938
+ const child = host._mChild();
25939
+ const alive = !!child && child.exitCode === null;
25940
+ if (!alive) return { ok: true, stopped: true };
25941
+ await new Promise((r) => setTimeout(r, 250));
25942
+ }
25943
+ return { ok: false, error: "upgrade-stop-timeout" };
25944
+ },
25945
+ resumeAfterUpgrade: async () => {
25946
+ if (host._mDesired() !== "running") host.setDesired("running");
25947
+ await host.startProcess();
25948
+ return { ok: true };
25949
+ }
25807
25950
  }
25808
25951
  });
25809
25952
  host._registerFixedPorts();
@@ -26097,10 +26240,7 @@ var require_lifecycle3 = __commonJS({
26097
26240
  return send(200, { sessionState: sup.sessionState ? sup.sessionState() : "unknown" });
26098
26241
  }
26099
26242
  if (req.method === "POST" && pathname === "/session/stop") {
26100
- if (!originAllowed(req)) {
26101
- req.resume();
26102
- return send(403, { ok: false, error: "cross-origin request rejected" });
26103
- }
26243
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26104
26244
  req.resume();
26105
26245
  return Promise.resolve(sup.shutdownAll()).then((r) => send(r && r.ok === false ? 400 : 200, r || { ok: true })).catch((e) => send(500, { ok: false, error: e.message }));
26106
26246
  }
@@ -26120,10 +26260,7 @@ var require_lifecycle3 = __commonJS({
26120
26260
  return lc ? send(200, lc.snapshot()) : send(404, { error: "\u6A21\u5757\u672A\u6CE8\u518C: " + id });
26121
26261
  }
26122
26262
  if (req.method === "POST" && action) {
26123
- if (!originAllowed(req)) {
26124
- req.resume();
26125
- return send(403, { ok: false, error: "cross-origin request rejected" });
26126
- }
26263
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26127
26264
  const lc = lm.get(id);
26128
26265
  if (!lc) return send(404, { error: "\u6A21\u5757\u672A\u6CE8\u518C: " + id });
26129
26266
  if (id === "dsh" && sup && (action === "start" || action === "stop" || action === "restart")) {
@@ -26225,18 +26362,12 @@ var require_native = __commonJS({
26225
26362
  });
26226
26363
  }
26227
26364
  if (req.method === "POST" && pathname === "/native/check-update") {
26228
- if (!originAllowed(req)) {
26229
- req.resume();
26230
- return send(403, { ok: false, error: "cross-origin request rejected" });
26231
- }
26365
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26232
26366
  sup.nativeManager.checkUpdate().then((r) => send(200, { ok: true, ...r })).catch((e) => send(500, { ok: false, error: e.message }));
26233
26367
  return;
26234
26368
  }
26235
26369
  if (req.method === "POST" && pathname === "/native/install") {
26236
- if (!originAllowed(req)) {
26237
- req.resume();
26238
- return send(403, { ok: false, error: "cross-origin request rejected" });
26239
- }
26370
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26240
26371
  collectBody(req, res, 1024, (body) => {
26241
26372
  let version = null;
26242
26373
  try {
@@ -26251,10 +26382,7 @@ var require_native = __commonJS({
26251
26382
  return;
26252
26383
  }
26253
26384
  if (req.method === "POST" && pathname === "/native/upgrade") {
26254
- if (!originAllowed(req)) {
26255
- req.resume();
26256
- return send(403, { ok: false, error: "cross-origin request rejected" });
26257
- }
26385
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26258
26386
  collectBody(req, res, 4096, (body) => {
26259
26387
  let requested = null;
26260
26388
  try {
@@ -26272,19 +26400,13 @@ var require_native = __commonJS({
26272
26400
  return;
26273
26401
  }
26274
26402
  if (req.method === "POST" && pathname === "/native/uninstall") {
26275
- if (!originAllowed(req)) {
26276
- req.resume();
26277
- return send(403, { ok: false, error: "cross-origin request rejected" });
26278
- }
26403
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26279
26404
  const r = sup.nativeManager.startUninstall();
26280
26405
  if (r && r.ok === false) return send(400, r);
26281
26406
  return send(202, { ok: true, accepted: true, state: "uninstalling" });
26282
26407
  }
26283
26408
  if (req.method === "POST" && pathname === "/native/settings") {
26284
- if (!originAllowed(req)) {
26285
- req.resume();
26286
- return send(403, { ok: false, error: "cross-origin request rejected" });
26287
- }
26409
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26288
26410
  collectBody(req, res, 4096, (body) => {
26289
26411
  try {
26290
26412
  const j = body ? JSON.parse(body) : {};
@@ -26350,10 +26472,7 @@ var require_guard = __commonJS({
26350
26472
  return send(200, sup.autostartStatus());
26351
26473
  }
26352
26474
  if (req.method === "POST" && pathname === "/autostart") {
26353
- if (!originAllowed(req)) {
26354
- req.resume();
26355
- return send(403, { ok: false, error: "cross-origin request rejected" });
26356
- }
26475
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26357
26476
  collectBody(req, res, 1024, (body) => {
26358
26477
  let enabled = null;
26359
26478
  try {
@@ -26371,10 +26490,7 @@ var require_guard = __commonJS({
26371
26490
  return send(200, sup.lanPanelStatus());
26372
26491
  }
26373
26492
  if (req.method === "POST" && pathname === "/settings/lan") {
26374
- if (!originAllowed(req)) {
26375
- req.resume();
26376
- return send(403, { ok: false, error: "cross-origin request rejected" });
26377
- }
26493
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26378
26494
  collectBody(req, res, 1024, (body) => {
26379
26495
  let enabled = null;
26380
26496
  try {
@@ -26392,10 +26508,7 @@ var require_guard = __commonJS({
26392
26508
  return send(200, sup.accessKeyStatus());
26393
26509
  }
26394
26510
  if (req.method === "POST" && pathname === "/settings/access-key") {
26395
- if (!originAllowed(req)) {
26396
- req.resume();
26397
- return send(403, { ok: false, error: "cross-origin request rejected" });
26398
- }
26511
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26399
26512
  collectBody(req, res, 4096, (body) => {
26400
26513
  let key = null;
26401
26514
  try {
@@ -26414,10 +26527,7 @@ var require_guard = __commonJS({
26414
26527
  return send(200, sup.closeActionStatus());
26415
26528
  }
26416
26529
  if (req.method === "POST" && pathname === "/settings/close-action") {
26417
- if (!originAllowed(req)) {
26418
- req.resume();
26419
- return send(403, {});
26420
- }
26530
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26421
26531
  collectBody(req, res, 1024, (body) => {
26422
26532
  let v = null;
26423
26533
  try {
@@ -26435,10 +26545,7 @@ var require_guard = __commonJS({
26435
26545
  return send(200, sup.externalBrowserStatus());
26436
26546
  }
26437
26547
  if (req.method === "POST" && pathname === "/settings/external-browser") {
26438
- if (!originAllowed(req)) {
26439
- req.resume();
26440
- return send(403, {});
26441
- }
26548
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26442
26549
  collectBody(req, res, 2048, (body) => {
26443
26550
  let id = null;
26444
26551
  let given = false;
@@ -26457,10 +26564,7 @@ var require_guard = __commonJS({
26457
26564
  return;
26458
26565
  }
26459
26566
  if (req.method === "POST" && pathname === "/shutdown") {
26460
- if (!originAllowed(req)) {
26461
- req.resume();
26462
- return send(403, {});
26463
- }
26567
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26464
26568
  req.resume();
26465
26569
  Promise.resolve(sup.shutdownAll()).then((r) => {
26466
26570
  try {
@@ -26472,10 +26576,7 @@ var require_guard = __commonJS({
26472
26576
  return;
26473
26577
  }
26474
26578
  if (req.method === "GET" && pathname === "/self-update/status") {
26475
- if (!originAllowed(req)) {
26476
- req.resume();
26477
- return send(403, {});
26478
- }
26579
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26479
26580
  Promise.resolve(sup.guardSelfUpdateStatus()).then((r) => send(r.ok ? 200 : 400, r));
26480
26581
  return;
26481
26582
  }
@@ -26498,35 +26599,23 @@ var require_guard = __commonJS({
26498
26599
  });
26499
26600
  }
26500
26601
  if (req.method === "GET" && pathname === "/env/dsh") {
26501
- if (!originAllowed(req)) {
26502
- req.resume();
26503
- return send(403, {});
26504
- }
26602
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26505
26603
  return send(200, sup.dshenvStatus());
26506
26604
  }
26507
26605
  if (req.method === "GET" && pathname === "/env/status") {
26508
- if (!originAllowed(req)) {
26509
- req.resume();
26510
- return send(403, {});
26511
- }
26606
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26512
26607
  return Promise.resolve(sup.envStatus()).then((r) => send(200, r)).catch((e) => send(500, { ok: false, error: e.message }));
26513
26608
  }
26514
26609
  if (req.method === "GET" && pathname === "/env/node-lts") {
26515
26610
  return sup.nodeLtsStatus().then((r) => send(200, r)).catch((e) => send(500, { ok: false, error: e.message }));
26516
26611
  }
26517
26612
  if (req.method === "GET" && pathname === "/env/environment") {
26518
- if (!originAllowed(req)) {
26519
- req.resume();
26520
- return send(403, { ok: false, error: "cross-origin request rejected" });
26521
- }
26613
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26522
26614
  const force = /[?&]force=1/.test(String(req.url || ""));
26523
26615
  return Promise.resolve(force ? environment.refresh({ persist: true, force: true }) : environment.form()).then((r) => send(200, r)).catch((e) => send(500, { ok: false, error: "\u73AF\u5883\u8868\u5355\u88C5\u914D\u5931\u8D25\uFF1A" + (e && e.message || e) }));
26524
26616
  }
26525
26617
  if (req.method === "GET" && pathname === "/env/environment/last") {
26526
- if (!originAllowed(req)) {
26527
- req.resume();
26528
- return send(403, { ok: false, error: "cross-origin request rejected" });
26529
- }
26618
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26530
26619
  return send(200, environment.lastSnapshot());
26531
26620
  }
26532
26621
  if (req.method === "POST" && pathname === "/env/open-url") {
@@ -26534,10 +26623,7 @@ var require_guard = __commonJS({
26534
26623
  req.resume();
26535
26624
  return send(403, { ok: false, error: "\u4EC5\u5185\u6838\u6240\u5728\u673A\u5668\u53EF\u8BF7\u5185\u6838\u8C03\u8D77\u6D4F\u89C8\u5668\uFF0C\u8BF7\u590D\u5236\u6216\u81EA\u884C\u6253\u5F00\u8BE5\u5730\u5740" });
26536
26625
  }
26537
- if (!originAllowed(req)) {
26538
- req.resume();
26539
- return send(403, { ok: false, error: "cross-origin request rejected" });
26540
- }
26626
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26541
26627
  collectBody(req, res, 4096, (body) => {
26542
26628
  let url = null;
26543
26629
  try {
@@ -26579,10 +26665,7 @@ var require_router4 = __commonJS({
26579
26665
  return Promise.resolve(sup.routerStatusView()).then((r) => send(200, r)).catch((e) => send(500, { ok: false, running: false, error: e && e.message || String(e) }));
26580
26666
  }
26581
26667
  if (req.method === "POST" && pathname.startsWith("/router/")) {
26582
- if (!originAllowed(req)) {
26583
- req.resume();
26584
- return send(403, { ok: false, error: "cross-origin request rejected" });
26585
- }
26668
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26586
26669
  const action = pathname.slice("/router/".length);
26587
26670
  req.resume();
26588
26671
  if (action === "start") {
@@ -26596,10 +26679,7 @@ var require_router4 = __commonJS({
26596
26679
  return Promise.resolve(sup.routerProviders()).then((r) => send(200, r)).catch((e) => send(500, { ok: false, error: e.message }));
26597
26680
  }
26598
26681
  if (req.method === "POST" && pathname === "/router/providers/add") {
26599
- if (!originAllowed(req)) {
26600
- req.resume();
26601
- return send(403, {});
26602
- }
26682
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26603
26683
  collectBody(req, res, 65536, (body) => {
26604
26684
  let j = {};
26605
26685
  try {
@@ -26615,18 +26695,12 @@ var require_router4 = __commonJS({
26615
26695
  return;
26616
26696
  }
26617
26697
  if (req.method === "POST" && pathname === "/router/proxy/login/start") {
26618
- if (!originAllowed(req)) {
26619
- req.resume();
26620
- return send(403, {});
26621
- }
26698
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26622
26699
  Promise.resolve(sup.routerApi().commandcodeLoginStart()).then((r) => send(r.ok ? 200 : 400, r)).catch((e) => send(500, { ok: false, error: e && e.message || String(e) }));
26623
26700
  return;
26624
26701
  }
26625
26702
  if (req.method === "POST" && pathname === "/router/proxy/login/wait") {
26626
- if (!originAllowed(req)) {
26627
- req.resume();
26628
- return send(403, {});
26629
- }
26703
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26630
26704
  collectBody(req, res, 4096, (body) => {
26631
26705
  const j = {};
26632
26706
  try {
@@ -26640,18 +26714,12 @@ var require_router4 = __commonJS({
26640
26714
  return;
26641
26715
  }
26642
26716
  if (req.method === "POST" && pathname === "/router/proxy/update/check") {
26643
- if (!originAllowed(req)) {
26644
- req.resume();
26645
- return send(403, {});
26646
- }
26717
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26647
26718
  Promise.resolve(sup.routerApi().refreshProxyUpdateInfo(true)).then((r) => send(200, { ok: true, versions: r })).catch((e) => send(500, { ok: false, error: e.message }));
26648
26719
  return;
26649
26720
  }
26650
26721
  if (req.method === "POST" && pathname === "/router/proxy/update/apply") {
26651
- if (!originAllowed(req)) {
26652
- req.resume();
26653
- return send(403, {});
26654
- }
26722
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26655
26723
  collectBody(req, res, 4096, (body) => {
26656
26724
  try {
26657
26725
  const j = body ? JSON.parse(body) : {};
@@ -26667,10 +26735,7 @@ var require_router4 = __commonJS({
26667
26735
  return Promise.resolve(sup.routerApi().proxyUpdateStatus(u.searchParams.get("appId") || "")).then((r) => send(200, r)).catch((e) => send(500, { ok: false, error: e.message }));
26668
26736
  }
26669
26737
  if (req.method === "POST" && pathname === "/router/providers/proxy/key") {
26670
- if (!originAllowed(req)) {
26671
- req.resume();
26672
- return send(403, {});
26673
- }
26738
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26674
26739
  collectBody(req, res, 65536, (body) => {
26675
26740
  try {
26676
26741
  const j = JSON.parse(body);
@@ -26682,10 +26747,7 @@ var require_router4 = __commonJS({
26682
26747
  return;
26683
26748
  }
26684
26749
  if (req.method === "POST" && pathname === "/router/providers/proxy/select") {
26685
- if (!originAllowed(req)) {
26686
- req.resume();
26687
- return send(403, {});
26688
- }
26750
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26689
26751
  collectBody(req, res, 4096, (body) => {
26690
26752
  try {
26691
26753
  const j = JSON.parse(body);
@@ -26697,10 +26759,7 @@ var require_router4 = __commonJS({
26697
26759
  return;
26698
26760
  }
26699
26761
  if (req.method === "POST" && pathname === "/router/providers/proxy/key/remove") {
26700
- if (!originAllowed(req)) {
26701
- req.resume();
26702
- return send(403, {});
26703
- }
26762
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26704
26763
  collectBody(req, res, 4096, (body) => {
26705
26764
  try {
26706
26765
  const j = JSON.parse(body);
@@ -26712,10 +26771,7 @@ var require_router4 = __commonJS({
26712
26771
  return;
26713
26772
  }
26714
26773
  if (req.method === "POST" && pathname === "/router/providers/keys/set") {
26715
- if (!originAllowed(req)) {
26716
- req.resume();
26717
- return send(403, {});
26718
- }
26774
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26719
26775
  collectBody(req, res, 65536, (body) => {
26720
26776
  try {
26721
26777
  const j = JSON.parse(body);
@@ -26728,10 +26784,7 @@ var require_router4 = __commonJS({
26728
26784
  return;
26729
26785
  }
26730
26786
  if (req.method === "POST" && pathname === "/router/providers/remove") {
26731
- if (!originAllowed(req)) {
26732
- req.resume();
26733
- return send(403, {});
26734
- }
26787
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26735
26788
  collectBody(req, res, 4096, (body) => {
26736
26789
  try {
26737
26790
  const j = body ? JSON.parse(body) : {};
@@ -26743,10 +26796,7 @@ var require_router4 = __commonJS({
26743
26796
  return;
26744
26797
  }
26745
26798
  if (req.method === "POST" && pathname === "/router/providers/key/use") {
26746
- if (!originAllowed(req)) {
26747
- req.resume();
26748
- return send(403, {});
26749
- }
26799
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26750
26800
  collectBody(req, res, 4096, (body) => {
26751
26801
  try {
26752
26802
  const j = body ? JSON.parse(body) : {};
@@ -26759,10 +26809,7 @@ var require_router4 = __commonJS({
26759
26809
  return;
26760
26810
  }
26761
26811
  if (req.method === "POST" && pathname === "/router/providers/account/discard") {
26762
- if (!originAllowed(req)) {
26763
- req.resume();
26764
- return send(403, {});
26765
- }
26812
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26766
26813
  collectBody(req, res, 4096, (body) => {
26767
26814
  try {
26768
26815
  const j = JSON.parse(body);
@@ -26774,10 +26821,7 @@ var require_router4 = __commonJS({
26774
26821
  return;
26775
26822
  }
26776
26823
  if (req.method === "POST" && pathname === "/router/providers/refresh") {
26777
- if (!originAllowed(req)) {
26778
- req.resume();
26779
- return send(403, {});
26780
- }
26824
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26781
26825
  collectBody(req, res, 4096, (body) => {
26782
26826
  try {
26783
26827
  const j = body ? JSON.parse(body) : {};
@@ -26790,10 +26834,7 @@ var require_router4 = __commonJS({
26790
26834
  return;
26791
26835
  }
26792
26836
  if (req.method === "POST" && pathname === "/router/providers/activate") {
26793
- if (!originAllowed(req)) {
26794
- req.resume();
26795
- return send(403, {});
26796
- }
26837
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26797
26838
  collectBody(req, res, 4096, (body) => {
26798
26839
  try {
26799
26840
  const j = body ? JSON.parse(body) : {};
@@ -26806,10 +26847,7 @@ var require_router4 = __commonJS({
26806
26847
  return;
26807
26848
  }
26808
26849
  if (req.method === "POST" && pathname === "/router/providers/deactivate") {
26809
- if (!originAllowed(req)) {
26810
- req.resume();
26811
- return send(403, {});
26812
- }
26850
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26813
26851
  collectBody(req, res, 4096, (body) => {
26814
26852
  try {
26815
26853
  const j = body ? JSON.parse(body) : {};
@@ -26856,10 +26894,7 @@ var require_plugins = __commonJS({
26856
26894
  return send(200, sup.pluginManager.installStatus(u.searchParams.get("job")));
26857
26895
  }
26858
26896
  if (req.method === "POST" && pathname.startsWith("/plugins/")) {
26859
- if (!originAllowed(req)) {
26860
- req.resume();
26861
- return send(403, { ok: false, error: "cross-origin request rejected" });
26862
- }
26897
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26863
26898
  const action = pathname.slice("/plugins/".length);
26864
26899
  collectBody(req, res, 65536, (body) => {
26865
26900
  let name = null;
@@ -26932,10 +26967,7 @@ var require_dist = __commonJS({
26932
26967
  return;
26933
26968
  }
26934
26969
  if (req.method === "POST" && pathname === "/dist/registry/set") {
26935
- if (!originAllowed(req)) {
26936
- req.resume();
26937
- return send(403, {});
26938
- }
26970
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26939
26971
  collectBody(req, res, 8192, (body) => {
26940
26972
  let j = {};
26941
26973
  try {
@@ -26951,18 +26983,12 @@ var require_dist = __commonJS({
26951
26983
  return;
26952
26984
  }
26953
26985
  if (req.method === "POST" && pathname === "/dist/registry/refresh") {
26954
- if (!originAllowed(req)) {
26955
- req.resume();
26956
- return send(403, {});
26957
- }
26986
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26958
26987
  sup.dist.selectRegistry(true).then(() => sup.dist.registryInfo()).then((r) => send(200, { ok: true, ...r })).catch((e) => send(500, { ok: false, error: e.message }));
26959
26988
  return;
26960
26989
  }
26961
26990
  if (req.method === "POST" && pathname === "/dist/registry/probe") {
26962
- if (!originAllowed(req)) {
26963
- req.resume();
26964
- return send(403, {});
26965
- }
26991
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
26966
26992
  return collectBody(req, res, 4096, (body) => {
26967
26993
  let j = {};
26968
26994
  try {
@@ -27279,10 +27305,7 @@ var require_instances = __commonJS({
27279
27305
  return render();
27280
27306
  }
27281
27307
  if (req.method === "POST" && pathname.startsWith("/instances/")) {
27282
- if (!originAllowed(req)) {
27283
- req.resume();
27284
- return send(403, {});
27285
- }
27308
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
27286
27309
  const act = pathname.slice("/instances/".length);
27287
27310
  collectBody(req, res, 65536, (body) => {
27288
27311
  try {
@@ -27361,10 +27384,7 @@ var require_relay = __commonJS({
27361
27384
  return Promise.resolve(sup.listLan()).then((r) => send(200, r)).catch((e) => send(500, { ok: false, error: e.message }));
27362
27385
  }
27363
27386
  if (req.method === "POST" && pathname.startsWith("/remote/")) {
27364
- if (!originAllowed(req)) {
27365
- req.resume();
27366
- return send(403, {});
27367
- }
27387
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
27368
27388
  const act = pathname.slice("/remote/".length);
27369
27389
  collectBody(req, res, 65536, (body) => {
27370
27390
  let j = {};
@@ -27424,10 +27444,7 @@ var require_shell2 = __commonJS({
27424
27444
  }
27425
27445
  }
27426
27446
  if (req.method === "POST" && pathname === "/shell/health") {
27427
- if (!originAllowed(req)) {
27428
- req.resume();
27429
- return send(403, {});
27430
- }
27447
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
27431
27448
  return collectBody(req, res, 8192, (body) => {
27432
27449
  let j = {};
27433
27450
  try {
@@ -27442,10 +27459,7 @@ var require_shell2 = __commonJS({
27442
27459
  });
27443
27460
  }
27444
27461
  if (req.method === "POST" && pathname === "/shell/check-update") {
27445
- if (!originAllowed(req)) {
27446
- req.resume();
27447
- return send(403, {});
27448
- }
27462
+ if (!originAllowed(req)) return ctx.rejectCrossOrigin(ctx);
27449
27463
  req.resume();
27450
27464
  return Promise.resolve(shell.checkUpdate(sup.dist, { authoritative: true })).then((r) => {
27451
27465
  if (sup.events) {
@@ -27461,6 +27475,107 @@ var require_shell2 = __commonJS({
27461
27475
  }
27462
27476
  });
27463
27477
 
27478
+ // src/api/contract.js
27479
+ var require_contract = __commonJS({
27480
+ "src/api/contract.js"(exports2, module2) {
27481
+ "use strict";
27482
+ var CATEGORIES = ["public", "operational", "internal", "deprecated"];
27483
+ var SURFACE = [
27484
+ { path: "/status", methods: ["GET"], domain: "lifecycle", category: "public", consumers: ["UI(polling)", "CLI(status)"], note: "\u72B6\u6001\u6458\u8981" },
27485
+ { path: "/events", methods: ["GET"], domain: "lifecycle", category: "public", consumers: ["UI(timeline)"], note: "\u589E\u91CF\u4E8B\u4EF6" },
27486
+ { path: "/healthz", methods: ["GET"], domain: "lifecycle", category: "public", consumers: ["\u58F3(\u63E1\u624B\u63A2\u9488)"], note: "\u5B58\u6D3B\u63A2\u9488" },
27487
+ { path: "/readyz", methods: ["GET"], domain: "lifecycle", category: "operational", consumers: ["\u76D1\u63A7/\u7F16\u6392\u63A2\u9488"], note: "\u5C31\u7EEA\u63A2\u9488\uFF08\u5B88\u536B\u5DF2\u521D\u59CB\u5316\u4E14\u672A\u505C\u673A\uFF09" },
27488
+ { path: "/session/status", methods: ["GET"], domain: "lifecycle", category: "public", consumers: ["\u58F3(get_session_state)"], note: "\u4F1A\u8BDD\u6001\u8BFB\u53D6\u53E3" },
27489
+ { path: "/session/stop", methods: ["POST"], domain: "lifecycle", category: "public", consumers: ["\u58F3(\u9000\u51FA\u63E1\u624B)"], note: "\u505C\u5168\u90E8\u88AB\u7BA1\u5BF9\u8C61 + \u56DE\u6267\uFF08\u5B88\u536B\u4E0D\u81EA\u505C\uFF09" },
27490
+ { path: "/metrics", methods: ["GET"], domain: "lifecycle", category: "operational", consumers: ["\u76D1\u63A7\u63A5\u5165"], note: "\u76D1\u63A7\uFF1A\u4E8B\u4EF6\u6D41\u6D3E\u751F\u9065\u6D4B\uFF08bySource/topTypes/\u4E8B\u4EF6\u7387\uFF09" },
27491
+ { path: "/logs/tail", methods: ["GET"], domain: "lifecycle", category: "operational", consumers: ["\u8FDC\u7A0B\u8BCA\u65AD"], note: "\u8BCA\u65AD\uFF1A\u5404 stream \u65E5\u5FD7\u5C3E\u90E8\uFF08\u8DE8\u673A\u6392\u969C\uFF1B\u672C\u673A CLI \u76F4\u8BFB\u6587\u4EF6\uFF09" },
27492
+ { path: "/logs/export", methods: ["GET"], domain: "lifecycle", category: "operational", consumers: ["\u5BA1\u8BA1/\u79BB\u7EBF\u5907\u4EFD"], note: "\u5BA1\u8BA1\uFF1A\u805A\u5408\u6D41 JSONL \u5BFC\u51FA\uFF08\u79BB\u7EBF\u5907\u4EFD/\u5408\u89C4\u7559\u75D5\uFF09" },
27493
+ { path: "/lifecycle", methods: ["GET"], domain: "lifecycle", category: "public", consumers: ["UI"], note: "\u6A21\u5757\u751F\u547D\u5468\u671F\u4E00\u89C8\uFF08=/lifecycle/status\uFF09" },
27494
+ { path: "/lifecycle/status", methods: ["GET"], domain: "lifecycle", category: "public", consumers: ["UI"], note: "\u540C\u4E0A\uFF08\u663E\u5F0F\u522B\u540D\uFF09" },
27495
+ { path: "/changelog", methods: ["GET"], domain: "guard", category: "public", consumers: ["UI(AboutCard)"], note: "DSH \u66F4\u65B0\u65E5\u5FD7\uFF08text/plain\uFF09" },
27496
+ { path: "/guard/changelog", methods: ["GET"], domain: "guard", category: "public", consumers: ["UI(AboutCard)"], note: "\u7BA1\u5BB6\u66F4\u65B0\u65E5\u5FD7\uFF08CHANGELOG.md\uFF09" },
27497
+ { path: "/guard/version", methods: ["GET"], domain: "guard", category: "public", consumers: ["UI(AboutCard)"], note: "\u672C\u5730\u7248\u672C\uFF08\u65E0\u7F51\u7EDC I/O\uFF09" },
27498
+ { path: "/guard/version/check", methods: ["POST"], domain: "guard", category: "public", consumers: ["UI(AboutCard, \u6E90\u7801\u5F62\u6001)"], note: "git \u4E0A\u6E38\u68C0\u67E5\uFF08\u6E90\u7801\u90E8\u7F72\u5F62\u6001\u66F4\u65B0\u901A\u9053\uFF09" },
27499
+ { path: "/autostart", methods: ["GET", "POST"], domain: "guard", category: "public", consumers: ["UI(StartupCard)"], note: "\u6574\u6761\u670D\u52A1\u94FE\u5F00\u673A\u81EA\u542F" },
27500
+ { path: "/shutdown", methods: ["POST"], domain: "guard", category: "deprecated", consumers: ["\u65E7\u7248\u58F3\u517C\u5BB9"], note: "\u66FF\u4EE3 = POST /session/stop\uFF1B\u4FDD\u7559\u4F9B\u65E7\u58F3\u9000\u51FA\uFF08\u79FB\u9664\u6761\u4EF6\uFF1A\u58F3\u6700\u4F4E\u7248\u672C >= \u4F7F\u7528 /session/stop \u7684\u7248\u672C\uFF09" },
27501
+ { path: "/ports", methods: ["GET"], domain: "guard", category: "public", consumers: ["UI(PortPanel)"], note: "\u7AEF\u53E3\u89C6\u56FE\uFF08\u805A\u5408\u4E09\u6CE8\u518C\u8868\uFF09" },
27502
+ { path: "/env/dsh", methods: ["GET"], domain: "guard", category: "public", consumers: ["README \u6587\u6863\u5316\uFF08\u5916\u90E8\u811A\u672C\uFF09"], note: "DSH \u672C\u4F53\u5B89\u88C5/\u7EB3\u7BA1\u5224\u5B9A\uFF08bin/binOk/managed/phase\uFF09" },
27503
+ { path: "/env/status", methods: ["GET"], domain: "guard", category: "public", consumers: ["UI(InstancesPage \u80FD\u529B\u77E9\u9635)"], note: "\u73AF\u5883 + \u5E73\u53F0\u80FD\u529B\u77E9\u9635 + catalog" },
27504
+ { path: "/env/node-lts", methods: ["GET"], domain: "guard", category: "public", consumers: ["UI(OverviewPage)"], note: "Node \u5F53\u524D vs \u5B98\u65B9\u6700\u65B0 LTS" },
27505
+ { path: "/env/open-url", methods: ["POST"], domain: "guard", category: "public", consumers: ["UI(externalOpen \u5730\u5740\u884C)"], note: "\u8BF7\u5185\u6838\u7528\u7CFB\u7EDF\u9ED8\u8BA4\u6D4F\u89C8\u5668\u6253\u5F00 http(s) \u5730\u5740\uFF08\u4E09\u6863\u7ED3\u679C\u539F\u6837\u56DE\u4F20\uFF0C\u5931\u8D25\u5E26 evidence.diagnostics \u63A2\u6D4B\u7559\u75D5\uFF1B\u4EC5\u56DE\u73AF\u6765\u6E90\uFF0C\u58F3\u5185 webview \u4E22\u5F03 window.open \u65F6\u4EE3\u7684\u552F\u4E00\u4EE3\u5F00\u65B9\uFF09" },
27506
+ { path: "/env/environment", methods: ["GET"], domain: "guard", category: "public", consumers: ["UI(OverviewPage \u73AF\u5883\u8868\u5355)", "README \u6587\u6863\u5316\uFF08\u4EBA\u5DE5/\u652F\u6301\u6392\u969C\u76F4\u8BFB\uFF1B\u6253\u5F00\u52A8\u4F5C\u7684\u8BCA\u65AD\u8D70 evidence.diagnostics\uFF09"], note: "\u73AF\u5883\u8868\u5355\uFF08\u53EA\u8BFB\u88C5\u914D\u9762\uFF0Cschema 2 \u7EF4\u5EA6\u53F0\u8D26\uFF09\uFF1A\u5019\u9009\u6D4F\u89C8\u5668 + \u7CFB\u7EDF\u9ED8\u8BA4\u53CA\u5176\u6765\u6E90 + \u56FE\u5F62\u4F1A\u8BDD + \u80FD\u529B\u6863\u4F4D + \u7528\u6237\u504F\u597D + \u8FD9\u4E00\u62CD\u7684\u5206\u53D1\u4F9D\u636E + \u8FD0\u884C\u65F6\uFF08Node/npm/\u955C\u50CF\u6E90/\u5168\u5C40\u524D\u7F00\uFF09+ \u51FA\u7F51\u6761\u4EF6\uFF08\u7CFB\u7EDF\u4EE3\u7406\u4E0E\u76EE\u6807\u57DF\u901A\u8DEF\uFF09+ \u6BCF\u6761\u7CFB\u7EDF\u67E5\u8BE2\u7559\u75D5\uFF1B?force=1 \u5F02\u6B65\u8865\u9F50\u5404\u7EF4\u5EA6\u5E76\u843D\u5FEB\u7167" },
27507
+ { path: "/env/environment/last", methods: ["GET"], domain: "guard", category: "public", consumers: ["UI(OverviewPage \u73AF\u5883\u8868\u5355\u7684\u4E0A\u4E00\u62CD\u7559\u75D5)", "README \u6587\u6863\u5316\uFF08\u4EBA\u5DE5/\u652F\u6301\u6392\u969C\u76F4\u8BFB\uFF09"], note: "\u4E0A\u4E00\u62CD\u73AF\u5883\u5FEB\u7167\u7684\u53EA\u8BFB\u56DE\u770B\u53E3\uFF08\u96F6\u6478\u7F51\u96F6\u5199\u76D8\uFF0C\u7EDD\u4E0D\u53C2\u4E0E\u5206\u53D1\u5224\u5B9A\uFF09\uFF1Aavailable/at/ageMs/path + \u6574\u4EFD\u4E0A\u4E00\u62CD\u8868\u5355\uFF1B\u6CA1\u5199\u8FC7\uFF08never-written\uFF09\u4E0E\u8BFB\u4E0D\u51FA\uFF08unreadable-or-schema-mismatch\uFF09\u5206\u5F00\u6807" },
27508
+ { path: "/settings/external-browser", methods: ["GET", "POST"], domain: "guard", category: "public", consumers: ["UI(OverviewPage \u73AF\u5883\u8868\u5355)"], note: "\u5916\u90E8\u6253\u5F00\u7684\u6D4F\u89C8\u5668\u504F\u597D\uFF08id \u5FC5\u987B\u662F\u672C\u673A\u5019\u9009\uFF1B\u7A7A\u4E32\u6E05\u9664\uFF09" },
27509
+ { path: "/settings/access-key", methods: ["GET", "POST"], domain: "guard", category: "public", consumers: ["UI(StartupCard)"], note: "\u8BBF\u95EE\u5BC6\u94A5" },
27510
+ { path: "/settings/close-action", methods: ["GET", "POST"], domain: "guard", category: "public", consumers: ["UI(StartupCard)", "\u58F3(\u8BFB\u53D6\u6267\u884C)"], note: "\u5173\u7A97\u884C\u4E3A\uFF08hide/exit\uFF09" },
27511
+ { path: "/settings/lan", methods: ["GET", "POST"], domain: "guard", category: "public", consumers: ["UI(StartupCard)"], note: "\u9762\u677F\u5C40\u57DF\u7F51\u8BBF\u95EE\u5F00\u5173" },
27512
+ { path: "/self-update/status", methods: ["GET"], domain: "guard", category: "public", consumers: ["UI(AboutCard)"], note: "\u5185\u6838\u66F4\u65B0\u72B6\u6001\uFF08\u53EA\u8BFB\uFF1B\u5B89\u88C5\u5F52\u684C\u9762\u58F3\uFF09" },
27513
+ { path: "/self-update/apply", methods: ["POST"], domain: "guard", category: "deprecated", consumers: ["\u65E0"], note: "\u5355\u5199\u5165\u8005=\u58F3\uFF1A\u8FD4\u56DE 410 KERNEL_UPDATE_SINGLE_WRITER\uFF1B\u66FF\u4EE3 = \u684C\u9762\u58F3 kernel_update_apply" },
27514
+ { path: "/self-update/restart-guard", methods: ["POST"], domain: "guard", category: "deprecated", consumers: ["\u65E0"], note: "\u5B88\u536B\u4E0D\u81EA\u91CD\u542F\uFF1A\u8FD4\u56DE 410\uFF1B\u66FF\u4EE3 = \u58F3\u5728\u5B89\u88C5\u540E\u7ECF\u670D\u52A1\u7BA1\u7406\u5668\u91CD\u542F\u5B88\u536B" },
27515
+ { path: "/native/status", methods: ["GET"], domain: "native", category: "public", consumers: ["UI(OverviewPage)", "CLI(status)"], note: "\u5B89\u88C5\u72B6\u6001 + \u7248\u672C + \u5347\u7EA7\u72B6\u6001\u673A" },
27516
+ { path: "/native/check-update", methods: ["POST"], domain: "native", category: "public", consumers: ["UI(OverviewPage)"], note: "\u89E6\u53D1\u7248\u672C\u68C0\u67E5" },
27517
+ { path: "/native/install", methods: ["POST"], domain: "native", category: "public", consumers: ["UI(OverviewPage)", "CLI"], note: "\u5F02\u6B65\u5B89\u88C5\uFF08202\uFF09" },
27518
+ { path: "/native/uninstall", methods: ["POST"], domain: "native", category: "public", consumers: ["UI(OverviewPage)"], note: "\u5F02\u6B65\u5378\u8F7D\uFF08202\uFF09" },
27519
+ { path: "/native/upgrade", methods: ["POST"], domain: "native", category: "public", consumers: ["UI(OverviewPage)", "CLI(upgrade)"], note: "\u4E00\u952E\u5347\u7EA7\uFF08\u5931\u8D25\u56DE\u6EDA\uFF09" },
27520
+ { path: "/native/settings", methods: ["POST"], domain: "native", category: "public", consumers: ["UI(OverviewPage)"], note: "main \u5143\u6570\u636E\u8865\u4E01\uFF08\u4EC5 guardian\uFF1B\u8FDC\u7A0B\u610F\u56FE\u552F\u4E00\u5165\u53E3\u5728 /remote/*\uFF09" },
27521
+ { path: "/instances", methods: ["GET"], domain: "instances", category: "public", consumers: ["UI(InstancesPage)"], note: "\u5B9E\u4F8B\u5217\u8868\uFF08+ POST /instances/{action}\uFF09\uFF1B\u8FDC\u7A0B\u8BBF\u95EE\u4EE4\u724C\u660E\u6587\u4EC5\u56DE\u73AF\u6765\u6E90\u4E0B\u53D1\uFF08\u5176\u4F59\u53EA\u89C1 tokenSet \u5E03\u5C14\uFF09\uFF0CauthUrl \u7684 ?token= \u540C\u5224\u636E" },
27522
+ { path: "/open", methods: ["GET"], domain: "instances", category: "public", consumers: ["UI(open-web \u2192 \u672C\u673A\u7CFB\u7EDF\u6D4F\u89C8\u5668\u4E00\u6B21\u6027\u7801\u8DF3\u8F6C)"], note: "\u4E00\u6B21\u6027\u7801\u6362\u53D6 dsh-auth cookie \u5E76\u56DE\u8DF3\u5B9E\u4F8B DSH \u9875\u9762\uFF08\u4EE4\u724C\u4E0D\u8FDB URL/argv\uFF09" },
27523
+ { path: "/plugins/market", methods: ["GET"], domain: "plugins", category: "public", consumers: ["UI(PluginsPage)"], note: "\u5E02\u573A\u7D22\u5F15\uFF08TTL \u7F13\u5B58\uFF09" },
27524
+ { path: "/plugins/installed", methods: ["GET"], domain: "plugins", category: "public", consumers: ["UI(PluginsPage)"], note: "\u5DF2\u88C5\u7B2C\u4E09\u65B9\u63D2\u4EF6" },
27525
+ { path: "/plugins/check-updates", methods: ["GET"], domain: "plugins", category: "public", consumers: ["UI(PluginsPage)"], note: "\u5DF2\u88C5\u63D2\u4EF6\u66F4\u65B0\u68C0\u6D4B" },
27526
+ { path: "/plugins/install-status", methods: ["GET"], domain: "plugins", category: "public", consumers: ["UI(PluginsPage, job \u8F6E\u8BE2)"], note: "\u63D2\u4EF6\u4EFB\u52A1\u8FDB\u5EA6" },
27527
+ { path: "/router/status", methods: ["GET"], domain: "router", category: "public", consumers: ["UI(RouterPage)"], note: "\u4E2D\u8F6C\u72B6\u6001 + \u7528\u91CF" },
27528
+ { path: "/router/providers", methods: ["GET"], domain: "router", category: "public", consumers: ["UI(RouterPage)"], note: "\u4F9B\u5E94\u5546 + \u8D26\u53F7 + \u5B9E\u4F8B\u89C6\u56FE" },
27529
+ { path: "/router/ports", methods: ["GET"], domain: "router", category: "internal", consumers: ["p2p-api \u5951\u7EA6\u6D4B\u8BD5\uFF08\u57DF\u5206\u79BB\u9A8C\u8BC1\uFF09"], note: "router \u81EA\u6CBB\u6BB5\u7AEF\u53E3\u89C6\u56FE\uFF08daemon \u6A21\u5F0F\u7269\u7406\u5206\u79BB\uFF09" },
27530
+ { path: "/router/domain-summary", methods: ["GET"], domain: "router", category: "internal", consumers: ["\u5B88\u536B\u76D1\u7763\u62CD\u81EA\u6D88\u8D39\uFF08\u5199\u76EE\u5F55 domainSummary\uFF09"], note: "\u57DF\u6458\u8981\u53EA\u8BFB\u7F13\u5B58" },
27531
+ { path: "/router/providers/account/discard", methods: ["POST"], domain: "router", category: "public", consumers: ["UI(RouterPage)"], note: "\u8D26\u53F7\u4E22\u5F03" },
27532
+ { path: "/router/providers/activate", methods: ["POST"], domain: "router", category: "public", consumers: ["UI(RouterPage)"], note: "\u6FC0\u6D3B\u4F9B\u5E94\u5546" },
27533
+ { path: "/router/providers/add", methods: ["POST"], domain: "router", category: "public", consumers: ["UI(RouterPage)"], note: "\u65B0\u589E\u4F9B\u5E94\u5546" },
27534
+ { path: "/router/providers/deactivate", methods: ["POST"], domain: "router", category: "public", consumers: ["UI(RouterPage)"], note: "\u505C\u7528\u4F9B\u5E94\u5546" },
27535
+ { path: "/router/providers/key/use", methods: ["POST"], domain: "router", category: "public", consumers: ["UI(RouterPage)"], note: "\u5207\u6362\u4F7F\u7528\u4E2D\u7684 Key" },
27536
+ { path: "/router/providers/keys/set", methods: ["POST"], domain: "router", category: "public", consumers: ["UI(RouterPage)"], note: "\u8BBE\u7F6E\u4F9B\u5E94\u5546 Key" },
27537
+ { path: "/router/providers/proxy/key", methods: ["POST"], domain: "router", category: "public", consumers: ["UI(RouterPage)"], note: "\u53CD\u4EE3 Key \u5199\u5165" },
27538
+ { path: "/router/providers/proxy/key/remove", methods: ["POST"], domain: "router", category: "public", consumers: ["UI(RouterPage)"], note: "\u53CD\u4EE3 Key \u79FB\u9664" },
27539
+ { path: "/router/providers/proxy/select", methods: ["POST"], domain: "router", category: "public", consumers: ["UI(RouterPage)"], note: "\u9009\u62E9\u53CD\u4EE3" },
27540
+ { path: "/router/providers/refresh", methods: ["POST"], domain: "router", category: "public", consumers: ["UI(RouterPage)"], note: "\u5237\u65B0\u4F9B\u5E94\u5546" },
27541
+ { path: "/router/providers/remove", methods: ["POST"], domain: "router", category: "public", consumers: ["UI(RouterPage)"], note: "\u5220\u9664\u4F9B\u5E94\u5546" },
27542
+ { path: "/router/proxy/login/start", methods: ["POST"], domain: "router", category: "public", consumers: ["UI(RouterPage)"], note: "Command Code \u4E00\u952E\u767B\u5F55\uFF08\u53D1\u8D77\uFF09" },
27543
+ { path: "/router/proxy/login/wait", methods: ["POST"], domain: "router", category: "public", consumers: ["UI(RouterPage)"], note: "\u767B\u5F55\u7B49\u5F85" },
27544
+ { path: "/router/proxy/update/apply", methods: ["POST"], domain: "router", category: "public", consumers: ["UI(RouterPage)"], note: "\u53CD\u4EE3\u66F4\u65B0\uFF08job\uFF09" },
27545
+ { path: "/router/proxy/update/check", methods: ["POST"], domain: "router", category: "public", consumers: ["UI(RouterPage)"], note: "\u53CD\u4EE3\u7248\u672C\u68C0\u6D4B" },
27546
+ { path: "/router/proxy/update/status", methods: ["GET"], domain: "router", category: "public", consumers: ["UI(RouterPage, job \u8F6E\u8BE2)"], note: "\u53CD\u4EE3\u66F4\u65B0\u8FDB\u5EA6" },
27547
+ { path: "/dist/registry", methods: ["GET"], domain: "dist", category: "public", consumers: ["UI(RegistryCard)"], note: "\u955C\u50CF\u6E90\u72B6\u6001" },
27548
+ { path: "/dist/registry/refresh", methods: ["POST"], domain: "dist", category: "public", consumers: ["UI(RegistryCard)"], note: "\u955C\u50CF\u6E90\u6D4B\u901F\u5237\u65B0" },
27549
+ { path: "/dist/registry/set", methods: ["POST"], domain: "dist", category: "public", consumers: ["UI(RegistryCard)"], note: "\u955C\u50CF\u6E90\u624B\u52A8\u56FA\u5B9A" },
27550
+ { path: "/dist/registry/probe", methods: ["POST"], domain: "dist", category: "public", consumers: ["UI(RegistryCard \u6D4B\u8BD5\u6309\u94AE)"], note: "\u540C\u6E90\u5355\u6E90\u63A2\u6D3B\uFF08\u670D\u52A1\u7AEF\uFF0C\u4E0D\u53D7\u9875\u9762 CSP \u9650\u5236\uFF09" },
27551
+ { path: "/lan-access", methods: ["GET"], domain: "relay", category: "public", consumers: ["UI(LanPage)"], note: "\u8FDC\u7A0B\u4EE3\u7406\u5217\u8868\uFF08\u8131\u654F\uFF1A\u4EFB\u4F55\u4EE4\u724C\u5B57\u6BB5\u90FD\u4E0D\u5916\u4F20\uFF1Bremote \u89C6\u56FE\u4E3A\u8BBF\u95EE URL/\u5C31\u7EEA\u5224\u5B9A\u7684\u5355\u4E00\u6765\u6E90\uFF09" },
27552
+ { path: "/remote/frp", methods: ["GET"], domain: "relay", category: "public", consumers: ["UI(LanPage)"], note: "frpc \u72B6\u6001\uFF08\u8BBE\u7F6E + \u8FD0\u884C\u6001 + wan \u66B4\u9732\u6E05\u5355\uFF09" },
27553
+ { path: "/tasks", methods: ["GET"], domain: "tasks", category: "public", consumers: ["UI(TasksPage)"], note: "\u7EDF\u4E00\u4EFB\u52A1\u5217\u8868\uFF08+ /tasks/{id}\uFF09" },
27554
+ { path: "/shell/status", methods: ["GET"], domain: "shell", category: "public", consumers: ["UI(\u58F3\u72B6\u6001\u5361)", "CLI"], note: "\u58F3\u8EAB\u4EFD + \u66F4\u65B0\u8D26\u672C + \u5224\u5B9A\u7ED3\u8BBA" },
27555
+ { path: "/shell/health", methods: ["POST"], domain: "shell", category: "operational", consumers: ["\u8FD0\u7EF4\uFF1A\u6392\u969C\u65F6\u624B\u5DE5\u4E0A\u62A5\u58F3\u9636\u6BB5\uFF08\u58F3\u672A\u63A5\u7EBF\uFF0C\u5B9E\u6D4B\u96F6\u8C03\u7528\uFF09"], note: "\u8BCA\u65AD\u7528\u9014\uFF1Aphase=ready \u5373\u66F4\u65B0\u786E\u8BA4\u4FE1\u53F7\uFF0C\u4F9B\u6392\u969C\u624B\u5DE5\u9A71\u52A8\u5B89\u5168\u7F51\uFF1B\u5F53\u524D evaluate() \u56E0\u7F3A\u8F93\u5165\u6052 idle" },
27556
+ { path: "/shell/update-pending", methods: ["POST"], domain: "shell", category: "operational", consumers: ["\u8FD0\u7EF4\uFF1A\u6392\u969C\u65F6\u624B\u5DE5\u5EFA\u7ACB\u66F4\u65B0\u8D26\u672C\uFF08\u58F3\u672A\u63A5\u7EBF\uFF0C\u5B9E\u6D4B\u96F6\u8C03\u7528\uFF09"], note: "\u8BCA\u65AD\u7528\u9014\uFF1A\u5EFA\u7ACB\u66F4\u65B0\u8D26\u672C\uFF08\u5F85\u91CD\u542F\u786E\u8BA4\uFF09\uFF0C\u4F9B\u6392\u969C\u624B\u5DE5\u9A71\u52A8\u5185\u6838\u4FA7\u5B89\u5168\u7F51" },
27557
+ { path: "/shell/check-update", methods: ["POST"], domain: "shell", category: "public", consumers: ["UI(\u5173\u4E8E\u5361)"], note: "\u58F3\u7248\u672C\u68C0\u6D4B\uFF08\u4E0E\u5185\u6838\u81EA\u66F4\u65B0\u540C\u6E90\uFF1Anpm registry + \u955C\u50CF\u56DE\u9000\uFF09" }
27558
+ ];
27559
+ var PREFIXES = [
27560
+ { prefix: "/dist/", domain: "dist", category: "public", consumers: ["UI"], note: "/dist/registry/{refresh|set}" },
27561
+ { prefix: "/guard/", domain: "guard", category: "public", consumers: ["UI"], note: "/guard/version|changelog \u7B49" },
27562
+ { prefix: "/instances/", domain: "instances", category: "public", consumers: ["UI"], note: "/instances/{add|remove|update|start|stop|check-update|open-web|upgrade}\uFF1Bopen-web \u56DE platform.browser.openBrowser \u7684\u4E09\u6863\u7ED3\u679C {ok,confirmed,handedOff,reason,error,url,evidence}\uFF0Curl \u6052\u5728\u573A\u4F9B\u9762\u677F\u590D\u5236/\u624B\u52A8\u6253\u5F00" },
27563
+ { prefix: "/lifecycle", domain: "lifecycle", category: "public", consumers: ["UI", "CLI"], note: "/lifecycle/{id}[/{action}]\uFF08\u552F\u4E00\u542F\u505C\u5165\u53E3\uFF09" },
27564
+ { prefix: "/lifecycle/", domain: "lifecycle", category: "public", consumers: ["UI", "CLI"], note: "\u540C\u4E0A\uFF08\u663E\u5F0F\u524D\u7F00\uFF09" },
27565
+ { prefix: "/logs", domain: "lifecycle", category: "operational", consumers: ["\u8BCA\u65AD/\u5BA1\u8BA1"], note: "/logs/{tail|export}\uFF08\u65E0 events-tail\uFF1A\u4E0E /events \u8BED\u4E49\u91CD\u590D\uFF09" },
27566
+ { prefix: "/native/", domain: "native", category: "public", consumers: ["UI", "CLI"], note: "/native/{status|install|uninstall|upgrade|...}" },
27567
+ { prefix: "/plugins/", domain: "plugins", category: "public", consumers: ["UI"], note: "/plugins/{install|enable|disable|uninstall|update}" },
27568
+ { prefix: "/remote/", domain: "relay", category: "public", consumers: ["UI"], note: "/remote/{set-mode|set-token|frp-server|frp-install}\uFF08\u610F\u56FE\u552F\u4E00\u5165\u53E3\uFF1Bset-mode \u5F00\u542F\u65F6\u65E0\u4EE4\u724C\u5373\u81EA\u52A8\u5206\u914D\u5E76\u56DE\u6267 tokenAutoAllocated\uFF0Cwan \u524D\u7F6E\u95F8=\u8BBF\u95EE\u4EE4\u724C \u22658 \u4F4D\uFF1Bset-token \u7A7A\u4E32=\u663E\u5F0F\u6E05\u9664\uFF09" },
27569
+ { prefix: "/router/", domain: "router", category: "public", consumers: ["UI"], note: "/router/... \uFF08ports/domain-summary \u4E3A internal\uFF0C\u89C1 SURFACE\uFF09" },
27570
+ { prefix: "/shell/", domain: "shell", category: "public", consumers: ["\u58F3", "UI"], note: "/shell/{status|health|update-pending|check-update|restart}\uFF08\u58F3\u66F4\u65B0\u5F3A\u5236\uFF0C\u65E0\u56DE\u9000\uFF09\uFF1B\u26A0 health/update-pending \u5B9E\u4E3A\u58F3\u96F6\u8C03\u7528\u7684\u6392\u969C\u5165\u53E3\uFF0C\u89C1\u4E0A\u65B9\u6761\u76EE" },
27571
+ { prefix: "/self-update/", domain: "guard", category: "public", consumers: ["UI"], note: "/self-update/status\uFF08\u53EA\u8BFB\uFF09\uFF1Bapply|restart-guard \u8FD4\u56DE 410" },
27572
+ { prefix: "/settings/", domain: "guard", category: "public", consumers: ["UI"], note: "/settings/{lan|access-key|close-action}" },
27573
+ { prefix: "/tasks/", domain: "tasks", category: "public", consumers: ["UI"], note: "/tasks/{id}" }
27574
+ ];
27575
+ module2.exports = { SURFACE, PREFIXES, CATEGORIES };
27576
+ }
27577
+ });
27578
+
27464
27579
  // src/api/router-table.js
27465
27580
  var require_router_table = __commonJS({
27466
27581
  "src/api/router-table.js"(exports2, module2) {
@@ -27477,7 +27592,19 @@ var require_router_table = __commonJS({
27477
27592
  require_relay(),
27478
27593
  require_shell2()
27479
27594
  ];
27480
- module2.exports = { API_DOMAINS };
27595
+ var { SURFACE } = require_contract();
27596
+ function assertSurfaceOwned(domains) {
27597
+ const orphans = [];
27598
+ for (const entry of SURFACE || []) {
27599
+ const path2 = typeof entry === "string" ? entry : entry && entry.path;
27600
+ if (!path2) continue;
27601
+ const owned = domains.some((d) => typeof d.owns === "function" && d.owns(path2));
27602
+ if (!owned) orphans.push(path2);
27603
+ }
27604
+ return orphans;
27605
+ }
27606
+ var API_DOMAINS_ORPHANS = assertSurfaceOwned(API_DOMAINS);
27607
+ module2.exports = { API_DOMAINS, API_DOMAINS_ORPHANS };
27481
27608
  }
27482
27609
  });
27483
27610
 
@@ -27646,6 +27773,14 @@ var require_server = __commonJS({
27646
27773
  } catch {
27647
27774
  }
27648
27775
  }
27776
+ function rejectCrossOrigin(ctx) {
27777
+ const { req, send } = ctx;
27778
+ try {
27779
+ req.resume();
27780
+ } catch {
27781
+ }
27782
+ return send(403, { ok: false, error: "cross-origin request rejected" });
27783
+ }
27649
27784
  function createServer(sup, deps) {
27650
27785
  const browser = deps && deps.browser || browserExit;
27651
27786
  const environment = deps && deps.environment || environmentExit;
@@ -27717,7 +27852,7 @@ var require_server = __commonJS({
27717
27852
  } catch (e) {
27718
27853
  return send(400, { error: "bad request encoding" });
27719
27854
  }
27720
- const ctx = { sup, req, res, pathname: decodedPathname, identity, send, collectBody, originAllowed: originAllowedLive, tokOf, browser, environment, server };
27855
+ const ctx = { sup, req, res, pathname: decodedPathname, identity, send, collectBody, originAllowed: originAllowedLive, rejectCrossOrigin, tokOf, browser, environment, server };
27721
27856
  for (const d of API_DOMAINS) {
27722
27857
  if (d.owns(pathname)) {
27723
27858
  try {
@@ -28288,15 +28423,19 @@ var require_ports3 = __commonJS({
28288
28423
  async function claim(segment, owner, opts) {
28289
28424
  const o = opts || {};
28290
28425
  const reservedPorts = o.reservedPorts || _reservedByOtherLedger(owner);
28291
- return registry.claimSlot(segment, owner, {
28292
- preferred: o.preferred,
28293
- bindingPreferred: !!o.bindingPreferred,
28294
- reservedPorts: reservedPorts || void 0,
28295
- onBindingLost: o.onBindingLost,
28296
- reclaimCmdMark: "domains/relay/daemon.js",
28297
- reclaimCfg: o.configPath || "",
28298
- waitMs: 8e3
28299
- });
28426
+ try {
28427
+ return await registry.claimSlot(segment, owner, {
28428
+ preferred: o.preferred,
28429
+ bindingPreferred: !!o.bindingPreferred,
28430
+ reservedPorts: reservedPorts || void 0,
28431
+ onBindingLost: o.onBindingLost,
28432
+ reclaimCmdMark: "domains/relay/daemon.js",
28433
+ reclaimCfg: o.configPath || "",
28434
+ waitMs: 8e3
28435
+ });
28436
+ } catch (e) {
28437
+ return { conflict: true, reason: "alloc-lock-unavailable", error: e && e.message || String(e) };
28438
+ }
28300
28439
  }
28301
28440
  function releaseOwner(owner) {
28302
28441
  try {
@@ -29306,6 +29445,7 @@ function findPackageRoot(start) {
29306
29445
  var ROOT = findPackageRoot(__dirname);
29307
29446
  var stateRoot = require_state_root();
29308
29447
  var BRAND = require_brand();
29448
+ var SHARED = require_shared_constants2();
29309
29449
  var SUPERVISOR_DIR = stateRoot.supervisorDir();
29310
29450
  var USER_CONFIG = path.join(SUPERVISOR_DIR, "config.json");
29311
29451
  var { buildDefaults } = require_config();
@@ -29351,9 +29491,9 @@ function readApiAddress() {
29351
29491
  const cfg = JSON.parse(fs.readFileSync(cfgPath, "utf8"));
29352
29492
  let host = cfg.apiHost || "127.0.0.1";
29353
29493
  if (host === "0.0.0.0" || host === "::") host = "127.0.0.1";
29354
- return { host, port: cfg.apiPort || 36360 };
29494
+ return { host, port: cfg.apiPort || SHARED.net.apiPort };
29355
29495
  } catch {
29356
- return { host: "127.0.0.1", port: 36360 };
29496
+ return { host: "127.0.0.1", port: SHARED.net.apiPort };
29357
29497
  }
29358
29498
  }
29359
29499
  function logFilePaths() {