@openacp/cli 2026.408.3 → 2026.408.4
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.js +281 -139
- package/dist/cli.js.map +1 -1
- package/dist/index.d.ts +2 -1
- package/dist/index.js +228 -112
- package/dist/index.js.map +1 -1
- package/package.json +1 -1
package/dist/index.d.ts
CHANGED
|
@@ -875,7 +875,7 @@ declare class AgentInstance extends TypedEmitter<AgentInstanceEvents> {
|
|
|
875
875
|
|
|
876
876
|
declare class AgentStore {
|
|
877
877
|
private data;
|
|
878
|
-
|
|
878
|
+
readonly filePath: string;
|
|
879
879
|
constructor(filePath?: string);
|
|
880
880
|
load(): void;
|
|
881
881
|
exists(): boolean;
|
|
@@ -889,6 +889,7 @@ declare class AgentStore {
|
|
|
889
889
|
|
|
890
890
|
declare class AgentCatalog {
|
|
891
891
|
private store;
|
|
892
|
+
private globalStore;
|
|
892
893
|
private registryAgents;
|
|
893
894
|
private cachePath;
|
|
894
895
|
private agentsDir;
|
package/dist/index.js
CHANGED
|
@@ -198,11 +198,11 @@ async function shutdownLogger() {
|
|
|
198
198
|
logDir = void 0;
|
|
199
199
|
initialized = false;
|
|
200
200
|
if (transport) {
|
|
201
|
-
await new Promise((
|
|
202
|
-
const timeout = setTimeout(
|
|
201
|
+
await new Promise((resolve7) => {
|
|
202
|
+
const timeout = setTimeout(resolve7, 3e3);
|
|
203
203
|
transport.on("close", () => {
|
|
204
204
|
clearTimeout(timeout);
|
|
205
|
-
|
|
205
|
+
resolve7();
|
|
206
206
|
});
|
|
207
207
|
transport.end();
|
|
208
208
|
});
|
|
@@ -289,7 +289,8 @@ __export(instance_context_exports, {
|
|
|
289
289
|
createInstanceContext: () => createInstanceContext,
|
|
290
290
|
generateSlug: () => generateSlug,
|
|
291
291
|
getGlobalRoot: () => getGlobalRoot,
|
|
292
|
-
resolveInstanceRoot: () => resolveInstanceRoot
|
|
292
|
+
resolveInstanceRoot: () => resolveInstanceRoot,
|
|
293
|
+
resolveRunningInstance: () => resolveRunningInstance
|
|
293
294
|
});
|
|
294
295
|
import path2 from "path";
|
|
295
296
|
import fs2 from "fs";
|
|
@@ -341,6 +342,38 @@ function resolveInstanceRoot(opts) {
|
|
|
341
342
|
function getGlobalRoot() {
|
|
342
343
|
return path2.join(os2.homedir(), ".openacp");
|
|
343
344
|
}
|
|
345
|
+
async function resolveRunningInstance(cwd) {
|
|
346
|
+
const globalRoot = getGlobalRoot();
|
|
347
|
+
let dir = path2.resolve(cwd);
|
|
348
|
+
while (true) {
|
|
349
|
+
const candidate = path2.join(dir, ".openacp");
|
|
350
|
+
if (candidate !== globalRoot && fs2.existsSync(candidate)) {
|
|
351
|
+
if (await isInstanceRunning(candidate)) return candidate;
|
|
352
|
+
}
|
|
353
|
+
const parent = path2.dirname(dir);
|
|
354
|
+
if (parent === dir) break;
|
|
355
|
+
dir = parent;
|
|
356
|
+
}
|
|
357
|
+
if (fs2.existsSync(globalRoot) && await isInstanceRunning(globalRoot)) return globalRoot;
|
|
358
|
+
return null;
|
|
359
|
+
}
|
|
360
|
+
async function isInstanceRunning(instanceRoot) {
|
|
361
|
+
const portFile = path2.join(instanceRoot, "api.port");
|
|
362
|
+
try {
|
|
363
|
+
const content = fs2.readFileSync(portFile, "utf-8").trim();
|
|
364
|
+
const port = parseInt(content, 10);
|
|
365
|
+
if (isNaN(port)) return false;
|
|
366
|
+
const controller = new AbortController();
|
|
367
|
+
const timeout = setTimeout(() => controller.abort(), 2e3);
|
|
368
|
+
const res = await fetch(`http://127.0.0.1:${port}/api/v1/system/health`, {
|
|
369
|
+
signal: controller.signal
|
|
370
|
+
});
|
|
371
|
+
clearTimeout(timeout);
|
|
372
|
+
return res.ok;
|
|
373
|
+
} catch {
|
|
374
|
+
return false;
|
|
375
|
+
}
|
|
376
|
+
}
|
|
344
377
|
var init_instance_context = __esm({
|
|
345
378
|
"src/core/instance/instance-context.ts"() {
|
|
346
379
|
"use strict";
|
|
@@ -875,6 +908,25 @@ var init_events = __esm({
|
|
|
875
908
|
}
|
|
876
909
|
});
|
|
877
910
|
|
|
911
|
+
// src/core/utils/apply-patch-detection.ts
|
|
912
|
+
function asRecord(value) {
|
|
913
|
+
return value !== null && typeof value === "object" && !Array.isArray(value) ? value : null;
|
|
914
|
+
}
|
|
915
|
+
function hasApplyPatchPatchText(rawInput) {
|
|
916
|
+
const input2 = asRecord(rawInput);
|
|
917
|
+
return !!input2 && (typeof input2.patchText === "string" || typeof input2.patch_text === "string");
|
|
918
|
+
}
|
|
919
|
+
function isApplyPatchOtherTool(kind, name, rawInput) {
|
|
920
|
+
if (kind !== "other") return false;
|
|
921
|
+
if (name.toLowerCase() === "apply_patch") return true;
|
|
922
|
+
return hasApplyPatchPatchText(rawInput);
|
|
923
|
+
}
|
|
924
|
+
var init_apply_patch_detection = __esm({
|
|
925
|
+
"src/core/utils/apply-patch-detection.ts"() {
|
|
926
|
+
"use strict";
|
|
927
|
+
}
|
|
928
|
+
});
|
|
929
|
+
|
|
878
930
|
// src/core/utils/bypass-detection.ts
|
|
879
931
|
function isPermissionBypass(value) {
|
|
880
932
|
const lower = value.toLowerCase();
|
|
@@ -2013,12 +2065,12 @@ function isProcessAlive(pid) {
|
|
|
2013
2065
|
}
|
|
2014
2066
|
}
|
|
2015
2067
|
function checkPortInUse(port) {
|
|
2016
|
-
return new Promise((
|
|
2068
|
+
return new Promise((resolve7) => {
|
|
2017
2069
|
const server = net.createServer();
|
|
2018
|
-
server.once("error", () =>
|
|
2070
|
+
server.once("error", () => resolve7(true));
|
|
2019
2071
|
server.once("listening", () => {
|
|
2020
2072
|
server.close();
|
|
2021
|
-
|
|
2073
|
+
resolve7(false);
|
|
2022
2074
|
});
|
|
2023
2075
|
server.listen(port, "127.0.0.1");
|
|
2024
2076
|
});
|
|
@@ -2110,7 +2162,7 @@ import https from "https";
|
|
|
2110
2162
|
import os9 from "os";
|
|
2111
2163
|
import { execFileSync as execFileSync4 } from "child_process";
|
|
2112
2164
|
function downloadFile(url, dest, maxRedirects = 10) {
|
|
2113
|
-
return new Promise((
|
|
2165
|
+
return new Promise((resolve7, reject) => {
|
|
2114
2166
|
const file = fs23.createWriteStream(dest);
|
|
2115
2167
|
const cleanup = () => {
|
|
2116
2168
|
try {
|
|
@@ -2129,7 +2181,7 @@ function downloadFile(url, dest, maxRedirects = 10) {
|
|
|
2129
2181
|
}
|
|
2130
2182
|
file.close(() => {
|
|
2131
2183
|
cleanup();
|
|
2132
|
-
downloadFile(response.headers.location, dest, maxRedirects - 1).then(
|
|
2184
|
+
downloadFile(response.headers.location, dest, maxRedirects - 1).then(resolve7).catch(reject);
|
|
2133
2185
|
});
|
|
2134
2186
|
return;
|
|
2135
2187
|
}
|
|
@@ -2153,7 +2205,7 @@ function downloadFile(url, dest, maxRedirects = 10) {
|
|
|
2153
2205
|
}
|
|
2154
2206
|
});
|
|
2155
2207
|
response.pipe(file);
|
|
2156
|
-
file.on("finish", () => file.close(() =>
|
|
2208
|
+
file.on("finish", () => file.close(() => resolve7(dest)));
|
|
2157
2209
|
file.on("error", (err) => {
|
|
2158
2210
|
file.close(() => {
|
|
2159
2211
|
cleanup();
|
|
@@ -4975,10 +5027,10 @@ var init_send_queue = __esm({
|
|
|
4975
5027
|
const type = opts?.type ?? "other";
|
|
4976
5028
|
const key = opts?.key;
|
|
4977
5029
|
const category = opts?.category;
|
|
4978
|
-
let
|
|
5030
|
+
let resolve7;
|
|
4979
5031
|
let reject;
|
|
4980
5032
|
const promise = new Promise((res, rej) => {
|
|
4981
|
-
|
|
5033
|
+
resolve7 = res;
|
|
4982
5034
|
reject = rej;
|
|
4983
5035
|
});
|
|
4984
5036
|
promise.catch(() => {
|
|
@@ -4989,12 +5041,12 @@ var init_send_queue = __esm({
|
|
|
4989
5041
|
);
|
|
4990
5042
|
if (idx !== -1) {
|
|
4991
5043
|
this.items[idx].resolve(void 0);
|
|
4992
|
-
this.items[idx] = { fn, type, key, category, resolve:
|
|
5044
|
+
this.items[idx] = { fn, type, key, category, resolve: resolve7, reject, promise };
|
|
4993
5045
|
this.scheduleProcess();
|
|
4994
5046
|
return promise;
|
|
4995
5047
|
}
|
|
4996
5048
|
}
|
|
4997
|
-
this.items.push({ fn, type, key, category, resolve:
|
|
5049
|
+
this.items.push({ fn, type, key, category, resolve: resolve7, reject, promise });
|
|
4998
5050
|
this.scheduleProcess();
|
|
4999
5051
|
return promise;
|
|
5000
5052
|
}
|
|
@@ -5256,7 +5308,7 @@ var init_stream_accumulator = __esm({
|
|
|
5256
5308
|
});
|
|
5257
5309
|
|
|
5258
5310
|
// src/core/adapter-primitives/display-spec-builder.ts
|
|
5259
|
-
function
|
|
5311
|
+
function asRecord3(value) {
|
|
5260
5312
|
if (value !== null && typeof value === "object" && !Array.isArray(value)) {
|
|
5261
5313
|
return value;
|
|
5262
5314
|
}
|
|
@@ -5289,8 +5341,21 @@ function parseApplyPatchTargets(patchText) {
|
|
|
5289
5341
|
function buildTitle(entry, kind) {
|
|
5290
5342
|
if (entry.displayTitle) return entry.displayTitle;
|
|
5291
5343
|
if (entry.displaySummary) return entry.displaySummary;
|
|
5292
|
-
const input2 =
|
|
5344
|
+
const input2 = asRecord3(entry.rawInput);
|
|
5293
5345
|
const nameLower = entry.name.toLowerCase();
|
|
5346
|
+
if (isApplyPatchOtherTool(entry.kind, entry.name, entry.rawInput)) {
|
|
5347
|
+
const patchText = getStringField(input2, ["patchText", "patch_text"]);
|
|
5348
|
+
if (patchText) {
|
|
5349
|
+
const targets = parseApplyPatchTargets(patchText);
|
|
5350
|
+
if (targets.length === 1) return targets[0];
|
|
5351
|
+
if (targets.length > 1) {
|
|
5352
|
+
const shown = targets.slice(0, 2).join(", ");
|
|
5353
|
+
const rest = targets.length - 2;
|
|
5354
|
+
return rest > 0 ? `${shown} (+${rest} more)` : shown;
|
|
5355
|
+
}
|
|
5356
|
+
}
|
|
5357
|
+
return "apply_patch";
|
|
5358
|
+
}
|
|
5294
5359
|
if (kind === "read") {
|
|
5295
5360
|
const filePath = getStringField(input2, ["file_path", "filePath", "path"]);
|
|
5296
5361
|
if (filePath) {
|
|
@@ -5339,36 +5404,6 @@ function buildTitle(entry, kind) {
|
|
|
5339
5404
|
}
|
|
5340
5405
|
return capitalize(entry.name);
|
|
5341
5406
|
}
|
|
5342
|
-
if (nameLower === "apply_patch") {
|
|
5343
|
-
const patchText = getStringField(input2, ["patchText", "patch_text"]);
|
|
5344
|
-
if (patchText) {
|
|
5345
|
-
const targets = parseApplyPatchTargets(patchText);
|
|
5346
|
-
if (targets.length === 1) return targets[0];
|
|
5347
|
-
if (targets.length > 1) {
|
|
5348
|
-
const shown = targets.slice(0, 2).join(", ");
|
|
5349
|
-
const remaining = targets.length - 2;
|
|
5350
|
-
return remaining > 0 ? `${shown} (+${remaining} more)` : shown;
|
|
5351
|
-
}
|
|
5352
|
-
}
|
|
5353
|
-
return "apply_patch";
|
|
5354
|
-
}
|
|
5355
|
-
if (nameLower === "todowrite") {
|
|
5356
|
-
const todos = Array.isArray(input2.todos) ? input2.todos : [];
|
|
5357
|
-
if (todos.length > 0) {
|
|
5358
|
-
const inProgress = todos.filter((t) => {
|
|
5359
|
-
if (!t || typeof t !== "object") return false;
|
|
5360
|
-
const status = t.status;
|
|
5361
|
-
return status === "in_progress";
|
|
5362
|
-
}).length;
|
|
5363
|
-
const completed = todos.filter((t) => {
|
|
5364
|
-
if (!t || typeof t !== "object") return false;
|
|
5365
|
-
const status = t.status;
|
|
5366
|
-
return status === "completed";
|
|
5367
|
-
}).length;
|
|
5368
|
-
return `Todo list (${completed}/${todos.length} done${inProgress > 0 ? `, ${inProgress} active` : ""})`;
|
|
5369
|
-
}
|
|
5370
|
-
return "Todo list";
|
|
5371
|
-
}
|
|
5372
5407
|
if (kind === "fetch" || kind === "web") {
|
|
5373
5408
|
const url = typeof input2.url === "string" ? input2.url : null;
|
|
5374
5409
|
if (url && url !== "undefined") return url.length > 60 ? url.slice(0, 57) + "..." : url;
|
|
@@ -5379,19 +5414,6 @@ function buildTitle(entry, kind) {
|
|
|
5379
5414
|
if (nameLower === "skill" && typeof input2.skill === "string" && input2.skill) {
|
|
5380
5415
|
return input2.skill;
|
|
5381
5416
|
}
|
|
5382
|
-
if (nameLower === "apply_patch") {
|
|
5383
|
-
const patchText = getStringField(input2, ["patchText", "patch_text"]);
|
|
5384
|
-
if (patchText) {
|
|
5385
|
-
const targets = parseApplyPatchTargets(patchText);
|
|
5386
|
-
if (targets.length === 1) return targets[0];
|
|
5387
|
-
if (targets.length > 1) {
|
|
5388
|
-
const shown = targets.slice(0, 2).join(", ");
|
|
5389
|
-
const rest = targets.length - 2;
|
|
5390
|
-
return rest > 0 ? `${shown} (+${rest} more)` : shown;
|
|
5391
|
-
}
|
|
5392
|
-
}
|
|
5393
|
-
return "apply_patch";
|
|
5394
|
-
}
|
|
5395
5417
|
if (nameLower === "todowrite") {
|
|
5396
5418
|
const todos = Array.isArray(input2.todos) ? input2.todos : [];
|
|
5397
5419
|
if (todos.length > 0) {
|
|
@@ -5421,6 +5443,7 @@ var init_display_spec_builder = __esm({
|
|
|
5421
5443
|
"src/core/adapter-primitives/display-spec-builder.ts"() {
|
|
5422
5444
|
"use strict";
|
|
5423
5445
|
init_format_types();
|
|
5446
|
+
init_apply_patch_detection();
|
|
5424
5447
|
EXECUTE_KINDS = /* @__PURE__ */ new Set(["execute", "bash", "command", "terminal"]);
|
|
5425
5448
|
INLINE_MAX_LINES = 15;
|
|
5426
5449
|
INLINE_MAX_CHARS = 800;
|
|
@@ -5429,12 +5452,12 @@ var init_display_spec_builder = __esm({
|
|
|
5429
5452
|
this.tunnelService = tunnelService;
|
|
5430
5453
|
}
|
|
5431
5454
|
buildToolSpec(entry, mode, sessionContext) {
|
|
5432
|
-
const effectiveKind = entry.displayKind ?? entry.kind;
|
|
5455
|
+
const effectiveKind = entry.displayKind ?? (isApplyPatchOtherTool(entry.kind, entry.name, entry.rawInput) ? "edit" : entry.kind);
|
|
5433
5456
|
const icon = KIND_ICONS[effectiveKind] ?? KIND_ICONS["other"] ?? "\u{1F6E0}\uFE0F";
|
|
5434
5457
|
const title = buildTitle(entry, effectiveKind);
|
|
5435
5458
|
const isHidden = entry.isNoise && mode !== "high";
|
|
5436
5459
|
const includeMeta = mode !== "low";
|
|
5437
|
-
const input2 =
|
|
5460
|
+
const input2 = asRecord3(entry.rawInput);
|
|
5438
5461
|
const rawDescription = typeof input2.description === "string" ? input2.description : null;
|
|
5439
5462
|
const descLower = rawDescription?.toLowerCase();
|
|
5440
5463
|
const description = includeMeta && rawDescription && rawDescription !== title && descLower !== effectiveKind && descLower !== entry.name.toLowerCase() ? rawDescription : null;
|
|
@@ -5819,14 +5842,14 @@ __export(version_exports, {
|
|
|
5819
5842
|
runUpdate: () => runUpdate
|
|
5820
5843
|
});
|
|
5821
5844
|
import { fileURLToPath as fileURLToPath2 } from "url";
|
|
5822
|
-
import { dirname as dirname10, join as join20, resolve as
|
|
5845
|
+
import { dirname as dirname10, join as join20, resolve as resolve6 } from "path";
|
|
5823
5846
|
import { existsSync as existsSync17, readFileSync as readFileSync15 } from "fs";
|
|
5824
5847
|
function findPackageJson() {
|
|
5825
5848
|
let dir = dirname10(fileURLToPath2(import.meta.url));
|
|
5826
5849
|
for (let i = 0; i < 5; i++) {
|
|
5827
5850
|
const candidate = join20(dir, "package.json");
|
|
5828
5851
|
if (existsSync17(candidate)) return candidate;
|
|
5829
|
-
const parent =
|
|
5852
|
+
const parent = resolve6(dir, "..");
|
|
5830
5853
|
if (parent === dir) break;
|
|
5831
5854
|
dir = parent;
|
|
5832
5855
|
}
|
|
@@ -5865,21 +5888,21 @@ function compareVersions(current, latest) {
|
|
|
5865
5888
|
}
|
|
5866
5889
|
async function runUpdate() {
|
|
5867
5890
|
const { spawn: spawn4 } = await import("child_process");
|
|
5868
|
-
return new Promise((
|
|
5891
|
+
return new Promise((resolve7) => {
|
|
5869
5892
|
const child = spawn4("npm", ["install", "-g", `${NPM_PACKAGE}@latest`], {
|
|
5870
5893
|
stdio: "inherit",
|
|
5871
5894
|
shell: true
|
|
5872
5895
|
});
|
|
5873
5896
|
const onSignal = () => {
|
|
5874
5897
|
child.kill("SIGTERM");
|
|
5875
|
-
|
|
5898
|
+
resolve7(false);
|
|
5876
5899
|
};
|
|
5877
5900
|
process.on("SIGINT", onSignal);
|
|
5878
5901
|
process.on("SIGTERM", onSignal);
|
|
5879
5902
|
child.on("close", (code) => {
|
|
5880
5903
|
process.off("SIGINT", onSignal);
|
|
5881
5904
|
process.off("SIGTERM", onSignal);
|
|
5882
|
-
|
|
5905
|
+
resolve7(code === 0);
|
|
5883
5906
|
});
|
|
5884
5907
|
});
|
|
5885
5908
|
}
|
|
@@ -10778,15 +10801,15 @@ var ChannelAdapter = class {
|
|
|
10778
10801
|
function nodeToWebWritable(nodeStream) {
|
|
10779
10802
|
return new WritableStream({
|
|
10780
10803
|
write(chunk) {
|
|
10781
|
-
return new Promise((
|
|
10804
|
+
return new Promise((resolve7, reject) => {
|
|
10782
10805
|
const ok2 = nodeStream.write(chunk);
|
|
10783
10806
|
if (ok2) {
|
|
10784
|
-
|
|
10807
|
+
resolve7();
|
|
10785
10808
|
return;
|
|
10786
10809
|
}
|
|
10787
10810
|
const onDrain = () => {
|
|
10788
10811
|
nodeStream.removeListener("error", onError);
|
|
10789
|
-
|
|
10812
|
+
resolve7();
|
|
10790
10813
|
};
|
|
10791
10814
|
const onError = (err) => {
|
|
10792
10815
|
nodeStream.removeListener("drain", onDrain);
|
|
@@ -11222,12 +11245,12 @@ var TerminalManager = class {
|
|
|
11222
11245
|
signal: state.exitStatus.signal
|
|
11223
11246
|
};
|
|
11224
11247
|
}
|
|
11225
|
-
return new Promise((
|
|
11248
|
+
return new Promise((resolve7) => {
|
|
11226
11249
|
state.process.on("exit", (code, signal) => {
|
|
11227
|
-
|
|
11250
|
+
resolve7({ exitCode: code, signal });
|
|
11228
11251
|
});
|
|
11229
11252
|
if (state.exitStatus !== null) {
|
|
11230
|
-
|
|
11253
|
+
resolve7({
|
|
11231
11254
|
exitCode: state.exitStatus.exitCode,
|
|
11232
11255
|
signal: state.exitStatus.signal
|
|
11233
11256
|
});
|
|
@@ -11450,7 +11473,7 @@ var AgentInstance = class _AgentInstance extends TypedEmitter {
|
|
|
11450
11473
|
env: filterEnv(process.env, agentDef.env)
|
|
11451
11474
|
}
|
|
11452
11475
|
);
|
|
11453
|
-
await new Promise((
|
|
11476
|
+
await new Promise((resolve7, reject) => {
|
|
11454
11477
|
instance.child.on("error", (err) => {
|
|
11455
11478
|
reject(
|
|
11456
11479
|
new Error(
|
|
@@ -11458,7 +11481,7 @@ var AgentInstance = class _AgentInstance extends TypedEmitter {
|
|
|
11458
11481
|
)
|
|
11459
11482
|
);
|
|
11460
11483
|
});
|
|
11461
|
-
instance.child.on("spawn", () =>
|
|
11484
|
+
instance.child.on("spawn", () => resolve7());
|
|
11462
11485
|
});
|
|
11463
11486
|
instance.stderrCapture = new StderrCapture(50);
|
|
11464
11487
|
instance.child.stderr.on("data", (chunk) => {
|
|
@@ -11964,15 +11987,15 @@ ${skipNote}`;
|
|
|
11964
11987
|
this._destroying = true;
|
|
11965
11988
|
this.terminalManager.destroyAll();
|
|
11966
11989
|
if (this.child.exitCode !== null) return;
|
|
11967
|
-
await new Promise((
|
|
11990
|
+
await new Promise((resolve7) => {
|
|
11968
11991
|
this.child.on("exit", () => {
|
|
11969
11992
|
clearTimeout(forceKillTimer);
|
|
11970
|
-
|
|
11993
|
+
resolve7();
|
|
11971
11994
|
});
|
|
11972
11995
|
this.child.kill("SIGTERM");
|
|
11973
11996
|
const forceKillTimer = setTimeout(() => {
|
|
11974
11997
|
if (this.child.exitCode === null) this.child.kill("SIGKILL");
|
|
11975
|
-
|
|
11998
|
+
resolve7();
|
|
11976
11999
|
}, 1e4);
|
|
11977
12000
|
if (typeof forceKillTimer === "object" && forceKillTimer !== null && "unref" in forceKillTimer) {
|
|
11978
12001
|
forceKillTimer.unref();
|
|
@@ -12026,8 +12049,8 @@ var PromptQueue = class {
|
|
|
12026
12049
|
processorSettled = null;
|
|
12027
12050
|
async enqueue(text3, attachments, routing, turnId) {
|
|
12028
12051
|
if (this.processing) {
|
|
12029
|
-
return new Promise((
|
|
12030
|
-
this.queue.push({ text: text3, attachments, routing, turnId, resolve:
|
|
12052
|
+
return new Promise((resolve7) => {
|
|
12053
|
+
this.queue.push({ text: text3, attachments, routing, turnId, resolve: resolve7 });
|
|
12031
12054
|
});
|
|
12032
12055
|
}
|
|
12033
12056
|
await this.process(text3, attachments, routing, turnId);
|
|
@@ -12101,8 +12124,8 @@ var PermissionGate = class {
|
|
|
12101
12124
|
this.request = request;
|
|
12102
12125
|
this.settled = false;
|
|
12103
12126
|
this.clearTimeout();
|
|
12104
|
-
return new Promise((
|
|
12105
|
-
this.resolveFn =
|
|
12127
|
+
return new Promise((resolve7, reject) => {
|
|
12128
|
+
this.resolveFn = resolve7;
|
|
12106
12129
|
this.rejectFn = reject;
|
|
12107
12130
|
this.timeoutTimer = setTimeout(() => {
|
|
12108
12131
|
this.reject("Permission request timed out (no response received)");
|
|
@@ -12711,7 +12734,11 @@ ${result.text}` : result.text;
|
|
|
12711
12734
|
import * as path8 from "path";
|
|
12712
12735
|
|
|
12713
12736
|
// src/core/utils/extract-file-info.ts
|
|
12714
|
-
|
|
12737
|
+
init_apply_patch_detection();
|
|
12738
|
+
function extractFileInfo(name, kind, content, rawInput, meta, rawOutput) {
|
|
12739
|
+
if (isApplyPatchOtherTool(kind, name, rawInput)) {
|
|
12740
|
+
return parseApplyPatchRawOutput(rawOutput);
|
|
12741
|
+
}
|
|
12715
12742
|
if (kind && !["read", "edit", "write"].includes(kind)) return null;
|
|
12716
12743
|
let info = null;
|
|
12717
12744
|
if (meta) {
|
|
@@ -12766,6 +12793,37 @@ function extractFileInfo(name, kind, content, rawInput, meta) {
|
|
|
12766
12793
|
if (!info.filePath || !info.content) return null;
|
|
12767
12794
|
return info;
|
|
12768
12795
|
}
|
|
12796
|
+
function parseApplyPatchRawOutput(rawOutput) {
|
|
12797
|
+
if (!rawOutput || typeof rawOutput !== "object" || Array.isArray(rawOutput)) return null;
|
|
12798
|
+
const output = rawOutput;
|
|
12799
|
+
const metadata = output.metadata;
|
|
12800
|
+
if (!metadata || typeof metadata !== "object" || Array.isArray(metadata)) return null;
|
|
12801
|
+
const files = metadata.files;
|
|
12802
|
+
if (!Array.isArray(files)) return null;
|
|
12803
|
+
const sortedFiles = [...files].sort((a, b) => getApplyPatchFileScore(b) - getApplyPatchFileScore(a));
|
|
12804
|
+
for (const file of sortedFiles) {
|
|
12805
|
+
if (!file || typeof file !== "object" || Array.isArray(file)) continue;
|
|
12806
|
+
const f = file;
|
|
12807
|
+
const filePath = typeof f.filePath === "string" ? f.filePath : typeof f.relativePath === "string" ? f.relativePath : null;
|
|
12808
|
+
if (!filePath) continue;
|
|
12809
|
+
const after = typeof f.after === "string" ? f.after : null;
|
|
12810
|
+
if (!after) continue;
|
|
12811
|
+
const before = typeof f.before === "string" ? f.before : void 0;
|
|
12812
|
+
return {
|
|
12813
|
+
filePath,
|
|
12814
|
+
content: after,
|
|
12815
|
+
oldContent: before
|
|
12816
|
+
};
|
|
12817
|
+
}
|
|
12818
|
+
return null;
|
|
12819
|
+
}
|
|
12820
|
+
function getApplyPatchFileScore(file) {
|
|
12821
|
+
if (!file || typeof file !== "object" || Array.isArray(file)) return 0;
|
|
12822
|
+
const f = file;
|
|
12823
|
+
const additions = typeof f.additions === "number" && Number.isFinite(f.additions) && f.additions >= 0 ? f.additions : 0;
|
|
12824
|
+
const deletions = typeof f.deletions === "number" && Number.isFinite(f.deletions) && f.deletions >= 0 ? f.deletions : 0;
|
|
12825
|
+
return additions + deletions;
|
|
12826
|
+
}
|
|
12769
12827
|
function resolveToolResponse(meta) {
|
|
12770
12828
|
const claudeCode = meta.claudeCode;
|
|
12771
12829
|
if (claudeCode?.toolResponse && typeof claudeCode.toolResponse === "object") {
|
|
@@ -12833,6 +12891,7 @@ function parseContent(content) {
|
|
|
12833
12891
|
}
|
|
12834
12892
|
|
|
12835
12893
|
// src/core/message-transformer.ts
|
|
12894
|
+
init_apply_patch_detection();
|
|
12836
12895
|
init_log();
|
|
12837
12896
|
var log5 = createChildLogger({ module: "message-transformer" });
|
|
12838
12897
|
var BINARY_VIEWER_EXTENSIONS = /* @__PURE__ */ new Set([
|
|
@@ -12888,6 +12947,63 @@ function computeLineDiff(oldStr, newStr) {
|
|
|
12888
12947
|
removed: Math.max(0, oldLines.length - prefixLen - suffixLen)
|
|
12889
12948
|
};
|
|
12890
12949
|
}
|
|
12950
|
+
function asRecord2(value) {
|
|
12951
|
+
return value !== null && typeof value === "object" && !Array.isArray(value) ? value : null;
|
|
12952
|
+
}
|
|
12953
|
+
function asNonNegativeNumber(value) {
|
|
12954
|
+
return typeof value === "number" && Number.isFinite(value) && value >= 0 ? value : null;
|
|
12955
|
+
}
|
|
12956
|
+
function extractDiffStatsFromRawOutput(rawOutput) {
|
|
12957
|
+
const output = asRecord2(rawOutput);
|
|
12958
|
+
const metadata = asRecord2(output?.metadata);
|
|
12959
|
+
if (!metadata) return null;
|
|
12960
|
+
const files = Array.isArray(metadata.files) ? metadata.files : null;
|
|
12961
|
+
if (files && files.length > 0) {
|
|
12962
|
+
let added2 = 0;
|
|
12963
|
+
let removed2 = 0;
|
|
12964
|
+
let hasAny = false;
|
|
12965
|
+
for (const file of files) {
|
|
12966
|
+
const fileMeta = asRecord2(file);
|
|
12967
|
+
if (!fileMeta) continue;
|
|
12968
|
+
const fileAdded = asNonNegativeNumber(fileMeta.additions);
|
|
12969
|
+
const fileRemoved = asNonNegativeNumber(fileMeta.deletions);
|
|
12970
|
+
if (fileAdded === null && fileRemoved === null) continue;
|
|
12971
|
+
added2 += fileAdded ?? 0;
|
|
12972
|
+
removed2 += fileRemoved ?? 0;
|
|
12973
|
+
hasAny = true;
|
|
12974
|
+
}
|
|
12975
|
+
if (hasAny && (added2 > 0 || removed2 > 0)) return { added: added2, removed: removed2 };
|
|
12976
|
+
}
|
|
12977
|
+
const added = asNonNegativeNumber(metadata.additions);
|
|
12978
|
+
const removed = asNonNegativeNumber(metadata.deletions);
|
|
12979
|
+
if (added === null && removed === null) return null;
|
|
12980
|
+
if ((added ?? 0) === 0 && (removed ?? 0) === 0) return null;
|
|
12981
|
+
return {
|
|
12982
|
+
added: added ?? 0,
|
|
12983
|
+
removed: removed ?? 0
|
|
12984
|
+
};
|
|
12985
|
+
}
|
|
12986
|
+
function extractDiffStatsFromToolPayload(name, kind, rawInput, rawOutput) {
|
|
12987
|
+
if (kind === "edit" || kind === "write") {
|
|
12988
|
+
const ri = asRecord2(rawInput);
|
|
12989
|
+
if (!ri) return null;
|
|
12990
|
+
const oldStr = typeof ri.old_string === "string" ? ri.old_string : typeof ri.oldText === "string" ? ri.oldText : null;
|
|
12991
|
+
const newStr = typeof ri.new_string === "string" ? ri.new_string : typeof ri.newText === "string" ? ri.newText : typeof ri.content === "string" ? ri.content : null;
|
|
12992
|
+
if (oldStr !== null && newStr !== null) {
|
|
12993
|
+
const stats = computeLineDiff(oldStr, newStr);
|
|
12994
|
+
return stats.added > 0 || stats.removed > 0 ? stats : null;
|
|
12995
|
+
}
|
|
12996
|
+
if (oldStr === null && newStr !== null && kind === "write") {
|
|
12997
|
+
const added = newStr.split("\n").length;
|
|
12998
|
+
return added > 0 ? { added, removed: 0 } : null;
|
|
12999
|
+
}
|
|
13000
|
+
return null;
|
|
13001
|
+
}
|
|
13002
|
+
if (isApplyPatchOtherTool(kind, name, rawInput)) {
|
|
13003
|
+
return extractDiffStatsFromRawOutput(rawOutput);
|
|
13004
|
+
}
|
|
13005
|
+
return null;
|
|
13006
|
+
}
|
|
12891
13007
|
var MessageTransformer = class {
|
|
12892
13008
|
tunnelService;
|
|
12893
13009
|
/** Cache rawInput from tool_call so it's available in tool_update (which often lacks it) */
|
|
@@ -13037,22 +13153,11 @@ var MessageTransformer = class {
|
|
|
13037
13153
|
return input2 !== null && input2 !== void 0 && typeof input2 === "object" && !Array.isArray(input2) && Object.keys(input2).length > 0;
|
|
13038
13154
|
}
|
|
13039
13155
|
enrichWithViewerLinks(event, metadata, sessionContext) {
|
|
13156
|
+
const name = "name" in event ? event.name || "" : "";
|
|
13040
13157
|
const kind = "kind" in event ? event.kind : void 0;
|
|
13041
|
-
if (!metadata.diffStats
|
|
13042
|
-
const
|
|
13043
|
-
if (
|
|
13044
|
-
const oldStr = typeof ri.old_string === "string" ? ri.old_string : typeof ri.oldText === "string" ? ri.oldText : null;
|
|
13045
|
-
const newStr = typeof ri.new_string === "string" ? ri.new_string : typeof ri.newText === "string" ? ri.newText : typeof ri.content === "string" ? ri.content : null;
|
|
13046
|
-
if (oldStr !== null && newStr !== null) {
|
|
13047
|
-
const stats = computeLineDiff(oldStr, newStr);
|
|
13048
|
-
if (stats.added > 0 || stats.removed > 0) {
|
|
13049
|
-
metadata.diffStats = stats;
|
|
13050
|
-
}
|
|
13051
|
-
} else if (oldStr === null && newStr !== null && kind === "write") {
|
|
13052
|
-
const added = newStr.split("\n").length;
|
|
13053
|
-
if (added > 0) metadata.diffStats = { added, removed: 0 };
|
|
13054
|
-
}
|
|
13055
|
-
}
|
|
13158
|
+
if (!metadata.diffStats) {
|
|
13159
|
+
const stats = extractDiffStatsFromToolPayload(name, kind, event.rawInput, event.rawOutput);
|
|
13160
|
+
if (stats) metadata.diffStats = stats;
|
|
13056
13161
|
}
|
|
13057
13162
|
if (!this.tunnelService || !sessionContext) {
|
|
13058
13163
|
log5.debug(
|
|
@@ -13061,7 +13166,6 @@ var MessageTransformer = class {
|
|
|
13061
13166
|
);
|
|
13062
13167
|
return;
|
|
13063
13168
|
}
|
|
13064
|
-
const name = "name" in event ? event.name || "" : "";
|
|
13065
13169
|
log5.debug(
|
|
13066
13170
|
{ name, kind, status: event.status, hasContent: !!event.content, hasRawInput: !!event.rawInput },
|
|
13067
13171
|
"enrichWithViewerLinks: inspecting event"
|
|
@@ -13071,7 +13175,8 @@ var MessageTransformer = class {
|
|
|
13071
13175
|
kind,
|
|
13072
13176
|
event.content,
|
|
13073
13177
|
event.rawInput,
|
|
13074
|
-
event.meta
|
|
13178
|
+
event.meta,
|
|
13179
|
+
event.rawOutput
|
|
13075
13180
|
);
|
|
13076
13181
|
if (!fileInfo) {
|
|
13077
13182
|
log5.debug(
|
|
@@ -14610,6 +14715,7 @@ var REGISTRY_URL = "https://cdn.agentclientprotocol.com/registry/v1/latest/regis
|
|
|
14610
14715
|
var DEFAULT_TTL_HOURS = 24;
|
|
14611
14716
|
var AgentCatalog = class {
|
|
14612
14717
|
store;
|
|
14718
|
+
globalStore = null;
|
|
14613
14719
|
registryAgents = [];
|
|
14614
14720
|
cachePath;
|
|
14615
14721
|
agentsDir;
|
|
@@ -14617,9 +14723,15 @@ var AgentCatalog = class {
|
|
|
14617
14723
|
this.store = store ?? new AgentStore();
|
|
14618
14724
|
this.cachePath = cachePath ?? path13.join(os6.homedir(), ".openacp", "registry-cache.json");
|
|
14619
14725
|
this.agentsDir = agentsDir;
|
|
14726
|
+
const globalPath = path13.join(os6.homedir(), ".openacp", "agents.json");
|
|
14727
|
+
const storePath = this.store.filePath;
|
|
14728
|
+
if (path13.resolve(storePath) !== path13.resolve(globalPath)) {
|
|
14729
|
+
this.globalStore = new AgentStore(globalPath);
|
|
14730
|
+
}
|
|
14620
14731
|
}
|
|
14621
14732
|
load() {
|
|
14622
14733
|
this.store.load();
|
|
14734
|
+
this.globalStore?.load();
|
|
14623
14735
|
this.loadRegistryFromCacheOrSnapshot();
|
|
14624
14736
|
this.enrichInstalledFromRegistry();
|
|
14625
14737
|
}
|
|
@@ -14659,19 +14771,20 @@ var AgentCatalog = class {
|
|
|
14659
14771
|
if (byId) return byId;
|
|
14660
14772
|
return this.registryAgents.find((a) => getAgentAlias(a.id) === keyOrId);
|
|
14661
14773
|
}
|
|
14662
|
-
// --- Installed ---
|
|
14774
|
+
// --- Installed (instance-first, global-fallback) ---
|
|
14663
14775
|
getInstalled() {
|
|
14664
|
-
|
|
14776
|
+
const merged = { ...this.globalStore?.getInstalled(), ...this.store.getInstalled() };
|
|
14777
|
+
return Object.values(merged);
|
|
14665
14778
|
}
|
|
14666
14779
|
getInstalledEntries() {
|
|
14667
|
-
return this.store.getInstalled();
|
|
14780
|
+
return { ...this.globalStore?.getInstalled(), ...this.store.getInstalled() };
|
|
14668
14781
|
}
|
|
14669
14782
|
getInstalledAgent(key) {
|
|
14670
|
-
return this.store.getAgent(key);
|
|
14783
|
+
return this.store.getAgent(key) ?? this.globalStore?.getAgent(key);
|
|
14671
14784
|
}
|
|
14672
14785
|
// --- Discovery ---
|
|
14673
14786
|
getAvailable() {
|
|
14674
|
-
const installed = this.
|
|
14787
|
+
const installed = this.getInstalledEntries();
|
|
14675
14788
|
const items = [];
|
|
14676
14789
|
const seenKeys = /* @__PURE__ */ new Set();
|
|
14677
14790
|
for (const [key, agent] of Object.entries(installed)) {
|
|
@@ -14745,15 +14858,18 @@ var AgentCatalog = class {
|
|
|
14745
14858
|
this.store.addAgent(key, data);
|
|
14746
14859
|
}
|
|
14747
14860
|
async uninstall(key) {
|
|
14748
|
-
if (
|
|
14749
|
-
|
|
14861
|
+
if (this.store.hasAgent(key)) {
|
|
14862
|
+
await uninstallAgent(key, this.store);
|
|
14863
|
+
return { ok: true };
|
|
14864
|
+
}
|
|
14865
|
+
if (this.globalStore?.getAgent(key)) {
|
|
14866
|
+
return { ok: false, error: `"${key}" is installed globally. Uninstall it from the global instance instead.` };
|
|
14750
14867
|
}
|
|
14751
|
-
|
|
14752
|
-
return { ok: true };
|
|
14868
|
+
return { ok: false, error: `"${key}" is not installed.` };
|
|
14753
14869
|
}
|
|
14754
14870
|
// --- Resolution (for AgentManager) ---
|
|
14755
14871
|
resolve(key) {
|
|
14756
|
-
const agent = this.store.getAgent(key);
|
|
14872
|
+
const agent = this.store.getAgent(key) ?? this.globalStore?.getAgent(key);
|
|
14757
14873
|
if (!agent) return void 0;
|
|
14758
14874
|
return {
|
|
14759
14875
|
name: key,
|
|
@@ -15355,13 +15471,13 @@ init_events();
|
|
|
15355
15471
|
var SETUP_TIMEOUT_MS = 3e4;
|
|
15356
15472
|
var TEARDOWN_TIMEOUT_MS = 1e4;
|
|
15357
15473
|
function withTimeout(promise, ms, label) {
|
|
15358
|
-
return new Promise((
|
|
15474
|
+
return new Promise((resolve7, reject) => {
|
|
15359
15475
|
const timer = setTimeout(() => reject(new Error(`Timeout: ${label} exceeded ${ms}ms`)), ms);
|
|
15360
15476
|
if (typeof timer === "object" && timer !== null && "unref" in timer) {
|
|
15361
15477
|
;
|
|
15362
15478
|
timer.unref();
|
|
15363
15479
|
}
|
|
15364
|
-
promise.then(
|
|
15480
|
+
promise.then(resolve7, reject).finally(() => clearTimeout(timer));
|
|
15365
15481
|
});
|
|
15366
15482
|
}
|
|
15367
15483
|
function resolvePluginConfig(pluginName, configManager) {
|
|
@@ -17688,7 +17804,7 @@ function startDaemon(pidPath = getPidPath(), logDir2, instanceRoot) {
|
|
|
17688
17804
|
return { pid: child.pid };
|
|
17689
17805
|
}
|
|
17690
17806
|
function sleep(ms) {
|
|
17691
|
-
return new Promise((
|
|
17807
|
+
return new Promise((resolve7) => setTimeout(resolve7, ms));
|
|
17692
17808
|
}
|
|
17693
17809
|
function isProcessAlive2(pid) {
|
|
17694
17810
|
try {
|