svamp-cli 0.2.258 → 0.2.259
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/{agentCommands-CQ89BZon.mjs → agentCommands-w72BRYhk.mjs} +6 -9
- package/dist/{auth-CaFsKYbx.mjs → auth-CLFNmaXL.mjs} +2 -5
- package/dist/cli.mjs +156 -69
- package/dist/{commands-DrfYv705.mjs → commands-BPxSEwAc.mjs} +3 -6
- package/dist/{commands-DutfM3U7.mjs → commands-BpcWHrQ7.mjs} +8 -9
- package/dist/{commands-D8l74hsL.mjs → commands-BtXxn3tI.mjs} +2 -5
- package/dist/{commands-B6eGMF5H.mjs → commands-CXiGBP6w.mjs} +2 -5
- package/dist/{commands--X8f4eSr.mjs → commands-D3jsQ9Sj.mjs} +8 -16
- package/dist/{commands-BgX0W0uK.mjs → commands-DVEsNZUB.mjs} +2 -5
- package/dist/{commands-Dd8xEIf0.mjs → commands-bQxTpr-M.mjs} +2 -5
- package/dist/{fleet-UvQnIWT1.mjs → fleet-BC9JHEWF.mjs} +3 -6
- package/dist/{frpc-IXxyfgPn.mjs → frpc-BCOnJSAM.mjs} +11 -10
- package/dist/{headlessCli-BK7WSS3D.mjs → headlessCli-fagwmUja.mjs} +3 -6
- package/dist/index.mjs +2 -5
- package/dist/{package-BdZX5mDv.mjs → package-Dn7kNPhz.mjs} +2 -2
- package/dist/{pinnedClaudeCode-DuLXaoGP.mjs → pinnedClaudeCode-B9O-hKxm.mjs} +1 -1
- package/dist/{rpc-CyACkgY1.mjs → rpc-D-1o_gWF.mjs} +2 -5
- package/dist/{rpc-D7DB3XCH.mjs → rpc-Dko-Fkk6.mjs} +2 -5
- package/dist/{run-C1ufZjIW.mjs → run-BWBtm0gY.mjs} +1 -5
- package/dist/{run-C1Unk4Zx.mjs → run-CT8Leg3-.mjs} +729 -425
- package/dist/{scheduler-7wve0Fy3.mjs → scheduler-CN8jChyQ.mjs} +2 -5
- package/dist/{serveCommands-iQJJLsMJ.mjs → serveCommands-sWtLnJRW.mjs} +5 -5
- package/dist/{serveManager-BszV0oIl.mjs → serveManager-BuXk1_SH.mjs} +122 -7
- package/dist/{sideband-DMPZ-ZoR.mjs → sideband-ByYvGtj3.mjs} +2 -5
- package/dist/{staticFileServer-FCEOLIYH.mjs → staticFileServer-CbYnj2bH.mjs} +21 -5
- package/package.json +2 -2
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { n as resolveProjectRoot, H as listWorkflows, I as isWorkflowEnabled, J as workflowCrons, C as runWorkflow, K as cronMatches } from './run-
|
|
1
|
+
import { n as resolveProjectRoot, H as listWorkflows, I as isWorkflowEnabled, J as workflowCrons, C as runWorkflow, K as cronMatches } from './run-CT8Leg3-.mjs';
|
|
2
2
|
import 'os';
|
|
3
3
|
import 'fs/promises';
|
|
4
4
|
import 'fs';
|
|
@@ -14,10 +14,7 @@ import 'node:path';
|
|
|
14
14
|
import 'node:events';
|
|
15
15
|
import 'node:os';
|
|
16
16
|
import '@agentclientprotocol/sdk';
|
|
17
|
-
import '
|
|
18
|
-
import '@modelcontextprotocol/sdk/client/stdio.js';
|
|
19
|
-
import '@modelcontextprotocol/sdk/types.js';
|
|
20
|
-
import 'zod';
|
|
17
|
+
import 'node:readline';
|
|
21
18
|
import 'node:fs/promises';
|
|
22
19
|
import 'node:util';
|
|
23
20
|
import 'yaml';
|
|
@@ -54,7 +54,7 @@ async function handleServeCommand() {
|
|
|
54
54
|
}
|
|
55
55
|
}
|
|
56
56
|
async function serveAdd(args, machineId) {
|
|
57
|
-
const { connectAndGetMachine } = await import('./commands-
|
|
57
|
+
const { connectAndGetMachine } = await import('./commands-BtXxn3tI.mjs');
|
|
58
58
|
const pos = positionalArgs(args);
|
|
59
59
|
const name = pos[0];
|
|
60
60
|
if (!name) {
|
|
@@ -93,7 +93,7 @@ async function serveAdd(args, machineId) {
|
|
|
93
93
|
}
|
|
94
94
|
}
|
|
95
95
|
async function serveApply(args, machineId) {
|
|
96
|
-
const { connectAndGetMachine } = await import('./commands-
|
|
96
|
+
const { connectAndGetMachine } = await import('./commands-BtXxn3tI.mjs');
|
|
97
97
|
const fs = await import('fs');
|
|
98
98
|
const yaml = await import('yaml');
|
|
99
99
|
const file = positionalArgs(args)[0];
|
|
@@ -182,7 +182,7 @@ async function serveApply(args, machineId) {
|
|
|
182
182
|
}
|
|
183
183
|
}
|
|
184
184
|
async function serveRemove(args, machineId) {
|
|
185
|
-
const { connectAndGetMachine } = await import('./commands-
|
|
185
|
+
const { connectAndGetMachine } = await import('./commands-BtXxn3tI.mjs');
|
|
186
186
|
const pos = positionalArgs(args);
|
|
187
187
|
const name = pos[0];
|
|
188
188
|
if (!name) {
|
|
@@ -202,7 +202,7 @@ async function serveRemove(args, machineId) {
|
|
|
202
202
|
}
|
|
203
203
|
}
|
|
204
204
|
async function serveList(args, machineId) {
|
|
205
|
-
const { connectAndGetMachine } = await import('./commands-
|
|
205
|
+
const { connectAndGetMachine } = await import('./commands-BtXxn3tI.mjs');
|
|
206
206
|
const all = hasFlag(args, "--all", "-a");
|
|
207
207
|
const json = hasFlag(args, "--json");
|
|
208
208
|
const sessionId = getFlag(args, "--session");
|
|
@@ -235,7 +235,7 @@ async function serveList(args, machineId) {
|
|
|
235
235
|
}
|
|
236
236
|
}
|
|
237
237
|
async function serveInfo(machineId) {
|
|
238
|
-
const { connectAndGetMachine } = await import('./commands-
|
|
238
|
+
const { connectAndGetMachine } = await import('./commands-BtXxn3tI.mjs');
|
|
239
239
|
const { machine, server } = await connectAndGetMachine(machineId);
|
|
240
240
|
try {
|
|
241
241
|
const info = await machine.serveInfo();
|
|
@@ -4,8 +4,8 @@ import * as fs from 'fs';
|
|
|
4
4
|
import * as http from 'http';
|
|
5
5
|
import * as net from 'net';
|
|
6
6
|
import * as path from 'path';
|
|
7
|
-
import { serveStaticMount } from './staticFileServer-
|
|
8
|
-
import { l as getHyphaServerUrl, S as ServeAuth, m as hasCookieToken } from './run-
|
|
7
|
+
import { serveStaticMount } from './staticFileServer-CbYnj2bH.mjs';
|
|
8
|
+
import { l as getHyphaServerUrl, S as ServeAuth, m as hasCookieToken } from './run-CT8Leg3-.mjs';
|
|
9
9
|
import 'os';
|
|
10
10
|
import 'fs/promises';
|
|
11
11
|
import 'url';
|
|
@@ -17,10 +17,7 @@ import 'node:path';
|
|
|
17
17
|
import 'node:events';
|
|
18
18
|
import 'node:os';
|
|
19
19
|
import '@agentclientprotocol/sdk';
|
|
20
|
-
import '
|
|
21
|
-
import '@modelcontextprotocol/sdk/client/stdio.js';
|
|
22
|
-
import '@modelcontextprotocol/sdk/types.js';
|
|
23
|
-
import 'zod';
|
|
20
|
+
import 'node:readline';
|
|
24
21
|
import 'node:fs/promises';
|
|
25
22
|
import 'node:util';
|
|
26
23
|
import 'yaml';
|
|
@@ -597,6 +594,21 @@ a{color:#0969da;text-decoration:none;font-weight:500}a:hover{text-decoration:und
|
|
|
597
594
|
const base = path.resolve(mount.directory);
|
|
598
595
|
const fp = path.resolve(path.join(base, basePath));
|
|
599
596
|
if (fp !== base && !fp.startsWith(base + path.sep)) return null;
|
|
597
|
+
try {
|
|
598
|
+
const realRoot = fs.realpathSync(base);
|
|
599
|
+
let ancestor = fp;
|
|
600
|
+
while (!fs.existsSync(ancestor) && path.dirname(ancestor) !== ancestor) {
|
|
601
|
+
ancestor = path.dirname(ancestor);
|
|
602
|
+
}
|
|
603
|
+
const realAncestor = fs.realpathSync(ancestor);
|
|
604
|
+
if (realAncestor !== realRoot && !realAncestor.startsWith(realRoot + path.sep)) return null;
|
|
605
|
+
if (fs.existsSync(fp) && fs.lstatSync(fp).isSymbolicLink()) {
|
|
606
|
+
const realTarget = fs.realpathSync(fp);
|
|
607
|
+
if (realTarget !== realRoot && !realTarget.startsWith(realRoot + path.sep)) return null;
|
|
608
|
+
}
|
|
609
|
+
} catch {
|
|
610
|
+
return null;
|
|
611
|
+
}
|
|
600
612
|
return fp;
|
|
601
613
|
};
|
|
602
614
|
if ((req.method === "PUT" || req.method === "DELETE") && mount && mount.directory) {
|
|
@@ -667,6 +679,14 @@ a{color:#0969da;text-decoration:none;font-weight:500}a:hover{text-decoration:und
|
|
|
667
679
|
res.end(`Backend error: ${err.message}`);
|
|
668
680
|
}
|
|
669
681
|
});
|
|
682
|
+
const abortUpstream = () => {
|
|
683
|
+
if (!proxyReq.destroyed) proxyReq.destroy();
|
|
684
|
+
};
|
|
685
|
+
req.on("aborted", abortUpstream);
|
|
686
|
+
res.on("close", () => {
|
|
687
|
+
if (!res.writableFinished) abortUpstream();
|
|
688
|
+
});
|
|
689
|
+
proxyReq.setTimeout(12e4, abortUpstream);
|
|
670
690
|
req.pipe(proxyReq);
|
|
671
691
|
return;
|
|
672
692
|
}
|
|
@@ -688,6 +708,101 @@ a{color:#0969da;text-decoration:none;font-weight:500}a:hover{text-decoration:und
|
|
|
688
708
|
res.end("Not found");
|
|
689
709
|
}
|
|
690
710
|
});
|
|
711
|
+
server.on("upgrade", (req, clientSocket, head) => {
|
|
712
|
+
const deny = (code, reason) => {
|
|
713
|
+
try {
|
|
714
|
+
clientSocket.write(`HTTP/1.1 ${code} ${reason}\r
|
|
715
|
+
Connection: close\r
|
|
716
|
+
\r
|
|
717
|
+
`);
|
|
718
|
+
} catch {
|
|
719
|
+
}
|
|
720
|
+
try {
|
|
721
|
+
clientSocket.destroy();
|
|
722
|
+
} catch {
|
|
723
|
+
}
|
|
724
|
+
};
|
|
725
|
+
void (async () => {
|
|
726
|
+
try {
|
|
727
|
+
const url = new URL(req.url || "/", `http://127.0.0.1:${this.port}`);
|
|
728
|
+
const incomingHost = (req.headers.host || "").split(":")[0].toLowerCase();
|
|
729
|
+
const hostMount = this.hostToMount.get(incomingHost);
|
|
730
|
+
let mountName;
|
|
731
|
+
let mountResolvedByHost = false;
|
|
732
|
+
if (hostMount && this.mounts.has(hostMount)) {
|
|
733
|
+
mountName = hostMount;
|
|
734
|
+
mountResolvedByHost = true;
|
|
735
|
+
} else {
|
|
736
|
+
mountName = url.pathname.split("/").filter(Boolean)[0];
|
|
737
|
+
}
|
|
738
|
+
const mount = mountName ? this.mounts.get(mountName) : void 0;
|
|
739
|
+
if (!mount || !mount.process) {
|
|
740
|
+
deny(404, "Not Found");
|
|
741
|
+
return;
|
|
742
|
+
}
|
|
743
|
+
if (mount.access !== "public" && mount.access !== "link") {
|
|
744
|
+
if (mount.access === "owner" && !mount.ownerEmail) {
|
|
745
|
+
deny(403, "Forbidden");
|
|
746
|
+
return;
|
|
747
|
+
}
|
|
748
|
+
const userEmail = this.auth ? await this.auth.authenticate(req).catch(() => null) : null;
|
|
749
|
+
const allowed = userEmail && this.auth ? this.auth.isAuthorized(userEmail, mount.access, mount.ownerEmail) : false;
|
|
750
|
+
if (!allowed) {
|
|
751
|
+
deny(userEmail ? 403 : 401, userEmail ? "Forbidden" : "Unauthorized");
|
|
752
|
+
return;
|
|
753
|
+
}
|
|
754
|
+
}
|
|
755
|
+
const cfg = mount.process;
|
|
756
|
+
if (cfg.wakeOnRequest || !this.managedProcs.has(mount.name)) {
|
|
757
|
+
try {
|
|
758
|
+
await this.ensureManagedRunning(mount.name);
|
|
759
|
+
} catch {
|
|
760
|
+
deny(503, "Backend Not Ready");
|
|
761
|
+
return;
|
|
762
|
+
}
|
|
763
|
+
}
|
|
764
|
+
const handle = this.managedProcs.get(mount.name);
|
|
765
|
+
if (handle) handle.lastRequestAt = Date.now();
|
|
766
|
+
const targetPath = mountResolvedByHost ? req.url || "/" : (url.pathname.slice(`/${mountName}`.length) || "/") + (url.search || "");
|
|
767
|
+
const upstream = net.connect(cfg.port, "127.0.0.1", () => {
|
|
768
|
+
const lines = [`${req.method} ${targetPath} HTTP/1.1`];
|
|
769
|
+
for (let i = 0; i < req.rawHeaders.length; i += 2) {
|
|
770
|
+
lines.push(`${req.rawHeaders[i]}: ${req.rawHeaders[i + 1]}`);
|
|
771
|
+
}
|
|
772
|
+
upstream.write(lines.join("\r\n") + "\r\n\r\n");
|
|
773
|
+
if (head && head.length) upstream.write(head);
|
|
774
|
+
upstream.pipe(clientSocket);
|
|
775
|
+
clientSocket.pipe(upstream);
|
|
776
|
+
});
|
|
777
|
+
const teardown = () => {
|
|
778
|
+
try {
|
|
779
|
+
upstream.destroy();
|
|
780
|
+
} catch {
|
|
781
|
+
}
|
|
782
|
+
try {
|
|
783
|
+
clientSocket.destroy();
|
|
784
|
+
} catch {
|
|
785
|
+
}
|
|
786
|
+
};
|
|
787
|
+
upstream.on("error", teardown);
|
|
788
|
+
clientSocket.on("error", teardown);
|
|
789
|
+
upstream.on("close", () => {
|
|
790
|
+
try {
|
|
791
|
+
clientSocket.destroy();
|
|
792
|
+
} catch {
|
|
793
|
+
}
|
|
794
|
+
});
|
|
795
|
+
clientSocket.on("close", () => {
|
|
796
|
+
try {
|
|
797
|
+
upstream.destroy();
|
|
798
|
+
} catch {
|
|
799
|
+
}
|
|
800
|
+
});
|
|
801
|
+
} catch {
|
|
802
|
+
deny(500, "Internal Server Error");
|
|
803
|
+
}
|
|
804
|
+
})();
|
|
805
|
+
});
|
|
691
806
|
this.proxyServer = server;
|
|
692
807
|
server.listen(this.port, "127.0.0.1", () => resolve());
|
|
693
808
|
server.on("error", reject);
|
|
@@ -739,7 +854,7 @@ a{color:#0969da;text-decoration:none;font-weight:500}a:hover{text-decoration:und
|
|
|
739
854
|
const mount = this.mounts.get(mountName);
|
|
740
855
|
const subdomainOverride = mount?.access === "link" && mount.linkToken ? /* @__PURE__ */ new Map([[this.port, buildLinkSubdomain(subdomainSafe, mount.linkToken)]]) : void 0;
|
|
741
856
|
try {
|
|
742
|
-
const { FrpcTunnel } = await import('./frpc-
|
|
857
|
+
const { FrpcTunnel } = await import('./frpc-BCOnJSAM.mjs');
|
|
743
858
|
let tunnel;
|
|
744
859
|
tunnel = new FrpcTunnel({
|
|
745
860
|
name: tunnelName,
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { R as READ_ONLY_TOOLS, N as loadMachineContext, O as buildMachineInstructions, P as machineToolsForRole, Q as buildMachineTools } from './run-
|
|
1
|
+
import { R as READ_ONLY_TOOLS, N as loadMachineContext, O as buildMachineInstructions, P as machineToolsForRole, Q as buildMachineTools } from './run-CT8Leg3-.mjs';
|
|
2
2
|
import 'node:child_process';
|
|
3
3
|
import 'os';
|
|
4
4
|
import 'fs/promises';
|
|
@@ -14,10 +14,7 @@ import 'node:path';
|
|
|
14
14
|
import 'node:events';
|
|
15
15
|
import 'node:os';
|
|
16
16
|
import '@agentclientprotocol/sdk';
|
|
17
|
-
import '
|
|
18
|
-
import '@modelcontextprotocol/sdk/client/stdio.js';
|
|
19
|
-
import '@modelcontextprotocol/sdk/types.js';
|
|
20
|
-
import 'zod';
|
|
17
|
+
import 'node:readline';
|
|
21
18
|
import 'node:fs/promises';
|
|
22
19
|
import 'node:util';
|
|
23
20
|
import 'yaml';
|
|
@@ -54,6 +54,16 @@ function containedPath(rootDir, relPath) {
|
|
|
54
54
|
if (fp !== base && !fp.startsWith(base + path.sep)) return null;
|
|
55
55
|
return fp;
|
|
56
56
|
}
|
|
57
|
+
function realContainedPath(rootDir, candidate) {
|
|
58
|
+
try {
|
|
59
|
+
const realRoot = fs.realpathSync(path.resolve(rootDir));
|
|
60
|
+
const real = fs.realpathSync(candidate);
|
|
61
|
+
if (real === realRoot || real.startsWith(realRoot + path.sep)) return real;
|
|
62
|
+
return null;
|
|
63
|
+
} catch {
|
|
64
|
+
return null;
|
|
65
|
+
}
|
|
66
|
+
}
|
|
57
67
|
function safeDecode(p) {
|
|
58
68
|
try {
|
|
59
69
|
return decodeURIComponent(p);
|
|
@@ -125,12 +135,18 @@ function serveStaticMount(req, res, opts) {
|
|
|
125
135
|
sendFile(req, res, rootDir, rootStat);
|
|
126
136
|
return;
|
|
127
137
|
}
|
|
128
|
-
const
|
|
129
|
-
if (!
|
|
138
|
+
const lexTarget = containedPath(rootDir, relPath.replace(/^\/+/, ""));
|
|
139
|
+
if (!lexTarget) {
|
|
130
140
|
res.writeHead(403, { ...CORS, "Content-Type": "text/plain" });
|
|
131
141
|
res.end("Forbidden");
|
|
132
142
|
return;
|
|
133
143
|
}
|
|
144
|
+
const target = realContainedPath(rootDir, lexTarget);
|
|
145
|
+
if (!target) {
|
|
146
|
+
res.writeHead(404, { ...CORS, "Content-Type": "text/plain" });
|
|
147
|
+
res.end("Not Found");
|
|
148
|
+
return;
|
|
149
|
+
}
|
|
134
150
|
let st;
|
|
135
151
|
try {
|
|
136
152
|
st = fs.statSync(target);
|
|
@@ -146,8 +162,8 @@ function serveStaticMount(req, res, opts) {
|
|
|
146
162
|
res.end();
|
|
147
163
|
return;
|
|
148
164
|
}
|
|
149
|
-
const indexPath = path.join(target, "index.html");
|
|
150
|
-
if (
|
|
165
|
+
const indexPath = realContainedPath(rootDir, path.join(target, "index.html"));
|
|
166
|
+
if (indexPath && fs.statSync(indexPath).isFile()) {
|
|
151
167
|
sendFile(req, res, indexPath, fs.statSync(indexPath));
|
|
152
168
|
return;
|
|
153
169
|
}
|
|
@@ -236,4 +252,4 @@ function pipeStream(stream, res) {
|
|
|
236
252
|
stream.pipe(res);
|
|
237
253
|
}
|
|
238
254
|
|
|
239
|
-
export { containedPath, contentTypeFor, directoryListingHtml, parseRange, serveStaticMount };
|
|
255
|
+
export { containedPath, contentTypeFor, directoryListingHtml, parseRange, realContainedPath, serveStaticMount };
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "svamp-cli",
|
|
3
|
-
"version": "0.2.
|
|
3
|
+
"version": "0.2.259",
|
|
4
4
|
"description": "Svamp CLI — AI workspace daemon on Hypha Cloud",
|
|
5
5
|
"author": "Amun AI AB",
|
|
6
6
|
"license": "SEE LICENSE IN LICENSE",
|
|
@@ -20,7 +20,7 @@
|
|
|
20
20
|
"scripts": {
|
|
21
21
|
"build": "rm -rf dist bin/skills bin/commands && mkdir -p bin/skills && cp -r ../../skills/artifact bin/skills/artifact && cp -r ../../skills/crew bin/skills/crew && cp -r ../../commands bin/commands && tsc --noEmit && pkgroll",
|
|
22
22
|
"typecheck": "tsc --noEmit",
|
|
23
|
-
"test": "npx tsx test/test-context-window.mjs && npx tsx test/test-ratelimit-retry.mjs && npx tsx test/test-instance-config.mjs && npx tsx test/test-authorize.mjs && npx tsx test/test-normalize-allowed-user.mjs && npx tsx test/test-share-url.mjs && npx tsx test/test-update-sharing-normalization.mjs && npx tsx test/test-sharing-notify-sync.mjs && npx tsx test/test-staged-homes-sweep.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-isolation-decision.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-claude-auth.mjs && npx tsx test/test-btw-proxy-env.mjs && npx tsx test/test-output-formatters.mjs && npx tsx test/test-inbox-guard.mjs && npx tsx test/test-auto-topic.mjs && npx tsx test/test-project-info.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-
|
|
23
|
+
"test": "npx tsx test/test-context-window.mjs && npx tsx test/test-ratelimit-retry.mjs && npx tsx test/test-instance-config.mjs && npx tsx test/test-authorize.mjs && npx tsx test/test-normalize-allowed-user.mjs && npx tsx test/test-share-url.mjs && npx tsx test/test-update-sharing-normalization.mjs && npx tsx test/test-sharing-notify-sync.mjs && npx tsx test/test-staged-homes-sweep.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-isolation-decision.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-claude-auth.mjs && npx tsx test/test-btw-proxy-env.mjs && npx tsx test/test-output-formatters.mjs && npx tsx test/test-inbox-guard.mjs && npx tsx test/test-auto-topic.mjs && npx tsx test/test-project-info.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-app-server.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-session-send-query.mjs && npx tsx test/test-skills.mjs && npx tsx test/test-agent-grouping.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-supervisor-lock.mjs && node test/test-supervisor-restart.mjs && npx tsx test/test-clear-detection.mjs && npx tsx test/test-session-consolidation.mjs && npx tsx test/test-inbox-store.mjs && npx tsx test/test-inbox.mjs && npx tsx test/test-inbox-cross-machine.mjs && npx tsx test/test-issue-store.mjs && npx tsx test/test-issue-close-gate.mjs && npx tsx test/test-loop-verify.mjs && npx tsx test/test-issue-rpc.mjs && npx tsx test/test-issue-pause.mjs && npx tsx test/test-workflow-store.mjs && npx tsx test/test-workflow-rpc.mjs && npx tsx test/test-workflow-scheduler.mjs && npx tsx test/test-cron.mjs && npx tsx test/test-workflow-runs.mjs && npx tsx test/test-workflow-idle.mjs && npx tsx test/test-serve-link-subdomain.mjs && npx tsx test/test-short-id.mjs && npx tsx test/test-transcript-edit.mjs && npx tsx test/test-edit-history.mjs && npx tsx test/test-friendly-name.mjs && npx tsx test/test-session-rpc-dispatch.mjs && npx tsx test/test-sandbox-cli.mjs && npx tsx test/test-serve-manager.mjs && npx tsx test/test-serve-ws-upgrade.mjs && npx tsx test/test-serve-auth.mjs && npx tsx test/test-static-file-server.mjs && npx tsx test/test-serve-stability.mjs && npx tsx test/test-frpc-e2e.mjs --unit-only && npx tsx test/test-frpc-status.mjs && node test/pinnedClaudeCode.test.mjs && node test/fleet.test.mjs && npx tsx test/test-session-file.mjs && npx tsx test/test-channel-rpc.mjs && npx tsx test/test-wise-agent.mjs && npx tsx test/test-channel-agent.mjs && npx tsx test/test-channels-service.mjs && npx tsx test/test-hotreload-seam.mjs && npx tsx test/test-hot-reload.mjs && npx tsx test/test-hot-reload-live.mjs && npx tsx test/test-session-core.mjs && npx tsx test/test-channel-async-reply.mjs && npx tsx test/test-outbox-reload.mjs && npx tsx test/test-channel-binding.mjs && npx tsx test/test-channel-identity.mjs && npx tsx test/test-shared-session-identity.mjs && npx tsx test/test-wise-agent-auth.mjs && npx tsx test/test-channel-http.mjs && npx tsx test/test-channel-upload.mjs && npx tsx test/test-wise-voice.mjs && npx tsx test/test-wise-headless.mjs && npx tsx test/test-wise-machine.mjs && npx tsx test/test-crew-merge.mjs && npx tsx test/test-crew-verdict-routing.mjs && npx tsx test/test-crew-standalone.mjs && npx tsx test/test-session-links.mjs && npx tsx test/test-issue-loop-pause-guard.mjs && npx tsx test/test-artifact-guard.mjs && npx tsx test/test-graceful-restart.mjs",
|
|
24
24
|
"test:hypha": "node --no-warnings test/test-hypha-service.mjs",
|
|
25
25
|
"dev": "tsx src/cli.ts",
|
|
26
26
|
"dev:daemon": "tsx src/cli.ts daemon start-sync",
|