acpx 0.17.1 → 0.19.0
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/{agent-registry-evUoJINz.js → agent-registry-Ct2yWPW7.js} +18 -18
- package/dist/agent-registry-Ct2yWPW7.js.map +1 -0
- package/dist/agent-registry.d.ts.map +1 -1
- package/dist/agent-registry.js +1 -1
- package/dist/{cli-B2ycKzaO.js → cli-Bmki9cj5.js} +5 -5
- package/dist/{cli-B2ycKzaO.js.map → cli-Bmki9cj5.js.map} +1 -1
- package/dist/cli.js +167 -131
- package/dist/cli.js.map +1 -1
- package/dist/{client-CkbBoSGd.d.ts → client-DzaUKazo.d.ts} +23 -15
- package/dist/client-DzaUKazo.d.ts.map +1 -0
- package/dist/{flows-xGyhmoHO.js → flows--Ewxn_fQ.js} +665 -460
- package/dist/flows--Ewxn_fQ.js.map +1 -0
- package/dist/flows.d.ts +19 -7
- package/dist/flows.d.ts.map +1 -1
- package/dist/flows.js +1 -1
- package/dist/{invocation-options-eZEBh4vd.js → invocation-options-DRzxHZmr.js} +34 -12
- package/dist/invocation-options-DRzxHZmr.js.map +1 -0
- package/dist/{ipc-D2rstexT.js → ipc-fMgj5vrO.js} +818 -302
- package/dist/ipc-fMgj5vrO.js.map +1 -0
- package/dist/{output-D2xL6wdp.js → output-D6kDs8BN.js} +30 -14
- package/dist/output-D6kDs8BN.js.map +1 -0
- package/dist/{queue-owner-runtime-Dgv3e2Tp.js → queue-owner-runtime-CLwjMYNL.js} +1448 -717
- package/dist/queue-owner-runtime-CLwjMYNL.js.map +1 -0
- package/dist/runtime.d.ts +57 -3
- package/dist/runtime.d.ts.map +1 -1
- package/dist/runtime.js +303 -166
- package/dist/runtime.js.map +1 -1
- package/dist/session-options-Dp6mzNSy.d.ts.map +1 -1
- package/dist/{session-watch-CTe9Bnbc.js → session-watch-BfdIo-n4.js} +5 -5
- package/dist/session-watch-BfdIo-n4.js.map +1 -0
- package/dist/{watch-DxuXEc8n.js → watch-DH-zXQH2.js} +2 -2
- package/dist/{watch-DxuXEc8n.js.map → watch-DH-zXQH2.js.map} +1 -1
- package/package.json +1 -1
- package/skills/acpx/SKILL.md +69 -30
- package/dist/agent-registry-evUoJINz.js.map +0 -1
- package/dist/client-CkbBoSGd.d.ts.map +0 -1
- package/dist/flows-xGyhmoHO.js.map +0 -1
- package/dist/invocation-options-eZEBh4vd.js.map +0 -1
- package/dist/ipc-D2rstexT.js.map +0 -1
- package/dist/output-D2xL6wdp.js.map +0 -1
- package/dist/queue-owner-runtime-Dgv3e2Tp.js.map +0 -1
- package/dist/session-watch-CTe9Bnbc.js.map +0 -1
package/dist/cli.js
CHANGED
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
|
-
import { n as getTextErrorRemediationHints, o as __exportAll, t as createOutputFormatter } from "./output-
|
|
3
|
-
import { A as
|
|
4
|
-
import {
|
|
5
|
-
import { O as renderArgvIdentity, i as DEFAULT_AGENT_NAME, l as normalizeAgentName$1, s as listBuiltInAgents } from "./agent-registry-
|
|
6
|
-
import { C as resolvePermissionMode, S as resolveOutputPolicy, T as
|
|
2
|
+
import { n as getTextErrorRemediationHints, o as __exportAll, t as createOutputFormatter } from "./output-D6kDs8BN.js";
|
|
3
|
+
import { A as findGitRepositoryRoot, B as writeSessionRecord, D as textPrompt, G as normalizeAgentSessionId, H as parseSessionRecord, I as normalizeName, M as findSessionByDirectoryWalk, Mt as AcpxOperationalError, Ot as OUTPUT_FORMATS, P as listSessions, Pt as AgentSpawnError, S as PromptInputValidationError, T as parsePromptSource, U as serializeSessionRecordForDisk, _t as writePrivateFile, ft as defaultSessionEventLog, ht as sessionEventLockPath, j as findSession, mt as sessionEventActivePath, u as probeQueueOwnerHealth, w as mergePromptSourceWithText, wt as EXIT_CODES, yt as isProcessAlive } from "./ipc-fMgj5vrO.js";
|
|
4
|
+
import { $ as getAcpxVersion, at as InterruptedError, d as flushPerfMetricsCapture, dt as normalizeOutputError, f as installPerfMetricsCapture, i as runOnce, it as isLegacyZedCodexAcpInvocation, n as runSessionQueueOwner, ot as TimeoutError, rt as listSessionEvents, s as DISCARD_OUTPUT_FORMATTER, u as buildQueueOwnerArgOverride, ut as exitCodeForOutputErrorCode } from "./queue-owner-runtime-CLwjMYNL.js";
|
|
5
|
+
import { O as renderArgvIdentity, i as DEFAULT_AGENT_NAME, l as normalizeAgentName$1, s as listBuiltInAgents } from "./agent-registry-Ct2yWPW7.js";
|
|
6
|
+
import { C as resolvePermissionMode, D as toTimerMilliseconds, E as resolveSessionsListFlags, S as resolveOutputPolicy, T as resolveSessionNameFromFlags, _ as parseSessionName, a as addGlobalFlags, b as resolveAgentInvocation, c as addSessionOption, d as parseDaysOlderThan, f as parseHistoryLimit, g as parsePruneBeforeDate, h as parseOutputFormat$1, i as addExecConfigOption, m as parseNonEmptyValue, n as sessionConnectionOptions, o as addPromptInputOption, p as parseMaxTurns, r as sessionOptionsFromGlobalFlags, s as addSessionNameOption, t as resolvePermissionPolicyFromFlags, u as parseAllowedTools, v as parseTimeoutSeconds, w as resolvePromptFlags, x as resolveGlobalFlags, y as parseTtlSeconds } from "./invocation-options-DRzxHZmr.js";
|
|
7
7
|
import { realpathSync } from "node:fs";
|
|
8
8
|
import { fileURLToPath, pathToFileURL } from "node:url";
|
|
9
9
|
import path from "node:path";
|
|
@@ -402,11 +402,11 @@ let sessionModulePromise;
|
|
|
402
402
|
let outputModulePromise;
|
|
403
403
|
let outputRenderModulePromise;
|
|
404
404
|
function loadSessionModule() {
|
|
405
|
-
sessionModulePromise ??= import("./output-
|
|
405
|
+
sessionModulePromise ??= import("./output-D6kDs8BN.js").then((n) => n.a);
|
|
406
406
|
return sessionModulePromise;
|
|
407
407
|
}
|
|
408
408
|
function loadOutputModule() {
|
|
409
|
-
outputModulePromise ??= import("./output-
|
|
409
|
+
outputModulePromise ??= import("./output-D6kDs8BN.js").then((n) => n.r);
|
|
410
410
|
return outputModulePromise;
|
|
411
411
|
}
|
|
412
412
|
function loadOutputRenderModule() {
|
|
@@ -483,11 +483,12 @@ async function findRoutedSessionOrThrow(agentCommand, agentName, cwd, sessionNam
|
|
|
483
483
|
throw new NoSessionError(`⚠ No acpx session found (searched up to ${walkBoundary}).\nCreate one: ${sessionName ? `acpx ${agentName} sessions new --name ${sessionName}` : `acpx ${agentName} sessions new`}`);
|
|
484
484
|
}
|
|
485
485
|
async function handlePrompt(explicitAgentName, promptParts, flags, command, config) {
|
|
486
|
+
const promptFlags = resolvePromptFlags(flags, command);
|
|
486
487
|
const globalFlags = resolveGlobalFlags(command, config);
|
|
487
488
|
const outputPolicy = resolveRequestedOutputPolicy(globalFlags);
|
|
488
489
|
const permissionMode = resolvePermissionMode(globalFlags, config.defaultPermissions);
|
|
489
490
|
const permissionPolicy = await resolvePermissionPolicyFromFlags(globalFlags);
|
|
490
|
-
const prompt = await readPromptInput(
|
|
491
|
+
const prompt = await readPromptInput(promptFlags.file, promptParts.join(" "), globalFlags.cwd);
|
|
491
492
|
const agent = resolveAgentInvocation(explicitAgentName, globalFlags, config);
|
|
492
493
|
const [{ createOutputFormatter }, { printPromptSessionBanner, printQueuedPromptByFormat }, { sendSession }] = await Promise.all([
|
|
493
494
|
loadOutputModule(),
|
|
@@ -514,7 +515,7 @@ async function handlePrompt(explicitAgentName, promptParts, flags, command, conf
|
|
|
514
515
|
ttlMs: globalFlags.ttl,
|
|
515
516
|
maxQueueDepth: config.queueMaxDepth,
|
|
516
517
|
promptRetries: globalFlags.promptRetries,
|
|
517
|
-
waitForCompletion:
|
|
518
|
+
waitForCompletion: promptFlags.wait,
|
|
518
519
|
sessionOptions: sessionOptionsFromGlobalFlags(globalFlags)
|
|
519
520
|
});
|
|
520
521
|
if ("queued" in result) {
|
|
@@ -525,24 +526,15 @@ async function handlePrompt(explicitAgentName, promptParts, flags, command, conf
|
|
|
525
526
|
if (globalFlags.verbose && result.loadError) process.stderr.write(`[acpx] session reconnect failed, started fresh session: ${result.loadError}\n`);
|
|
526
527
|
}
|
|
527
528
|
async function handleExec(explicitAgentName, promptParts, flags, command, config) {
|
|
528
|
-
if (config.disableExec) {
|
|
529
|
-
if (resolveRequestedOutputPolicy(resolveGlobalFlags(command, config)).format === "json") process.stdout.write(`${JSON.stringify({
|
|
530
|
-
jsonrpc: "2.0",
|
|
531
|
-
error: {
|
|
532
|
-
code: -32603,
|
|
533
|
-
message: "exec subcommand is disabled by configuration (disableExec: true)",
|
|
534
|
-
data: { acpxCode: "EXEC_DISABLED" }
|
|
535
|
-
}
|
|
536
|
-
})}\n`);
|
|
537
|
-
else process.stderr.write("Error: exec subcommand is disabled by configuration (disableExec: true)\n");
|
|
538
|
-
process.exitCode = 1;
|
|
539
|
-
return;
|
|
540
|
-
}
|
|
541
529
|
const globalFlags = resolveGlobalFlags(command, config);
|
|
530
|
+
if (config.disableExec) throw new AcpxOperationalError("exec subcommand is disabled by configuration (disableExec: true)", {
|
|
531
|
+
outputCode: "EXEC_DISABLED",
|
|
532
|
+
origin: "cli"
|
|
533
|
+
});
|
|
542
534
|
const outputPolicy = resolveRequestedOutputPolicy(globalFlags);
|
|
543
535
|
const permissionMode = resolvePermissionMode(globalFlags, config.defaultPermissions);
|
|
544
536
|
const permissionPolicy = await resolvePermissionPolicyFromFlags(globalFlags);
|
|
545
|
-
const prompt = await readPromptInput(flags.file, promptParts.join(" "), globalFlags.cwd);
|
|
537
|
+
const prompt = await readPromptInput(resolvePromptFlags(flags, command).file, promptParts.join(" "), globalFlags.cwd);
|
|
546
538
|
const [{ createOutputFormatter }, { runOnce }] = await Promise.all([loadOutputModule(), loadSessionModule()]);
|
|
547
539
|
const outputFormatter = createOutputFormatter(outputPolicy.format, { suppressReads: outputPolicy.suppressReads });
|
|
548
540
|
const agent = resolveAgentInvocation(explicitAgentName, globalFlags, config);
|
|
@@ -694,17 +686,18 @@ async function tryListAgentSessions(agent, flags, globalFlags, config) {
|
|
|
694
686
|
}
|
|
695
687
|
}
|
|
696
688
|
async function handleSessionsList(explicitAgentName, flags, command, config) {
|
|
689
|
+
const listFlags = resolveSessionsListFlags(flags, command);
|
|
697
690
|
const globalFlags = resolveGlobalFlags(command, config);
|
|
698
691
|
const agent = resolveAgentInvocation(explicitAgentName, globalFlags, config);
|
|
699
|
-
const filterCwd = resolveSessionListFilterCwd(
|
|
700
|
-
if (
|
|
701
|
-
if (
|
|
692
|
+
const filterCwd = resolveSessionListFilterCwd(listFlags, agent.cwd);
|
|
693
|
+
if (listFlags.local) {
|
|
694
|
+
if (listFlags.cursor) throw new InvalidArgumentError("--cursor cannot be combined with --local");
|
|
702
695
|
await printLocalSessionsList(agent.agentCommand, filterCwd, globalFlags.format);
|
|
703
696
|
return;
|
|
704
697
|
}
|
|
705
|
-
const [result, { printAgentSessionsByFormat }] = await Promise.all([tryListAgentSessions(agent,
|
|
698
|
+
const [result, { printAgentSessionsByFormat }] = await Promise.all([tryListAgentSessions(agent, listFlags, globalFlags, config), loadOutputRenderModule()]);
|
|
706
699
|
if (!result || result === "spawn-failed") {
|
|
707
|
-
if (result !== "spawn-failed" && (
|
|
700
|
+
if (result !== "spawn-failed" && (listFlags.cursor || listFlags.filterCwd)) throw new Error(`Agent command "${agent.agentCommand}" does not advertise sessionCapabilities.list; cannot use agent-side session/list filters`);
|
|
708
701
|
await printLocalSessionsList(agent.agentCommand, void 0, globalFlags.format);
|
|
709
702
|
return;
|
|
710
703
|
}
|
|
@@ -880,18 +873,19 @@ async function handleSessionsHistory(explicitAgentName, sessionName, flags, comm
|
|
|
880
873
|
async function handleSessionsWatch(explicitAgentName, flags, command, config) {
|
|
881
874
|
const globalFlags = resolveGlobalFlags(command, config);
|
|
882
875
|
const agent = resolveAgentInvocation(explicitAgentName, globalFlags, config);
|
|
876
|
+
const sessionName = resolveSessionNameFromFlags({ session: flags.name }, command);
|
|
883
877
|
const scope = {
|
|
884
878
|
agentCommand: agent.agentCommand,
|
|
885
879
|
cwd: agent.cwd,
|
|
886
|
-
name:
|
|
880
|
+
name: sessionName,
|
|
887
881
|
readOnly: true
|
|
888
882
|
};
|
|
889
883
|
const record = await findSession(scope) ?? await findSession({
|
|
890
884
|
...scope,
|
|
891
885
|
includeClosed: true
|
|
892
886
|
});
|
|
893
|
-
if (!record) throw new Error(missingScopedSessionMessage(agent,
|
|
894
|
-
const { runSessionWatch } = await import("./session-watch-
|
|
887
|
+
if (!record) throw new Error(missingScopedSessionMessage(agent, sessionName));
|
|
888
|
+
const { runSessionWatch } = await import("./session-watch-BfdIo-n4.js");
|
|
895
889
|
await runSessionWatch(record, {
|
|
896
890
|
cursor: flags.cursor,
|
|
897
891
|
policy: resolveRequestedOutputPolicy(globalFlags)
|
|
@@ -951,6 +945,37 @@ async function handleSessionsPrune(explicitAgentName, flags, command, config) {
|
|
|
951
945
|
}), globalFlags.format);
|
|
952
946
|
}
|
|
953
947
|
//#endregion
|
|
948
|
+
//#region src/cli/compare-args.ts
|
|
949
|
+
function addCompareOptions(command) {
|
|
950
|
+
return command.option("--cwd <dir>", "Target workspace").option("--approve-all", "Auto-approve all permission requests").option("--approve-reads", "Auto-approve read/search requests and prompt for writes").option("--deny-all", "Deny all permission requests").option("--timeout <seconds>", "Per-agent timeout in seconds", parseTimeoutSeconds).option("--format <fmt>", "Output format: text, json, quiet", parseOutputFormat$1).option("--json", "Alias for --format json").option("-f, --file <path>", "Read prompt text from file path (use - for stdin)", (value) => parseNonEmptyValue("Prompt file", value)).option("--prompt-file <path>", "Alias for --file", (value) => parseNonEmptyValue("Prompt file", value));
|
|
951
|
+
}
|
|
952
|
+
const VALUE_FLAGS = new Set(addCompareOptions(new Command()).options.filter((option) => option.required).flatMap((option) => [option.long, option.short].filter((flag) => flag !== void 0)));
|
|
953
|
+
function captureCompareOutputFlag(output, token, nextToken) {
|
|
954
|
+
if (token === "--json") output.json = true;
|
|
955
|
+
else if (token === "--format") output.format = nextToken;
|
|
956
|
+
else if (token.startsWith("--format=")) output.format = token.slice(9);
|
|
957
|
+
}
|
|
958
|
+
function scanCompareArgs(argv) {
|
|
959
|
+
let cwd;
|
|
960
|
+
const output = {};
|
|
961
|
+
for (let index = 0; index < argv.length; index += 1) {
|
|
962
|
+
const token = argv[index];
|
|
963
|
+
if (token === "--") return {
|
|
964
|
+
cwd,
|
|
965
|
+
...output,
|
|
966
|
+
promptTokens: argv.slice(index + 1)
|
|
967
|
+
};
|
|
968
|
+
if (token === "--cwd") cwd = argv[index + 1];
|
|
969
|
+
else if (token.startsWith("--cwd=")) cwd = token.slice(6);
|
|
970
|
+
captureCompareOutputFlag(output, token, argv[index + 1]);
|
|
971
|
+
if (VALUE_FLAGS.has(token)) index += 1;
|
|
972
|
+
}
|
|
973
|
+
return {
|
|
974
|
+
cwd,
|
|
975
|
+
...output
|
|
976
|
+
};
|
|
977
|
+
}
|
|
978
|
+
//#endregion
|
|
954
979
|
//#region src/cli/compare-command.ts
|
|
955
980
|
const DEFAULT_COMPARE_TIMEOUT_MS = 3e5;
|
|
956
981
|
const FINAL_MESSAGE_PREVIEW_CHARS = 200;
|
|
@@ -972,14 +997,15 @@ function truncate(value, maxChars) {
|
|
|
972
997
|
if (value.length <= maxChars) return value;
|
|
973
998
|
return `${value.slice(0, Math.max(0, maxChars - 3))}...`;
|
|
974
999
|
}
|
|
975
|
-
function
|
|
976
|
-
|
|
977
|
-
|
|
978
|
-
|
|
979
|
-
|
|
980
|
-
|
|
981
|
-
|
|
982
|
-
|
|
1000
|
+
function splitCompareArgs(args, filePath, promptTokens) {
|
|
1001
|
+
if (promptTokens !== void 0) {
|
|
1002
|
+
const agents = args.slice(0, args.length - promptTokens.length);
|
|
1003
|
+
if (agents.length === 0) throw new InvalidArgumentError("At least one agent is required");
|
|
1004
|
+
return {
|
|
1005
|
+
agents,
|
|
1006
|
+
promptText: promptTokens.join(" ")
|
|
1007
|
+
};
|
|
1008
|
+
}
|
|
983
1009
|
if (filePath) {
|
|
984
1010
|
if (args.length === 0) throw new InvalidArgumentError("At least one agent is required");
|
|
985
1011
|
return {
|
|
@@ -987,15 +1013,6 @@ function splitCompareArgs(args, filePath, command) {
|
|
|
987
1013
|
promptText: ""
|
|
988
1014
|
};
|
|
989
1015
|
}
|
|
990
|
-
const promptTokens = promptTokensAfterDoubleDash(command);
|
|
991
|
-
if (promptTokens.length > 0) {
|
|
992
|
-
const agents = args.slice(0, -promptTokens.length);
|
|
993
|
-
if (agents.length === 0) throw new InvalidArgumentError("At least one agent is required");
|
|
994
|
-
return {
|
|
995
|
-
agents,
|
|
996
|
-
promptText: promptTokens.join(" ")
|
|
997
|
-
};
|
|
998
|
-
}
|
|
999
1016
|
if (args.length < 2) throw new InvalidArgumentError("Usage: acpx compare <agent>... '<prompt>'");
|
|
1000
1017
|
return {
|
|
1001
1018
|
agents: args.slice(0, -1),
|
|
@@ -1007,12 +1024,7 @@ function captureUsage(update, capture) {
|
|
|
1007
1024
|
capture.usage = {
|
|
1008
1025
|
input_tokens: numberField(source, ["input_tokens", "inputTokens"]) ?? void 0,
|
|
1009
1026
|
output_tokens: numberField(source, ["output_tokens", "outputTokens"]) ?? void 0,
|
|
1010
|
-
total_tokens: numberField(source, [
|
|
1011
|
-
"total_tokens",
|
|
1012
|
-
"totalTokens",
|
|
1013
|
-
"size",
|
|
1014
|
-
"used"
|
|
1015
|
-
]) ?? void 0
|
|
1027
|
+
total_tokens: numberField(source, ["total_tokens", "totalTokens"]) ?? void 0
|
|
1016
1028
|
};
|
|
1017
1029
|
}
|
|
1018
1030
|
function captureSessionUpdate(notification, capture) {
|
|
@@ -1149,22 +1161,53 @@ function updateCompareExitCode(rows) {
|
|
|
1149
1161
|
}
|
|
1150
1162
|
if (rows.some((row) => row.status === "cancelled")) process.exitCode = EXIT_CODES.TIMEOUT;
|
|
1151
1163
|
}
|
|
1164
|
+
async function runCompareAgents(agents, run) {
|
|
1165
|
+
const rows = [];
|
|
1166
|
+
let interrupted = false;
|
|
1167
|
+
const onInterrupt = () => {
|
|
1168
|
+
interrupted = true;
|
|
1169
|
+
};
|
|
1170
|
+
const signals = [
|
|
1171
|
+
"SIGINT",
|
|
1172
|
+
"SIGTERM",
|
|
1173
|
+
"SIGHUP"
|
|
1174
|
+
];
|
|
1175
|
+
for (const signal of signals) process.once(signal, onInterrupt);
|
|
1176
|
+
try {
|
|
1177
|
+
for (const agentName of agents) {
|
|
1178
|
+
if (interrupted) break;
|
|
1179
|
+
const row = await run(agentName);
|
|
1180
|
+
rows.push(interrupted ? {
|
|
1181
|
+
...row,
|
|
1182
|
+
status: "cancelled",
|
|
1183
|
+
error: "Interrupted"
|
|
1184
|
+
} : row);
|
|
1185
|
+
}
|
|
1186
|
+
} finally {
|
|
1187
|
+
for (const signal of signals) process.off(signal, onInterrupt);
|
|
1188
|
+
}
|
|
1189
|
+
return {
|
|
1190
|
+
rows,
|
|
1191
|
+
interrupted
|
|
1192
|
+
};
|
|
1193
|
+
}
|
|
1152
1194
|
function resolvePromptFile(flags) {
|
|
1153
1195
|
if (flags.file && flags.promptFile && flags.file !== flags.promptFile) throw new InvalidArgumentError("Use only one prompt file flag: --file or --prompt-file");
|
|
1154
1196
|
return flags.file ?? flags.promptFile;
|
|
1155
1197
|
}
|
|
1156
1198
|
function registerCompareCommand(program, config) {
|
|
1157
|
-
program.command("compare").description("Run one prompt across multiple agents and summarize the results").argument("<args...>", "Agents followed by prompt text, or agents with --file")
|
|
1199
|
+
addCompareOptions(program.command("compare").description("Run one prompt across multiple agents and summarize the results").argument("<args...>", "Agents followed by prompt text, or agents with --file")).action(async function(args, flags) {
|
|
1158
1200
|
if (config.disableExec) throw new Error("compare subcommand is disabled by configuration (disableExec: true)");
|
|
1159
1201
|
const globalFlags = resolveGlobalFlags(this, config);
|
|
1202
|
+
if (flags.cwd !== void 0) globalFlags.cwd = path.resolve(flags.cwd);
|
|
1160
1203
|
if (globalFlags.agent) throw new InvalidArgumentError("Do not combine compare with --agent; pass agent names");
|
|
1161
|
-
const outputPolicy = resolveOutputPolicy(
|
|
1204
|
+
const outputPolicy = resolveOutputPolicy(globalFlags.format, globalFlags.jsonStrict === true);
|
|
1162
1205
|
const promptFile = resolvePromptFile(flags);
|
|
1163
|
-
const {
|
|
1206
|
+
const { promptTokens } = scanCompareArgs(program.args.slice(1));
|
|
1207
|
+
const { agents, promptText } = splitCompareArgs(args, promptFile, promptTokens);
|
|
1164
1208
|
const prompt = await readPromptInput(promptFile, promptText, globalFlags.cwd, "final argument");
|
|
1165
1209
|
const permissionPolicy = await resolvePermissionPolicyFromFlags(globalFlags);
|
|
1166
|
-
const rows =
|
|
1167
|
-
for (const agentName of agents) rows.push(await runAgentForCompare({
|
|
1210
|
+
const { rows, interrupted } = await runCompareAgents(agents, async (agentName) => await runAgentForCompare({
|
|
1168
1211
|
agentName,
|
|
1169
1212
|
prompt,
|
|
1170
1213
|
config,
|
|
@@ -1172,7 +1215,8 @@ function registerCompareCommand(program, config) {
|
|
|
1172
1215
|
permissionPolicy
|
|
1173
1216
|
}));
|
|
1174
1217
|
printRows(rows, outputPolicy.format);
|
|
1175
|
-
|
|
1218
|
+
if (interrupted) process.exitCode = EXIT_CODES.INTERRUPTED;
|
|
1219
|
+
else updateCompareExitCode(rows);
|
|
1176
1220
|
});
|
|
1177
1221
|
}
|
|
1178
1222
|
//#endregion
|
|
@@ -1185,6 +1229,10 @@ function parseNonEmptyString(value, path) {
|
|
|
1185
1229
|
if (typeof value !== "string" || value.trim().length === 0) throw new Error(`Invalid ${path}: expected non-empty string`);
|
|
1186
1230
|
return value.trim();
|
|
1187
1231
|
}
|
|
1232
|
+
function parseString(value, path) {
|
|
1233
|
+
if (typeof value !== "string") throw new Error(`Invalid ${path}: expected string`);
|
|
1234
|
+
return value;
|
|
1235
|
+
}
|
|
1188
1236
|
function parseNameValuePairs(value, path) {
|
|
1189
1237
|
if (value == null) return [];
|
|
1190
1238
|
if (!Array.isArray(value)) throw new Error(`Invalid ${path}: expected array`);
|
|
@@ -1194,7 +1242,7 @@ function parseNameValuePairs(value, path) {
|
|
|
1194
1242
|
if (!entry) throw new Error(`Invalid ${path}[${index}]: expected object`);
|
|
1195
1243
|
entries.push({
|
|
1196
1244
|
name: parseNonEmptyString(entry.name, `${path}[${index}].name`),
|
|
1197
|
-
value:
|
|
1245
|
+
value: parseString(entry.value, `${path}[${index}].value`)
|
|
1198
1246
|
});
|
|
1199
1247
|
}
|
|
1200
1248
|
return entries;
|
|
@@ -1203,10 +1251,7 @@ function parseArgs(value, path) {
|
|
|
1203
1251
|
if (value == null) return [];
|
|
1204
1252
|
if (!Array.isArray(value)) throw new Error(`Invalid ${path}: expected array`);
|
|
1205
1253
|
const args = [];
|
|
1206
|
-
for (const [index, rawArg] of value.entries()) {
|
|
1207
|
-
if (typeof rawArg !== "string") throw new Error(`Invalid ${path}[${index}]: expected string`);
|
|
1208
|
-
args.push(rawArg);
|
|
1209
|
-
}
|
|
1254
|
+
for (const [index, rawArg] of value.entries()) args.push(parseString(rawArg, `${path}[${index}]`));
|
|
1210
1255
|
return args;
|
|
1211
1256
|
}
|
|
1212
1257
|
function parseMeta(value, path) {
|
|
@@ -1336,9 +1381,7 @@ function parseDefaultAgent(value, sourcePath) {
|
|
|
1336
1381
|
function parseAgents(value, sourcePath) {
|
|
1337
1382
|
if (value == null) return;
|
|
1338
1383
|
if (!isObject(value)) throw new Error(`Invalid config agents in ${sourcePath}: expected object`);
|
|
1339
|
-
|
|
1340
|
-
for (const [name, raw] of Object.entries(value)) parsed[normalizeAgentName$1(name)] = parseAgentEntry(raw, name, sourcePath);
|
|
1341
|
-
return parsed;
|
|
1384
|
+
return Object.fromEntries(Object.entries(value).map(([name, raw]) => [normalizeAgentName$1(name), parseAgentEntry(raw, name, sourcePath)]));
|
|
1342
1385
|
}
|
|
1343
1386
|
function parseAgentEntry(raw, name, sourcePath) {
|
|
1344
1387
|
if (!isObject(raw)) throw new Error(`Invalid config agents.${name} in ${sourcePath}: expected object with command`);
|
|
@@ -1490,8 +1533,7 @@ function resolveMcpServers(projectConfig, projectPath, globalConfig, globalPath,
|
|
|
1490
1533
|
return [];
|
|
1491
1534
|
}
|
|
1492
1535
|
function toConfigDisplay(config) {
|
|
1493
|
-
const agents = {};
|
|
1494
|
-
for (const [name, agent] of Object.entries(config.agents)) agents[name] = agent.argv ? { argv: [...agent.argv] } : { command: agent.command };
|
|
1536
|
+
const agents = Object.fromEntries(Object.entries(config.agents).map(([name, agent]) => [name, agent.argv ? { argv: [...agent.argv] } : { command: agent.command }]));
|
|
1495
1537
|
return {
|
|
1496
1538
|
defaultAgent: config.defaultAgent,
|
|
1497
1539
|
defaultPermissions: config.defaultPermissions,
|
|
@@ -2074,7 +2116,7 @@ function registerAgentCommand(program, agentName, config) {
|
|
|
2074
2116
|
}
|
|
2075
2117
|
function registerFlowCommand(program, config) {
|
|
2076
2118
|
program.command("flow").description("Run multi-step ACP workflows from flow files").command("run").description("Run a flow file").argument("<file>", "Flow module path").option("--input-json <json>", "Flow input as JSON").option("--input-file <path>", "Read flow input JSON from file").option("--default-agent <name>", "Default agent profile for ACP nodes without profile", (value) => parseNonEmptyValue("Default agent", value)).action(async function(file, flags) {
|
|
2077
|
-
const { handleFlowRun } = await import("./cli-
|
|
2119
|
+
const { handleFlowRun } = await import("./cli-Bmki9cj5.js");
|
|
2078
2120
|
await handleFlowRun(file, flags, this, config);
|
|
2079
2121
|
});
|
|
2080
2122
|
}
|
|
@@ -2280,57 +2322,41 @@ function detectAgentToken(argv) {
|
|
|
2280
2322
|
for (let index = 0; index < argv.length; index += 1) {
|
|
2281
2323
|
const token = argv[index];
|
|
2282
2324
|
const step = scanAgentTokenStep(token, hasAgentOverride);
|
|
2283
|
-
if (step.result) return
|
|
2325
|
+
if (step.result) return {
|
|
2326
|
+
...step.result,
|
|
2327
|
+
index
|
|
2328
|
+
};
|
|
2284
2329
|
if (step.hasAgentOverride) hasAgentOverride = true;
|
|
2285
2330
|
index += step.indexDelta;
|
|
2286
2331
|
}
|
|
2287
2332
|
return { hasAgentOverride };
|
|
2288
2333
|
}
|
|
2289
|
-
function
|
|
2334
|
+
function lastTopLevelFlagValue(argv, flag) {
|
|
2335
|
+
let value;
|
|
2290
2336
|
for (let index = 0; index < argv.length; index += 1) {
|
|
2291
2337
|
const token = argv[index];
|
|
2292
2338
|
const scan = classifyTopLevelFlagScan(token);
|
|
2293
2339
|
if (scan.stop) break;
|
|
2294
|
-
|
|
2295
|
-
if (
|
|
2296
|
-
if (isCwdFlagToken(token)) break;
|
|
2340
|
+
if (token === flag) value = argv[index + 1];
|
|
2341
|
+
else if (token.startsWith(`${flag}=`)) value = token.slice(flag.length + 1);
|
|
2297
2342
|
if (scan.skipNext) index += 1;
|
|
2298
2343
|
}
|
|
2299
|
-
return
|
|
2344
|
+
return value;
|
|
2300
2345
|
}
|
|
2301
|
-
function
|
|
2302
|
-
|
|
2303
|
-
|
|
2304
|
-
|
|
2305
|
-
if (
|
|
2346
|
+
function detectInitialCwd(argv) {
|
|
2347
|
+
const command = detectAgentToken(argv);
|
|
2348
|
+
if (command.token === "compare" && command.index !== void 0) {
|
|
2349
|
+
const { cwd } = scanCompareArgs(argv.slice(command.index + 1));
|
|
2350
|
+
if (cwd !== void 0) return path.resolve(cwd);
|
|
2306
2351
|
}
|
|
2352
|
+
return path.resolve(lastTopLevelFlagValue(argv, "--cwd") ?? process.cwd());
|
|
2307
2353
|
}
|
|
2308
|
-
function
|
|
2309
|
-
|
|
2310
|
-
|
|
2311
|
-
path: resolveMcpConfigPath(nextToken, cwd),
|
|
2312
|
-
stop: true
|
|
2313
|
-
};
|
|
2314
|
-
if (token.startsWith("--mcp-config=")) return {
|
|
2315
|
-
path: resolveMcpConfigPath(token.slice(13), cwd),
|
|
2316
|
-
stop: true
|
|
2317
|
-
};
|
|
2318
|
-
return { skipNext: TOP_LEVEL_VERSION_VALUE_FLAGS.has(token) };
|
|
2319
|
-
}
|
|
2320
|
-
function resolveMcpConfigPath(value, cwd) {
|
|
2321
|
-
const trimmed = value?.trim();
|
|
2322
|
-
return trimmed && trimmed !== "--" ? path.resolve(cwd, trimmed) : void 0;
|
|
2323
|
-
}
|
|
2324
|
-
function isCwdFlagToken(token) {
|
|
2325
|
-
return token === "--cwd" || token.startsWith("--cwd=");
|
|
2326
|
-
}
|
|
2327
|
-
function readCwdFlagValue(token, nextToken) {
|
|
2328
|
-
const value = (token === "--cwd" ? nextToken : readInlineFlagValue(token, "--cwd"))?.trim();
|
|
2329
|
-
if (!value || value === "--") return;
|
|
2330
|
-
return value;
|
|
2354
|
+
function detectMcpConfigPath(argv, cwd) {
|
|
2355
|
+
const value = lastTopLevelFlagValue(argv, "--mcp-config");
|
|
2356
|
+
return value ? path.resolve(cwd, value) : void 0;
|
|
2331
2357
|
}
|
|
2332
2358
|
function detectRequestedOutputFormat(argv, fallback) {
|
|
2333
|
-
let detectedFormat
|
|
2359
|
+
let detectedFormat;
|
|
2334
2360
|
for (let index = 0; index < argv.length; index += 1) {
|
|
2335
2361
|
const token = argv[index];
|
|
2336
2362
|
const scan = classifyTopLevelFlagScan(token);
|
|
@@ -2340,7 +2366,14 @@ function detectRequestedOutputFormat(argv, fallback) {
|
|
|
2340
2366
|
if (format) detectedFormat = format;
|
|
2341
2367
|
if (scan.skipNext) index += 1;
|
|
2342
2368
|
}
|
|
2343
|
-
return detectedFormat;
|
|
2369
|
+
return detectCompareOutputFormat(argv, detectedFormat, fallback);
|
|
2370
|
+
}
|
|
2371
|
+
function detectCompareOutputFormat(argv, rootFormat, fallback) {
|
|
2372
|
+
const command = detectAgentToken(argv);
|
|
2373
|
+
if (command.token !== "compare" || command.index === void 0) return rootFormat ?? fallback;
|
|
2374
|
+
const local = scanCompareArgs(argv.slice(command.index + 1));
|
|
2375
|
+
const localFormat = isOutputFormat(local.format) ? local.format : void 0;
|
|
2376
|
+
return local.json ? "json" : rootFormat ?? localFormat ?? fallback;
|
|
2344
2377
|
}
|
|
2345
2378
|
function classifyTopLevelFlagScan(token) {
|
|
2346
2379
|
if (token === "--" || !token.startsWith("-") || token === "-") return {
|
|
@@ -2487,34 +2520,37 @@ async function main(argv = process.argv) {
|
|
|
2487
2520
|
return;
|
|
2488
2521
|
}
|
|
2489
2522
|
await maybeHandleSkillflag(normalizedArgv);
|
|
2490
|
-
const initialCwd = detectInitialCwd(rawArgs);
|
|
2491
|
-
const config = await loadResolvedConfig(initialCwd, { mcpConfigPath: detectMcpConfigPath(rawArgs, initialCwd) });
|
|
2492
2523
|
const requestedJsonStrict = detectJsonStrict(rawArgs);
|
|
2493
|
-
|
|
2494
|
-
|
|
2495
|
-
...resolveOutputPolicy(requestedOutputFormat, requestedJsonStrict),
|
|
2524
|
+
let requestedOutputPolicy = {
|
|
2525
|
+
...resolveOutputPolicy(detectRequestedOutputFormat(rawArgs, "text"), requestedJsonStrict),
|
|
2496
2526
|
suppressReads: rawArgs.some((token) => token === "--suppress-reads")
|
|
2497
2527
|
};
|
|
2498
|
-
const program = createProgram(requestedJsonStrict);
|
|
2499
|
-
addGlobalFlags(program);
|
|
2500
|
-
configurePublicCli({
|
|
2501
|
-
program,
|
|
2502
|
-
argv: rawArgs,
|
|
2503
|
-
config,
|
|
2504
|
-
requestedJsonStrict,
|
|
2505
|
-
topLevelVerbs: TOP_LEVEL_VERBS,
|
|
2506
|
-
listBuiltInAgents,
|
|
2507
|
-
detectAgentToken,
|
|
2508
|
-
registerAgentCommand,
|
|
2509
|
-
registerDefaultCommands,
|
|
2510
|
-
handlePromptAction: async (command, promptParts) => {
|
|
2511
|
-
await handlePrompt(void 0, promptParts, {}, command, config);
|
|
2512
|
-
}
|
|
2513
|
-
});
|
|
2514
|
-
program.exitOverride((error) => {
|
|
2515
|
-
throw error;
|
|
2516
|
-
});
|
|
2517
2528
|
try {
|
|
2529
|
+
const initialCwd = detectInitialCwd(rawArgs);
|
|
2530
|
+
const config = await loadResolvedConfig(initialCwd, { mcpConfigPath: detectMcpConfigPath(rawArgs, initialCwd) });
|
|
2531
|
+
requestedOutputPolicy = {
|
|
2532
|
+
...resolveOutputPolicy(detectRequestedOutputFormat(rawArgs, config.format), requestedJsonStrict),
|
|
2533
|
+
suppressReads: requestedOutputPolicy.suppressReads
|
|
2534
|
+
};
|
|
2535
|
+
const program = createProgram(requestedJsonStrict);
|
|
2536
|
+
addGlobalFlags(program);
|
|
2537
|
+
configurePublicCli({
|
|
2538
|
+
program,
|
|
2539
|
+
argv: rawArgs,
|
|
2540
|
+
config,
|
|
2541
|
+
requestedJsonStrict,
|
|
2542
|
+
topLevelVerbs: TOP_LEVEL_VERBS,
|
|
2543
|
+
listBuiltInAgents,
|
|
2544
|
+
detectAgentToken,
|
|
2545
|
+
registerAgentCommand,
|
|
2546
|
+
registerDefaultCommands,
|
|
2547
|
+
handlePromptAction: async (command, promptParts) => {
|
|
2548
|
+
await handlePrompt(void 0, promptParts, {}, command, config);
|
|
2549
|
+
}
|
|
2550
|
+
});
|
|
2551
|
+
program.exitOverride((error) => {
|
|
2552
|
+
throw error;
|
|
2553
|
+
});
|
|
2518
2554
|
await program.parseAsync(normalizedArgv);
|
|
2519
2555
|
} catch (error) {
|
|
2520
2556
|
await handleProgramParseError(error, requestedOutputPolicy);
|