svamp-cli 0.2.86 → 0.2.89

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/cli.mjs CHANGED
@@ -1,4 +1,5 @@
1
- import { s as startDaemon, b as stopDaemon, d as daemonStatus } from './run-rWXfNd7e.mjs';
1
+ import { e as clearStopMarker, f as stopMarkerExists, s as startDaemon, b as stopDaemon, d as daemonStatus } from './run-C4i9N-F6.mjs';
2
+ import { ensureSupervisorViaServiceManager, LAUNCHD_LABEL } from './serviceManager-hlOVxkhW.mjs';
2
3
  import 'os';
3
4
  import 'fs/promises';
4
5
  import 'fs';
@@ -11,6 +12,7 @@ import 'util';
11
12
  import 'node:crypto';
12
13
  import 'node:path';
13
14
  import 'node:os';
15
+ import 'node:vm';
14
16
  import 'node:child_process';
15
17
  import '@agentclientprotocol/sdk';
16
18
  import '@modelcontextprotocol/sdk/client/index.js';
@@ -32,7 +34,7 @@ const subcommand = args[0];
32
34
  let daemonSubcommand = args[1];
33
35
  async function main() {
34
36
  try {
35
- const { getLoadedConfig } = await import('./run-rWXfNd7e.mjs').then(function (n) { return n.L; });
37
+ const { getLoadedConfig } = await import('./run-C4i9N-F6.mjs').then(function (n) { return n.O; });
36
38
  getLoadedConfig();
37
39
  } catch {
38
40
  }
@@ -49,7 +51,7 @@ async function main() {
49
51
  console.error(`svamp daemon restart: ${err.message || err}`);
50
52
  process.exit(1);
51
53
  }
52
- const { restartDaemon } = await import('./run-rWXfNd7e.mjs').then(function (n) { return n.N; });
54
+ const { restartDaemon } = await import('./run-C4i9N-F6.mjs').then(function (n) { return n.Q; });
53
55
  await restartDaemon();
54
56
  process.exit(0);
55
57
  }
@@ -61,35 +63,58 @@ async function main() {
61
63
  console.error(`svamp daemon start: ${err.message || err}`);
62
64
  process.exit(1);
63
65
  }
66
+ clearStopMarker();
64
67
  const { spawn } = await import('child_process');
65
- const { existsSync, mkdirSync, openSync, closeSync, statSync } = await import('fs');
68
+ const { existsSync, mkdirSync, openSync, closeSync, statSync, readFileSync } = await import('fs');
66
69
  const { join } = await import('path');
67
70
  const os = await import('os');
68
71
  const svampHome = process.env.SVAMP_HOME || join(os.homedir(), ".svamp");
69
72
  const logsDir = join(svampHome, "logs");
70
73
  mkdirSync(logsDir, { recursive: true });
71
- const bootLogPath = join(logsDir, "daemon-boot.log");
72
- const bootFd = openSync(bootLogPath, "a");
73
- const extraArgs = [];
74
- if (args.includes("--no-auto-continue")) extraArgs.push("--no-auto-continue");
75
- const child = spawn(process.execPath, [
76
- "--no-warnings",
77
- "--no-deprecation",
78
- ...process.argv.slice(1, 2),
79
- // the script path
80
- "daemon",
81
- "start-supervised",
82
- ...extraArgs
83
- ], {
84
- detached: true,
85
- stdio: ["ignore", bootFd, bootFd],
86
- env: process.env
87
- });
74
+ const supervisorPidFile = join(svampHome, "supervisor.pid");
75
+ let supervisorAlive = false;
88
76
  try {
89
- closeSync(bootFd);
77
+ if (existsSync(supervisorPidFile)) {
78
+ const pid = parseInt(readFileSync(supervisorPidFile, "utf-8").trim(), 10);
79
+ if (pid && !isNaN(pid)) {
80
+ try {
81
+ process.kill(pid, 0);
82
+ supervisorAlive = true;
83
+ } catch {
84
+ }
85
+ }
86
+ }
90
87
  } catch {
91
88
  }
92
- child.unref();
89
+ if (supervisorAlive) {
90
+ console.log("Daemon already running");
91
+ process.exit(0);
92
+ }
93
+ const startedViaService = await ensureSupervisorViaServiceManager();
94
+ const bootLogPath = join(logsDir, "daemon-boot.log");
95
+ if (!startedViaService) {
96
+ const bootFd = openSync(bootLogPath, "a");
97
+ const extraArgs = [];
98
+ if (args.includes("--no-auto-continue")) extraArgs.push("--no-auto-continue");
99
+ const child = spawn(process.execPath, [
100
+ "--no-warnings",
101
+ "--no-deprecation",
102
+ ...process.argv.slice(1, 2),
103
+ // the script path
104
+ "daemon",
105
+ "start-supervised",
106
+ ...extraArgs
107
+ ], {
108
+ detached: true,
109
+ stdio: ["ignore", bootFd, bootFd],
110
+ env: process.env
111
+ });
112
+ try {
113
+ closeSync(bootFd);
114
+ } catch {
115
+ }
116
+ child.unref();
117
+ }
93
118
  const stateFile = join(svampHome, "daemon.state.json");
94
119
  let beforeMtimeMs = -1;
95
120
  try {
@@ -153,14 +178,17 @@ async function main() {
153
178
  console.error(`svamp daemon: another supervisor is already running (PID ${lock.heldBy}).`);
154
179
  process.exit(0);
155
180
  }
156
- try {
157
- const orphans = findOrphanedSyncPids(process.pid);
158
- if (orphans.length > 0) {
159
- await killOrphanedSyncs(orphans, { log, gracePeriodMs: 3e3 });
181
+ if (process.env.SVAMP_SKIP_ORPHAN_SCAN !== "1") {
182
+ try {
183
+ const orphans = findOrphanedSyncPids(process.pid);
184
+ if (orphans.length > 0) {
185
+ await killOrphanedSyncs(orphans, { log, gracePeriodMs: 3e3 });
186
+ }
187
+ } catch (err) {
188
+ log(`Orphan scan failed (non-fatal): ${err?.message || err}`);
160
189
  }
161
- } catch (err) {
162
- log(`Orphan scan failed (non-fatal): ${err?.message || err}`);
163
190
  }
191
+ clearStopMarker();
164
192
  const extraSyncArgs = [];
165
193
  if (args.includes("--no-auto-continue")) extraSyncArgs.push("--no-auto-continue");
166
194
  const BASE_DELAY_MS = 2e3;
@@ -199,7 +227,16 @@ async function main() {
199
227
  ...extraSyncArgs
200
228
  ], {
201
229
  stdio: ["ignore", "inherit", "inherit"],
202
- env: { ...process.env, SVAMP_SUPERVISED: "1" }
230
+ env: { ...process.env, SVAMP_SUPERVISED: "1" },
231
+ // CRITICAL for launchd KeepAlive: give the child its OWN
232
+ // process group/session (detached). Otherwise, if the
233
+ // supervisor dies abnormally (SIGKILL/OOM) while the child
234
+ // is alive, the child — still in the supervisor's process
235
+ // group — keeps launchd's job "active", so KeepAlive never
236
+ // relaunches the supervisor and the daemon stays dead. The
237
+ // orphaned child is then reaped by the new supervisor's
238
+ // orphan scan and its own parent-death watchdog.
239
+ detached: true
203
240
  });
204
241
  currentChild = child;
205
242
  child.on("exit", (code) => resolve(code));
@@ -220,8 +257,8 @@ async function main() {
220
257
  log("Graceful restart: respawning daemon with new binary from disk");
221
258
  continue;
222
259
  }
223
- if (exitCode === 0) {
224
- log("Daemon exited cleanly (exit 0), not restarting");
260
+ if (stopMarkerExists()) {
261
+ log(`Daemon exited (code ${exitCode}) and stop marker present \u2014 intentional stop, not restarting`);
225
262
  break;
226
263
  }
227
264
  if (uptime > BACKOFF_RESET_UPTIME_MS) {
@@ -248,6 +285,12 @@ async function main() {
248
285
  releaseSupervisorLock(supervisorPidFile, process.pid);
249
286
  process.exit(0);
250
287
  } else if (daemonSubcommand === "start-sync") {
288
+ if (process.env.SVAMP_TEST_SYNC_EXIT !== void 0) {
289
+ const code = Number(process.env.SVAMP_TEST_SYNC_EXIT) || 0;
290
+ const lifeMs = Number(process.env.SVAMP_TEST_SYNC_LIFE_MS) || 0;
291
+ await new Promise((r) => setTimeout(r, lifeMs));
292
+ process.exit(code);
293
+ }
251
294
  const noAutoContinue = args.includes("--no-auto-continue");
252
295
  await startDaemon({ noAutoContinue });
253
296
  process.exit(0);
@@ -301,7 +344,7 @@ async function main() {
301
344
  console.error("svamp service: Service commands are not available in sandboxed sessions.");
302
345
  process.exit(1);
303
346
  }
304
- const { handleServiceCommand } = await import('./commands-BkUoyPy-.mjs');
347
+ const { handleServiceCommand } = await import('./commands-25hlQVK5.mjs');
305
348
  await handleServiceCommand();
306
349
  } else if (subcommand === "serve") {
307
350
  const { isSandboxed: isSandboxedServe } = await import('./sandboxDetect-DNTcbgWD.mjs');
@@ -309,7 +352,7 @@ async function main() {
309
352
  console.error("svamp serve: Serve commands are not available in sandboxed sessions.");
310
353
  process.exit(1);
311
354
  }
312
- const { handleServeCommand } = await import('./serveCommands-Cw5hnh0B.mjs');
355
+ const { handleServeCommand } = await import('./serveCommands-B2brwRfz.mjs');
313
356
  await handleServeCommand();
314
357
  process.exit(0);
315
358
  } else if (subcommand === "process" || subcommand === "proc") {
@@ -318,7 +361,7 @@ async function main() {
318
361
  console.error("svamp process: Process commands are not available in sandboxed sessions.");
319
362
  process.exit(1);
320
363
  }
321
- const { processCommand } = await import('./commands-Db9HLZR5.mjs');
364
+ const { processCommand } = await import('./commands-CVPCcCqU.mjs');
322
365
  let machineId;
323
366
  const processArgs = args.slice(1);
324
367
  const mIdx = processArgs.findIndex((a) => a === "--machine" || a === "-m");
@@ -332,15 +375,18 @@ async function main() {
332
375
  }), machineId);
333
376
  process.exit(0);
334
377
  } else if (subcommand === "routine" || subcommand === "routines") {
335
- const { routineCommand } = await import('./commands-DQaKE9SC.mjs');
378
+ const { routineCommand } = await import('./commands-CA-A0G2y.mjs');
336
379
  await routineCommand(args.slice(1));
337
380
  process.exit(0);
381
+ } else if (subcommand === "wise-agent" || subcommand === "wise") {
382
+ await handleWiseAgentCommand(args.slice(1));
383
+ process.exit(0);
338
384
  } else if (subcommand === "--help" || subcommand === "-h") {
339
385
  printHelp();
340
386
  } else if (!subcommand || subcommand === "start") {
341
387
  await handleInteractiveCommand();
342
388
  } else if (subcommand === "--version" || subcommand === "-v") {
343
- const pkg = await import('./package-C93hgi-7.mjs').catch(() => ({ default: { version: "unknown" } }));
389
+ const pkg = await import('./package-jHkQchZL.mjs').catch(() => ({ default: { version: "unknown" } }));
344
390
  console.log(`svamp version: ${pkg.default.version}`);
345
391
  } else {
346
392
  console.error(`Unknown command: ${subcommand}`);
@@ -349,7 +395,7 @@ async function main() {
349
395
  }
350
396
  }
351
397
  async function handleInteractiveCommand() {
352
- const { runInteractive } = await import('./run-CEs0etJC.mjs');
398
+ const { runInteractive } = await import('./run-DLtX5Yom.mjs');
353
399
  const interactiveArgs = subcommand === "start" ? args.slice(1) : args;
354
400
  let directory = process.cwd();
355
401
  let resumeSessionId;
@@ -394,7 +440,7 @@ async function handleAgentCommand() {
394
440
  return;
395
441
  }
396
442
  if (agentArgs[0] === "list") {
397
- const { KNOWN_ACP_AGENTS, KNOWN_MCP_AGENTS: KNOWN_MCP_AGENTS2 } = await import('./run-rWXfNd7e.mjs').then(function (n) { return n.H; });
443
+ const { KNOWN_ACP_AGENTS, KNOWN_MCP_AGENTS: KNOWN_MCP_AGENTS2 } = await import('./run-C4i9N-F6.mjs').then(function (n) { return n.K; });
398
444
  console.log("Known agents:");
399
445
  for (const [name, config2] of Object.entries(KNOWN_ACP_AGENTS)) {
400
446
  console.log(` ${name.padEnd(12)} ${config2.command} ${config2.args.join(" ")} (ACP)`);
@@ -406,7 +452,7 @@ async function handleAgentCommand() {
406
452
  console.log('Use "svamp agent -- <command> [args]" for a custom ACP agent.');
407
453
  return;
408
454
  }
409
- const { resolveAcpAgentConfig, KNOWN_MCP_AGENTS } = await import('./run-rWXfNd7e.mjs').then(function (n) { return n.H; });
455
+ const { resolveAcpAgentConfig, KNOWN_MCP_AGENTS } = await import('./run-C4i9N-F6.mjs').then(function (n) { return n.K; });
410
456
  let cwd = process.cwd();
411
457
  const filteredArgs = [];
412
458
  for (let i = 0; i < agentArgs.length; i++) {
@@ -430,12 +476,12 @@ async function handleAgentCommand() {
430
476
  console.log(`Starting ${config.agentName} agent in ${cwd}...`);
431
477
  let backend;
432
478
  if (KNOWN_MCP_AGENTS[config.agentName]) {
433
- const { CodexMcpBackend } = await import('./run-rWXfNd7e.mjs').then(function (n) { return n.I; });
479
+ const { CodexMcpBackend } = await import('./run-C4i9N-F6.mjs').then(function (n) { return n.L; });
434
480
  backend = new CodexMcpBackend({ cwd, log: logFn });
435
481
  } else {
436
- const { AcpBackend } = await import('./run-rWXfNd7e.mjs').then(function (n) { return n.G; });
437
- const { GeminiTransport } = await import('./run-rWXfNd7e.mjs').then(function (n) { return n.J; });
438
- const { DefaultTransport } = await import('./run-rWXfNd7e.mjs').then(function (n) { return n.F; });
482
+ const { AcpBackend } = await import('./run-C4i9N-F6.mjs').then(function (n) { return n.J; });
483
+ const { GeminiTransport } = await import('./run-C4i9N-F6.mjs').then(function (n) { return n.M; });
484
+ const { DefaultTransport } = await import('./run-C4i9N-F6.mjs').then(function (n) { return n.I; });
439
485
  const transportHandler = config.agentName === "gemini" ? new GeminiTransport() : new DefaultTransport(config.agentName);
440
486
  backend = new AcpBackend({
441
487
  agentName: config.agentName,
@@ -562,7 +608,7 @@ async function handleSessionCommand() {
562
608
  process.exit(1);
563
609
  }
564
610
  }
565
- const { sessionList, sessionSpawn, sessionArchive, sessionResume, sessionDelete, sessionInfo, sessionMessages, sessionAttach, sessionMachines, sessionSend, sessionWait, sessionShare, sessionRalphStart, sessionRalphCancel, sessionRalphStatus, sessionInboxSend, sessionInboxList, sessionInboxRead, sessionInboxReply, sessionInboxClear } = await import('./commands-Dj7Be8dw.mjs');
611
+ const { sessionList, sessionWhoami, sessionSpawn, sessionArchive, sessionResume, sessionDelete, sessionInfo, sessionMessages, sessionAttach, sessionMachines, sessionSend, sessionWait, sessionShare, sessionRalphStart, sessionRalphCancel, sessionRalphStatus, sessionInboxSend, sessionInboxList, sessionInboxRead, sessionInboxReply, sessionInboxClear } = await import('./commands-DY1ciMPa.mjs');
566
612
  const parseFlagStr = (flag, shortFlag) => {
567
613
  for (let i = 1; i < sessionArgs.length; i++) {
568
614
  if ((sessionArgs[i] === flag || shortFlag) && i + 1 < sessionArgs.length) {
@@ -585,6 +631,8 @@ async function handleSessionCommand() {
585
631
  active: hasFlag("--active"),
586
632
  json: hasFlag("--json")
587
633
  });
634
+ } else if (sessionSubcommand === "whoami" || sessionSubcommand === "env") {
635
+ await sessionWhoami({ json: hasFlag("--json"), all: hasFlag("--all") });
588
636
  } else if (sessionSubcommand === "spawn") {
589
637
  const agent = sessionArgs[1] || "claude";
590
638
  let dir = process.cwd();
@@ -628,7 +676,7 @@ async function handleSessionCommand() {
628
676
  allowDomain.push(sessionArgs[++i]);
629
677
  }
630
678
  }
631
- const { parseShareArg } = await import('./commands-Dj7Be8dw.mjs');
679
+ const { parseShareArg } = await import('./commands-DY1ciMPa.mjs');
632
680
  const shareEntries = share.map((s) => parseShareArg(s));
633
681
  await sessionSpawn(agent, dir, targetMachineId, {
634
682
  message,
@@ -691,7 +739,7 @@ async function handleSessionCommand() {
691
739
  await sessionAttach(sessionArgs[1], targetMachineId);
692
740
  } else if (sessionSubcommand === "send") {
693
741
  if (!sessionArgs[1] || !sessionArgs[2]) {
694
- console.error('Usage: svamp session send <session-id> <message> [--model <id>] [--subject "..."] [--urgency urgent|normal] [--wait] [--response] [--btw] [--require-approval] [--timeout N] [--json]');
742
+ console.error('Usage: svamp session send <session-id> <message> [--model <id>] [--plain] [--subject "..."] [--urgency urgent|normal] [--wait] [--response] [--btw] [--require-approval] [--timeout N] [--json]');
695
743
  console.error(" --model <id> Switch the session model (e.g. claude-opus-4-7, claude-sonnet-4-6) before delivering the message \u2014 forces a respawn.");
696
744
  process.exit(1);
697
745
  }
@@ -704,7 +752,8 @@ async function handleSessionCommand() {
704
752
  json: hasFlag("--json"),
705
753
  subject: parseFlagStr("--subject"),
706
754
  urgency: parseFlagStr("--urgency"),
707
- model: parseFlagStr("--model")
755
+ model: parseFlagStr("--model"),
756
+ plain: hasFlag("--plain")
708
757
  });
709
758
  } else if (sessionSubcommand === "query") {
710
759
  const dir = sessionArgs[1];
@@ -714,7 +763,7 @@ async function handleSessionCommand() {
714
763
  console.error(" Spawns a stateless Claude session in <directory>, sends <prompt>, prints the answer, then deletes the session.");
715
764
  process.exit(1);
716
765
  }
717
- const { sessionQuery } = await import('./commands-Dj7Be8dw.mjs');
766
+ const { sessionQuery } = await import('./commands-DY1ciMPa.mjs');
718
767
  await sessionQuery(dir, prompt, targetMachineId, {
719
768
  timeout: parseFlagInt("--timeout"),
720
769
  json: hasFlag("--json"),
@@ -747,7 +796,7 @@ async function handleSessionCommand() {
747
796
  console.error("Usage: svamp session approve <session-id> [request-id] [--json]");
748
797
  process.exit(1);
749
798
  }
750
- const { sessionApprove } = await import('./commands-Dj7Be8dw.mjs');
799
+ const { sessionApprove } = await import('./commands-DY1ciMPa.mjs');
751
800
  const approveReqId = sessionArgs[2] && !sessionArgs[2].startsWith("--") ? sessionArgs[2] : void 0;
752
801
  await sessionApprove(sessionArgs[1], approveReqId, targetMachineId, {
753
802
  json: hasFlag("--json")
@@ -757,7 +806,7 @@ async function handleSessionCommand() {
757
806
  console.error("Usage: svamp session deny <session-id> [request-id] [--json]");
758
807
  process.exit(1);
759
808
  }
760
- const { sessionDeny } = await import('./commands-Dj7Be8dw.mjs');
809
+ const { sessionDeny } = await import('./commands-DY1ciMPa.mjs');
761
810
  const denyReqId = sessionArgs[2] && !sessionArgs[2].startsWith("--") ? sessionArgs[2] : void 0;
762
811
  await sessionDeny(sessionArgs[1], denyReqId, targetMachineId, {
763
812
  json: hasFlag("--json")
@@ -793,7 +842,7 @@ async function handleSessionCommand() {
793
842
  console.error("Usage: svamp session set-title <title>");
794
843
  process.exit(1);
795
844
  }
796
- const { sessionSetTitle } = await import('./agentCommands-BiIVrk52.mjs');
845
+ const { sessionSetTitle } = await import('./agentCommands-7zzJYIzN.mjs');
797
846
  await sessionSetTitle(title);
798
847
  } else if (sessionSubcommand === "set-link") {
799
848
  const url = sessionArgs[1];
@@ -802,7 +851,7 @@ async function handleSessionCommand() {
802
851
  process.exit(1);
803
852
  }
804
853
  const label = sessionArgs[2] && !sessionArgs[2].startsWith("--") ? sessionArgs[2] : void 0;
805
- const { sessionSetLink } = await import('./agentCommands-BiIVrk52.mjs');
854
+ const { sessionSetLink } = await import('./agentCommands-7zzJYIzN.mjs');
806
855
  await sessionSetLink(url, label);
807
856
  } else if (sessionSubcommand === "notify") {
808
857
  const message = sessionArgs[1];
@@ -811,7 +860,7 @@ async function handleSessionCommand() {
811
860
  process.exit(1);
812
861
  }
813
862
  const level = parseFlagStr("--level") || "info";
814
- const { sessionNotify } = await import('./agentCommands-BiIVrk52.mjs');
863
+ const { sessionNotify } = await import('./agentCommands-7zzJYIzN.mjs');
815
864
  await sessionNotify(message, level);
816
865
  } else if (sessionSubcommand === "broadcast") {
817
866
  const action = sessionArgs[1];
@@ -819,7 +868,7 @@ async function handleSessionCommand() {
819
868
  console.error("Usage: svamp session broadcast <action> [args...]\nActions: open-canvas <url> [label], close-canvas, toast <message>");
820
869
  process.exit(1);
821
870
  }
822
- const { sessionBroadcast } = await import('./agentCommands-BiIVrk52.mjs');
871
+ const { sessionBroadcast } = await import('./agentCommands-7zzJYIzN.mjs');
823
872
  await sessionBroadcast(action, sessionArgs.slice(2).filter((a) => !a.startsWith("--")));
824
873
  } else if (sessionSubcommand === "inbox") {
825
874
  const inboxSubcmd = sessionArgs[1];
@@ -830,7 +879,7 @@ async function handleSessionCommand() {
830
879
  process.exit(1);
831
880
  }
832
881
  if (agentSessionId) {
833
- const { inboxSend } = await import('./agentCommands-BiIVrk52.mjs');
882
+ const { inboxSend } = await import('./agentCommands-7zzJYIzN.mjs');
834
883
  await inboxSend(sessionArgs[2], {
835
884
  body: sessionArgs[3],
836
885
  subject: parseFlagStr("--subject"),
@@ -845,7 +894,7 @@ async function handleSessionCommand() {
845
894
  }
846
895
  } else if (inboxSubcmd === "list" || inboxSubcmd === "ls") {
847
896
  if (agentSessionId && !sessionArgs[2]) {
848
- const { inboxList } = await import('./agentCommands-BiIVrk52.mjs');
897
+ const { inboxList } = await import('./agentCommands-7zzJYIzN.mjs');
849
898
  await inboxList({
850
899
  unread: hasFlag("--unread"),
851
900
  limit: parseFlagInt("--limit"),
@@ -867,7 +916,7 @@ async function handleSessionCommand() {
867
916
  process.exit(1);
868
917
  }
869
918
  if (agentSessionId && !sessionArgs[3]) {
870
- const { inboxList } = await import('./agentCommands-BiIVrk52.mjs');
919
+ const { inboxList } = await import('./agentCommands-7zzJYIzN.mjs');
871
920
  await sessionInboxRead(agentSessionId, sessionArgs[2], targetMachineId);
872
921
  } else if (sessionArgs[3]) {
873
922
  await sessionInboxRead(sessionArgs[2], sessionArgs[3], targetMachineId);
@@ -877,7 +926,7 @@ async function handleSessionCommand() {
877
926
  }
878
927
  } else if (inboxSubcmd === "reply") {
879
928
  if (agentSessionId && sessionArgs[2] && sessionArgs[3] && !sessionArgs[4]) {
880
- const { inboxReply } = await import('./agentCommands-BiIVrk52.mjs');
929
+ const { inboxReply } = await import('./agentCommands-7zzJYIzN.mjs');
881
930
  await inboxReply(sessionArgs[2], sessionArgs[3]);
882
931
  } else if (sessionArgs[2] && sessionArgs[3] && sessionArgs[4]) {
883
932
  await sessionInboxReply(sessionArgs[2], sessionArgs[3], sessionArgs[4], targetMachineId);
@@ -913,7 +962,7 @@ async function handleMachineCommand() {
913
962
  return;
914
963
  }
915
964
  if (machineSubcommand === "share") {
916
- const { machineShare } = await import('./commands-Dj7Be8dw.mjs');
965
+ const { machineShare } = await import('./commands-DY1ciMPa.mjs');
917
966
  let machineId;
918
967
  const shareArgs = [];
919
968
  for (let i = 1; i < machineArgs.length; i++) {
@@ -943,7 +992,7 @@ async function handleMachineCommand() {
943
992
  }
944
993
  await machineShare(machineId, { add, remove, list, configPath, showConfig });
945
994
  } else if (machineSubcommand === "exec") {
946
- const { machineExec } = await import('./commands-Dj7Be8dw.mjs');
995
+ const { machineExec } = await import('./commands-DY1ciMPa.mjs');
947
996
  let machineId;
948
997
  let cwd;
949
998
  const cmdParts = [];
@@ -963,7 +1012,7 @@ async function handleMachineCommand() {
963
1012
  }
964
1013
  await machineExec(machineId, command, cwd);
965
1014
  } else if (machineSubcommand === "info") {
966
- const { machineInfo } = await import('./commands-Dj7Be8dw.mjs');
1015
+ const { machineInfo } = await import('./commands-DY1ciMPa.mjs');
967
1016
  let machineId;
968
1017
  for (let i = 1; i < machineArgs.length; i++) {
969
1018
  if ((machineArgs[i] === "--machine" || machineArgs[i] === "-m") && i + 1 < machineArgs.length) {
@@ -983,10 +1032,10 @@ async function handleMachineCommand() {
983
1032
  level = machineArgs[++i];
984
1033
  }
985
1034
  }
986
- const { machineNotify } = await import('./agentCommands-BiIVrk52.mjs');
1035
+ const { machineNotify } = await import('./agentCommands-7zzJYIzN.mjs');
987
1036
  await machineNotify(message, level);
988
1037
  } else if (machineSubcommand === "ls") {
989
- const { machineLs } = await import('./commands-Dj7Be8dw.mjs');
1038
+ const { machineLs } = await import('./commands-DY1ciMPa.mjs');
990
1039
  let machineId;
991
1040
  let showHidden = false;
992
1041
  let path;
@@ -1044,24 +1093,24 @@ Examples:
1044
1093
  };
1045
1094
  const hasFlag = (name) => fleetArgs.includes(`--${name}`);
1046
1095
  if (sub === "status") {
1047
- const { fleetStatus } = await import('./fleet-DHV-NyW1.mjs');
1096
+ const { fleetStatus } = await import('./fleet-B_HW0j1E.mjs');
1048
1097
  await fleetStatus();
1049
1098
  } else if (sub === "exec") {
1050
1099
  const command = fleetArgs.slice(1).filter((a) => !a.startsWith("--")).join(" ");
1051
- const { fleetExec } = await import('./fleet-DHV-NyW1.mjs');
1100
+ const { fleetExec } = await import('./fleet-B_HW0j1E.mjs');
1052
1101
  await fleetExec(command, { cwd: flag("cwd") });
1053
1102
  } else if (sub === "upgrade-claude") {
1054
- const { fleetUpgradeClaude } = await import('./fleet-DHV-NyW1.mjs');
1103
+ const { fleetUpgradeClaude } = await import('./fleet-B_HW0j1E.mjs');
1055
1104
  await fleetUpgradeClaude({ version: flag("version", "-v") });
1056
1105
  } else if (sub === "upgrade-svamp") {
1057
- const { fleetUpgradeSvamp } = await import('./fleet-DHV-NyW1.mjs');
1106
+ const { fleetUpgradeSvamp } = await import('./fleet-B_HW0j1E.mjs');
1058
1107
  await fleetUpgradeSvamp({ version: flag("version", "-v"), excludeSelf: hasFlag("exclude-self") });
1059
1108
  } else if (sub === "daemon-restart") {
1060
- const { fleetDaemonRestart } = await import('./fleet-DHV-NyW1.mjs');
1109
+ const { fleetDaemonRestart } = await import('./fleet-B_HW0j1E.mjs');
1061
1110
  await fleetDaemonRestart({ graceful: !hasFlag("cleanup") });
1062
1111
  } else if (sub === "push-skill") {
1063
1112
  const name = fleetArgs[1];
1064
- const { fleetPushSkill } = await import('./fleet-DHV-NyW1.mjs');
1113
+ const { fleetPushSkill } = await import('./fleet-B_HW0j1E.mjs');
1065
1114
  await fleetPushSkill(name);
1066
1115
  } else {
1067
1116
  console.error(`Unknown fleet subcommand: ${sub}`);
@@ -1077,7 +1126,7 @@ async function handleSkillsCommand() {
1077
1126
  await printSkillsHelp();
1078
1127
  return;
1079
1128
  }
1080
- const { skillsFind, skillsInstall, skillsList, skillsRemove, skillsPublish } = await import('./commands-BKYz39Hl.mjs');
1129
+ const { skillsFind, skillsInstall, skillsList, skillsRemove, skillsPublish } = await import('./commands-BIsNPVCT.mjs');
1081
1130
  if (skillsSubcommand === "find" || skillsSubcommand === "search") {
1082
1131
  const query = skillsArgs.slice(1).filter((a) => !a.startsWith("--")).join(" ");
1083
1132
  if (!query) {
@@ -1124,7 +1173,7 @@ async function loginToHypha() {
1124
1173
  process.exit(1);
1125
1174
  }
1126
1175
  const anchor = anchorArg.replace(/\/+$/, "");
1127
- const { loadInstanceConfig } = await import('./run-rWXfNd7e.mjs').then(function (n) { return n.L; });
1176
+ const { loadInstanceConfig } = await import('./run-C4i9N-F6.mjs').then(function (n) { return n.O; });
1128
1177
  let cfg = null;
1129
1178
  try {
1130
1179
  cfg = await loadInstanceConfig({ anchor, force: true });
@@ -1235,7 +1284,7 @@ async function logoutFromHypha() {
1235
1284
  } catch {
1236
1285
  }
1237
1286
  try {
1238
- const { clearInstanceConfigCache } = await import('./run-rWXfNd7e.mjs').then(function (n) { return n.L; });
1287
+ const { clearInstanceConfigCache } = await import('./run-C4i9N-F6.mjs').then(function (n) { return n.O; });
1239
1288
  clearInstanceConfigCache();
1240
1289
  } catch {
1241
1290
  }
@@ -1263,7 +1312,6 @@ async function logoutFromHypha() {
1263
1312
  }
1264
1313
  console.log("Logged out successfully");
1265
1314
  }
1266
- const LAUNCHD_LABEL = "io.hypha.svamp.daemon";
1267
1315
  async function installDaemonService() {
1268
1316
  const os = await import('os');
1269
1317
  const { join, dirname } = await import('path');
@@ -1304,6 +1352,8 @@ async function installDaemonService() {
1304
1352
  </array>
1305
1353
  <key>RunAtLoad</key>
1306
1354
  <true/>
1355
+ <key>KeepAlive</key>
1356
+ <true/>
1307
1357
  <key>StandardOutPath</key>
1308
1358
  <string>${logsDir}/daemon-supervised.log</string>
1309
1359
  <key>StandardErrorPath</key>
@@ -1320,11 +1370,20 @@ async function installDaemonService() {
1320
1370
  `;
1321
1371
  fs.writeFileSync(plistPath, plist, "utf-8");
1322
1372
  console.log(`Plist written: ${plistPath}`);
1373
+ const uid = typeof process.getuid === "function" ? process.getuid() : 0;
1374
+ try {
1375
+ execSync(`launchctl bootout gui/${uid}/${LAUNCHD_LABEL} 2>/dev/null`, { stdio: "ignore" });
1376
+ } catch {
1377
+ }
1378
+ execSync(`launchctl bootstrap gui/${uid} "${plistPath}"`);
1379
+ try {
1380
+ execSync(`launchctl enable gui/${uid}/${LAUNCHD_LABEL} 2>/dev/null`, { stdio: "ignore" });
1381
+ } catch {
1382
+ }
1323
1383
  try {
1324
- execSync(`launchctl unload "${plistPath}" 2>/dev/null`, { stdio: "ignore" });
1384
+ execSync(`launchctl kickstart gui/${uid}/${LAUNCHD_LABEL} 2>/dev/null`, { stdio: "ignore" });
1325
1385
  } catch {
1326
1386
  }
1327
- execSync(`launchctl load "${plistPath}"`);
1328
1387
  console.log(`
1329
1388
  Svamp daemon service installed and started!`);
1330
1389
  console.log(` Service: ${LAUNCHD_LABEL}`);
@@ -1355,6 +1414,8 @@ Wants=network-online.target
1355
1414
  ExecStart=${svampBinary} daemon start-supervised
1356
1415
  Environment=PATH=${supervisedPath}
1357
1416
  Environment=SVAMP_HOME=${svampHome}
1417
+ Restart=on-failure
1418
+ RestartSec=3
1358
1419
  StandardOutput=append:${logsDir}/daemon-supervised.log
1359
1420
  StandardError=append:${logsDir}/daemon-supervised.log
1360
1421
 
@@ -1405,9 +1466,14 @@ async function uninstallDaemonService() {
1405
1466
  console.log("Svamp daemon service is not installed.");
1406
1467
  return;
1407
1468
  }
1469
+ const uid = typeof process.getuid === "function" ? process.getuid() : 0;
1408
1470
  try {
1409
- execSync(`launchctl unload "${plistPath}"`, { stdio: "pipe" });
1471
+ execSync(`launchctl bootout gui/${uid}/${LAUNCHD_LABEL} 2>/dev/null`, { stdio: "pipe" });
1410
1472
  } catch {
1473
+ try {
1474
+ execSync(`launchctl unload "${plistPath}" 2>/dev/null`, { stdio: "pipe" });
1475
+ } catch {
1476
+ }
1411
1477
  }
1412
1478
  fs.unlinkSync(plistPath);
1413
1479
  console.log("Svamp daemon service uninstalled (launchd).");
@@ -1470,6 +1536,7 @@ Commands:
1470
1536
  svamp session messages <id> Show message history (--last N, --json, --raw)
1471
1537
  svamp session info <id> Show session status & pending permissions
1472
1538
  svamp session list List sessions
1539
+ svamp session whoami Show your environment: peers on this machine & other machines, how to reach them
1473
1540
  svamp session archive <id> Archive a session (preserves history, resumable later)
1474
1541
  svamp session resume <id> Resume an archived session
1475
1542
  svamp session delete <id> Permanently delete a session (cannot be undone)
@@ -1548,7 +1615,7 @@ async function applyClaudeAuthFlags(argv) {
1548
1615
  "--use-hypha-proxy, --use-claude-login, and --anthropic-base-url/--anthropic-api-key are mutually exclusive"
1549
1616
  );
1550
1617
  }
1551
- const mod = await import('./run-rWXfNd7e.mjs').then(function (n) { return n.K; });
1618
+ const mod = await import('./run-C4i9N-F6.mjs').then(function (n) { return n.N; });
1552
1619
  if (hasHypha) {
1553
1620
  let url;
1554
1621
  const hyphaIdx = argv.indexOf("--use-hypha-proxy");
@@ -1602,7 +1669,7 @@ async function applyDaemonShareFlag(argv) {
1602
1669
  }
1603
1670
  }
1604
1671
  if (collected.length === 0) return;
1605
- const { updateEnvFile } = await import('./run-rWXfNd7e.mjs').then(function (n) { return n.K; });
1672
+ const { updateEnvFile } = await import('./run-C4i9N-F6.mjs').then(function (n) { return n.N; });
1606
1673
  const seen = /* @__PURE__ */ new Set();
1607
1674
  const deduped = collected.filter((e) => {
1608
1675
  const k = e.toLowerCase();
@@ -1613,9 +1680,54 @@ async function applyDaemonShareFlag(argv) {
1613
1680
  updateEnvFile({ [DAEMON_SHARE_ENV_KEY]: deduped.join(",") });
1614
1681
  console.log(`Machine sharing seed updated: ${deduped.join(", ")} (will be added at next daemon start).`);
1615
1682
  }
1683
+ async function handleWiseAgentCommand(rest) {
1684
+ const sub = rest[0];
1685
+ if (sub === "--help" || sub === "-h") {
1686
+ console.log(`Usage: svamp wise-agent auth <command>
1687
+
1688
+ Configure the server-side WISE Agent's fast model (text companion to the deep agent).
1689
+
1690
+ status Show the effective provider / model / base URL / key.
1691
+ use-openai [KEY] Route via OpenAI (default provider). Optional API key.
1692
+ use-hypha-proxy [URL] Route via the Hypha LLM proxy (quota-governed).
1693
+ use-claude-haiku [URL] Fallback: Claude Haiku via the proxy (no OpenAI key).
1694
+ set-model <model> Override the model id (e.g. gpt-5-mini).
1695
+ set-base-url <url> Override the OpenAI-compatible base URL.
1696
+
1697
+ Persisted to ~/.svamp/.env. Run \`svamp daemon restart\` afterwards to apply.`);
1698
+ return;
1699
+ }
1700
+ if (rest[0] && rest[0] !== "auth") {
1701
+ console.error("Usage: svamp wise-agent auth <status|use-openai|use-hypha-proxy|use-claude-haiku|set-model|set-base-url>");
1702
+ process.exitCode = 1;
1703
+ return;
1704
+ }
1705
+ const authArgs = rest.slice(1);
1706
+ const mod = await import('./auth-BRm_dfqc.mjs');
1707
+ let action;
1708
+ try {
1709
+ action = mod.parseWiseAgentAuthArgs(authArgs);
1710
+ } catch (e) {
1711
+ console.error(e?.message || String(e));
1712
+ process.exitCode = 1;
1713
+ return;
1714
+ }
1715
+ if (action) {
1716
+ const { updateEnvFile } = await import('./run-C4i9N-F6.mjs').then(function (n) { return n.N; });
1717
+ const updates = mod.buildWiseAgentEnvUpdates(action);
1718
+ updateEnvFile(updates);
1719
+ for (const [k, v] of Object.entries(updates)) {
1720
+ if (v === void 0) delete process.env[k];
1721
+ else process.env[k] = v;
1722
+ }
1723
+ console.log("Updated ~/.svamp/.env. Run `svamp daemon restart` to apply.");
1724
+ }
1725
+ const status = mod.describeWiseAgentAuth(process.env);
1726
+ console.log(`WISE Agent: provider=${status.provider} model=${status.model} base=${status.baseUrl} key=${status.keyRedacted}`);
1727
+ }
1616
1728
  async function handleDaemonAuthCommand(argv) {
1617
1729
  const sub = (argv[0] || "status").toLowerCase();
1618
- const mod = await import('./run-rWXfNd7e.mjs').then(function (n) { return n.K; });
1730
+ const mod = await import('./run-C4i9N-F6.mjs').then(function (n) { return n.N; });
1619
1731
  if (sub === "--help" || sub === "-h" || sub === "help") {
1620
1732
  console.log(`
1621
1733
  svamp daemon auth \u2014 Configure how Claude subprocesses authenticate
@@ -1724,6 +1836,10 @@ COMMANDS:
1724
1836
  machines List discoverable machines
1725
1837
  info <id> [--json] Show status & pending permissions
1726
1838
 
1839
+ Discover:
1840
+ whoami [--json] Your environment: this session, same-machine peers,
1841
+ same-user sessions on other machines, and how to reach them (alias: env)
1842
+
1727
1843
  Communicate:
1728
1844
  send <id> <message> [--wait] [--response] [--btw] [--require-approval] [--timeout N] [--json]
1729
1845
  Send a message to a running session.
@@ -1908,7 +2024,7 @@ Examples:
1908
2024
  async function printSkillsHelp() {
1909
2025
  let browseUrl = "<HYPHA_SERVER_URL>/<workspace>/artifacts/marketplace (set HYPHA_SERVER_URL)";
1910
2026
  try {
1911
- const { getArtifactBaseUrl, getSkillsCollectionName } = await import('./run-rWXfNd7e.mjs').then(function (n) { return n.M; });
2027
+ const { getArtifactBaseUrl, getSkillsCollectionName } = await import('./run-C4i9N-F6.mjs').then(function (n) { return n.P; });
1912
2028
  browseUrl = `${getArtifactBaseUrl()}/${getSkillsCollectionName()}`;
1913
2029
  } catch {
1914
2030
  }