svamp-cli 0.2.342 → 0.2.356

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 (67) hide show
  1. package/bin/skills/artifact/SKILL.md +19 -5
  2. package/bin/skills/crew/SKILL.md +62 -13
  3. package/dist/DefaultTransport-vfp78fug.mjs +47 -0
  4. package/dist/GeminiTransport-3OkhtFRO.mjs +130 -0
  5. package/dist/KimiTransport-D8n009Tr.mjs +141 -0
  6. package/dist/acpAgentConfig-CObOPlA8.mjs +48 -0
  7. package/dist/acpBackend-UaBD4zL3.mjs +925 -0
  8. package/dist/{adminCommands-CRTBDZan.mjs → adminCommands-BvsYnRDA.mjs} +2 -18
  9. package/dist/{agentCommands-BuO988tJ.mjs → agentCommands-D91RcjqQ.mjs} +6 -23
  10. package/dist/api-BHjyC0Ph.mjs +157 -0
  11. package/dist/{auth--WS0wezs.mjs → auth-CRz8TsEl.mjs} +1 -22
  12. package/dist/bootStatus-DqtNgJch.mjs +143 -0
  13. package/dist/claudeAuth-C0wc1GTM.mjs +291 -0
  14. package/dist/cli.mjs +2948 -5
  15. package/dist/codexAppServerBackend-VGsYtbqg.mjs +786 -0
  16. package/dist/codexProvider-BtxYc5Rj.mjs +68 -0
  17. package/dist/{commands-DDuGBSsz.mjs → commands-B-yczgz_.mjs} +115 -49
  18. package/dist/{commands-DU4B-4Gh.mjs → commands-BMeDrpSv.mjs} +55 -25
  19. package/dist/{commands-DXLOKJOj.mjs → commands-BbmypSgx.mjs} +62 -27
  20. package/dist/{commands-C0HQiu-S.mjs → commands-BkdbelFo.mjs} +78 -38
  21. package/dist/{commands-DXM17M6n.mjs → commands-C13-yE2R.mjs} +42 -19
  22. package/dist/{commands-BKb1g8Gq.mjs → commands-CoOc4qiw.mjs} +20 -30
  23. package/dist/{commands-BsKgZ5sQ.mjs → commands-DW5RnHZw.mjs} +2 -19
  24. package/dist/{commands-Cwxy-C5N.mjs → commands-sPvRcG3J.mjs} +10 -32
  25. package/dist/cron-hHGdb5kU.mjs +132 -0
  26. package/dist/detectIsolation-CrV8IFDv.mjs +339 -0
  27. package/dist/envFlag-COOuJ3AH.mjs +11 -0
  28. package/dist/fileLock-BMPwCrB6.mjs +80 -0
  29. package/dist/{fleet-BHzlAvnu.mjs → fleet-Ca-UjJNL.mjs} +122 -36
  30. package/dist/flushExit-C-i6SGjj.mjs +37 -0
  31. package/dist/friendlyName-1UZcyDhu.mjs +586 -0
  32. package/dist/{headlessCli-C2gvOpOt.mjs → headlessCli-C8HzQvis.mjs} +3 -21
  33. package/dist/hookSettings-FFc1pi8j.mjs +10546 -0
  34. package/dist/{httpServer-Be1Hcddr.mjs → httpServer-BzEDbOGn.mjs} +14 -5
  35. package/dist/hyphaClient-ybivOjZo.mjs +49 -0
  36. package/dist/index.mjs +40 -8
  37. package/dist/instance-CeHz5C8v.mjs +203 -0
  38. package/dist/kimiProvider-DbxODebR.mjs +69 -0
  39. package/dist/kimiSetup-NGsoYB5h.mjs +48 -0
  40. package/dist/loopVerify-DALtTk2V.mjs +444 -0
  41. package/dist/machineTools-DygM1jXW.mjs +580 -0
  42. package/dist/model-CUHojegn.mjs +66 -0
  43. package/dist/{notifyCommands-0aZUwKQK.mjs → notifyCommands-CCUE18Q-.mjs} +3 -18
  44. package/dist/package-BrsiNutS.mjs +64 -0
  45. package/dist/pinnedCodex-XW4qvOAe.mjs +11 -0
  46. package/dist/pinnedNono-5ZHb6328.mjs +15 -0
  47. package/dist/{rpc-rAQQ1q8t.mjs → rpc-CBkSkzsI.mjs} +38 -6
  48. package/dist/{rpc-B2Lc2BAB.mjs → rpc-ccY7xvlo.mjs} +33 -22
  49. package/dist/{run-C7QVfyw4.mjs → run-DCq3aEiF.mjs} +17 -9
  50. package/dist/run-DDmeV9K3.mjs +9826 -0
  51. package/dist/sandboxDetect-Cdzsj5TC.mjs +19 -0
  52. package/dist/{scheduler-CzF4lOe_.mjs → scheduler-BkVJ27Ki.mjs} +38 -6
  53. package/dist/securityContext-Cm5UTCuD.mjs +218 -0
  54. package/dist/serveAuth-4M0vwMyj.mjs +460 -0
  55. package/dist/{serveCommands-EIEqdaVu.mjs → serveCommands-CLhkccJM.mjs} +13 -34
  56. package/dist/sharingNotificationSync-qGIQ-3yf.mjs +359 -0
  57. package/dist/{sideband-BoutiRJi.mjs → sideband-68HhGT0i.mjs} +1 -21
  58. package/dist/store-B4E6NzG6.mjs +356 -0
  59. package/dist/store-fi0f-ff1.mjs +184 -0
  60. package/dist/types-57J3Re0n.mjs +17 -0
  61. package/dist/wantsHelp-6bMOeNUz.mjs +5 -0
  62. package/dist/wrapCommand-CdNawSaa.mjs +117 -0
  63. package/package.json +3 -3
  64. package/dist/cli-B24CmIli.mjs +0 -2780
  65. package/dist/package-CTbGYaJG.mjs +0 -64
  66. package/dist/run-CF4kAVPW.mjs +0 -26508
  67. package/dist/sandboxDetect-DNTcbgWD.mjs +0 -12
@@ -1,25 +1,9 @@
1
- import { c as connectToHypha, O as computeCollectionConfigUpdate, P as SYSTEM_COLLECTION_CONFIG } from './run-CF4kAVPW.mjs';
1
+ import { c as connectToHypha } from './hyphaClient-ybivOjZo.mjs';
2
+ import { c as computeCollectionConfigUpdate, a as SYSTEM_COLLECTION_CONFIG } from './sharingNotificationSync-qGIQ-3yf.mjs';
2
3
  import { existsSync, readFileSync } from 'node:fs';
3
4
  import { join } from 'node:path';
4
5
  import os from 'node:os';
5
- import 'os';
6
- import 'fs/promises';
7
- import 'fs';
8
- import 'path';
9
- import 'url';
10
- import 'child_process';
11
- import 'crypto';
12
6
  import 'node:crypto';
13
- import 'node:child_process';
14
- import 'util';
15
- import 'http';
16
- import 'net';
17
- import 'node:events';
18
- import '@agentclientprotocol/sdk';
19
- import 'node:util';
20
- import 'node:readline';
21
- import 'node:fs/promises';
22
- import 'yaml';
23
7
 
24
8
  const SYSTEM_COLLECTIONS = [
25
9
  { id: "public/svamp-user-events", alias: "svamp-user-events", name: "Svamp User Events", description: "Cross-workspace user event inbox (bell notifications)" },
@@ -1,26 +1,9 @@
1
1
  import { existsSync, readFileSync, mkdirSync, writeFileSync, renameSync } from 'node:fs';
2
2
  import { join, dirname } from 'node:path';
3
3
  import os from 'node:os';
4
- import { requireNotSandboxed } from './sandboxDetect-DNTcbgWD.mjs';
5
- import { e as shortId } from './run-CF4kAVPW.mjs';
6
- import 'os';
7
- import 'fs/promises';
8
- import 'fs';
9
- import 'path';
10
- import 'url';
11
- import 'child_process';
12
- import 'crypto';
4
+ import { requireNotSandboxed } from './sandboxDetect-Cdzsj5TC.mjs';
5
+ import { s as shortId } from './friendlyName-1UZcyDhu.mjs';
13
6
  import 'node:crypto';
14
- import 'node:child_process';
15
- import 'util';
16
- import 'http';
17
- import 'net';
18
- import 'node:events';
19
- import '@agentclientprotocol/sdk';
20
- import 'node:util';
21
- import 'node:readline';
22
- import 'node:fs/promises';
23
- import 'yaml';
24
7
 
25
8
  const SVAMP_HOME = process.env.SVAMP_HOME || join(os.homedir(), ".svamp");
26
9
  function getConfigPath(sessionId) {
@@ -96,7 +79,7 @@ async function sessionSetTitle(title) {
96
79
  }
97
80
  async function sessionSetProjectDescription(description) {
98
81
  const dir = process.cwd();
99
- const { projectName, writeProjectInfo, sanitizeDescription, projectInfoPath } = await import('./run-CF4kAVPW.mjs').then(function (n) { return n.aw; });
82
+ const { projectName, writeProjectInfo, sanitizeDescription, projectInfoPath } = await import('./run-DDmeV9K3.mjs').then(function (n) { return n.p; });
100
83
  const desc = sanitizeDescription(description, 240);
101
84
  if (!desc) {
102
85
  console.error("Project description is empty.");
@@ -399,7 +382,7 @@ async function sessionBroadcast(action, args) {
399
382
  console.log(`Broadcast sent: ${action}`);
400
383
  }
401
384
  async function connectToMachineService() {
402
- const { connectAndGetMachine } = await import('./commands-DDuGBSsz.mjs');
385
+ const { connectAndGetMachine } = await import('./commands-B-yczgz_.mjs');
403
386
  return connectAndGetMachine();
404
387
  }
405
388
  function buildInboxMessage(args) {
@@ -482,7 +465,7 @@ async function inboxSend(targetSessionId, opts) {
482
465
  console.error("Message body is required.");
483
466
  process.exit(1);
484
467
  }
485
- const { connectAndResolveSession } = await import('./commands-DDuGBSsz.mjs');
468
+ const { connectAndResolveSession } = await import('./commands-B-yczgz_.mjs');
486
469
  let server;
487
470
  try {
488
471
  const { targetId, messageId } = await inboxSendCore(
@@ -537,7 +520,7 @@ async function inboxReply(messageId, body, opts) {
537
520
  console.error("SVAMP_SESSION_ID not set. This command must be run inside a Svamp session.");
538
521
  process.exit(1);
539
522
  }
540
- const { connectAndResolveSession } = await import('./commands-DDuGBSsz.mjs');
523
+ const { connectAndResolveSession } = await import('./commands-B-yczgz_.mjs');
541
524
  const { server: localServer, machine: localMachine } = await connectToMachineService();
542
525
  let localDisconnected = false;
543
526
  const disconnectLocal = async () => {
@@ -0,0 +1,157 @@
1
+ import os from 'os';
2
+ import { join } from 'path';
3
+ import { g as getSkillsCollection, a as getSkillsServerUrl, b as getSkillsWorkspace } from './instance-CeHz5C8v.mjs';
4
+ import 'fs';
5
+
6
+ const SKILLS_DIR = join(os.homedir(), ".claude", "skills");
7
+ function getSkillsWorkspaceName() {
8
+ return getSkillsWorkspace();
9
+ }
10
+ function getSkillsCollectionName() {
11
+ return getSkillsCollection();
12
+ }
13
+ function getSkillsServer() {
14
+ return getSkillsServerUrl();
15
+ }
16
+ function getArtifactBaseUrl() {
17
+ return `${getSkillsServer()}/${getSkillsWorkspaceName()}/artifacts`;
18
+ }
19
+ async function fetchWithTimeout(url, options = {}, timeoutMs = 3e4) {
20
+ const controller = new AbortController();
21
+ const timer = setTimeout(() => controller.abort(), timeoutMs);
22
+ try {
23
+ return await fetch(url, { ...options, signal: controller.signal });
24
+ } catch (err) {
25
+ if (err.name === "AbortError") throw new Error(`Request timed out after ${timeoutMs}ms: ${url}`);
26
+ throw err;
27
+ } finally {
28
+ clearTimeout(timer);
29
+ }
30
+ }
31
+ function parseFrontmatter(content) {
32
+ const match = content.match(/^---\s*\n([\s\S]*?)\n---/);
33
+ if (!match) return null;
34
+ const yaml = match[1];
35
+ const result = {};
36
+ let currentKey = null;
37
+ let nestedObj = null;
38
+ for (const line of yaml.split("\n")) {
39
+ if (!line.trim() || line.trim().startsWith("#")) continue;
40
+ const indentMatch = line.match(/^(\s*)/);
41
+ const indent = indentMatch ? indentMatch[1].length : 0;
42
+ if (indent > 0 && currentKey && nestedObj !== null) {
43
+ const kvMatch2 = line.trim().match(/^([^:]+):\s*(.*)$/);
44
+ if (kvMatch2) {
45
+ nestedObj[kvMatch2[1].trim()] = kvMatch2[2].trim().replace(/^["']|["']$/g, "");
46
+ }
47
+ continue;
48
+ }
49
+ if (nestedObj !== null && currentKey) {
50
+ result[currentKey] = nestedObj;
51
+ nestedObj = null;
52
+ currentKey = null;
53
+ }
54
+ const kvMatch = line.match(/^([^:]+):\s*(.*)$/);
55
+ if (!kvMatch) continue;
56
+ const key = kvMatch[1].trim();
57
+ const value = kvMatch[2].trim();
58
+ if (!value) {
59
+ currentKey = key;
60
+ nestedObj = {};
61
+ } else {
62
+ result[key] = value.replace(/^["']|["']$/g, "");
63
+ }
64
+ }
65
+ if (nestedObj !== null && currentKey) {
66
+ result[currentKey] = nestedObj;
67
+ }
68
+ if (!result.name || typeof result.name !== "string") return null;
69
+ if (!result.description || typeof result.description !== "string") return null;
70
+ return result;
71
+ }
72
+ async function searchSkills(query) {
73
+ const base = getArtifactBaseUrl();
74
+ const filters = encodeURIComponent(JSON.stringify({ type: "skill" }));
75
+ const url = `${base}/${getSkillsCollectionName()}/children?keywords=${encodeURIComponent(query)}&filters=${filters}&limit=50`;
76
+ const resp = await fetchWithTimeout(url);
77
+ if (!resp.ok) {
78
+ if (resp.status === 404) return [];
79
+ throw new Error(`Search failed: ${resp.status} ${resp.statusText}`);
80
+ }
81
+ const data = await resp.json();
82
+ return normalizeSkillList(Array.isArray(data) ? data : data.items || []);
83
+ }
84
+ async function listAllSkills(offset = 0, limit = 100) {
85
+ const base = getArtifactBaseUrl();
86
+ const filters = encodeURIComponent(JSON.stringify({ type: "skill" }));
87
+ const url = `${base}/${getSkillsCollectionName()}/children?filters=${filters}&offset=${offset}&limit=${limit}`;
88
+ const resp = await fetchWithTimeout(url);
89
+ if (!resp.ok) {
90
+ if (resp.status === 404) return [];
91
+ throw new Error(`List failed: ${resp.status} ${resp.statusText}`);
92
+ }
93
+ const data = await resp.json();
94
+ return normalizeSkillList(Array.isArray(data) ? data : data.items || []);
95
+ }
96
+ async function getSkillInfo(skillAlias) {
97
+ const base = getArtifactBaseUrl();
98
+ const url = `${base}/${skillAlias}`;
99
+ const resp = await fetchWithTimeout(url);
100
+ if (!resp.ok) {
101
+ if (resp.status === 404) return null;
102
+ throw new Error(`Get skill failed: ${resp.status} ${resp.statusText}`);
103
+ }
104
+ const data = await resp.json();
105
+ return normalizeSkill(data);
106
+ }
107
+ async function listSkillFiles(skillAlias, dir = "") {
108
+ const base = getArtifactBaseUrl();
109
+ const pathPart = dir ? `/${dir}/` : "/";
110
+ const url = `${base}/${skillAlias}/files${pathPart}`;
111
+ const resp = await fetchWithTimeout(url);
112
+ if (!resp.ok) {
113
+ throw new Error(`List files failed: ${resp.status} ${resp.statusText}`);
114
+ }
115
+ const data = await resp.json();
116
+ return Array.isArray(data) ? data : data.items || [];
117
+ }
118
+ async function downloadSkillFile(skillAlias, filePath) {
119
+ const base = getArtifactBaseUrl();
120
+ const url = `${base}/${skillAlias}/files/${filePath}`;
121
+ const resp = await fetchWithTimeout(url, { redirect: "follow" }, 6e4);
122
+ if (!resp.ok) {
123
+ throw new Error(`Download failed for ${filePath}: ${resp.status} ${resp.statusText}`);
124
+ }
125
+ return await resp.text();
126
+ }
127
+ async function downloadSkillZip(skillAlias) {
128
+ const base = getArtifactBaseUrl();
129
+ const url = `${base}/${skillAlias}/create-zip-file`;
130
+ const resp = await fetchWithTimeout(url, {}, 12e4);
131
+ if (!resp.ok) {
132
+ throw new Error(`Zip download failed: ${resp.status} ${resp.statusText}`);
133
+ }
134
+ const ab = await resp.arrayBuffer();
135
+ return Buffer.from(ab);
136
+ }
137
+ function normalizeSkillList(items) {
138
+ return items.map(normalizeSkill).filter((s) => s !== null);
139
+ }
140
+ function normalizeSkill(item) {
141
+ if (!item) return null;
142
+ const manifest = item.manifest || {};
143
+ return {
144
+ alias: item.alias || manifest.name || item.id || "unknown",
145
+ name: manifest.name || item.alias || "unknown",
146
+ description: manifest.description || "",
147
+ author: manifest.metadata?.author || manifest.author,
148
+ version: manifest.metadata?.version || manifest.version,
149
+ tags: manifest.tags,
150
+ created_at: item.created_at,
151
+ last_modified: item.last_modified,
152
+ versions: item.versions,
153
+ git_url: item.git_url
154
+ };
155
+ }
156
+
157
+ export { SKILLS_DIR, downloadSkillFile, downloadSkillZip, fetchWithTimeout, getArtifactBaseUrl, getSkillInfo, getSkillsCollectionName, getSkillsServer, getSkillsWorkspaceName, listAllSkills, listSkillFiles, parseFrontmatter, searchSkills };
@@ -1,25 +1,4 @@
1
- import { a4 as resolveModel } from './run-CF4kAVPW.mjs';
2
- import 'os';
3
- import 'fs/promises';
4
- import 'fs';
5
- import 'path';
6
- import 'url';
7
- import 'child_process';
8
- import 'crypto';
9
- import 'node:fs';
10
- import 'node:path';
11
- import 'node:crypto';
12
- import 'node:child_process';
13
- import 'util';
14
- import 'http';
15
- import 'net';
16
- import 'node:os';
17
- import 'node:events';
18
- import '@agentclientprotocol/sdk';
19
- import 'node:util';
20
- import 'node:readline';
21
- import 'node:fs/promises';
22
- import 'yaml';
1
+ import { r as resolveModel } from './model-CUHojegn.mjs';
23
2
 
24
3
  function buildWiseAgentEnvUpdates(action) {
25
4
  switch (action.kind) {
@@ -0,0 +1,143 @@
1
+ import { readFileSync, unlinkSync, writeFileSync, renameSync } from 'fs';
2
+ import { join } from 'path';
3
+
4
+ const TOKEN_LIFETIME_SEC = 180 * 24 * 60 * 60;
5
+ const RENEW_BEFORE_MS = 30 * 24 * 60 * 60 * 1e3;
6
+ const RENEW_CHECK_INTERVAL_MS = 24 * 60 * 60 * 1e3;
7
+ function decodeTokenExpiry(token) {
8
+ if (!token || typeof token !== "string") return void 0;
9
+ const parts = token.split(".");
10
+ if (parts.length !== 3) return void 0;
11
+ try {
12
+ const payload = JSON.parse(Buffer.from(parts[1], "base64").toString("utf-8"));
13
+ const exp = payload?.exp;
14
+ return typeof exp === "number" && Number.isFinite(exp) ? exp * 1e3 : void 0;
15
+ } catch {
16
+ return void 0;
17
+ }
18
+ }
19
+ function shouldRenewToken(args) {
20
+ const { expiresAt, now, renewBeforeMs = RENEW_BEFORE_MS } = args;
21
+ if (expiresAt === void 0) return true;
22
+ return expiresAt - now < renewBeforeMs;
23
+ }
24
+ function isTokenExpired(expiresAt, now) {
25
+ return expiresAt !== void 0 && expiresAt <= now;
26
+ }
27
+ function isAuthExpiryError(err) {
28
+ const text = err instanceof Error ? `${err.message}` : typeof err === "string" ? err : (() => {
29
+ try {
30
+ return JSON.stringify(err);
31
+ } catch {
32
+ return String(err);
33
+ }
34
+ })();
35
+ if (!text) return false;
36
+ return /token has expired|invalid or expired|token is expired|expired token|authentication error/i.test(text);
37
+ }
38
+
39
+ const BOOT_STATUS_FILENAME = "daemon-boot-status.json";
40
+ const AUTH_FIX_HINT = "Fix: svamp login <frontend-url> then: svamp daemon restart";
41
+ function bootStatusPath(svampHome) {
42
+ return join(svampHome, BOOT_STATUS_FILENAME);
43
+ }
44
+ function writeBootStatus(svampHome, status) {
45
+ try {
46
+ const p = bootStatusPath(svampHome);
47
+ const tmp = `${p}.tmp.${process.pid}`;
48
+ writeFileSync(tmp, JSON.stringify(status), "utf-8");
49
+ renameSync(tmp, p);
50
+ } catch {
51
+ }
52
+ }
53
+ function readBootStatus(svampHome) {
54
+ try {
55
+ const raw = readFileSync(bootStatusPath(svampHome), "utf-8");
56
+ const parsed = JSON.parse(raw);
57
+ if (parsed && typeof parsed === "object" && typeof parsed.ok === "boolean" && typeof parsed.at === "number") {
58
+ return parsed;
59
+ }
60
+ return null;
61
+ } catch {
62
+ return null;
63
+ }
64
+ }
65
+ function clearBootStatus(svampHome) {
66
+ try {
67
+ unlinkSync(bootStatusPath(svampHome));
68
+ } catch {
69
+ }
70
+ }
71
+ function classifyBootFailure(err, opts) {
72
+ const agoMs = opts?.preflightExpiredAgoMs;
73
+ if (typeof agoMs === "number" && agoMs >= 0) {
74
+ const h = Math.floor(agoMs / 36e5);
75
+ const when = h >= 1 ? `${h}h ago` : "less than an hour ago";
76
+ return {
77
+ code: "auth-expired",
78
+ message: `HYPHA_TOKEN expired ${when} \u2014 the daemon cannot connect to Hypha.`,
79
+ hint: AUTH_FIX_HINT
80
+ };
81
+ }
82
+ if (isAuthExpiryError(err)) {
83
+ return {
84
+ code: "auth-expired",
85
+ message: "Hypha rejected the HYPHA_TOKEN (expired or invalid) \u2014 the daemon cannot connect.",
86
+ hint: AUTH_FIX_HINT
87
+ };
88
+ }
89
+ const text = err instanceof Error ? err.message : String(err);
90
+ if (/timeout connecting to hypha/i.test(text)) {
91
+ return {
92
+ code: "connect-timeout",
93
+ message: `Timed out connecting to the Hypha server. ${text.replace(/\s+/g, " ").slice(0, 160)}`.trim(),
94
+ hint: "Check network reachability to HYPHA_SERVER_URL, then: svamp daemon restart"
95
+ };
96
+ }
97
+ return {
98
+ code: "connect-failed",
99
+ message: `Failed to connect to Hypha: ${text.replace(/\s+/g, " ").slice(0, 200)}`.trim(),
100
+ hint: "Check the boot log for details, then: svamp daemon restart"
101
+ };
102
+ }
103
+ function shouldStopForAuthExpiry(bootStatus, childStartedAt) {
104
+ if (!bootStatus || bootStatus.ok) return false;
105
+ if (bootStatus.code !== "auth-expired") return false;
106
+ return typeof bootStatus.at === "number" && bootStatus.at >= childStartedAt;
107
+ }
108
+ function describeSupervisorState(args) {
109
+ const { bootStatus, daemonState, now, bootStatusMaxAgeMs = 15 * 60 * 1e3 } = args;
110
+ if (bootStatus && bootStatus.ok === false && now - bootStatus.at <= bootStatusMaxAgeMs) {
111
+ return {
112
+ kind: "wedged",
113
+ code: bootStatus.code || "connect-failed",
114
+ message: bootStatus.message || "The daemon failed to connect to Hypha.",
115
+ hint: bootStatus.hint || AUTH_FIX_HINT
116
+ };
117
+ }
118
+ if (daemonState && daemonState.hyphaConnected === false) {
119
+ const reason = daemonState.hyphaDisconnectReason || "";
120
+ const isAuth = /auth:|expired|invalid/i.test(reason);
121
+ return {
122
+ kind: "wedged",
123
+ code: isAuth ? "auth-expired" : "disconnected",
124
+ message: `The supervisor is running but the daemon is DISCONNECTED from Hypha${reason ? ` (${reason})` : ""} \u2014 it is offline in the frontend.`,
125
+ hint: isAuth ? AUTH_FIX_HINT : "Reconnect with: svamp daemon restart"
126
+ };
127
+ }
128
+ return { kind: "healthy" };
129
+ }
130
+
131
+ var bootStatus = /*#__PURE__*/Object.freeze({
132
+ __proto__: null,
133
+ AUTH_FIX_HINT: AUTH_FIX_HINT,
134
+ BOOT_STATUS_FILENAME: BOOT_STATUS_FILENAME,
135
+ classifyBootFailure: classifyBootFailure,
136
+ clearBootStatus: clearBootStatus,
137
+ describeSupervisorState: describeSupervisorState,
138
+ readBootStatus: readBootStatus,
139
+ shouldStopForAuthExpiry: shouldStopForAuthExpiry,
140
+ writeBootStatus: writeBootStatus
141
+ });
142
+
143
+ export { RENEW_CHECK_INTERVAL_MS as R, TOKEN_LIFETIME_SEC as T, clearBootStatus as a, isAuthExpiryError as b, classifyBootFailure as c, decodeTokenExpiry as d, bootStatus as e, isTokenExpired as i, shouldRenewToken as s, writeBootStatus as w };