@integrity-labs/agt-cli 0.28.626 → 0.28.628
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.
|
@@ -54,7 +54,7 @@ import {
|
|
|
54
54
|
safeWriteJsonAtomic,
|
|
55
55
|
setConfigHash,
|
|
56
56
|
tripClass
|
|
57
|
-
} from "../chunk-
|
|
57
|
+
} from "../chunk-G3FPZ4KK.js";
|
|
58
58
|
import {
|
|
59
59
|
getProjectDir as getProjectDir2,
|
|
60
60
|
getReadyTasks,
|
|
@@ -196,8 +196,8 @@ import {
|
|
|
196
196
|
import { createHash as createHash17 } from "crypto";
|
|
197
197
|
import { readFileSync as readFileSync28, writeFileSync as writeFileSync14, mkdirSync as mkdirSync11, existsSync as existsSync15, rmSync as rmSync5, readdirSync as readdirSync9, statSync as statSync8, copyFileSync } from "fs";
|
|
198
198
|
import { execFileSync as syncExecFile } from "child_process";
|
|
199
|
-
import { join as
|
|
200
|
-
import { homedir as
|
|
199
|
+
import { join as join35, dirname as dirname9, delimiter as pathDelimiter } from "path";
|
|
200
|
+
import { homedir as homedir17 } from "os";
|
|
201
201
|
import { fileURLToPath } from "url";
|
|
202
202
|
|
|
203
203
|
// src/lib/single-flight.ts
|
|
@@ -215,8 +215,8 @@ function createSingleFlight(task, opts = {}) {
|
|
|
215
215
|
}
|
|
216
216
|
running2 = true;
|
|
217
217
|
let markSettled;
|
|
218
|
-
settled = new Promise((
|
|
219
|
-
markSettled =
|
|
218
|
+
settled = new Promise((resolve2) => {
|
|
219
|
+
markSettled = resolve2;
|
|
220
220
|
});
|
|
221
221
|
const primary = (async () => {
|
|
222
222
|
try {
|
|
@@ -1556,6 +1556,62 @@ var DependencyRecoveryLedger = class {
|
|
|
1556
1556
|
}
|
|
1557
1557
|
};
|
|
1558
1558
|
|
|
1559
|
+
// src/lib/mcp-assets-ready.ts
|
|
1560
|
+
import { existsSync as nodeExistsSync, readFileSync as nodeReadFileSync } from "fs";
|
|
1561
|
+
import { homedir as homedir2 } from "os";
|
|
1562
|
+
import { join as join4, resolve, sep } from "path";
|
|
1563
|
+
function getSharedMcpDir(homeDir = homedir2()) {
|
|
1564
|
+
return join4(homeDir, ".augmented", "_mcp");
|
|
1565
|
+
}
|
|
1566
|
+
function isPathInsideDir(candidate, dir) {
|
|
1567
|
+
const resolvedDir = resolve(dir);
|
|
1568
|
+
const resolvedCandidate = resolve(candidate);
|
|
1569
|
+
if (resolvedCandidate === resolvedDir) return false;
|
|
1570
|
+
return resolvedCandidate.startsWith(resolvedDir.endsWith(sep) ? resolvedDir : resolvedDir + sep);
|
|
1571
|
+
}
|
|
1572
|
+
function findMissingMcpBundles(mcpConfigPath, deps = {}) {
|
|
1573
|
+
const existsSync16 = deps.existsSync ?? nodeExistsSync;
|
|
1574
|
+
const readFileSync29 = deps.readFileSync ?? nodeReadFileSync;
|
|
1575
|
+
const mcpDir = deps.mcpDir ?? getSharedMcpDir();
|
|
1576
|
+
let parsed;
|
|
1577
|
+
try {
|
|
1578
|
+
parsed = JSON.parse(readFileSync29(mcpConfigPath, "utf-8"));
|
|
1579
|
+
} catch {
|
|
1580
|
+
return [];
|
|
1581
|
+
}
|
|
1582
|
+
const servers = parsed?.mcpServers;
|
|
1583
|
+
if (!servers || typeof servers !== "object" || Array.isArray(servers)) return [];
|
|
1584
|
+
const missing = [];
|
|
1585
|
+
const seenPaths = /* @__PURE__ */ new Set();
|
|
1586
|
+
for (const [key, rawEntry] of Object.entries(servers)) {
|
|
1587
|
+
if (!rawEntry || typeof rawEntry !== "object" || Array.isArray(rawEntry)) continue;
|
|
1588
|
+
const entry = rawEntry;
|
|
1589
|
+
if (entry.command !== "node") continue;
|
|
1590
|
+
if (!Array.isArray(entry.args) || entry.args.length === 0) continue;
|
|
1591
|
+
const bundlePath = entry.args[0];
|
|
1592
|
+
if (typeof bundlePath !== "string" || bundlePath.length === 0) continue;
|
|
1593
|
+
if (!isPathInsideDir(bundlePath, mcpDir)) continue;
|
|
1594
|
+
const resolvedBundlePath = resolve(bundlePath);
|
|
1595
|
+
if (seenPaths.has(resolvedBundlePath)) continue;
|
|
1596
|
+
let present;
|
|
1597
|
+
try {
|
|
1598
|
+
present = existsSync16(bundlePath);
|
|
1599
|
+
} catch {
|
|
1600
|
+
continue;
|
|
1601
|
+
}
|
|
1602
|
+
if (!present) {
|
|
1603
|
+
seenPaths.add(resolvedBundlePath);
|
|
1604
|
+
missing.push({ key, path: bundlePath });
|
|
1605
|
+
}
|
|
1606
|
+
}
|
|
1607
|
+
return missing.sort((a, b) => a.key.localeCompare(b.key));
|
|
1608
|
+
}
|
|
1609
|
+
function formatMissingMcpBundles(missing) {
|
|
1610
|
+
if (missing.length === 0) return "all declared MCP bundles present";
|
|
1611
|
+
const detail = missing.map((m) => `${m.key} (${m.path})`).join(", ");
|
|
1612
|
+
return `MCP bundle(s) not yet on disk in the host-shared _mcp mount: ${detail}`;
|
|
1613
|
+
}
|
|
1614
|
+
|
|
1559
1615
|
// src/lib/self-update-coalesce.ts
|
|
1560
1616
|
import { readFileSync as readFileSync5, writeFileSync as writeFileSync3, mkdirSync as mkdirSync3 } from "fs";
|
|
1561
1617
|
import { dirname as dirname3 } from "path";
|
|
@@ -1925,14 +1981,14 @@ function formatReaperBootLine(opts) {
|
|
|
1925
1981
|
}
|
|
1926
1982
|
|
|
1927
1983
|
// src/lib/direct-chat-delivery.ts
|
|
1928
|
-
import { join as
|
|
1984
|
+
import { join as join5 } from "path";
|
|
1929
1985
|
var DEFAULT_DIRECT_CHAT_MAX_AGE_MS = 30 * 6e4;
|
|
1930
1986
|
function directChatMaxAgeMs() {
|
|
1931
1987
|
const raw = parseInt(process.env["AGT_DIRECT_CHAT_MAX_AGE_MS"] ?? "", 10);
|
|
1932
1988
|
return Number.isFinite(raw) && raw >= 0 ? raw : DEFAULT_DIRECT_CHAT_MAX_AGE_MS;
|
|
1933
1989
|
}
|
|
1934
1990
|
function directChatDoorbellPath(agentId, home) {
|
|
1935
|
-
return
|
|
1991
|
+
return join5(home, ".augmented", agentId, "direct-chat-doorbell");
|
|
1936
1992
|
}
|
|
1937
1993
|
function isDirectChatMessageExpired(createdAt, nowMs, maxAgeMs) {
|
|
1938
1994
|
if (!maxAgeMs || maxAgeMs <= 0) return false;
|
|
@@ -1944,15 +2000,15 @@ function isDirectChatMessageExpired(createdAt, nowMs, maxAgeMs) {
|
|
|
1944
2000
|
|
|
1945
2001
|
// src/lib/id-keyed-migration.ts
|
|
1946
2002
|
import { existsSync as existsSync2, lstatSync, readlinkSync, renameSync } from "fs";
|
|
1947
|
-
import { join as
|
|
1948
|
-
import { homedir as
|
|
2003
|
+
import { join as join6 } from "path";
|
|
2004
|
+
import { homedir as homedir3 } from "os";
|
|
1949
2005
|
var ID_KEYED_MIGRATION_FLAG = "id-keyed-layout-migration";
|
|
1950
2006
|
function agentHasActiveWhatsapp(channelConfigs, codeNameDir) {
|
|
1951
2007
|
if (channelConfigs && Object.prototype.hasOwnProperty.call(channelConfigs, "whatsapp")) {
|
|
1952
2008
|
return true;
|
|
1953
2009
|
}
|
|
1954
2010
|
try {
|
|
1955
|
-
if (existsSync2(
|
|
2011
|
+
if (existsSync2(join6(codeNameDir, "whatsapp-pending-inbound"))) return true;
|
|
1956
2012
|
} catch {
|
|
1957
2013
|
}
|
|
1958
2014
|
return false;
|
|
@@ -1982,12 +2038,12 @@ function finishTranscriptMove(oldCwd, newCwd, codeName, log2) {
|
|
|
1982
2038
|
log2(`[id-keyed-migration] moved transcript store for '${codeName}' to the id-keyed key`);
|
|
1983
2039
|
}
|
|
1984
2040
|
function maybeMigrateAgentToIdKeyedLayout(agent, deps) {
|
|
1985
|
-
const home = deps.home ??
|
|
2041
|
+
const home = deps.home ?? homedir3();
|
|
1986
2042
|
const { code_name: codeName, agent_id: agentId } = agent;
|
|
1987
|
-
const codeNamePath =
|
|
1988
|
-
const idPath =
|
|
1989
|
-
const oldCwd =
|
|
1990
|
-
const newCwd =
|
|
2043
|
+
const codeNamePath = join6(home, ".augmented", codeName);
|
|
2044
|
+
const idPath = join6(home, ".augmented", agentId);
|
|
2045
|
+
const oldCwd = join6(home, ".augmented", codeName, "project");
|
|
2046
|
+
const newCwd = join6(idPath, "project");
|
|
1991
2047
|
let codeNameKind;
|
|
1992
2048
|
try {
|
|
1993
2049
|
codeNameKind = lstatSync(codeNamePath).isSymbolicLink() ? "symlink" : "realdir";
|
|
@@ -2115,7 +2171,7 @@ function collectEnvGates(env) {
|
|
|
2115
2171
|
|
|
2116
2172
|
// ../../packages/core/dist/direct-chat/cursor-advance-telemetry.js
|
|
2117
2173
|
import { readFileSync as readFileSync7, writeFileSync as writeFileSync4 } from "fs";
|
|
2118
|
-
import { join as
|
|
2174
|
+
import { join as join7 } from "path";
|
|
2119
2175
|
var CURSOR_SHORTFALL_COUNTER_SUFFIX = "-cursor-advance-classifications.json";
|
|
2120
2176
|
function recordCursorAdvanceOutcome(agentDir, source, route, verdict) {
|
|
2121
2177
|
if (!agentDir)
|
|
@@ -2123,7 +2179,7 @@ function recordCursorAdvanceOutcome(agentDir, source, route, verdict) {
|
|
|
2123
2179
|
const key = cursorAdvanceCounterKey(route, verdict);
|
|
2124
2180
|
if (key === null)
|
|
2125
2181
|
return;
|
|
2126
|
-
const path =
|
|
2182
|
+
const path = join7(agentDir, `${source}${CURSOR_SHORTFALL_COUNTER_SUFFIX}`);
|
|
2127
2183
|
const counts = {};
|
|
2128
2184
|
try {
|
|
2129
2185
|
const parsed = JSON.parse(readFileSync7(path, "utf-8"));
|
|
@@ -2143,8 +2199,8 @@ function recordCursorAdvanceOutcome(agentDir, source, route, verdict) {
|
|
|
2143
2199
|
}
|
|
2144
2200
|
|
|
2145
2201
|
// src/lib/artifact-stream.ts
|
|
2146
|
-
import { join as
|
|
2147
|
-
import { homedir as
|
|
2202
|
+
import { join as join8 } from "path";
|
|
2203
|
+
import { homedir as homedir4 } from "os";
|
|
2148
2204
|
import { readdir, stat, readFile } from "fs/promises";
|
|
2149
2205
|
var ARTEFACT_ENTRY_FILE = "index.html";
|
|
2150
2206
|
function errMessage(err) {
|
|
@@ -2229,7 +2285,7 @@ var ArtifactStreamScanner = class {
|
|
|
2229
2285
|
return;
|
|
2230
2286
|
}
|
|
2231
2287
|
for (const name of names) {
|
|
2232
|
-
const file =
|
|
2288
|
+
const file = join8(this.artifactsDir, name, ARTEFACT_ENTRY_FILE);
|
|
2233
2289
|
const mtime = await this.fsDeps.mtimeMs(file).catch(() => null);
|
|
2234
2290
|
if (mtime === null) continue;
|
|
2235
2291
|
if (this.seenMtime.get(name) === mtime) continue;
|
|
@@ -2260,7 +2316,7 @@ var ArtifactStreamScanner = class {
|
|
|
2260
2316
|
}
|
|
2261
2317
|
};
|
|
2262
2318
|
function artifactsDirFor(codeName) {
|
|
2263
|
-
return
|
|
2319
|
+
return join8(homedir4(), ".augmented", codeName, "artifacts");
|
|
2264
2320
|
}
|
|
2265
2321
|
var nodeArtifactFs = {
|
|
2266
2322
|
async listArtefactNames(artifactsDir) {
|
|
@@ -2312,6 +2368,7 @@ async function maybeReportUsageBanner(args) {
|
|
|
2312
2368
|
const next = {
|
|
2313
2369
|
lastPct: existing?.lastPct ?? null,
|
|
2314
2370
|
lastWeekResetsAt: existing?.lastWeekResetsAt ?? null,
|
|
2371
|
+
lastLimitScope: existing?.lastLimitScope ?? null,
|
|
2315
2372
|
lastCheckedAt: nowMs
|
|
2316
2373
|
};
|
|
2317
2374
|
if (!tail) {
|
|
@@ -2326,7 +2383,7 @@ async function maybeReportUsageBanner(args) {
|
|
|
2326
2383
|
}
|
|
2327
2384
|
const observedAtIso = next.lastWeekResetsAt;
|
|
2328
2385
|
const weekResetsAtIso = observation.weekResetsAt.toISOString();
|
|
2329
|
-
if (existing && existing.lastPct === observation.pct && observedAtIso === weekResetsAtIso) {
|
|
2386
|
+
if (existing && existing.lastPct === observation.pct && observedAtIso === weekResetsAtIso && existing.lastLimitScope === observation.limitScope) {
|
|
2330
2387
|
state.set(codeName, next);
|
|
2331
2388
|
return;
|
|
2332
2389
|
}
|
|
@@ -2340,10 +2397,25 @@ async function maybeReportUsageBanner(args) {
|
|
|
2340
2397
|
// server cannot tell a measurement from a guess, which is how a reset
|
|
2341
2398
|
// three days early reached an operator as a precise timestamp.
|
|
2342
2399
|
reset_precision: observation.resetPrecision,
|
|
2400
|
+
// ENG-9007 wired the producer end. `classifyLimitScope` had been reading
|
|
2401
|
+
// the banner's qualifier and `parseUsageBanner` had been returning it on
|
|
2402
|
+
// every observation, but this POST never carried it — so the API's
|
|
2403
|
+
// validate-or-'unknown' contract (host-runtime.ts: an older host that
|
|
2404
|
+
// does not send it is not an error) resolved EVERY observation on the
|
|
2405
|
+
// fleet to `limit_scope: 'unknown'`, and every usage alert rendered
|
|
2406
|
+
// "banner qualifier not recognised, treated as weekly".
|
|
2407
|
+
//
|
|
2408
|
+
// That sentence was false on its face for the commonest banner of all —
|
|
2409
|
+
// "You've used 93% of your weekly limit", whose qualifier the parser
|
|
2410
|
+
// hard-codes to 'weekly'. Nothing was unrecognised; nobody had asked.
|
|
2411
|
+
// Sending the field is the whole fix: a session cap can now be told from
|
|
2412
|
+
// a weekly one, which is what ENG-9007 exists to do.
|
|
2413
|
+
limit_scope: observation.limitScope,
|
|
2343
2414
|
source: "pane_log"
|
|
2344
2415
|
});
|
|
2345
2416
|
next.lastPct = observation.pct;
|
|
2346
2417
|
next.lastWeekResetsAt = weekResetsAtIso;
|
|
2418
|
+
next.lastLimitScope = observation.limitScope;
|
|
2347
2419
|
state.set(codeName, next);
|
|
2348
2420
|
} catch (err) {
|
|
2349
2421
|
log2(`[usage-banner] POST /host/usage-observations failed for '${codeName}': ${err.message}`);
|
|
@@ -2354,13 +2426,13 @@ async function maybeReportUsageBanner(args) {
|
|
|
2354
2426
|
// src/lib/claude-account-fingerprint.ts
|
|
2355
2427
|
import { createHash as createHash6 } from "crypto";
|
|
2356
2428
|
import { readFile as readFile3, readdir as readdir3 } from "fs/promises";
|
|
2357
|
-
import { homedir as
|
|
2358
|
-
import { dirname as dirname4, join as
|
|
2429
|
+
import { homedir as homedir6, platform as platform2 } from "os";
|
|
2430
|
+
import { dirname as dirname4, join as join10 } from "path";
|
|
2359
2431
|
|
|
2360
2432
|
// src/lib/claude-auth-detect.ts
|
|
2361
2433
|
import { readFile as readFile2, readdir as readdir2 } from "fs/promises";
|
|
2362
|
-
import { homedir as
|
|
2363
|
-
import { join as
|
|
2434
|
+
import { homedir as homedir5, platform } from "os";
|
|
2435
|
+
import { join as join9 } from "path";
|
|
2364
2436
|
import { execFile } from "child_process";
|
|
2365
2437
|
import { promisify } from "util";
|
|
2366
2438
|
var execFileAsync = promisify(execFile);
|
|
@@ -2375,16 +2447,16 @@ async function detectClaudeAuth() {
|
|
|
2375
2447
|
}
|
|
2376
2448
|
async function findClaudeCredentialsPaths() {
|
|
2377
2449
|
const candidates = [
|
|
2378
|
-
|
|
2379
|
-
|
|
2450
|
+
join9(homedir5(), ".claude", ".credentials.json"),
|
|
2451
|
+
join9(homedir5(), ".claude", "credentials.json")
|
|
2380
2452
|
];
|
|
2381
2453
|
const isLinuxRoot = platform() === "linux" && typeof process.getuid === "function" && process.getuid() === 0;
|
|
2382
2454
|
if (isLinuxRoot) {
|
|
2383
2455
|
try {
|
|
2384
2456
|
const entries = await readdir2("/home", { withFileTypes: true });
|
|
2385
2457
|
for (const entry of entries.filter((entry2) => entry2.isDirectory()).sort((a, b) => a.name.localeCompare(b.name))) {
|
|
2386
|
-
candidates.push(
|
|
2387
|
-
candidates.push(
|
|
2458
|
+
candidates.push(join9("/home", entry.name, ".claude", ".credentials.json"));
|
|
2459
|
+
candidates.push(join9("/home", entry.name, ".claude", "credentials.json"));
|
|
2388
2460
|
}
|
|
2389
2461
|
} catch {
|
|
2390
2462
|
}
|
|
@@ -2462,13 +2534,13 @@ function parseExpiresAt(raw) {
|
|
|
2462
2534
|
|
|
2463
2535
|
// src/lib/claude-account-fingerprint.ts
|
|
2464
2536
|
async function candidateHomes() {
|
|
2465
|
-
const homes = [
|
|
2537
|
+
const homes = [homedir6()];
|
|
2466
2538
|
const isLinuxRoot = platform2() === "linux" && typeof process.getuid === "function" && process.getuid() === 0;
|
|
2467
2539
|
if (isLinuxRoot) {
|
|
2468
2540
|
try {
|
|
2469
2541
|
const entries = await readdir3("/home", { withFileTypes: true });
|
|
2470
2542
|
for (const entry of entries.filter((e) => e.isDirectory()).sort((a, b) => a.name.localeCompare(b.name))) {
|
|
2471
|
-
homes.push(
|
|
2543
|
+
homes.push(join10("/home", entry.name));
|
|
2472
2544
|
}
|
|
2473
2545
|
} catch {
|
|
2474
2546
|
}
|
|
@@ -2488,11 +2560,11 @@ async function homeOfActiveCredentials() {
|
|
|
2488
2560
|
async function claudeConfigCandidatePaths() {
|
|
2489
2561
|
const paths = [];
|
|
2490
2562
|
const configDir = process.env["CLAUDE_CONFIG_DIR"]?.trim();
|
|
2491
|
-
if (configDir) paths.push(
|
|
2563
|
+
if (configDir) paths.push(join10(configDir, ".claude.json"));
|
|
2492
2564
|
const activeHome = await homeOfActiveCredentials();
|
|
2493
|
-
if (activeHome) paths.push(
|
|
2565
|
+
if (activeHome) paths.push(join10(activeHome, ".claude.json"));
|
|
2494
2566
|
for (const home of await candidateHomes()) {
|
|
2495
|
-
const path =
|
|
2567
|
+
const path = join10(home, ".claude.json");
|
|
2496
2568
|
if (!paths.includes(path)) paths.push(path);
|
|
2497
2569
|
}
|
|
2498
2570
|
return paths;
|
|
@@ -2590,10 +2662,10 @@ function diffAuthTuples(recorded, current) {
|
|
|
2590
2662
|
|
|
2591
2663
|
// src/lib/account-enforcement-marker.ts
|
|
2592
2664
|
import { mkdirSync as mkdirSync4, renameSync as renameSync2, rmSync as rmSync2, writeFileSync as writeFileSync5 } from "fs";
|
|
2593
|
-
import { homedir as
|
|
2594
|
-
import { join as
|
|
2665
|
+
import { homedir as homedir7 } from "os";
|
|
2666
|
+
import { join as join11 } from "path";
|
|
2595
2667
|
function accountEnforcementMarkerPath(codeName) {
|
|
2596
|
-
return
|
|
2668
|
+
return join11(homedir7(), ".augmented", codeName, ACCOUNT_ENFORCEMENT_MARKER_FILENAME);
|
|
2597
2669
|
}
|
|
2598
2670
|
function syncAccountEnforcementMarker(codeName, level, log2 = (m) => process.stderr.write(`${m}
|
|
2599
2671
|
`), text) {
|
|
@@ -2601,8 +2673,8 @@ function syncAccountEnforcementMarker(codeName, level, log2 = (m) => process.std
|
|
|
2601
2673
|
clearAccountEnforcementMarker(codeName, log2);
|
|
2602
2674
|
return;
|
|
2603
2675
|
}
|
|
2604
|
-
const dir =
|
|
2605
|
-
const path =
|
|
2676
|
+
const dir = join11(homedir7(), ".augmented", codeName);
|
|
2677
|
+
const path = join11(dir, ACCOUNT_ENFORCEMENT_MARKER_FILENAME);
|
|
2606
2678
|
const tempPath = `${path}.${process.pid}.tmp`;
|
|
2607
2679
|
try {
|
|
2608
2680
|
mkdirSync4(dir, { recursive: true });
|
|
@@ -2628,7 +2700,7 @@ function clearAccountEnforcementMarker(codeName, log2 = (m) => process.stderr.wr
|
|
|
2628
2700
|
|
|
2629
2701
|
// src/lib/token-usage-monitor.ts
|
|
2630
2702
|
import { readdirSync, readFileSync as readFileSync8, statSync } from "fs";
|
|
2631
|
-
import { join as
|
|
2703
|
+
import { join as join12 } from "path";
|
|
2632
2704
|
var MIN_CHECK_INTERVAL_MS2 = 6e4;
|
|
2633
2705
|
var TRANSCRIPT_MTIME_WINDOW_MS = 2 * 24 * 60 * 60 * 1e3;
|
|
2634
2706
|
var MAX_ENTRIES_PER_POST = 200;
|
|
@@ -2657,7 +2729,7 @@ async function maybeReportTokenUsage(args) {
|
|
|
2657
2729
|
if (!name.endsWith(".jsonl")) continue;
|
|
2658
2730
|
const sessionId = name.slice(0, -".jsonl".length);
|
|
2659
2731
|
if (!sessionId) continue;
|
|
2660
|
-
const path =
|
|
2732
|
+
const path = join12(dir, name);
|
|
2661
2733
|
let st;
|
|
2662
2734
|
try {
|
|
2663
2735
|
st = statSync(path);
|
|
@@ -2755,7 +2827,7 @@ async function maybeReportTokenUsage(args) {
|
|
|
2755
2827
|
|
|
2756
2828
|
// src/lib/workflow-run-reconciler.ts
|
|
2757
2829
|
import { readdirSync as readdirSync2, readFileSync as readFileSync9, statSync as statSync2 } from "fs";
|
|
2758
|
-
import { join as
|
|
2830
|
+
import { join as join13 } from "path";
|
|
2759
2831
|
var MIN_CHECK_INTERVAL_MS3 = 5 * 6e4;
|
|
2760
2832
|
var SETTLE_MS = 3e4;
|
|
2761
2833
|
var TRANSCRIPT_MTIME_WINDOW_MS2 = 2 * 24 * 60 * 60 * 1e3;
|
|
@@ -2774,7 +2846,7 @@ function collectJsonlRecursive(dir, minMtimeMs, out, depth) {
|
|
|
2774
2846
|
return;
|
|
2775
2847
|
}
|
|
2776
2848
|
for (const name of entries) {
|
|
2777
|
-
const p =
|
|
2849
|
+
const p = join13(dir, name);
|
|
2778
2850
|
let st;
|
|
2779
2851
|
try {
|
|
2780
2852
|
st = statSync2(p);
|
|
@@ -2797,7 +2869,7 @@ function enumerateTranscriptFiles(transcriptDir, nowMs, minMtimeMs = nowMs - TRA
|
|
|
2797
2869
|
return out;
|
|
2798
2870
|
}
|
|
2799
2871
|
for (const name of entries) {
|
|
2800
|
-
const path =
|
|
2872
|
+
const path = join13(transcriptDir, name);
|
|
2801
2873
|
let st;
|
|
2802
2874
|
try {
|
|
2803
2875
|
st = statSync2(path);
|
|
@@ -2809,7 +2881,7 @@ function enumerateTranscriptFiles(transcriptDir, nowMs, minMtimeMs = nowMs - TRA
|
|
|
2809
2881
|
continue;
|
|
2810
2882
|
}
|
|
2811
2883
|
if (st.isDirectory()) {
|
|
2812
|
-
collectJsonlRecursive(
|
|
2884
|
+
collectJsonlRecursive(join13(path, "subagents"), minMtimeMs, out, 0);
|
|
2813
2885
|
}
|
|
2814
2886
|
}
|
|
2815
2887
|
return out;
|
|
@@ -2900,7 +2972,7 @@ async function maybeReconcileWorkflowRunTokens(args) {
|
|
|
2900
2972
|
|
|
2901
2973
|
// src/lib/conversation-evaluator.ts
|
|
2902
2974
|
import { readdirSync as readdirSync3, readFileSync as readFileSync10, statSync as statSync3 } from "fs";
|
|
2903
|
-
import { join as
|
|
2975
|
+
import { join as join14 } from "path";
|
|
2904
2976
|
var MIN_CHECK_INTERVAL_MS4 = 5 * 6e4;
|
|
2905
2977
|
var TRANSCRIPT_MTIME_WINDOW_MS3 = 7 * 24 * 60 * 60 * 1e3;
|
|
2906
2978
|
var WINDOW_PAD_MS = 5 * 6e4;
|
|
@@ -3336,7 +3408,7 @@ function readRecentTurns(dir, nowMs) {
|
|
|
3336
3408
|
return;
|
|
3337
3409
|
}
|
|
3338
3410
|
for (const ent of entries) {
|
|
3339
|
-
const full =
|
|
3411
|
+
const full = join14(d, ent.name);
|
|
3340
3412
|
if (ent.isDirectory()) {
|
|
3341
3413
|
visit(full);
|
|
3342
3414
|
continue;
|
|
@@ -3641,18 +3713,18 @@ async function reportSkip2(api2, agentId, conversationId, log2, codeName) {
|
|
|
3641
3713
|
}
|
|
3642
3714
|
|
|
3643
3715
|
// src/lib/tool-call-audit.ts
|
|
3644
|
-
import { homedir as
|
|
3645
|
-
import { join as
|
|
3716
|
+
import { homedir as homedir11 } from "os";
|
|
3717
|
+
import { join as join19 } from "path";
|
|
3646
3718
|
|
|
3647
3719
|
// src/lib/agent-logging-mode.ts
|
|
3648
3720
|
import { readFileSync as readFileSync11 } from "fs";
|
|
3649
|
-
import { homedir as
|
|
3650
|
-
import { join as
|
|
3721
|
+
import { homedir as homedir8 } from "os";
|
|
3722
|
+
import { join as join15 } from "path";
|
|
3651
3723
|
var LOGGING_MODES = ["hash-only", "redacted", "full-local"];
|
|
3652
3724
|
function charterPath(codeName, homeDir) {
|
|
3653
|
-
const home = homeDir ?? (process.env["HOME"]?.trim() ||
|
|
3725
|
+
const home = homeDir ?? (process.env["HOME"]?.trim() || homedir8());
|
|
3654
3726
|
const key = agentRuntimeKey(codeName, homeDir);
|
|
3655
|
-
return
|
|
3727
|
+
return join15(home, ".augmented", key, "provision", "CHARTER.md");
|
|
3656
3728
|
}
|
|
3657
3729
|
function readAgentLoggingMode(codeName, homeDir) {
|
|
3658
3730
|
let raw;
|
|
@@ -3682,14 +3754,14 @@ function loggingModeWithholdsTargets(reading) {
|
|
|
3682
3754
|
// src/lib/tool-call-path-salt.ts
|
|
3683
3755
|
import { randomBytes } from "crypto";
|
|
3684
3756
|
import { existsSync as existsSync3, mkdirSync as mkdirSync5, readFileSync as readFileSync12, renameSync as renameSync3, unlinkSync, writeFileSync as writeFileSync6 } from "fs";
|
|
3685
|
-
import { homedir as
|
|
3686
|
-
import { dirname as dirname5, join as
|
|
3757
|
+
import { homedir as homedir9 } from "os";
|
|
3758
|
+
import { dirname as dirname5, join as join16 } from "path";
|
|
3687
3759
|
var SALT_BYTES = 32;
|
|
3688
3760
|
var SALT_RE = /^[0-9a-f]{64}$/;
|
|
3689
3761
|
function pathSaltPath(codeName, homeDir) {
|
|
3690
|
-
const home = homeDir ?? (process.env["HOME"]?.trim() ||
|
|
3762
|
+
const home = homeDir ?? (process.env["HOME"]?.trim() || homedir9());
|
|
3691
3763
|
const key = agentRuntimeKey(codeName, homeDir);
|
|
3692
|
-
return
|
|
3764
|
+
return join16(home, ".augmented", key, "tool-call-path-salt");
|
|
3693
3765
|
}
|
|
3694
3766
|
function readToolCallPathSalt(codeName, homeDir) {
|
|
3695
3767
|
let file;
|
|
@@ -3766,7 +3838,7 @@ function readHostArchiveAddress(path) {
|
|
|
3766
3838
|
|
|
3767
3839
|
// src/lib/tool-call-extractor.ts
|
|
3768
3840
|
import { closeSync, fstatSync, openSync, readFileSync as readFileSync14, readSync, readdirSync as readdirSync4 } from "fs";
|
|
3769
|
-
import { basename, join as
|
|
3841
|
+
import { basename, join as join17, relative } from "path";
|
|
3770
3842
|
import { StringDecoder } from "string_decoder";
|
|
3771
3843
|
|
|
3772
3844
|
// src/lib/tool-call-redaction.ts
|
|
@@ -3895,7 +3967,7 @@ function redactToolTargetInner(toolName, input, ctx) {
|
|
|
3895
3967
|
var EXTRACTOR_VERSION = "e1";
|
|
3896
3968
|
function enumerateSessionTranscripts(transcriptDir, sessionId, projectsRoot) {
|
|
3897
3969
|
const files = [];
|
|
3898
|
-
const mainAbs =
|
|
3970
|
+
const mainAbs = join17(transcriptDir, `${sessionId}.jsonl`);
|
|
3899
3971
|
files.push({
|
|
3900
3972
|
absPath: mainAbs,
|
|
3901
3973
|
relPath: relative(projectsRoot, mainAbs),
|
|
@@ -3903,7 +3975,7 @@ function enumerateSessionTranscripts(transcriptDir, sessionId, projectsRoot) {
|
|
|
3903
3975
|
isSubagent: false,
|
|
3904
3976
|
subagentId: null
|
|
3905
3977
|
});
|
|
3906
|
-
const subDir =
|
|
3978
|
+
const subDir = join17(transcriptDir, sessionId, "subagents");
|
|
3907
3979
|
let entries;
|
|
3908
3980
|
try {
|
|
3909
3981
|
entries = readdirSync4(subDir);
|
|
@@ -3912,7 +3984,7 @@ function enumerateSessionTranscripts(transcriptDir, sessionId, projectsRoot) {
|
|
|
3912
3984
|
}
|
|
3913
3985
|
for (const name of entries) {
|
|
3914
3986
|
if (!name.endsWith(".jsonl")) continue;
|
|
3915
|
-
const abs =
|
|
3987
|
+
const abs = join17(subDir, name);
|
|
3916
3988
|
const stem = basename(name, ".jsonl");
|
|
3917
3989
|
files.push({
|
|
3918
3990
|
absPath: abs,
|
|
@@ -4111,8 +4183,8 @@ function extractTranscriptWindow(file, opts, from) {
|
|
|
4111
4183
|
|
|
4112
4184
|
// src/lib/tool-call-cursor.ts
|
|
4113
4185
|
import { existsSync as existsSync4, readFileSync as readFileSync15 } from "fs";
|
|
4114
|
-
import { homedir as
|
|
4115
|
-
import { join as
|
|
4186
|
+
import { homedir as homedir10 } from "os";
|
|
4187
|
+
import { join as join18 } from "path";
|
|
4116
4188
|
var COVERAGE_DISPOSITIONS = [
|
|
4117
4189
|
"ok",
|
|
4118
4190
|
"not_entitled",
|
|
@@ -4165,9 +4237,9 @@ function parseCursorKey(key) {
|
|
|
4165
4237
|
return { sessionId: sessionId.length > 0 ? sessionId : null, transcriptRef: key.slice(i + 1) };
|
|
4166
4238
|
}
|
|
4167
4239
|
function cursorStatePath(codeName, homeDir) {
|
|
4168
|
-
const home = homeDir ?? (process.env["HOME"]?.trim() ||
|
|
4240
|
+
const home = homeDir ?? (process.env["HOME"]?.trim() || homedir10());
|
|
4169
4241
|
const key = agentRuntimeKey(codeName, homeDir);
|
|
4170
|
-
return
|
|
4242
|
+
return join18(home, ".augmented", key, "tool-call-cursors.json");
|
|
4171
4243
|
}
|
|
4172
4244
|
function loadCursors(path) {
|
|
4173
4245
|
const out = /* @__PURE__ */ new Map();
|
|
@@ -4579,8 +4651,8 @@ async function maybeScanToolCalls(args) {
|
|
|
4579
4651
|
if (!salt && !hashOnly) {
|
|
4580
4652
|
log2(`[tool-call-audit] ${codeName}: no path-hash salt available \u2014 file targets withheld`);
|
|
4581
4653
|
}
|
|
4582
|
-
const home = args.homeDir ?? (process.env["HOME"]?.trim() ||
|
|
4583
|
-
const projectsRoot = args.projectsRoot ??
|
|
4654
|
+
const home = args.homeDir ?? (process.env["HOME"]?.trim() || homedir11());
|
|
4655
|
+
const projectsRoot = args.projectsRoot ?? join19(home, ".claude", "projects");
|
|
4584
4656
|
const transcriptDir = args.transcriptDir ?? sessionTranscriptDir(getProjectDir(codeName));
|
|
4585
4657
|
const current = peekCurrentSession(codeName);
|
|
4586
4658
|
const sessionIds = current ? [current.sessionId] : [];
|
|
@@ -4610,10 +4682,10 @@ async function maybeScanToolCalls(args) {
|
|
|
4610
4682
|
|
|
4611
4683
|
// src/lib/activity-cache-monitor.ts
|
|
4612
4684
|
import { existsSync as existsSync5, readFileSync as readFileSync16 } from "fs";
|
|
4613
|
-
import { homedir as
|
|
4614
|
-
import { join as
|
|
4685
|
+
import { homedir as homedir12 } from "os";
|
|
4686
|
+
import { join as join20 } from "path";
|
|
4615
4687
|
var MIN_CHECK_INTERVAL_MS7 = 6e4;
|
|
4616
|
-
var STATS_CACHE_PATH =
|
|
4688
|
+
var STATS_CACHE_PATH = join20(homedir12(), ".claude", "stats-cache.json");
|
|
4617
4689
|
var ISO_DATE_RE = /^\d{4}-\d{2}-\d{2}$/;
|
|
4618
4690
|
var state6 = { lastObservedDate: null, lastCheckedAt: 0 };
|
|
4619
4691
|
function selectNewDailyRows(raw, lastObservedDate) {
|
|
@@ -4894,10 +4966,10 @@ function computeChannelConfigHash(input) {
|
|
|
4894
4966
|
|
|
4895
4967
|
// src/lib/channel-hash-cache.ts
|
|
4896
4968
|
import { existsSync as existsSync6, readFileSync as readFileSync17, writeFileSync as writeFileSync7 } from "fs";
|
|
4897
|
-
import { join as
|
|
4969
|
+
import { join as join21 } from "path";
|
|
4898
4970
|
var CACHE_FILENAME = "channel-hash-cache.json";
|
|
4899
4971
|
function getChannelHashCacheFile(configDir) {
|
|
4900
|
-
return
|
|
4972
|
+
return join21(configDir, CACHE_FILENAME);
|
|
4901
4973
|
}
|
|
4902
4974
|
function loadChannelHashCache(target, configDir) {
|
|
4903
4975
|
const path = getChannelHashCacheFile(configDir);
|
|
@@ -4925,7 +4997,7 @@ function saveChannelHashCache(source, configDir) {
|
|
|
4925
4997
|
|
|
4926
4998
|
// src/lib/sender-policy-baseline.ts
|
|
4927
4999
|
import { existsSync as existsSync7, readFileSync as readFileSync18 } from "fs";
|
|
4928
|
-
import { join as
|
|
5000
|
+
import { join as join22 } from "path";
|
|
4929
5001
|
var BASELINE_FILENAME = "sender-policy-baseline.json";
|
|
4930
5002
|
var SENDER_POLICY_BASELINE_VERSION = 1;
|
|
4931
5003
|
var BASELINE_CONCERNS = ["senderPolicy", "slackBehaviour", "msteamsBehaviour"];
|
|
@@ -4937,7 +5009,7 @@ function createDeliveryBaselineMaps() {
|
|
|
4937
5009
|
};
|
|
4938
5010
|
}
|
|
4939
5011
|
function getSenderPolicyBaselineFile(configDir) {
|
|
4940
|
-
return
|
|
5012
|
+
return join22(configDir, BASELINE_FILENAME);
|
|
4941
5013
|
}
|
|
4942
5014
|
function loadSenderPolicyBaseline(target, configDir, log2) {
|
|
4943
5015
|
const path = getSenderPolicyBaselineFile(configDir);
|
|
@@ -5467,7 +5539,7 @@ function planGlobalSkillSync(globalSkills, prevIds, hashOf, knownHash, options)
|
|
|
5467
5539
|
}
|
|
5468
5540
|
|
|
5469
5541
|
// src/lib/manager/integration-skill-cache.ts
|
|
5470
|
-
import { join as
|
|
5542
|
+
import { join as join23 } from "path";
|
|
5471
5543
|
function integrationSkillHashKey(agentId, skillId) {
|
|
5472
5544
|
return `plugin-skill:${agentId}:${skillId}`;
|
|
5473
5545
|
}
|
|
@@ -5483,16 +5555,16 @@ function forgetIntegrationSkill(cache3, agentId, skillId) {
|
|
|
5483
5555
|
function removeIntegrationSkillFolder(opts) {
|
|
5484
5556
|
forgetIntegrationSkill(opts.cache, opts.agentId, opts.entry);
|
|
5485
5557
|
for (const dir of opts.dirs) {
|
|
5486
|
-
opts.removeDir(
|
|
5558
|
+
opts.removeDir(join23(dir, opts.entry));
|
|
5487
5559
|
}
|
|
5488
5560
|
}
|
|
5489
5561
|
|
|
5490
5562
|
// src/lib/manager/managed-skill-manifest.ts
|
|
5491
5563
|
import { existsSync as existsSync8, mkdirSync as mkdirSync6, readFileSync as readFileSync19, writeFileSync as writeFileSync8 } from "fs";
|
|
5492
|
-
import { dirname as dirname6, join as
|
|
5564
|
+
import { dirname as dirname6, join as join24 } from "path";
|
|
5493
5565
|
var MANIFEST_VERSION = 1;
|
|
5494
5566
|
function managedSkillManifestPath(agentRootDir) {
|
|
5495
|
-
return
|
|
5567
|
+
return join24(agentRootDir, "managed-skills.json");
|
|
5496
5568
|
}
|
|
5497
5569
|
function readManagedSkillManifest(path) {
|
|
5498
5570
|
try {
|
|
@@ -5590,7 +5662,7 @@ function resolveModelChain(refreshData) {
|
|
|
5590
5662
|
const modelDefaults = refreshData.model_defaults;
|
|
5591
5663
|
const platform3 = modelDefaults?.platform ?? {};
|
|
5592
5664
|
const org = modelDefaults?.org ?? {};
|
|
5593
|
-
function
|
|
5665
|
+
function resolve2(tier) {
|
|
5594
5666
|
const agentField = `${tier}_model`;
|
|
5595
5667
|
const platformField = `default_${tier}_model`;
|
|
5596
5668
|
const agentVal = agent?.[agentField];
|
|
@@ -5602,16 +5674,16 @@ function resolveModelChain(refreshData) {
|
|
|
5602
5674
|
return void 0;
|
|
5603
5675
|
}
|
|
5604
5676
|
return {
|
|
5605
|
-
primary:
|
|
5606
|
-
secondary:
|
|
5607
|
-
tertiary:
|
|
5677
|
+
primary: resolve2("primary"),
|
|
5678
|
+
secondary: resolve2("secondary"),
|
|
5679
|
+
tertiary: resolve2("tertiary")
|
|
5608
5680
|
};
|
|
5609
5681
|
}
|
|
5610
5682
|
|
|
5611
5683
|
// src/lib/manager/claude-auth.ts
|
|
5612
5684
|
import { existsSync as existsSync9, rmSync as rmSync3 } from "fs";
|
|
5613
|
-
import { join as
|
|
5614
|
-
import { homedir as
|
|
5685
|
+
import { join as join25 } from "path";
|
|
5686
|
+
import { homedir as homedir13 } from "os";
|
|
5615
5687
|
async function applyClaudeAuthToEnv(childEnv, label) {
|
|
5616
5688
|
const apiKey = getApiKey();
|
|
5617
5689
|
if (!apiKey) {
|
|
@@ -5623,9 +5695,9 @@ async function applyClaudeAuthToEnv(childEnv, label) {
|
|
|
5623
5695
|
throw new Error("claude_auth_mode=api_key but /host/exchange returned no decrypted key");
|
|
5624
5696
|
}
|
|
5625
5697
|
childEnv.ANTHROPIC_API_KEY = exchange.anthropicApiKey;
|
|
5626
|
-
const claudeDir =
|
|
5698
|
+
const claudeDir = join25(homedir13(), ".claude");
|
|
5627
5699
|
for (const filename of [".credentials.json", "credentials.json"]) {
|
|
5628
|
-
const p =
|
|
5700
|
+
const p = join25(claudeDir, filename);
|
|
5629
5701
|
if (existsSync9(p)) {
|
|
5630
5702
|
try {
|
|
5631
5703
|
rmSync3(p, { force: true });
|
|
@@ -5708,7 +5780,7 @@ function heartbeatRuntimeAuthFields(probeVerdict) {
|
|
|
5708
5780
|
|
|
5709
5781
|
// src/lib/manager/kanban/parsers.ts
|
|
5710
5782
|
import { existsSync as existsSync10, readFileSync as readFileSync20 } from "fs";
|
|
5711
|
-
import { join as
|
|
5783
|
+
import { join as join26 } from "path";
|
|
5712
5784
|
var STANDUP_TEMPLATES = /* @__PURE__ */ new Set(["daily-standup", "end-of-day-summary"]);
|
|
5713
5785
|
var TASK_UPDATE_TEMPLATES = /* @__PURE__ */ new Set(["hourly-status", "task-update"]);
|
|
5714
5786
|
var PLAN_TEMPLATES = /* @__PURE__ */ new Set(["morning-plan"]);
|
|
@@ -5860,8 +5932,8 @@ function getBuiltInSkillContent(skillId) {
|
|
|
5860
5932
|
if (builtInSkillCache.has(skillId)) return builtInSkillCache.get(skillId);
|
|
5861
5933
|
try {
|
|
5862
5934
|
const candidates = [
|
|
5863
|
-
|
|
5864
|
-
|
|
5935
|
+
join26(process.cwd(), "skills", skillId, "SKILL.md"),
|
|
5936
|
+
join26(new URL(".", import.meta.url).pathname, "..", "..", "..", "..", "..", "..", "skills", skillId, "SKILL.md")
|
|
5865
5937
|
];
|
|
5866
5938
|
for (const candidate of candidates) {
|
|
5867
5939
|
if (existsSync10(candidate)) {
|
|
@@ -6007,11 +6079,11 @@ function formatBoardForPrompt(items, template) {
|
|
|
6007
6079
|
|
|
6008
6080
|
// src/lib/manager/kanban/nudge-state-cache.ts
|
|
6009
6081
|
import { existsSync as existsSync11, readFileSync as readFileSync21, writeFileSync as writeFileSync9 } from "fs";
|
|
6010
|
-
import { join as
|
|
6082
|
+
import { join as join27 } from "path";
|
|
6011
6083
|
var CACHE_FILENAME2 = "kanban-nudge-state.json";
|
|
6012
6084
|
var KANBAN_NUDGE_STATE_VERSION = 1;
|
|
6013
6085
|
function getKanbanNudgeStateFile(configDir) {
|
|
6014
|
-
return
|
|
6086
|
+
return join27(configDir, CACHE_FILENAME2);
|
|
6015
6087
|
}
|
|
6016
6088
|
function loadKanbanNudgeState(target, configDir) {
|
|
6017
6089
|
const path = getKanbanNudgeStateFile(configDir);
|
|
@@ -6228,7 +6300,7 @@ async function maybePostSlackThreadHint(agentCodeName, channelId, primaryTs) {
|
|
|
6228
6300
|
// src/lib/manager/channels/telegram.ts
|
|
6229
6301
|
import https from "https";
|
|
6230
6302
|
function telegramApiCall(botToken, method, body) {
|
|
6231
|
-
return new Promise((
|
|
6303
|
+
return new Promise((resolve2, reject) => {
|
|
6232
6304
|
const postData = JSON.stringify(body);
|
|
6233
6305
|
const req = https.request({
|
|
6234
6306
|
hostname: "api.telegram.org",
|
|
@@ -6245,7 +6317,7 @@ function telegramApiCall(botToken, method, body) {
|
|
|
6245
6317
|
});
|
|
6246
6318
|
res.on("end", () => {
|
|
6247
6319
|
try {
|
|
6248
|
-
|
|
6320
|
+
resolve2(JSON.parse(data));
|
|
6249
6321
|
} catch {
|
|
6250
6322
|
reject(new Error("Invalid JSON from Telegram API"));
|
|
6251
6323
|
}
|
|
@@ -6552,7 +6624,7 @@ async function finishRun(runId, outcome, options = {}) {
|
|
|
6552
6624
|
log(
|
|
6553
6625
|
`[runs] finish attempt ${attempt + 1}/${maxRetries + 1} failed for run_id=${runId} outcome=${outcome} status=${status} error_id=${errId} \u2014 retrying`
|
|
6554
6626
|
);
|
|
6555
|
-
await new Promise((
|
|
6627
|
+
await new Promise((resolve2) => setTimeout(resolve2, baseMs * 2 ** attempt));
|
|
6556
6628
|
continue;
|
|
6557
6629
|
}
|
|
6558
6630
|
log(
|
|
@@ -6637,8 +6709,8 @@ function closeSessionRunForCode(codeName, outcome, reason) {
|
|
|
6637
6709
|
// src/lib/manager/scheduler/kanban-route.ts
|
|
6638
6710
|
import { createHash as createHash12 } from "crypto";
|
|
6639
6711
|
import { writeFileSync as writeFileSync10, renameSync as renameSync4, mkdirSync as mkdirSync7, readFileSync as readFileSync22, unlinkSync as unlinkSync2 } from "fs";
|
|
6640
|
-
import { homedir as
|
|
6641
|
-
import { join as
|
|
6712
|
+
import { homedir as homedir14 } from "os";
|
|
6713
|
+
import { join as join28, dirname as dirname7 } from "path";
|
|
6642
6714
|
|
|
6643
6715
|
// src/lib/manager/scheduler/notify.ts
|
|
6644
6716
|
import { createHash as createHash11 } from "crypto";
|
|
@@ -6997,7 +7069,7 @@ function resolveScheduledSlackTarget(task) {
|
|
|
6997
7069
|
}
|
|
6998
7070
|
function stampScheduledTurnMarker(codeName, taskId, target) {
|
|
6999
7071
|
try {
|
|
7000
|
-
const file =
|
|
7072
|
+
const file = join28(homedir14(), ".augmented", codeName, SCHEDULED_TURN_MARKER_FILENAME);
|
|
7001
7073
|
const marker = { ts: Date.now(), task_id: taskId, ...target ? { target } : {} };
|
|
7002
7074
|
const tmp = `${file}.tmp`;
|
|
7003
7075
|
writeFileSync10(tmp, JSON.stringify(marker), "utf8");
|
|
@@ -7007,7 +7079,7 @@ function stampScheduledTurnMarker(codeName, taskId, target) {
|
|
|
7007
7079
|
}
|
|
7008
7080
|
}
|
|
7009
7081
|
function clearScheduledTurnMarkerForTask(codeName, taskId) {
|
|
7010
|
-
const file =
|
|
7082
|
+
const file = join28(homedir14(), ".augmented", codeName, SCHEDULED_TURN_MARKER_FILENAME);
|
|
7011
7083
|
try {
|
|
7012
7084
|
const raw = JSON.parse(readFileSync22(file, "utf8"));
|
|
7013
7085
|
if (typeof raw?.task_id !== "string" || raw.task_id !== taskId) return;
|
|
@@ -7069,7 +7141,7 @@ async function routeScheduledTaskViaKanban(codeName, agentId, task, prompt, dura
|
|
|
7069
7141
|
return false;
|
|
7070
7142
|
}
|
|
7071
7143
|
try {
|
|
7072
|
-
const doorbell = directChatDoorbellPath(agentId,
|
|
7144
|
+
const doorbell = directChatDoorbellPath(agentId, homedir14());
|
|
7073
7145
|
mkdirSync7(dirname7(doorbell), { recursive: true });
|
|
7074
7146
|
writeFileSync10(doorbell, String(Date.now()));
|
|
7075
7147
|
} catch (err) {
|
|
@@ -7221,12 +7293,12 @@ async function processClaudeTaskResult(codeName, agentId, templateId, rawOutput,
|
|
|
7221
7293
|
|
|
7222
7294
|
// src/lib/manager/scheduler/execution.ts
|
|
7223
7295
|
import { createHash as createHash13 } from "crypto";
|
|
7224
|
-
import { homedir as
|
|
7225
|
-
import { join as
|
|
7296
|
+
import { homedir as homedir15 } from "os";
|
|
7297
|
+
import { join as join30 } from "path";
|
|
7226
7298
|
|
|
7227
7299
|
// src/lib/agent-serving-probe.ts
|
|
7228
7300
|
import { readFileSync as readFileSync23, readdirSync as readdirSync5, statSync as statSync5 } from "fs";
|
|
7229
|
-
import { join as
|
|
7301
|
+
import { join as join29 } from "path";
|
|
7230
7302
|
var RATE_LIMIT_WINDOW_MS = 6 * 60 * 60 * 1e3;
|
|
7231
7303
|
function probeRateLimit(args) {
|
|
7232
7304
|
const now = args.now ?? /* @__PURE__ */ new Date();
|
|
@@ -7242,7 +7314,7 @@ function probeRateLimit(args) {
|
|
|
7242
7314
|
let newest = UNKNOWN_RATE_LIMIT;
|
|
7243
7315
|
for (const name of entries) {
|
|
7244
7316
|
if (!name.endsWith(".jsonl")) continue;
|
|
7245
|
-
const path =
|
|
7317
|
+
const path = join29(dir, name);
|
|
7246
7318
|
try {
|
|
7247
7319
|
const st = statSync5(path);
|
|
7248
7320
|
if (!st.isFile() || st.mtimeMs < startMs) continue;
|
|
@@ -7313,7 +7385,7 @@ function shouldLogUsageCapDeferral(site, codeName, limitedUntil) {
|
|
|
7313
7385
|
|
|
7314
7386
|
// src/lib/manager/scheduler/execution.ts
|
|
7315
7387
|
function claudePidFilePath() {
|
|
7316
|
-
return
|
|
7388
|
+
return join30(homedir15(), ".augmented", "manager-claude-pids.json");
|
|
7317
7389
|
}
|
|
7318
7390
|
var inFlightClaudePids = /* @__PURE__ */ new Map();
|
|
7319
7391
|
function registerClaudeSpawn(record) {
|
|
@@ -7384,7 +7456,7 @@ async function syncAndCheckClaudeScheduler(agent, tasks, boardItems, refreshData
|
|
|
7384
7456
|
|
|
7385
7457
|
// src/lib/occupancy-gate.ts
|
|
7386
7458
|
import { closeSync as closeSync2, openSync as openSync2, readdirSync as readdirSync6, readSync as readSync2, statSync as statSync6 } from "fs";
|
|
7387
|
-
import { join as
|
|
7459
|
+
import { join as join31 } from "path";
|
|
7388
7460
|
function rostersMeasuredZero(mode, attested, runtimeRunning) {
|
|
7389
7461
|
return mode === "enforce" && attested && runtimeRunning;
|
|
7390
7462
|
}
|
|
@@ -7473,10 +7545,10 @@ function candidateTranscriptPaths(dir) {
|
|
|
7473
7545
|
let complete = true;
|
|
7474
7546
|
for (const name of top) {
|
|
7475
7547
|
if (name.endsWith(".jsonl")) {
|
|
7476
|
-
paths.push(
|
|
7548
|
+
paths.push(join31(dir, name));
|
|
7477
7549
|
continue;
|
|
7478
7550
|
}
|
|
7479
|
-
const subDir =
|
|
7551
|
+
const subDir = join31(dir, name, "subagents");
|
|
7480
7552
|
let subs;
|
|
7481
7553
|
try {
|
|
7482
7554
|
subs = readdirSync6(subDir);
|
|
@@ -7485,7 +7557,7 @@ function candidateTranscriptPaths(dir) {
|
|
|
7485
7557
|
continue;
|
|
7486
7558
|
}
|
|
7487
7559
|
for (const sub of subs) {
|
|
7488
|
-
if (sub.endsWith(".jsonl")) paths.push(
|
|
7560
|
+
if (sub.endsWith(".jsonl")) paths.push(join31(subDir, sub));
|
|
7489
7561
|
}
|
|
7490
7562
|
}
|
|
7491
7563
|
return { paths, complete };
|
|
@@ -8969,7 +9041,7 @@ async function fireOpencodeScheduledTask(agent, task) {
|
|
|
8969
9041
|
import { createHash as createHash16 } from "crypto";
|
|
8970
9042
|
import { existsSync as existsSync13, mkdirSync as mkdirSync8, readFileSync as readFileSync25, renameSync as renameSync5, unlinkSync as unlinkSync3, writeFileSync as writeFileSync11 } from "fs";
|
|
8971
9043
|
import { randomUUID } from "crypto";
|
|
8972
|
-
import { join as
|
|
9044
|
+
import { join as join32 } from "path";
|
|
8973
9045
|
|
|
8974
9046
|
// src/lib/telegram-ingest.ts
|
|
8975
9047
|
import https2 from "https";
|
|
@@ -9191,7 +9263,7 @@ function buildTelegramPeerClassifierConfigFromEnv(env, opts) {
|
|
|
9191
9263
|
}
|
|
9192
9264
|
|
|
9193
9265
|
// src/lib/telegram-ingest.ts
|
|
9194
|
-
var nodeHttpsTelegramFetch = (url, init) => new Promise((
|
|
9266
|
+
var nodeHttpsTelegramFetch = (url, init) => new Promise((resolve2, reject) => {
|
|
9195
9267
|
const u = new URL(url);
|
|
9196
9268
|
const body = init?.body;
|
|
9197
9269
|
const headers = { ...init?.headers ?? {} };
|
|
@@ -9217,7 +9289,7 @@ var nodeHttpsTelegramFetch = (url, init) => new Promise((resolve, reject) => {
|
|
|
9217
9289
|
});
|
|
9218
9290
|
res.on("end", () => {
|
|
9219
9291
|
const status = res.statusCode ?? 0;
|
|
9220
|
-
|
|
9292
|
+
resolve2({
|
|
9221
9293
|
ok: status >= 200 && status < 300,
|
|
9222
9294
|
status,
|
|
9223
9295
|
json: async () => JSON.parse(data.length > 0 ? data : "{}")
|
|
@@ -9406,8 +9478,8 @@ function defaultAddReaction2(botToken, fetchImpl, log2) {
|
|
|
9406
9478
|
};
|
|
9407
9479
|
}
|
|
9408
9480
|
function sleep(ms) {
|
|
9409
|
-
return new Promise((
|
|
9410
|
-
setTimeout(
|
|
9481
|
+
return new Promise((resolve2) => {
|
|
9482
|
+
setTimeout(resolve2, ms).unref?.();
|
|
9411
9483
|
});
|
|
9412
9484
|
}
|
|
9413
9485
|
function startTelegramIngest(config2) {
|
|
@@ -9517,7 +9589,7 @@ function createFileOffsetStore(codeName, log2, currentBotId) {
|
|
|
9517
9589
|
let filePath;
|
|
9518
9590
|
try {
|
|
9519
9591
|
dir = getFramework("opencode").getAgentDir(codeName);
|
|
9520
|
-
filePath =
|
|
9592
|
+
filePath = join32(dir, "telegram-getupdates-offset-opencode.json");
|
|
9521
9593
|
} catch {
|
|
9522
9594
|
dir = null;
|
|
9523
9595
|
filePath = null;
|
|
@@ -9797,14 +9869,14 @@ function partitionActionableByPoison(actionable, states, config2) {
|
|
|
9797
9869
|
|
|
9798
9870
|
// src/lib/restart-flags.ts
|
|
9799
9871
|
import { existsSync as existsSync14, mkdirSync as mkdirSync9, readdirSync as readdirSync7, readFileSync as readFileSync26, renameSync as renameSync6, rmSync as rmSync4, writeFileSync as writeFileSync12 } from "fs";
|
|
9800
|
-
import { homedir as
|
|
9801
|
-
import { join as
|
|
9872
|
+
import { homedir as homedir16 } from "os";
|
|
9873
|
+
import { join as join33 } from "path";
|
|
9802
9874
|
import { randomUUID as randomUUID2 } from "crypto";
|
|
9803
9875
|
function restartFlagsDir() {
|
|
9804
|
-
return
|
|
9876
|
+
return join33(homedir16(), ".augmented", "restart-flags");
|
|
9805
9877
|
}
|
|
9806
9878
|
function flagPath(codeName) {
|
|
9807
|
-
return
|
|
9879
|
+
return join33(restartFlagsDir(), `${codeName}.flag`);
|
|
9808
9880
|
}
|
|
9809
9881
|
function readRestartFlags() {
|
|
9810
9882
|
const dir = restartFlagsDir();
|
|
@@ -9813,7 +9885,7 @@ function readRestartFlags() {
|
|
|
9813
9885
|
for (const entry of readdirSync7(dir)) {
|
|
9814
9886
|
if (!entry.endsWith(".flag")) continue;
|
|
9815
9887
|
try {
|
|
9816
|
-
const raw = readFileSync26(
|
|
9888
|
+
const raw = readFileSync26(join33(dir, entry), "utf8");
|
|
9817
9889
|
const parsed = JSON.parse(raw);
|
|
9818
9890
|
if (typeof parsed.codeName !== "string" || parsed.codeName.length === 0) {
|
|
9819
9891
|
parsed.codeName = entry.replace(/\.flag$/, "");
|
|
@@ -9932,7 +10004,7 @@ async function sendError(flag, opts, text) {
|
|
|
9932
10004
|
|
|
9933
10005
|
// src/lib/restart-context.ts
|
|
9934
10006
|
import { readdirSync as readdirSync8, readFileSync as readFileSync27, writeFileSync as writeFileSync13, mkdirSync as mkdirSync10, unlinkSync as unlinkSync4 } from "fs";
|
|
9935
|
-
import { dirname as dirname8, join as
|
|
10007
|
+
import { dirname as dirname8, join as join34 } from "path";
|
|
9936
10008
|
var SLACK_PENDING_INBOUND_DIRNAME = "slack-pending-inbound";
|
|
9937
10009
|
var SLACK_RESTART_CONTEXT_DIRNAME = "slack-restart-context";
|
|
9938
10010
|
var MAX_TOPIC_CHARS = 140;
|
|
@@ -9944,10 +10016,10 @@ function augmentedAgentDir(codeName) {
|
|
|
9944
10016
|
return dirname8(getProjectDir(codeName));
|
|
9945
10017
|
}
|
|
9946
10018
|
function slackPendingInboundDir(codeName) {
|
|
9947
|
-
return
|
|
10019
|
+
return join34(augmentedAgentDir(codeName), SLACK_PENDING_INBOUND_DIRNAME);
|
|
9948
10020
|
}
|
|
9949
10021
|
function slackRestartContextDir(codeName) {
|
|
9950
|
-
return
|
|
10022
|
+
return join34(augmentedAgentDir(codeName), SLACK_RESTART_CONTEXT_DIRNAME);
|
|
9951
10023
|
}
|
|
9952
10024
|
function sanitizeTopic(raw) {
|
|
9953
10025
|
const cleaned = raw.replace(/\s+/g, " ").trim().replace(/[<>]/g, " ").replace(/\s+/g, " ").trim();
|
|
@@ -10007,7 +10079,7 @@ function pruneHintsExcept(codeName, freshFilenames) {
|
|
|
10007
10079
|
if (!filename.endsWith(".json")) continue;
|
|
10008
10080
|
if (freshFilenames.has(filename)) continue;
|
|
10009
10081
|
try {
|
|
10010
|
-
unlinkSync4(
|
|
10082
|
+
unlinkSync4(join34(ctxDir, filename));
|
|
10011
10083
|
} catch {
|
|
10012
10084
|
}
|
|
10013
10085
|
}
|
|
@@ -10028,7 +10100,7 @@ function refreshSlackRestartContextHints(codeNames, opts = {}) {
|
|
|
10028
10100
|
}
|
|
10029
10101
|
const markers = [];
|
|
10030
10102
|
for (const filename of markerFilenames.slice(0, cap)) {
|
|
10031
|
-
const parsed = readStrandedMarker(
|
|
10103
|
+
const parsed = readStrandedMarker(join34(markerDir, filename));
|
|
10032
10104
|
if (parsed) markers.push({ filename, channel: parsed.channel, thread_ts: parsed.thread_ts });
|
|
10033
10105
|
}
|
|
10034
10106
|
if (markers.length === 0) {
|
|
@@ -10042,7 +10114,7 @@ function refreshSlackRestartContextHints(codeNames, opts = {}) {
|
|
|
10042
10114
|
const freshFilenames = /* @__PURE__ */ new Set();
|
|
10043
10115
|
for (const { filename, hint } of hints) {
|
|
10044
10116
|
try {
|
|
10045
|
-
writeHintFile(
|
|
10117
|
+
writeHintFile(join34(ctxDir, filename), ctxDir, hint);
|
|
10046
10118
|
freshFilenames.add(filename);
|
|
10047
10119
|
} catch (err) {
|
|
10048
10120
|
log2(`[restart-context] ${codeName}: hint write failed for ${filename}: ${err.message}`);
|
|
@@ -11644,7 +11716,7 @@ var runningChannelSecretHashes = /* @__PURE__ */ new Map();
|
|
|
11644
11716
|
var sessionLaunchManagedStructure = /* @__PURE__ */ new Map();
|
|
11645
11717
|
function projectMcpHash(_codeName, projectDir) {
|
|
11646
11718
|
try {
|
|
11647
|
-
const raw = readFileSync28(
|
|
11719
|
+
const raw = readFileSync28(join35(projectDir, ".mcp.json"), "utf-8");
|
|
11648
11720
|
return createHash17("sha256").update(canonicalJson(JSON.parse(raw))).digest("hex");
|
|
11649
11721
|
} catch {
|
|
11650
11722
|
return null;
|
|
@@ -11652,7 +11724,7 @@ function projectMcpHash(_codeName, projectDir) {
|
|
|
11652
11724
|
}
|
|
11653
11725
|
function projectMcpKeys(_codeName, projectDir) {
|
|
11654
11726
|
try {
|
|
11655
|
-
const raw = readFileSync28(
|
|
11727
|
+
const raw = readFileSync28(join35(projectDir, ".mcp.json"), "utf-8");
|
|
11656
11728
|
const parsed = JSON.parse(raw);
|
|
11657
11729
|
const servers = parsed.mcpServers;
|
|
11658
11730
|
if (!servers || typeof servers !== "object") return /* @__PURE__ */ new Set();
|
|
@@ -11670,7 +11742,7 @@ function seedSessionLaunchBaselines(codeName, projectDir) {
|
|
|
11670
11742
|
else runningMcpServerKeys.delete(codeName);
|
|
11671
11743
|
let launchStructure = null;
|
|
11672
11744
|
try {
|
|
11673
|
-
const raw = readFileSync28(
|
|
11745
|
+
const raw = readFileSync28(join35(projectDir, ".mcp.json"), "utf-8");
|
|
11674
11746
|
launchStructure = managedMcpStructureHashFromFile(
|
|
11675
11747
|
JSON.parse(raw),
|
|
11676
11748
|
isManagedMcpServerKey
|
|
@@ -11792,7 +11864,7 @@ async function runAgentSessionToolBindProbes(agent, integrations, projectDir, op
|
|
|
11792
11864
|
if (result && result.rebindCandidates.length > 0 && hostFlagStore().getBoolean("session-tool-rebind")) {
|
|
11793
11865
|
let mcpJsonForRebind = null;
|
|
11794
11866
|
try {
|
|
11795
|
-
mcpJsonForRebind = JSON.parse(readFileSync28(
|
|
11867
|
+
mcpJsonForRebind = JSON.parse(readFileSync28(join35(projectDir, ".mcp.json"), "utf-8"));
|
|
11796
11868
|
} catch {
|
|
11797
11869
|
mcpJsonForRebind = null;
|
|
11798
11870
|
}
|
|
@@ -11937,7 +12009,7 @@ function checkMcpConfigDriftAndScheduleRestart(codeName, projectDir) {
|
|
|
11937
12009
|
function projectChannelSecretHash(projectDir) {
|
|
11938
12010
|
try {
|
|
11939
12011
|
const entries = parseEnvIntegrations(
|
|
11940
|
-
readFileSync28(
|
|
12012
|
+
readFileSync28(join35(projectDir, ".env.integrations"), "utf-8")
|
|
11941
12013
|
);
|
|
11942
12014
|
return channelSecretValueHash(entries, CHANNEL_SECRET_ENV_KEYS);
|
|
11943
12015
|
} catch {
|
|
@@ -12033,7 +12105,7 @@ var agentRestartTimezoneInputs = /* @__PURE__ */ new Map();
|
|
|
12033
12105
|
var lastVersionCheckAt = 0;
|
|
12034
12106
|
var VERSION_CHECK_INTERVAL_MS = 5 * 60 * 1e3;
|
|
12035
12107
|
var lastResponsivenessProbeAt = 0;
|
|
12036
|
-
var agtCliVersion = true ? "0.28.
|
|
12108
|
+
var agtCliVersion = true ? "0.28.628" : "dev";
|
|
12037
12109
|
function resolveBrewPath(execFileSync3) {
|
|
12038
12110
|
try {
|
|
12039
12111
|
const out = execFileSync3("which", ["brew"], { timeout: 5e3 }).toString().trim();
|
|
@@ -12320,7 +12392,7 @@ async function reapSupersededRuntimeImages(imageUri, localTag) {
|
|
|
12320
12392
|
}
|
|
12321
12393
|
}
|
|
12322
12394
|
function runAsync(cmd, args, opts) {
|
|
12323
|
-
return new Promise((
|
|
12395
|
+
return new Promise((resolve2, reject) => {
|
|
12324
12396
|
import("child_process").then(({ spawn }) => {
|
|
12325
12397
|
const child = spawn(cmd, args, { stdio: ["ignore", "pipe", "pipe"], cwd: opts.cwd });
|
|
12326
12398
|
let stdout = "";
|
|
@@ -12354,7 +12426,7 @@ function runAsync(cmd, args, opts) {
|
|
|
12354
12426
|
if (settled) return;
|
|
12355
12427
|
settled = true;
|
|
12356
12428
|
clearTimeout(timer3);
|
|
12357
|
-
|
|
12429
|
+
resolve2({ code: code ?? -1, stdout, stderr });
|
|
12358
12430
|
});
|
|
12359
12431
|
}).catch(reject);
|
|
12360
12432
|
});
|
|
@@ -12421,7 +12493,7 @@ async function ensureOpencodeBinary() {
|
|
|
12421
12493
|
try {
|
|
12422
12494
|
const prefix = execFileSync3("npm", ["prefix", "-g"], { encoding: "utf-8", timeout: 1e4 }).trim();
|
|
12423
12495
|
if (prefix) {
|
|
12424
|
-
const npmBin =
|
|
12496
|
+
const npmBin = join35(prefix, "bin");
|
|
12425
12497
|
const current = (process.env.PATH ?? "").split(pathDelimiter);
|
|
12426
12498
|
if (!current.includes(npmBin)) {
|
|
12427
12499
|
process.env.PATH = [npmBin, ...current.filter(Boolean)].join(pathDelimiter);
|
|
@@ -12538,7 +12610,7 @@ ${r.stderr}`;
|
|
|
12538
12610
|
}
|
|
12539
12611
|
var UPDATE_CHECK_INTERVAL_MS = 5 * 60 * 1e3;
|
|
12540
12612
|
function selfUpdateAppliedMarkerPath() {
|
|
12541
|
-
return
|
|
12613
|
+
return join35(homedir17(), ".augmented", ".last-self-update-applied");
|
|
12542
12614
|
}
|
|
12543
12615
|
var selfUpdateUpToDateLogged = false;
|
|
12544
12616
|
var selfUpdatePinnedLogged = false;
|
|
@@ -12567,7 +12639,7 @@ async function checkAndUpdateCli(opts) {
|
|
|
12567
12639
|
const isNpmGlobal = !isBrewFormula && resolvedPath.includes("node_modules");
|
|
12568
12640
|
if (!isBrewFormula && !isNpmGlobal) return "noop";
|
|
12569
12641
|
const { readFileSync: readF, writeFileSync: writeF } = await import("fs");
|
|
12570
|
-
const markerPath =
|
|
12642
|
+
const markerPath = join35(homedir17(), ".augmented", ".last-update-check");
|
|
12571
12643
|
if (!force) {
|
|
12572
12644
|
try {
|
|
12573
12645
|
const lastCheck = parseInt(readF(markerPath, "utf-8").trim(), 10);
|
|
@@ -12973,7 +13045,7 @@ async function runClaudeRuntimeAuthProbe() {
|
|
|
12973
13045
|
];
|
|
12974
13046
|
try {
|
|
12975
13047
|
const { stdout, stderr } = await execFilePromiseLong(resolveClaudeBinary(), args, {
|
|
12976
|
-
cwd:
|
|
13048
|
+
cwd: homedir17(),
|
|
12977
13049
|
timeout: RUNTIME_AUTH_PROBE_TIMEOUT_MS,
|
|
12978
13050
|
stdin: "ignore",
|
|
12979
13051
|
env: childEnv,
|
|
@@ -13020,12 +13092,12 @@ async function checkClaudeAuth() {
|
|
|
13020
13092
|
var evalEmptyMcpConfigPath = null;
|
|
13021
13093
|
function ensureEvalEmptyMcpConfig() {
|
|
13022
13094
|
if (evalEmptyMcpConfigPath && existsSync15(evalEmptyMcpConfigPath)) return evalEmptyMcpConfigPath;
|
|
13023
|
-
const dir =
|
|
13095
|
+
const dir = join35(homedir17(), ".augmented");
|
|
13024
13096
|
try {
|
|
13025
13097
|
mkdirSync11(dir, { recursive: true });
|
|
13026
13098
|
} catch {
|
|
13027
13099
|
}
|
|
13028
|
-
const p =
|
|
13100
|
+
const p = join35(dir, ".eval-empty-mcp.json");
|
|
13029
13101
|
writeFileSync14(p, JSON.stringify({ mcpServers: {} }));
|
|
13030
13102
|
evalEmptyMcpConfigPath = p;
|
|
13031
13103
|
return p;
|
|
@@ -13051,7 +13123,7 @@ async function runEvalClaude(prompt, model) {
|
|
|
13051
13123
|
""
|
|
13052
13124
|
];
|
|
13053
13125
|
const { stdout } = await execFilePromiseLong(resolveClaudeBinary(), args, {
|
|
13054
|
-
cwd:
|
|
13126
|
+
cwd: homedir17(),
|
|
13055
13127
|
timeout: 12e4,
|
|
13056
13128
|
stdin: "ignore",
|
|
13057
13129
|
env: childEnv,
|
|
@@ -13120,10 +13192,10 @@ function resolveConversationEvalBackend() {
|
|
|
13120
13192
|
return conversationEvalBackend;
|
|
13121
13193
|
}
|
|
13122
13194
|
function getStateFile() {
|
|
13123
|
-
return
|
|
13195
|
+
return join35(config?.configDir ?? join35(process.env["HOME"] ?? "/tmp", ".augmented"), "manager-state.json");
|
|
13124
13196
|
}
|
|
13125
13197
|
function channelHashCacheDir() {
|
|
13126
|
-
return config?.configDir ??
|
|
13198
|
+
return config?.configDir ?? join35(process.env["HOME"] ?? "/tmp", ".augmented");
|
|
13127
13199
|
}
|
|
13128
13200
|
function loadChannelHashCache2() {
|
|
13129
13201
|
loadChannelHashCache(agentState.knownChannelConfigHashes, channelHashCacheDir());
|
|
@@ -13177,7 +13249,7 @@ function removeDeliveryBaselineEntries(agentId) {
|
|
|
13177
13249
|
var _channelQuarantineStore = null;
|
|
13178
13250
|
function channelQuarantineStore() {
|
|
13179
13251
|
if (!_channelQuarantineStore) {
|
|
13180
|
-
const dir = config?.configDir ??
|
|
13252
|
+
const dir = config?.configDir ?? join35(process.env["HOME"] ?? "/tmp", ".augmented");
|
|
13181
13253
|
_channelQuarantineStore = new ChannelQuarantineStore(defaultQuarantinePath(dir));
|
|
13182
13254
|
}
|
|
13183
13255
|
return _channelQuarantineStore;
|
|
@@ -13194,7 +13266,7 @@ function claudeMdSizeFor(codeName) {
|
|
|
13194
13266
|
var _hostFlagStore = null;
|
|
13195
13267
|
function hostFlagStore() {
|
|
13196
13268
|
if (!_hostFlagStore) {
|
|
13197
|
-
const dir = config?.configDir ??
|
|
13269
|
+
const dir = config?.configDir ?? join35(process.env["HOME"] ?? "/tmp", ".augmented");
|
|
13198
13270
|
_hostFlagStore = new HostFlagStore({ cachePath: defaultFlagsCachePath(dir), log });
|
|
13199
13271
|
}
|
|
13200
13272
|
return _hostFlagStore;
|
|
@@ -13268,12 +13340,12 @@ function parseSkillFrontmatter(content) {
|
|
|
13268
13340
|
}
|
|
13269
13341
|
async function refreshSkillsIndexInClaudeMd(configDir, codeName, log2) {
|
|
13270
13342
|
const { readdirSync: readdirSync10, readFileSync: rfs, existsSync: ex, writeFileSync: writeFileSync15 } = await import("fs");
|
|
13271
|
-
const skillsDir =
|
|
13272
|
-
const claudeMdPath =
|
|
13343
|
+
const skillsDir = join35(configDir, codeName, "project", ".claude", "skills");
|
|
13344
|
+
const claudeMdPath = join35(configDir, codeName, "project", "CLAUDE.md");
|
|
13273
13345
|
if (!ex(skillsDir) || !ex(claudeMdPath)) return;
|
|
13274
13346
|
const entries = [];
|
|
13275
13347
|
for (const dir of readdirSync10(skillsDir).sort()) {
|
|
13276
|
-
const skillFile =
|
|
13348
|
+
const skillFile = join35(skillsDir, dir, "SKILL.md");
|
|
13277
13349
|
if (!ex(skillFile)) continue;
|
|
13278
13350
|
try {
|
|
13279
13351
|
const { name, description } = parseSkillFrontmatter(rfs(skillFile, "utf-8"));
|
|
@@ -13777,10 +13849,10 @@ async function pollCycleInner() {
|
|
|
13777
13849
|
const paneTail = readFileSync28(paneLogPath(codeName), "utf8").slice(-65536);
|
|
13778
13850
|
const transient = detectTransientApiErrorInLog(paneTail);
|
|
13779
13851
|
if (transient) {
|
|
13780
|
-
const wedgeHome =
|
|
13852
|
+
const wedgeHome = join35(homedir17(), ".augmented", codeName);
|
|
13781
13853
|
if (existsSync15(wedgeHome)) {
|
|
13782
13854
|
atomicWriteFileSync(
|
|
13783
|
-
|
|
13855
|
+
join35(wedgeHome, "watchdog-give-up.json"),
|
|
13784
13856
|
JSON.stringify({
|
|
13785
13857
|
gave_up_at: wedgeNow.toISOString(),
|
|
13786
13858
|
reason: "transient_overload"
|
|
@@ -14074,7 +14146,7 @@ async function pollCycleInner() {
|
|
|
14074
14146
|
const adapter = resolveAgentFramework(prev.codeName);
|
|
14075
14147
|
stopAgentRuntime2(prev.codeName, "removed-from-host");
|
|
14076
14148
|
killAgentChannelProcesses(prev.codeName, { log });
|
|
14077
|
-
const agentDir =
|
|
14149
|
+
const agentDir = join35(adapter.getAgentDir(prev.codeName), "provision");
|
|
14078
14150
|
await cleanupAgentFiles(prev.codeName, agentDir);
|
|
14079
14151
|
clearAgentCaches(prev.agentId, prev.codeName);
|
|
14080
14152
|
}
|
|
@@ -14161,10 +14233,10 @@ async function pollCycleInner() {
|
|
|
14161
14233
|
// pending-inbound marker. Best-effort: a write failure is logged by
|
|
14162
14234
|
// the watchdog, never fails the poll cycle.
|
|
14163
14235
|
signalGiveUp: (codeName) => {
|
|
14164
|
-
const dir =
|
|
14236
|
+
const dir = join35(homedir17(), ".augmented", codeName);
|
|
14165
14237
|
if (!existsSync15(dir)) return;
|
|
14166
14238
|
atomicWriteFileSync(
|
|
14167
|
-
|
|
14239
|
+
join35(dir, "watchdog-give-up.json"),
|
|
14168
14240
|
JSON.stringify({ gave_up_at: (/* @__PURE__ */ new Date()).toISOString() })
|
|
14169
14241
|
);
|
|
14170
14242
|
}
|
|
@@ -14360,7 +14432,7 @@ async function processAgent(agent, agentStates, managedToolkits) {
|
|
|
14360
14432
|
}
|
|
14361
14433
|
const now = (/* @__PURE__ */ new Date()).toISOString();
|
|
14362
14434
|
const adapter = resolveAgentFramework(agent.code_name);
|
|
14363
|
-
let agentDir =
|
|
14435
|
+
let agentDir = join35(adapter.getAgentDir(agent.code_name), "provision");
|
|
14364
14436
|
if (agent.status === "draft" || agent.status === "paused") {
|
|
14365
14437
|
if (previousKnownStatus !== agent.status) {
|
|
14366
14438
|
log(`Agent '${agent.code_name}' is ${agent.status}, skipping provisioning`);
|
|
@@ -14534,7 +14606,7 @@ async function processAgent(agent, agentStates, managedToolkits) {
|
|
|
14534
14606
|
const frameworkId = refreshData.agent.framework ?? DEFAULT_FRAMEWORK;
|
|
14535
14607
|
agentFrameworkCache.set(agent.code_name, frameworkId);
|
|
14536
14608
|
const frameworkAdapter = getFramework(frameworkId);
|
|
14537
|
-
agentDir =
|
|
14609
|
+
agentDir = join35(frameworkAdapter.getAgentDir(agent.code_name), "provision");
|
|
14538
14610
|
cacheAgentDeliveryMetadata(agent.code_name, refreshData);
|
|
14539
14611
|
agentRestartTimezoneInputs.set(agent.code_name, {
|
|
14540
14612
|
agentTimezone: typeof refreshData.agent.timezone === "string" ? refreshData.agent.timezone : null,
|
|
@@ -14583,7 +14655,7 @@ async function processAgent(agent, agentStates, managedToolkits) {
|
|
|
14583
14655
|
const changedFiles = [];
|
|
14584
14656
|
mkdirSync11(agentDir, { recursive: true });
|
|
14585
14657
|
for (const artifact of artifacts) {
|
|
14586
|
-
const filePath =
|
|
14658
|
+
const filePath = join35(agentDir, artifact.relativePath);
|
|
14587
14659
|
let existingHash;
|
|
14588
14660
|
let newHash;
|
|
14589
14661
|
let writeContent = artifact.content;
|
|
@@ -14602,7 +14674,7 @@ async function processAgent(agent, agentStates, managedToolkits) {
|
|
|
14602
14674
|
};
|
|
14603
14675
|
newHash = sha256(stripDynamicSections(artifact.content));
|
|
14604
14676
|
try {
|
|
14605
|
-
const projectClaudeMd =
|
|
14677
|
+
const projectClaudeMd = join35(config.configDir, agent.code_name, "project", "CLAUDE.md");
|
|
14606
14678
|
const existing = readFileSync28(projectClaudeMd, "utf-8");
|
|
14607
14679
|
existingHash = sha256(stripDynamicSections(existing));
|
|
14608
14680
|
} catch {
|
|
@@ -14653,12 +14725,12 @@ async function processAgent(agent, agentStates, managedToolkits) {
|
|
|
14653
14725
|
}
|
|
14654
14726
|
}
|
|
14655
14727
|
if (changedFiles.length > 0) {
|
|
14656
|
-
const isFirst = !existsSync15(
|
|
14728
|
+
const isFirst = !existsSync15(join35(agentDir, "CHARTER.md"));
|
|
14657
14729
|
const verb = isFirst ? "Provisioning" : "Updating";
|
|
14658
14730
|
const fileNames = changedFiles.map((f) => f.relativePath).join(", ");
|
|
14659
14731
|
log(`${verb} '${agent.code_name}': ${fileNames}`);
|
|
14660
14732
|
for (const file of changedFiles) {
|
|
14661
|
-
const filePath =
|
|
14733
|
+
const filePath = join35(agentDir, file.relativePath);
|
|
14662
14734
|
mkdirSync11(dirname9(filePath), { recursive: true });
|
|
14663
14735
|
if (file.relativePath === ".mcp.json") {
|
|
14664
14736
|
safeWriteJsonAtomic(filePath, file.content, { mode: 384 });
|
|
@@ -14667,12 +14739,12 @@ async function processAgent(agent, agentStates, managedToolkits) {
|
|
|
14667
14739
|
}
|
|
14668
14740
|
}
|
|
14669
14741
|
try {
|
|
14670
|
-
const provSkillsDir =
|
|
14742
|
+
const provSkillsDir = join35(agentDir, ".claude", "skills");
|
|
14671
14743
|
if (existsSync15(provSkillsDir)) {
|
|
14672
14744
|
for (const folder of readdirSync9(provSkillsDir)) {
|
|
14673
14745
|
if (folder.startsWith("knowledge-")) {
|
|
14674
14746
|
try {
|
|
14675
|
-
rmSync5(
|
|
14747
|
+
rmSync5(join35(provSkillsDir, folder), { recursive: true });
|
|
14676
14748
|
} catch {
|
|
14677
14749
|
}
|
|
14678
14750
|
}
|
|
@@ -14685,7 +14757,7 @@ async function processAgent(agent, agentStates, managedToolkits) {
|
|
|
14685
14757
|
const trackedFiles2 = frameworkAdapter.driftTrackedFiles();
|
|
14686
14758
|
const hashes = /* @__PURE__ */ new Map();
|
|
14687
14759
|
for (const file of trackedFiles2) {
|
|
14688
|
-
const h = hashFile(
|
|
14760
|
+
const h = hashFile(join35(agentDir, file));
|
|
14689
14761
|
if (h) hashes.set(file, h);
|
|
14690
14762
|
}
|
|
14691
14763
|
agentState.writtenHashes.set(agent.agent_id, hashes);
|
|
@@ -14703,14 +14775,14 @@ async function processAgent(agent, agentStates, managedToolkits) {
|
|
|
14703
14775
|
}
|
|
14704
14776
|
if (Array.isArray(refreshData.workflows)) {
|
|
14705
14777
|
try {
|
|
14706
|
-
const provWorkflowsDir =
|
|
14778
|
+
const provWorkflowsDir = join35(agentDir, ".claude", "workflows");
|
|
14707
14779
|
if (existsSync15(provWorkflowsDir)) {
|
|
14708
14780
|
const expected = new Set(refreshData.workflows.map((w) => `${w.name}.js`));
|
|
14709
14781
|
for (const file of readdirSync9(provWorkflowsDir)) {
|
|
14710
14782
|
if (!file.endsWith(".js")) continue;
|
|
14711
14783
|
if (expected.has(file)) continue;
|
|
14712
14784
|
try {
|
|
14713
|
-
rmSync5(
|
|
14785
|
+
rmSync5(join35(provWorkflowsDir, file));
|
|
14714
14786
|
} catch {
|
|
14715
14787
|
}
|
|
14716
14788
|
}
|
|
@@ -14792,7 +14864,7 @@ async function processAgent(agent, agentStates, managedToolkits) {
|
|
|
14792
14864
|
if (written && existsSync15(agentDir)) {
|
|
14793
14865
|
const driftedFiles = [];
|
|
14794
14866
|
for (const [file, expectedHash] of written) {
|
|
14795
|
-
const localHash = hashFile(
|
|
14867
|
+
const localHash = hashFile(join35(agentDir, file));
|
|
14796
14868
|
if (localHash && localHash !== expectedHash) {
|
|
14797
14869
|
driftedFiles.push(file);
|
|
14798
14870
|
}
|
|
@@ -14803,7 +14875,7 @@ async function processAgent(agent, agentStates, managedToolkits) {
|
|
|
14803
14875
|
try {
|
|
14804
14876
|
const localHashes = {};
|
|
14805
14877
|
for (const file of driftedFiles) {
|
|
14806
|
-
localHashes[file] = hashFile(
|
|
14878
|
+
localHashes[file] = hashFile(join35(agentDir, file));
|
|
14807
14879
|
}
|
|
14808
14880
|
await api.post("/host/drift", {
|
|
14809
14881
|
agent_id: agent.agent_id,
|
|
@@ -15005,7 +15077,7 @@ async function processAgent(agent, agentStates, managedToolkits) {
|
|
|
15005
15077
|
const addedChannels = [...restartDecision.added];
|
|
15006
15078
|
const writeDmNoticeMarkers = isChannelAddRestart ? () => {
|
|
15007
15079
|
try {
|
|
15008
|
-
const agentAugmentedDir =
|
|
15080
|
+
const agentAugmentedDir = join35(homedir17(), ".augmented", agent.code_name);
|
|
15009
15081
|
mkdirSync11(agentAugmentedDir, { recursive: true });
|
|
15010
15082
|
const markerJson = JSON.stringify({
|
|
15011
15083
|
version: 1,
|
|
@@ -15013,7 +15085,7 @@ async function processAgent(agent, agentStates, managedToolkits) {
|
|
|
15013
15085
|
added: addedChannels
|
|
15014
15086
|
});
|
|
15015
15087
|
for (const file of ["slack-channel-add-restart.json", "telegram-channel-add-restart.json"]) {
|
|
15016
|
-
atomicWriteFileSync(
|
|
15088
|
+
atomicWriteFileSync(join35(agentAugmentedDir, file), markerJson);
|
|
15017
15089
|
}
|
|
15018
15090
|
} catch (err) {
|
|
15019
15091
|
log(`[hot-reload] channel-add DM-notice marker write failed for '${agent.code_name}' (non-fatal): ${err.message}`);
|
|
@@ -15202,18 +15274,18 @@ async function processAgent(agent, agentStates, managedToolkits) {
|
|
|
15202
15274
|
if (agentSessionMode === "persistent" && (agentFrameworkCache.get(agent.code_name) ?? DEFAULT_FRAMEWORK) === "claude-code") {
|
|
15203
15275
|
try {
|
|
15204
15276
|
const agentProvisionDir = agentDir;
|
|
15205
|
-
const projectDir =
|
|
15277
|
+
const projectDir = join35(homedir17(), ".augmented", agent.code_name, "project");
|
|
15206
15278
|
mkdirSync11(agentProvisionDir, { recursive: true });
|
|
15207
15279
|
mkdirSync11(projectDir, { recursive: true });
|
|
15208
|
-
const provisionMcpPath =
|
|
15209
|
-
const projectMcpPath =
|
|
15280
|
+
const provisionMcpPath = join35(agentProvisionDir, ".mcp.json");
|
|
15281
|
+
const projectMcpPath = join35(projectDir, ".mcp.json");
|
|
15210
15282
|
let mcpConfig = { mcpServers: {} };
|
|
15211
15283
|
try {
|
|
15212
15284
|
mcpConfig = JSON.parse(readFileSync28(provisionMcpPath, "utf-8"));
|
|
15213
15285
|
if (!mcpConfig.mcpServers) mcpConfig.mcpServers = {};
|
|
15214
15286
|
} catch {
|
|
15215
15287
|
}
|
|
15216
|
-
const localDirectChatChannel =
|
|
15288
|
+
const localDirectChatChannel = join35(homedir17(), ".augmented", "_mcp", "direct-chat-channel.js");
|
|
15217
15289
|
const directChatTeamSettings = refreshData.team?.settings;
|
|
15218
15290
|
const directChatTz = (() => {
|
|
15219
15291
|
const tz = directChatTeamSettings?.["timezone"];
|
|
@@ -15239,7 +15311,7 @@ async function processAgent(agent, agentStates, managedToolkits) {
|
|
|
15239
15311
|
// ~/.augmented/<codeName>/.current-turn-initiator.json. Note getAgentDir
|
|
15240
15312
|
// returns the agent root (NOT the /provision subdir `agentDir` points at),
|
|
15241
15313
|
// so it byte-matches the broker readers' path.
|
|
15242
|
-
AGT_TURN_INITIATOR_FILE:
|
|
15314
|
+
AGT_TURN_INITIATOR_FILE: join35(
|
|
15243
15315
|
frameworkAdapter.getAgentDir(agent.code_name),
|
|
15244
15316
|
".current-turn-initiator.json"
|
|
15245
15317
|
)
|
|
@@ -15259,7 +15331,7 @@ async function processAgent(agent, agentStates, managedToolkits) {
|
|
|
15259
15331
|
log(`Channel credentials written for '${agent.code_name}/direct-chat'`);
|
|
15260
15332
|
}
|
|
15261
15333
|
}
|
|
15262
|
-
const staleChannelsPath =
|
|
15334
|
+
const staleChannelsPath = join35(projectDir, ".mcp-channels.json");
|
|
15263
15335
|
if (existsSync15(staleChannelsPath)) {
|
|
15264
15336
|
try {
|
|
15265
15337
|
rmSync5(staleChannelsPath, { force: true });
|
|
@@ -15349,7 +15421,7 @@ async function processAgent(agent, agentStates, managedToolkits) {
|
|
|
15349
15421
|
}
|
|
15350
15422
|
if (hostFlagStore().getBoolean("connectivity-probe")) {
|
|
15351
15423
|
try {
|
|
15352
|
-
const probeProjectDir =
|
|
15424
|
+
const probeProjectDir = join35(homedir17(), ".augmented", agent.code_name, "project");
|
|
15353
15425
|
let probeSet = integrations;
|
|
15354
15426
|
try {
|
|
15355
15427
|
const quarantined = await api.post("/host/agent-integrations/quarantined", { agent_id: agent.agent_id });
|
|
@@ -15395,7 +15467,7 @@ async function processAgent(agent, agentStates, managedToolkits) {
|
|
|
15395
15467
|
const forceDue = attemptsLeft > 0;
|
|
15396
15468
|
let probeRan = false;
|
|
15397
15469
|
try {
|
|
15398
|
-
const probeProjectDir =
|
|
15470
|
+
const probeProjectDir = join35(homedir17(), ".augmented", agent.code_name, "project");
|
|
15399
15471
|
probeRan = await runAgentSessionToolBindProbes(agent, integrations, probeProjectDir, { forceDue });
|
|
15400
15472
|
} catch (err) {
|
|
15401
15473
|
log(`Session-tool-bind probe failed for '${agent.code_name}': ${err.message}`);
|
|
@@ -15472,8 +15544,8 @@ async function processAgent(agent, agentStates, managedToolkits) {
|
|
|
15472
15544
|
const intHash = computeIntegrationsHash(integrations);
|
|
15473
15545
|
const prevIntHash = agentState.knownIntegrationHashes.get(agent.agent_id);
|
|
15474
15546
|
if (intHash !== prevIntHash) {
|
|
15475
|
-
const projectDir =
|
|
15476
|
-
const envIntPath =
|
|
15547
|
+
const projectDir = join35(homedir17(), ".augmented", agent.code_name, "project");
|
|
15548
|
+
const envIntPath = join35(projectDir, ".env.integrations");
|
|
15477
15549
|
let preWriteEnv;
|
|
15478
15550
|
try {
|
|
15479
15551
|
preWriteEnv = readFileSync28(envIntPath, "utf-8");
|
|
@@ -15495,7 +15567,7 @@ async function processAgent(agent, agentStates, managedToolkits) {
|
|
|
15495
15567
|
}
|
|
15496
15568
|
if (fw === "claude-code" && isSessionHealthy(agent.code_name)) {
|
|
15497
15569
|
try {
|
|
15498
|
-
const projectMcpPath =
|
|
15570
|
+
const projectMcpPath = join35(projectDir, ".mcp.json");
|
|
15499
15571
|
const postWriteEnv = readFileSync28(envIntPath, "utf-8");
|
|
15500
15572
|
const mcpContent = readFileSync28(projectMcpPath, "utf-8");
|
|
15501
15573
|
const changedVars = diffEnvIntegrations(preWriteEnv, postWriteEnv);
|
|
@@ -15760,16 +15832,16 @@ async function processAgent(agent, agentStates, managedToolkits) {
|
|
|
15760
15832
|
}
|
|
15761
15833
|
try {
|
|
15762
15834
|
const { readdirSync: readdirSync10, rmSync: rmSync6 } = await import("fs");
|
|
15763
|
-
const { homedir:
|
|
15835
|
+
const { homedir: homedir18 } = await import("os");
|
|
15764
15836
|
const frameworkId2 = frameworkAdapter.id;
|
|
15765
15837
|
const candidateSkillDirs = [
|
|
15766
15838
|
// Claude Code — framework runtime tree
|
|
15767
|
-
|
|
15839
|
+
join35(homedir18(), ".augmented", agent.code_name, "skills"),
|
|
15768
15840
|
// Claude Code — project tree
|
|
15769
|
-
|
|
15841
|
+
join35(homedir18(), ".augmented", agent.code_name, "project", ".claude", "skills"),
|
|
15770
15842
|
// Defensive: legacy provision-side path, not currently an
|
|
15771
15843
|
// install target but cheap to sweep.
|
|
15772
|
-
|
|
15844
|
+
join35(agentDir, ".claude", "skills")
|
|
15773
15845
|
];
|
|
15774
15846
|
const existingDirs = candidateSkillDirs.filter((d) => existsSync15(d));
|
|
15775
15847
|
const discoveredEntries = /* @__PURE__ */ new Set();
|
|
@@ -15810,7 +15882,7 @@ async function processAgent(agent, agentStates, managedToolkits) {
|
|
|
15810
15882
|
const sharedSkillsPayload = refreshAny.shared_skills;
|
|
15811
15883
|
const desiredResolved = globalSkillsPayload !== void 0 || sharedSkillsPayload !== void 0;
|
|
15812
15884
|
const manifestPath = managedSkillManifestPath(
|
|
15813
|
-
|
|
15885
|
+
join35(homedir17(), ".augmented", agent.code_name)
|
|
15814
15886
|
);
|
|
15815
15887
|
const prevIds = /* @__PURE__ */ new Set([
|
|
15816
15888
|
...agentState.knownGlobalSkillIds.get(agent.agent_id) ?? /* @__PURE__ */ new Set(),
|
|
@@ -15830,15 +15902,15 @@ async function processAgent(agent, agentStates, managedToolkits) {
|
|
|
15830
15902
|
}
|
|
15831
15903
|
if (plan.removes.length) {
|
|
15832
15904
|
const globalSkillDirs = [
|
|
15833
|
-
|
|
15834
|
-
|
|
15835
|
-
|
|
15905
|
+
join35(homedir17(), ".augmented", agent.code_name, "skills"),
|
|
15906
|
+
join35(homedir17(), ".augmented", agent.code_name, "project", ".claude", "skills"),
|
|
15907
|
+
join35(agentDir, ".claude", "skills")
|
|
15836
15908
|
];
|
|
15837
15909
|
for (const id of plan.removes) {
|
|
15838
15910
|
let prunedAny = false;
|
|
15839
15911
|
for (const dir of globalSkillDirs) {
|
|
15840
|
-
const p =
|
|
15841
|
-
if (existsSync15(p) && existsSync15(
|
|
15912
|
+
const p = join35(dir, id);
|
|
15913
|
+
if (existsSync15(p) && existsSync15(join35(p, "SKILL.md"))) {
|
|
15842
15914
|
rmSync5(p, { recursive: true, force: true });
|
|
15843
15915
|
prunedAny = true;
|
|
15844
15916
|
}
|
|
@@ -16070,7 +16142,7 @@ async function processAgent(agent, agentStates, managedToolkits) {
|
|
|
16070
16142
|
const sess = getSessionState(agent.code_name);
|
|
16071
16143
|
let mcpJsonParsed = null;
|
|
16072
16144
|
try {
|
|
16073
|
-
const mcpPath =
|
|
16145
|
+
const mcpPath = join35(getProjectDir(agent.code_name), ".mcp.json");
|
|
16074
16146
|
mcpJsonParsed = JSON.parse(readFileSync28(mcpPath, "utf-8"));
|
|
16075
16147
|
} catch {
|
|
16076
16148
|
}
|
|
@@ -16505,7 +16577,7 @@ Retried to the limit after repeated stalls \u2014 needs a look.`).catch(() => {
|
|
|
16505
16577
|
if (trackedFiles.length > 0 && existsSync15(agentDir)) {
|
|
16506
16578
|
const hashes = /* @__PURE__ */ new Map();
|
|
16507
16579
|
for (const file of trackedFiles) {
|
|
16508
|
-
const h = hashFile(
|
|
16580
|
+
const h = hashFile(join35(agentDir, file));
|
|
16509
16581
|
if (h) hashes.set(file, h);
|
|
16510
16582
|
}
|
|
16511
16583
|
agentState.writtenHashes.set(agent.agent_id, hashes);
|
|
@@ -16520,7 +16592,7 @@ Retried to the limit after repeated stalls \u2014 needs a look.`).catch(() => {
|
|
|
16520
16592
|
refreshData.agent.onboarding_state
|
|
16521
16593
|
);
|
|
16522
16594
|
const obStep = obState.step;
|
|
16523
|
-
const markerPath =
|
|
16595
|
+
const markerPath = join35(homedir17(), ".augmented", agent.code_name, "onboarding-drive.json");
|
|
16524
16596
|
const marker = readOnboardingDriveMarker(markerPath);
|
|
16525
16597
|
const obContactRaw = refreshData.agent.manager_last_contacted_at;
|
|
16526
16598
|
const obContact = typeof obContactRaw === "string" && obContactRaw ? obContactRaw : null;
|
|
@@ -16622,7 +16694,7 @@ async function ensureOpencodeRuntime(agent, refreshData, agentTimezone) {
|
|
|
16622
16694
|
}
|
|
16623
16695
|
stopOpencodeSlackIngest(codeName, log);
|
|
16624
16696
|
stopOpencodeTelegramIngest(codeName, log);
|
|
16625
|
-
const opencodeProjectDir =
|
|
16697
|
+
const opencodeProjectDir = join35(getFramework("opencode").getAgentDir(codeName), "provision");
|
|
16626
16698
|
const serveEnv = {
|
|
16627
16699
|
AGT_HOST: requireHost(),
|
|
16628
16700
|
AGT_API_KEY: getApiKey() ?? void 0,
|
|
@@ -16677,8 +16749,8 @@ async function ensurePersistentSession(agent, tasks, boardItems, refreshData) {
|
|
|
16677
16749
|
});
|
|
16678
16750
|
}
|
|
16679
16751
|
const projectDir = getProjectDir(codeName);
|
|
16680
|
-
const mcpConfigPath =
|
|
16681
|
-
const claudeMdPath =
|
|
16752
|
+
const mcpConfigPath = join35(projectDir, ".mcp.json");
|
|
16753
|
+
const claudeMdPath = join35(projectDir, "CLAUDE.md");
|
|
16682
16754
|
if (restartBreaker.isTripped(codeName)) {
|
|
16683
16755
|
const trip = restartBreaker.getTrip(codeName);
|
|
16684
16756
|
return {
|
|
@@ -16688,6 +16760,21 @@ async function ensurePersistentSession(agent, tasks, boardItems, refreshData) {
|
|
|
16688
16760
|
detail: trip.statusMessage
|
|
16689
16761
|
};
|
|
16690
16762
|
}
|
|
16763
|
+
if ((agentFrameworkCache.get(codeName) ?? DEFAULT_FRAMEWORK) === "claude-code" && !isSessionHealthy(codeName)) {
|
|
16764
|
+
const missingMcpBundles = findMissingMcpBundles(mcpConfigPath);
|
|
16765
|
+
if (missingMcpBundles.length > 0) {
|
|
16766
|
+
const detail = formatMissingMcpBundles(missingMcpBundles);
|
|
16767
|
+
log(
|
|
16768
|
+
`[persistent-session] '${codeName}': deferring spawn \u2014 ${detail}. Not counted as a restart; will spawn once the host deploys them.`
|
|
16769
|
+
);
|
|
16770
|
+
return {
|
|
16771
|
+
decision: "skipped-mcp-assets-not-ready",
|
|
16772
|
+
spawnAttempted: false,
|
|
16773
|
+
sessionHealthyAfter: false,
|
|
16774
|
+
detail
|
|
16775
|
+
};
|
|
16776
|
+
}
|
|
16777
|
+
}
|
|
16691
16778
|
const teamSettingsForTz = refreshData.team?.settings;
|
|
16692
16779
|
const agentTimezone = (() => {
|
|
16693
16780
|
const ownTzRaw = refreshData.agent?.timezone;
|
|
@@ -17780,7 +17867,7 @@ async function processDirectChatMessage(agent, msg) {
|
|
|
17780
17867
|
const useDoorbell = hostFlagStore().getBoolean("direct-chat-doorbell") || isolationMode(agent.codeName) === "docker";
|
|
17781
17868
|
if (useDoorbell) {
|
|
17782
17869
|
try {
|
|
17783
|
-
const doorbell = directChatDoorbellPath(agent.agentId,
|
|
17870
|
+
const doorbell = directChatDoorbellPath(agent.agentId, homedir17());
|
|
17784
17871
|
mkdirSync11(dirname9(doorbell), { recursive: true });
|
|
17785
17872
|
writeFileSync14(doorbell, String(Date.now()));
|
|
17786
17873
|
log(`[direct-chat] Doorbell rung for '${agent.codeName}' (msg=${msg.id}) \u2014 in-session MCP will pull via the cursor`);
|
|
@@ -17909,7 +17996,7 @@ ${formatRunMarker(run_id)}` : KANBAN_CHECK_COMMAND;
|
|
|
17909
17996
|
}
|
|
17910
17997
|
if (run_id) openInjectedRunByCode.set(codeName, run_id);
|
|
17911
17998
|
try {
|
|
17912
|
-
const doorbell = directChatDoorbellPath(agentId,
|
|
17999
|
+
const doorbell = directChatDoorbellPath(agentId, homedir17());
|
|
17913
18000
|
mkdirSync11(dirname9(doorbell), { recursive: true });
|
|
17914
18001
|
writeFileSync14(doorbell, String(Date.now()));
|
|
17915
18002
|
} catch (err) {
|
|
@@ -18269,8 +18356,8 @@ function parseMemoryFile(raw, fallbackName) {
|
|
|
18269
18356
|
};
|
|
18270
18357
|
}
|
|
18271
18358
|
async function syncMemories(agent, configDir, log2) {
|
|
18272
|
-
const projectDir =
|
|
18273
|
-
const memoryDir =
|
|
18359
|
+
const projectDir = join35(configDir, agent.code_name, "project");
|
|
18360
|
+
const memoryDir = join35(projectDir, "memory");
|
|
18274
18361
|
const isFreshSync = pendingFreshMemorySync.has(agent.agent_id);
|
|
18275
18362
|
if (isFreshSync) {
|
|
18276
18363
|
log2(`[memory-sync] Fresh-sync requested for '${agent.code_name}' \u2014 pulling DB first`);
|
|
@@ -18288,7 +18375,7 @@ async function syncMemories(agent, configDir, log2) {
|
|
|
18288
18375
|
for (const file of readdirSync9(memoryDir)) {
|
|
18289
18376
|
if (!file.endsWith(".md")) continue;
|
|
18290
18377
|
try {
|
|
18291
|
-
const raw = readFileSync28(
|
|
18378
|
+
const raw = readFileSync28(join35(memoryDir, file), "utf-8");
|
|
18292
18379
|
const fileHash = createHash17("sha256").update(raw).digest("hex").slice(0, 16);
|
|
18293
18380
|
currentHashes.set(file, fileHash);
|
|
18294
18381
|
if (prevHashes.get(file) === fileHash) continue;
|
|
@@ -18313,7 +18400,7 @@ async function syncMemories(agent, configDir, log2) {
|
|
|
18313
18400
|
} catch (err) {
|
|
18314
18401
|
for (const mem of changedMemories) {
|
|
18315
18402
|
for (const [file] of currentHashes) {
|
|
18316
|
-
const parsed = parseMemoryFile(readFileSync28(
|
|
18403
|
+
const parsed = parseMemoryFile(readFileSync28(join35(memoryDir, file), "utf-8"), file.replace(/\.md$/, ""));
|
|
18317
18404
|
if (parsed?.name === mem.name) currentHashes.delete(file);
|
|
18318
18405
|
}
|
|
18319
18406
|
}
|
|
@@ -18348,7 +18435,7 @@ async function downloadMemories(agent, memoryDir, log2, { force }) {
|
|
|
18348
18435
|
const mem = dbMemories.memories[i];
|
|
18349
18436
|
const rawSlug = mem.name.toLowerCase().replace(/[^a-z0-9]+/g, "-").replace(/(^-|-$)/g, "").slice(0, 60);
|
|
18350
18437
|
const slug = rawSlug || `memory-${i}`;
|
|
18351
|
-
const filePath =
|
|
18438
|
+
const filePath = join35(memoryDir, `${slug}.md`);
|
|
18352
18439
|
const desired = `---
|
|
18353
18440
|
name: ${JSON.stringify(mem.name)}
|
|
18354
18441
|
type: ${mem.type}
|
|
@@ -18522,7 +18609,7 @@ async function reportSelfUpdateRestarts() {
|
|
|
18522
18609
|
});
|
|
18523
18610
|
})
|
|
18524
18611
|
).then(() => void 0);
|
|
18525
|
-
const deadline = new Promise((
|
|
18612
|
+
const deadline = new Promise((resolve2) => setTimeout(resolve2, 3e3));
|
|
18526
18613
|
await Promise.race([posts, deadline]);
|
|
18527
18614
|
}
|
|
18528
18615
|
function scheduleNext() {
|
|
@@ -18656,7 +18743,7 @@ function startManager(opts) {
|
|
|
18656
18743
|
log(`[startup] state rehydration failed (continuing with empty state): ${err.message}`);
|
|
18657
18744
|
}
|
|
18658
18745
|
log(
|
|
18659
|
-
`[startup] worker pid=${process.pid} ppid=${process.ppid} node=${process.version} log=${
|
|
18746
|
+
`[startup] worker pid=${process.pid} ppid=${process.ppid} node=${process.version} log=${join35(homedir17(), ".augmented", "manager.log")}`
|
|
18660
18747
|
);
|
|
18661
18748
|
deployMcpAssets();
|
|
18662
18749
|
reapOrphanChannelMcps({ log });
|
|
@@ -18782,14 +18869,14 @@ function restartRunningChannelMcps(basenames) {
|
|
|
18782
18869
|
}
|
|
18783
18870
|
}
|
|
18784
18871
|
function deployMcpAssets() {
|
|
18785
|
-
const targetDir =
|
|
18872
|
+
const targetDir = join35(homedir17(), ".augmented", "_mcp");
|
|
18786
18873
|
mkdirSync11(targetDir, { recursive: true });
|
|
18787
18874
|
const moduleDir = dirname9(fileURLToPath(import.meta.url));
|
|
18788
18875
|
let mcpSourceDir = "";
|
|
18789
18876
|
let dir = moduleDir;
|
|
18790
18877
|
for (let i = 0; i < 6; i++) {
|
|
18791
|
-
const candidate =
|
|
18792
|
-
if (existsSync15(
|
|
18878
|
+
const candidate = join35(dir, "dist", "mcp");
|
|
18879
|
+
if (existsSync15(join35(candidate, "index.js"))) {
|
|
18793
18880
|
mcpSourceDir = candidate;
|
|
18794
18881
|
break;
|
|
18795
18882
|
}
|
|
@@ -18802,6 +18889,8 @@ function deployMcpAssets() {
|
|
|
18802
18889
|
return;
|
|
18803
18890
|
}
|
|
18804
18891
|
const changedBasenames = [];
|
|
18892
|
+
const attemptedFiles = [];
|
|
18893
|
+
const failedFiles = [];
|
|
18805
18894
|
const fileHash = (p) => {
|
|
18806
18895
|
try {
|
|
18807
18896
|
if (!existsSync15(p)) return null;
|
|
@@ -18876,9 +18965,10 @@ function deployMcpAssets() {
|
|
|
18876
18965
|
// needs restarting to pick up a token rotation.
|
|
18877
18966
|
"xero.js"
|
|
18878
18967
|
]) {
|
|
18879
|
-
const src =
|
|
18880
|
-
const dst =
|
|
18968
|
+
const src = join35(mcpSourceDir, file);
|
|
18969
|
+
const dst = join35(targetDir, file);
|
|
18881
18970
|
if (!existsSync15(src)) continue;
|
|
18971
|
+
attemptedFiles.push(file);
|
|
18882
18972
|
const before = fileHash(dst);
|
|
18883
18973
|
try {
|
|
18884
18974
|
copyFileSync(src, dst);
|
|
@@ -18887,22 +18977,29 @@ function deployMcpAssets() {
|
|
|
18887
18977
|
changedBasenames.push(file.replace(/\.js$/, ""));
|
|
18888
18978
|
}
|
|
18889
18979
|
} catch (err) {
|
|
18980
|
+
failedFiles.push(file);
|
|
18890
18981
|
log(`[manager] Failed to deploy ${file}: ${err.message}`);
|
|
18891
18982
|
}
|
|
18892
18983
|
}
|
|
18893
|
-
|
|
18984
|
+
if (failedFiles.length > 0) {
|
|
18985
|
+
log(
|
|
18986
|
+
`[manager] MCP asset deployment INCOMPLETE for ${targetDir} \u2014 ${failedFiles.length}/${attemptedFiles.length} bundle(s) failed to copy: ${failedFiles.join(", ")}. Agents declaring these bundles will be held out of spawn (ENG-9125) until this succeeds. A read-only target directory is the usual cause.`
|
|
18987
|
+
);
|
|
18988
|
+
} else {
|
|
18989
|
+
log(`[manager] MCP assets deployed to ${targetDir} (${attemptedFiles.length} bundle(s))`);
|
|
18990
|
+
}
|
|
18894
18991
|
if (changedBasenames.length > 0) {
|
|
18895
18992
|
log(`[manager] Bundle(s) updated: ${changedBasenames.join(", ")} \u2014 signalling running instances to restart`);
|
|
18896
18993
|
restartRunningChannelMcps(changedBasenames);
|
|
18897
18994
|
}
|
|
18898
|
-
const localMcpPath =
|
|
18995
|
+
const localMcpPath = join35(targetDir, "index.js");
|
|
18899
18996
|
try {
|
|
18900
|
-
const agentsDir =
|
|
18997
|
+
const agentsDir = join35(homedir17(), ".augmented", "agents");
|
|
18901
18998
|
if (existsSync15(agentsDir)) {
|
|
18902
18999
|
for (const entry of readdirSync9(agentsDir, { withFileTypes: true })) {
|
|
18903
19000
|
if (!entry.isDirectory()) continue;
|
|
18904
19001
|
for (const subdir of ["provision", "project"]) {
|
|
18905
|
-
const mcpJsonPath =
|
|
19002
|
+
const mcpJsonPath = join35(agentsDir, entry.name, subdir, ".mcp.json");
|
|
18906
19003
|
try {
|
|
18907
19004
|
const raw = readFileSync28(mcpJsonPath, "utf-8");
|
|
18908
19005
|
if (!raw.includes("@integrity-labs/augmented-mcp")) continue;
|