svamp-cli 0.2.7 → 0.2.9

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.
@@ -148,7 +148,7 @@ async function sessionBroadcast(action, args) {
148
148
  console.log(`Broadcast sent: ${action}`);
149
149
  }
150
150
  async function connectToMachineService() {
151
- const { connectAndGetMachine } = await import('./commands-Bh7MIzIQ.mjs');
151
+ const { connectAndGetMachine } = await import('./commands-h1lFrJKK.mjs');
152
152
  return connectAndGetMachine();
153
153
  }
154
154
  async function inboxSend(targetSessionId, opts) {
@@ -165,7 +165,7 @@ async function inboxSend(targetSessionId, opts) {
165
165
  }
166
166
  const { server, machine } = await connectToMachineService();
167
167
  try {
168
- const { resolveSessionId } = await import('./commands-Bh7MIzIQ.mjs');
168
+ const { resolveSessionId } = await import('./commands-h1lFrJKK.mjs');
169
169
  const sessions = await machine.listSessions();
170
170
  const match = resolveSessionId(sessions, targetSessionId);
171
171
  const fullTargetId = match.sessionId;
package/dist/cli.mjs CHANGED
@@ -1,4 +1,4 @@
1
- import { b as stopDaemon, s as startDaemon, d as daemonStatus } from './run-1sh7lcBI.mjs';
1
+ import { b as stopDaemon, s as startDaemon, d as daemonStatus } from './run-IDo93bqK.mjs';
2
2
  import 'os';
3
3
  import 'fs/promises';
4
4
  import 'fs';
@@ -223,15 +223,24 @@ async function main() {
223
223
  console.error("svamp service: Service commands are not available in sandboxed sessions.");
224
224
  process.exit(1);
225
225
  }
226
- const { handleServiceCommand } = await import('./commands-BYbuedOK.mjs');
226
+ const { handleServiceCommand } = await import('./commands-BJJTEZD4.mjs');
227
227
  await handleServiceCommand();
228
+ } else if (subcommand === "serve") {
229
+ const { isSandboxed: isSandboxedServe } = await import('./sandboxDetect-BWA3zQlA.mjs');
230
+ if (isSandboxedServe()) {
231
+ console.error("svamp serve: Serve commands are not available in sandboxed sessions.");
232
+ process.exit(1);
233
+ }
234
+ const { handleServeCommand } = await import('./serveCommands-BguUrQAM.mjs');
235
+ await handleServeCommand();
236
+ process.exit(0);
228
237
  } else if (subcommand === "process" || subcommand === "proc") {
229
238
  const { isSandboxed: isSandboxedProc } = await import('./sandboxDetect-BWA3zQlA.mjs');
230
239
  if (isSandboxedProc()) {
231
240
  console.error("svamp process: Process commands are not available in sandboxed sessions.");
232
241
  process.exit(1);
233
242
  }
234
- const { processCommand } = await import('./commands-B5yjf3Me.mjs');
243
+ const { processCommand } = await import('./commands-C1xgznG4.mjs');
235
244
  let machineId;
236
245
  const processArgs = args.slice(1);
237
246
  const mIdx = processArgs.findIndex((a) => a === "--machine" || a === "-m");
@@ -249,7 +258,7 @@ async function main() {
249
258
  } else if (!subcommand || subcommand === "start") {
250
259
  await handleInteractiveCommand();
251
260
  } else if (subcommand === "--version" || subcommand === "-v") {
252
- const pkg = await import('./package-rfyKrDIy.mjs').catch(() => ({ default: { version: "unknown" } }));
261
+ const pkg = await import('./package-Bx_FLMjC.mjs').catch(() => ({ default: { version: "unknown" } }));
253
262
  console.log(`svamp version: ${pkg.default.version}`);
254
263
  } else {
255
264
  console.error(`Unknown command: ${subcommand}`);
@@ -258,7 +267,7 @@ async function main() {
258
267
  }
259
268
  }
260
269
  async function handleInteractiveCommand() {
261
- const { runInteractive } = await import('./run-CKmnXg7d.mjs');
270
+ const { runInteractive } = await import('./run-wHgMyNHQ.mjs');
262
271
  const interactiveArgs = subcommand === "start" ? args.slice(1) : args;
263
272
  let directory = process.cwd();
264
273
  let resumeSessionId;
@@ -303,7 +312,7 @@ async function handleAgentCommand() {
303
312
  return;
304
313
  }
305
314
  if (agentArgs[0] === "list") {
306
- const { KNOWN_ACP_AGENTS, KNOWN_MCP_AGENTS: KNOWN_MCP_AGENTS2 } = await import('./run-1sh7lcBI.mjs').then(function (n) { return n.i; });
315
+ const { KNOWN_ACP_AGENTS, KNOWN_MCP_AGENTS: KNOWN_MCP_AGENTS2 } = await import('./run-IDo93bqK.mjs').then(function (n) { return n.i; });
307
316
  console.log("Known agents:");
308
317
  for (const [name, config2] of Object.entries(KNOWN_ACP_AGENTS)) {
309
318
  console.log(` ${name.padEnd(12)} ${config2.command} ${config2.args.join(" ")} (ACP)`);
@@ -315,7 +324,7 @@ async function handleAgentCommand() {
315
324
  console.log('Use "svamp agent -- <command> [args]" for a custom ACP agent.');
316
325
  return;
317
326
  }
318
- const { resolveAcpAgentConfig, KNOWN_MCP_AGENTS } = await import('./run-1sh7lcBI.mjs').then(function (n) { return n.i; });
327
+ const { resolveAcpAgentConfig, KNOWN_MCP_AGENTS } = await import('./run-IDo93bqK.mjs').then(function (n) { return n.i; });
319
328
  let cwd = process.cwd();
320
329
  const filteredArgs = [];
321
330
  for (let i = 0; i < agentArgs.length; i++) {
@@ -339,12 +348,12 @@ async function handleAgentCommand() {
339
348
  console.log(`Starting ${config.agentName} agent in ${cwd}...`);
340
349
  let backend;
341
350
  if (KNOWN_MCP_AGENTS[config.agentName]) {
342
- const { CodexMcpBackend } = await import('./run-1sh7lcBI.mjs').then(function (n) { return n.j; });
351
+ const { CodexMcpBackend } = await import('./run-IDo93bqK.mjs').then(function (n) { return n.j; });
343
352
  backend = new CodexMcpBackend({ cwd, log: logFn });
344
353
  } else {
345
- const { AcpBackend } = await import('./run-1sh7lcBI.mjs').then(function (n) { return n.h; });
346
- const { GeminiTransport } = await import('./run-1sh7lcBI.mjs').then(function (n) { return n.G; });
347
- const { DefaultTransport } = await import('./run-1sh7lcBI.mjs').then(function (n) { return n.D; });
354
+ const { AcpBackend } = await import('./run-IDo93bqK.mjs').then(function (n) { return n.h; });
355
+ const { GeminiTransport } = await import('./run-IDo93bqK.mjs').then(function (n) { return n.G; });
356
+ const { DefaultTransport } = await import('./run-IDo93bqK.mjs').then(function (n) { return n.D; });
348
357
  const transportHandler = config.agentName === "gemini" ? new GeminiTransport() : new DefaultTransport(config.agentName);
349
358
  backend = new AcpBackend({
350
359
  agentName: config.agentName,
@@ -471,7 +480,7 @@ async function handleSessionCommand() {
471
480
  process.exit(1);
472
481
  }
473
482
  }
474
- const { sessionList, sessionSpawn, sessionStop, sessionInfo, sessionMessages, sessionAttach, sessionMachines, sessionSend, sessionWait, sessionShare, sessionRalphStart, sessionRalphCancel, sessionRalphStatus, sessionInboxSend, sessionInboxList, sessionInboxRead, sessionInboxReply, sessionInboxClear } = await import('./commands-Bh7MIzIQ.mjs');
483
+ const { sessionList, sessionSpawn, sessionStop, sessionInfo, sessionMessages, sessionAttach, sessionMachines, sessionSend, sessionWait, sessionShare, sessionRalphStart, sessionRalphCancel, sessionRalphStatus, sessionInboxSend, sessionInboxList, sessionInboxRead, sessionInboxReply, sessionInboxClear } = await import('./commands-h1lFrJKK.mjs');
475
484
  const parseFlagStr = (flag, shortFlag) => {
476
485
  for (let i = 1; i < sessionArgs.length; i++) {
477
486
  if ((sessionArgs[i] === flag || shortFlag) && i + 1 < sessionArgs.length) {
@@ -531,7 +540,7 @@ async function handleSessionCommand() {
531
540
  allowDomain.push(sessionArgs[++i]);
532
541
  }
533
542
  }
534
- const { parseShareArg } = await import('./commands-Bh7MIzIQ.mjs');
543
+ const { parseShareArg } = await import('./commands-h1lFrJKK.mjs');
535
544
  const shareEntries = share.map((s) => parseShareArg(s));
536
545
  await sessionSpawn(agent, dir, targetMachineId, {
537
546
  message,
@@ -617,7 +626,7 @@ async function handleSessionCommand() {
617
626
  console.error("Usage: svamp session approve <session-id> [request-id] [--json]");
618
627
  process.exit(1);
619
628
  }
620
- const { sessionApprove } = await import('./commands-Bh7MIzIQ.mjs');
629
+ const { sessionApprove } = await import('./commands-h1lFrJKK.mjs');
621
630
  const approveReqId = sessionArgs[2] && !sessionArgs[2].startsWith("--") ? sessionArgs[2] : void 0;
622
631
  await sessionApprove(sessionArgs[1], approveReqId, targetMachineId, {
623
632
  json: hasFlag("--json")
@@ -627,7 +636,7 @@ async function handleSessionCommand() {
627
636
  console.error("Usage: svamp session deny <session-id> [request-id] [--json]");
628
637
  process.exit(1);
629
638
  }
630
- const { sessionDeny } = await import('./commands-Bh7MIzIQ.mjs');
639
+ const { sessionDeny } = await import('./commands-h1lFrJKK.mjs');
631
640
  const denyReqId = sessionArgs[2] && !sessionArgs[2].startsWith("--") ? sessionArgs[2] : void 0;
632
641
  await sessionDeny(sessionArgs[1], denyReqId, targetMachineId, {
633
642
  json: hasFlag("--json")
@@ -663,7 +672,7 @@ async function handleSessionCommand() {
663
672
  console.error("Usage: svamp session set-title <title>");
664
673
  process.exit(1);
665
674
  }
666
- const { sessionSetTitle } = await import('./agentCommands-vROerKBL.mjs');
675
+ const { sessionSetTitle } = await import('./agentCommands-CrfvZzCn.mjs');
667
676
  await sessionSetTitle(title);
668
677
  } else if (sessionSubcommand === "set-link") {
669
678
  const url = sessionArgs[1];
@@ -672,7 +681,7 @@ async function handleSessionCommand() {
672
681
  process.exit(1);
673
682
  }
674
683
  const label = sessionArgs[2] && !sessionArgs[2].startsWith("--") ? sessionArgs[2] : void 0;
675
- const { sessionSetLink } = await import('./agentCommands-vROerKBL.mjs');
684
+ const { sessionSetLink } = await import('./agentCommands-CrfvZzCn.mjs');
676
685
  await sessionSetLink(url, label);
677
686
  } else if (sessionSubcommand === "notify") {
678
687
  const message = sessionArgs[1];
@@ -681,7 +690,7 @@ async function handleSessionCommand() {
681
690
  process.exit(1);
682
691
  }
683
692
  const level = parseFlagStr("--level") || "info";
684
- const { sessionNotify } = await import('./agentCommands-vROerKBL.mjs');
693
+ const { sessionNotify } = await import('./agentCommands-CrfvZzCn.mjs');
685
694
  await sessionNotify(message, level);
686
695
  } else if (sessionSubcommand === "broadcast") {
687
696
  const action = sessionArgs[1];
@@ -689,7 +698,7 @@ async function handleSessionCommand() {
689
698
  console.error("Usage: svamp session broadcast <action> [args...]\nActions: open-canvas <url> [label], close-canvas, toast <message>");
690
699
  process.exit(1);
691
700
  }
692
- const { sessionBroadcast } = await import('./agentCommands-vROerKBL.mjs');
701
+ const { sessionBroadcast } = await import('./agentCommands-CrfvZzCn.mjs');
693
702
  await sessionBroadcast(action, sessionArgs.slice(2).filter((a) => !a.startsWith("--")));
694
703
  } else if (sessionSubcommand === "inbox") {
695
704
  const inboxSubcmd = sessionArgs[1];
@@ -700,7 +709,7 @@ async function handleSessionCommand() {
700
709
  process.exit(1);
701
710
  }
702
711
  if (agentSessionId) {
703
- const { inboxSend } = await import('./agentCommands-vROerKBL.mjs');
712
+ const { inboxSend } = await import('./agentCommands-CrfvZzCn.mjs');
704
713
  await inboxSend(sessionArgs[2], {
705
714
  body: sessionArgs[3],
706
715
  subject: parseFlagStr("--subject"),
@@ -715,7 +724,7 @@ async function handleSessionCommand() {
715
724
  }
716
725
  } else if (inboxSubcmd === "list" || inboxSubcmd === "ls") {
717
726
  if (agentSessionId && !sessionArgs[2]) {
718
- const { inboxList } = await import('./agentCommands-vROerKBL.mjs');
727
+ const { inboxList } = await import('./agentCommands-CrfvZzCn.mjs');
719
728
  await inboxList({
720
729
  unread: hasFlag("--unread"),
721
730
  limit: parseFlagInt("--limit"),
@@ -737,7 +746,7 @@ async function handleSessionCommand() {
737
746
  process.exit(1);
738
747
  }
739
748
  if (agentSessionId && !sessionArgs[3]) {
740
- const { inboxList } = await import('./agentCommands-vROerKBL.mjs');
749
+ const { inboxList } = await import('./agentCommands-CrfvZzCn.mjs');
741
750
  await sessionInboxRead(agentSessionId, sessionArgs[2], targetMachineId);
742
751
  } else if (sessionArgs[3]) {
743
752
  await sessionInboxRead(sessionArgs[2], sessionArgs[3], targetMachineId);
@@ -747,7 +756,7 @@ async function handleSessionCommand() {
747
756
  }
748
757
  } else if (inboxSubcmd === "reply") {
749
758
  if (agentSessionId && sessionArgs[2] && sessionArgs[3] && !sessionArgs[4]) {
750
- const { inboxReply } = await import('./agentCommands-vROerKBL.mjs');
759
+ const { inboxReply } = await import('./agentCommands-CrfvZzCn.mjs');
751
760
  await inboxReply(sessionArgs[2], sessionArgs[3]);
752
761
  } else if (sessionArgs[2] && sessionArgs[3] && sessionArgs[4]) {
753
762
  await sessionInboxReply(sessionArgs[2], sessionArgs[3], sessionArgs[4], targetMachineId);
@@ -783,7 +792,7 @@ async function handleMachineCommand() {
783
792
  return;
784
793
  }
785
794
  if (machineSubcommand === "share") {
786
- const { machineShare } = await import('./commands-Bh7MIzIQ.mjs');
795
+ const { machineShare } = await import('./commands-h1lFrJKK.mjs');
787
796
  let machineId;
788
797
  const shareArgs = [];
789
798
  for (let i = 1; i < machineArgs.length; i++) {
@@ -813,7 +822,7 @@ async function handleMachineCommand() {
813
822
  }
814
823
  await machineShare(machineId, { add, remove, list, configPath, showConfig });
815
824
  } else if (machineSubcommand === "exec") {
816
- const { machineExec } = await import('./commands-Bh7MIzIQ.mjs');
825
+ const { machineExec } = await import('./commands-h1lFrJKK.mjs');
817
826
  let machineId;
818
827
  let cwd;
819
828
  const cmdParts = [];
@@ -833,7 +842,7 @@ async function handleMachineCommand() {
833
842
  }
834
843
  await machineExec(machineId, command, cwd);
835
844
  } else if (machineSubcommand === "info") {
836
- const { machineInfo } = await import('./commands-Bh7MIzIQ.mjs');
845
+ const { machineInfo } = await import('./commands-h1lFrJKK.mjs');
837
846
  let machineId;
838
847
  for (let i = 1; i < machineArgs.length; i++) {
839
848
  if ((machineArgs[i] === "--machine" || machineArgs[i] === "-m") && i + 1 < machineArgs.length) {
@@ -853,10 +862,10 @@ async function handleMachineCommand() {
853
862
  level = machineArgs[++i];
854
863
  }
855
864
  }
856
- const { machineNotify } = await import('./agentCommands-vROerKBL.mjs');
865
+ const { machineNotify } = await import('./agentCommands-CrfvZzCn.mjs');
857
866
  await machineNotify(message, level);
858
867
  } else if (machineSubcommand === "ls") {
859
- const { machineLs } = await import('./commands-Bh7MIzIQ.mjs');
868
+ const { machineLs } = await import('./commands-h1lFrJKK.mjs');
860
869
  let machineId;
861
870
  let showHidden = false;
862
871
  let path;
@@ -1256,6 +1265,13 @@ Commands:
1256
1265
  svamp session approve/deny <id> Approve or deny pending permission requests
1257
1266
  svamp session --help Show ALL session commands and detailed options
1258
1267
 
1268
+ File serving:
1269
+ svamp serve <name> [directory] Serve a directory via the shared file server
1270
+ svamp serve remove <name> Remove a served mount
1271
+ svamp serve list [--all] List served mounts
1272
+ svamp serve info Show server status and URL
1273
+ svamp serve --help Show all serve commands
1274
+
1259
1275
  Other:
1260
1276
  svamp machine --help Machine sharing & security contexts
1261
1277
  svamp skills --help Skills marketplace (find, install, publish)
@@ -320,7 +320,7 @@ async function serviceServe(args) {
320
320
  if (subdomain) validateSubdomain(subdomain);
321
321
  const healthInterval = healthIntervalStr ? parseInt(healthIntervalStr, 10) : void 0;
322
322
  try {
323
- const { startStaticServer } = await import('./staticServer-CWcmMF5V.mjs');
323
+ const { startStaticServer } = await import('./staticServer-_-FoZQpD.mjs');
324
324
  const resolvedDir = require("path").resolve(directory);
325
325
  console.log(`Serving ${resolvedDir}`);
326
326
  const staticServer = await startStaticServer({
@@ -1,11 +1,11 @@
1
1
  import { writeFileSync, readFileSync } from 'fs';
2
2
  import { resolve } from 'path';
3
- import { connectAndGetMachine } from './commands-Bh7MIzIQ.mjs';
3
+ import { connectAndGetMachine } from './commands-h1lFrJKK.mjs';
4
4
  import 'node:fs';
5
5
  import 'node:child_process';
6
6
  import 'node:path';
7
7
  import 'node:os';
8
- import './run-1sh7lcBI.mjs';
8
+ import './run-IDo93bqK.mjs';
9
9
  import 'os';
10
10
  import 'fs/promises';
11
11
  import 'url';
@@ -2,7 +2,7 @@ import { existsSync, readFileSync } from 'node:fs';
2
2
  import { execSync } from 'node:child_process';
3
3
  import { resolve, join } from 'node:path';
4
4
  import os from 'node:os';
5
- import { l as loadSecurityContextConfig, e as resolveSecurityContext, f as buildSecurityContextFromFlags, m as mergeSecurityContexts, c as connectToHypha } from './run-1sh7lcBI.mjs';
5
+ import { l as loadSecurityContextConfig, e as resolveSecurityContext, f as buildSecurityContextFromFlags, m as mergeSecurityContexts, c as connectToHypha } from './run-IDo93bqK.mjs';
6
6
  import 'os';
7
7
  import 'fs/promises';
8
8
  import 'fs';
package/dist/index.mjs CHANGED
@@ -1,4 +1,4 @@
1
- export { c as connectToHypha, d as daemonStatus, g as getHyphaServerUrl, r as registerMachineService, a as registerSessionService, s as startDaemon, b as stopDaemon } from './run-1sh7lcBI.mjs';
1
+ export { c as connectToHypha, d as daemonStatus, g as getHyphaServerUrl, r as registerMachineService, a as registerSessionService, s as startDaemon, b as stopDaemon } from './run-IDo93bqK.mjs';
2
2
  import 'os';
3
3
  import 'fs/promises';
4
4
  import 'fs';
@@ -1,5 +1,5 @@
1
1
  var name = "svamp-cli";
2
- var version = "0.2.7";
2
+ var version = "0.2.9";
3
3
  var description = "Svamp CLI — AI workspace daemon on Hypha Cloud";
4
4
  var author = "Amun AI AB";
5
5
  var license = "SEE LICENSE IN LICENSE";
@@ -19,7 +19,7 @@ var exports$1 = {
19
19
  var scripts = {
20
20
  build: "rm -rf dist && tsc --noEmit && pkgroll",
21
21
  typecheck: "tsc --noEmit",
22
- test: "npx tsx test/test-authorize.mjs && npx tsx test/test-session-helpers.mjs && npx tsx test/test-cli-routing.mjs && npx tsx test/test-security-context.mjs && npx tsx test/test-ralph-loop.mjs && npx tsx test/test-message-helpers.mjs && npx tsx test/test-agent-config.mjs && npx tsx test/test-wrap-command.mjs && npx tsx test/test-credential-staging.mjs && npx tsx test/test-output-formatters.mjs && npx tsx test/test-agent-types.mjs && npx tsx test/test-transport.mjs && npx tsx test/test-session-update-handlers.mjs && npx tsx test/test-session-scanner.mjs && npx tsx test/test-hypha-client.mjs && npx tsx test/test-hook-settings.mjs && npx tsx test/test-session-service-logic.mjs && npx tsx test/test-daemon-persistence.mjs && npx tsx test/test-detect-isolation.mjs && npx tsx test/test-machine-service-logic.mjs && npx tsx test/test-interactive-helpers.mjs && npx tsx test/test-codex-backend.mjs && npx tsx test/test-acp-backend.mjs && npx tsx test/test-acp-bridge.mjs && npx tsx test/test-hook-server.mjs && npx tsx test/test-session-commands.mjs && npx tsx test/test-interactive-console.mjs && npx tsx test/test-session-messages.mjs && npx tsx test/test-skills.mjs && npx tsx test/test-agent-grouping.mjs && npx tsx test/test-ralph-loop-integration.mjs && npx tsx test/test-ralph-loop-modes.mjs && npx tsx test/test-machine-list-directory.mjs && npx tsx test/test-service-commands.mjs && npx tsx test/test-supervisor.mjs && npx tsx test/test-clear-detection.mjs && npx tsx test/test-session-consolidation.mjs && npx tsx test/test-inbox.mjs && npx tsx test/test-session-rpc-dispatch.mjs && npx tsx test/test-sandbox-cli.mjs",
22
+ test: "npx tsx test/test-authorize.mjs && npx tsx test/test-session-helpers.mjs && npx tsx test/test-cli-routing.mjs && npx tsx test/test-security-context.mjs && npx tsx test/test-ralph-loop.mjs && npx tsx test/test-message-helpers.mjs && npx tsx test/test-agent-config.mjs && npx tsx test/test-wrap-command.mjs && npx tsx test/test-credential-staging.mjs && npx tsx test/test-output-formatters.mjs && npx tsx test/test-agent-types.mjs && npx tsx test/test-transport.mjs && npx tsx test/test-session-update-handlers.mjs && npx tsx test/test-session-scanner.mjs && npx tsx test/test-hypha-client.mjs && npx tsx test/test-hook-settings.mjs && npx tsx test/test-session-service-logic.mjs && npx tsx test/test-daemon-persistence.mjs && npx tsx test/test-detect-isolation.mjs && npx tsx test/test-machine-service-logic.mjs && npx tsx test/test-interactive-helpers.mjs && npx tsx test/test-codex-backend.mjs && npx tsx test/test-acp-backend.mjs && npx tsx test/test-acp-bridge.mjs && npx tsx test/test-hook-server.mjs && npx tsx test/test-session-commands.mjs && npx tsx test/test-interactive-console.mjs && npx tsx test/test-session-messages.mjs && npx tsx test/test-skills.mjs && npx tsx test/test-agent-grouping.mjs && npx tsx test/test-ralph-loop-integration.mjs && npx tsx test/test-ralph-loop-modes.mjs && npx tsx test/test-machine-list-directory.mjs && npx tsx test/test-service-commands.mjs && npx tsx test/test-supervisor.mjs && npx tsx test/test-clear-detection.mjs && npx tsx test/test-session-consolidation.mjs && npx tsx test/test-inbox.mjs && npx tsx test/test-session-rpc-dispatch.mjs && npx tsx test/test-sandbox-cli.mjs && npx tsx test/test-serve-manager.mjs",
23
23
  "test:hypha": "node --no-warnings test/test-hypha-service.mjs",
24
24
  dev: "tsx src/cli.ts",
25
25
  "dev:daemon": "tsx src/cli.ts daemon start-sync",