@integrity-labs/agt-cli 0.28.299 → 0.28.301
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/bin/agt.js +4 -4
- package/dist/{chunk-KMJHNKPQ.js → chunk-E6L7SSE7.js} +218 -27
- package/dist/chunk-E6L7SSE7.js.map +1 -0
- package/dist/{chunk-V23GLSEX.js → chunk-HRER2SCW.js} +3 -3
- package/dist/{claude-pair-runtime-ZJZ3XYH4.js → claude-pair-runtime-BEUY5L6C.js} +2 -2
- package/dist/lib/manager-worker.js +148 -112
- package/dist/lib/manager-worker.js.map +1 -1
- package/dist/mcp/index.js +1 -1
- package/dist/mcp/origami.js +252 -73
- package/dist/mcp/slack-channel.js +146 -72
- package/dist/{persistent-session-RSM62IW7.js → persistent-session-HWVIMZAY.js} +2 -2
- package/dist/{responsiveness-probe-DAKU7GSN.js → responsiveness-probe-WFO4SRHV.js} +2 -2
- package/package.json +1 -1
- package/dist/chunk-KMJHNKPQ.js.map +0 -1
- /package/dist/{chunk-V23GLSEX.js.map → chunk-HRER2SCW.js.map} +0 -0
- /package/dist/{claude-pair-runtime-ZJZ3XYH4.js.map → claude-pair-runtime-BEUY5L6C.js.map} +0 -0
- /package/dist/{persistent-session-RSM62IW7.js.map → persistent-session-HWVIMZAY.js.map} +0 -0
- /package/dist/{responsiveness-probe-DAKU7GSN.js.map → responsiveness-probe-WFO4SRHV.js.map} +0 -0
|
@@ -39,7 +39,7 @@ import {
|
|
|
39
39
|
requireHost,
|
|
40
40
|
safeWriteJsonAtomic,
|
|
41
41
|
setConfigHash
|
|
42
|
-
} from "../chunk-
|
|
42
|
+
} from "../chunk-HRER2SCW.js";
|
|
43
43
|
import {
|
|
44
44
|
getProjectDir as getProjectDir2,
|
|
45
45
|
getReadyTasks,
|
|
@@ -55,6 +55,7 @@ import {
|
|
|
55
55
|
KANBAN_CHECK_COMMAND,
|
|
56
56
|
KANBAN_NUDGE_ACTIONABLE_STATUSES,
|
|
57
57
|
MAX_AVATAR_ENV_URL_BYTES,
|
|
58
|
+
SCHEDULED_TURN_MARKER_FILENAME,
|
|
58
59
|
SUPPRESS_SENTINEL,
|
|
59
60
|
StreamEncoder,
|
|
60
61
|
appendDmFooter,
|
|
@@ -126,17 +127,17 @@ import {
|
|
|
126
127
|
takeZombieDetection,
|
|
127
128
|
transcriptActivityAgeSeconds,
|
|
128
129
|
writeEgressAllowlist
|
|
129
|
-
} from "../chunk-
|
|
130
|
+
} from "../chunk-E6L7SSE7.js";
|
|
130
131
|
import {
|
|
131
132
|
reapOrphanChannelMcps
|
|
132
133
|
} from "../chunk-XWVM4KPK.js";
|
|
133
134
|
|
|
134
135
|
// src/lib/manager-worker.ts
|
|
135
136
|
import { createHash as createHash11 } from "crypto";
|
|
136
|
-
import { readFileSync as readFileSync15, writeFileSync as
|
|
137
|
+
import { readFileSync as readFileSync15, writeFileSync as writeFileSync8, mkdirSync as mkdirSync7, existsSync as existsSync9, rmSync as rmSync4, readdirSync as readdirSync5, statSync as statSync4, copyFileSync } from "fs";
|
|
137
138
|
import { execFileSync as syncExecFile } from "child_process";
|
|
138
|
-
import { join as
|
|
139
|
-
import { homedir as
|
|
139
|
+
import { join as join18, dirname as dirname6 } from "path";
|
|
140
|
+
import { homedir as homedir10 } from "os";
|
|
140
141
|
import { fileURLToPath } from "url";
|
|
141
142
|
|
|
142
143
|
// src/lib/claude-code-upgrade-throttle.ts
|
|
@@ -4703,6 +4704,9 @@ function closeScheduledRunsForCode(codeName, outcome, reason) {
|
|
|
4703
4704
|
|
|
4704
4705
|
// src/lib/manager/scheduler/kanban-route.ts
|
|
4705
4706
|
import { createHash as createHash9 } from "crypto";
|
|
4707
|
+
import { writeFileSync as writeFileSync6, renameSync } from "fs";
|
|
4708
|
+
import { homedir as homedir7 } from "os";
|
|
4709
|
+
import { join as join15 } from "path";
|
|
4706
4710
|
|
|
4707
4711
|
// src/lib/manager/delivery/scheduled-output.ts
|
|
4708
4712
|
async function deliverScheduledTaskOutput(agentCodeName, agentId, rawTarget, body, taskId) {
|
|
@@ -4989,6 +4993,32 @@ var SCHEDULED_CARD_PLAN_INSTRUCTION = `
|
|
|
4989
4993
|
---
|
|
4990
4994
|
[planning task \u2014 system]
|
|
4991
4995
|
This is a board-PLANNING task. Review your current board with kanban_list, then create each item of today's plan as its OWN card using kanban_add (status: todo, with a sensible priority and estimate). Do NOT just write the plan as text \u2014 the cards you create with kanban_add ARE the deliverable; nothing parses a plan out of this card's result. When done, write a brief summary of the plan you created as this card's result and mark it done.`;
|
|
4996
|
+
function resolveScheduledSlackTarget(task) {
|
|
4997
|
+
if (task.deliveryChannel !== "slack") return void 0;
|
|
4998
|
+
const to = task.deliveryTo;
|
|
4999
|
+
if (to == null) return void 0;
|
|
5000
|
+
if (typeof to === "string") {
|
|
5001
|
+
if (!to.startsWith("channel:")) return void 0;
|
|
5002
|
+
const id = to.slice("channel:".length).trim();
|
|
5003
|
+
return id ? { channel_id: id } : void 0;
|
|
5004
|
+
}
|
|
5005
|
+
const parsed = parseDeliveryTarget(to);
|
|
5006
|
+
if (!isParseError(parsed) && parsed.kind === "channel" && parsed.provider === "slack" && parsed.channel_id) {
|
|
5007
|
+
return { channel_id: parsed.channel_id, ...parsed.thread_ts ? { thread_ts: parsed.thread_ts } : {} };
|
|
5008
|
+
}
|
|
5009
|
+
return void 0;
|
|
5010
|
+
}
|
|
5011
|
+
function stampScheduledTurnMarker(codeName, taskId, target) {
|
|
5012
|
+
try {
|
|
5013
|
+
const file = join15(homedir7(), ".augmented", codeName, SCHEDULED_TURN_MARKER_FILENAME);
|
|
5014
|
+
const marker = { ts: Date.now(), task_id: taskId, ...target ? { target } : {} };
|
|
5015
|
+
const tmp = `${file}.tmp`;
|
|
5016
|
+
writeFileSync6(tmp, JSON.stringify(marker), "utf8");
|
|
5017
|
+
renameSync(tmp, file);
|
|
5018
|
+
} catch (err) {
|
|
5019
|
+
log(`[scheduled-kanban] scheduled-turn marker write failed for '${codeName}': ${err.message}`);
|
|
5020
|
+
}
|
|
5021
|
+
}
|
|
4992
5022
|
async function routeScheduledTaskViaKanban(codeName, agentId, task, prompt) {
|
|
4993
5023
|
const priorRuns = await fetchPriorScheduledRuns(agentId, task.taskId);
|
|
4994
5024
|
const contextBlocks = buildScheduledTaskContextBlocks({ priorRuns, timezone: task.timezone });
|
|
@@ -5021,6 +5051,7 @@ async function routeScheduledTaskViaKanban(codeName, agentId, task, prompt) {
|
|
|
5021
5051
|
const nudge = TOOL_DELIVERED_TEMPLATES.has(task.templateId) ? `You have a new scheduled task on your kanban board: id=${kanban_item_id} title=${JSON.stringify(task.name)}. Call kanban_move("${kanban_item_id}", "in_progress"), then do the work described on the card. This task DELIVERS VIA A TOOL, not the card: you MUST call the tool the task specifies \u2014 for the weekly performance review that is submit_performance_review \u2014 to actually deliver it. Writing a summary to the card does NOT send anything and is NOT a substitute for the tool call. After the tool call, note briefly on the card what you sent and mark it done.
|
|
5022
5052
|
` + formatRunMarker(run_id) : `You have a new scheduled task on your kanban board: id=${kanban_item_id} title=${JSON.stringify(task.name)}. Call kanban_move("${kanban_item_id}", "in_progress"), do the work described on the card, then write the finished result onto the card and mark it done. Do NOT send, post, or message the result to anyone yourself \u2014 the result you write on the card IS the message that will be delivered to the user; delivery happens automatically from the card.
|
|
5023
5053
|
` + suppressionTeaching + formatRunMarker(run_id);
|
|
5054
|
+
stampScheduledTurnMarker(codeName, task.taskId, resolveScheduledSlackTarget(task));
|
|
5024
5055
|
let injectStatus;
|
|
5025
5056
|
try {
|
|
5026
5057
|
injectStatus = await injectMessageWithStatus(codeName, "task", nudge, { task_name: "scheduled-task" }, log);
|
|
@@ -5165,10 +5196,10 @@ async function processClaudeTaskResult(codeName, agentId, templateId, rawOutput,
|
|
|
5165
5196
|
|
|
5166
5197
|
// src/lib/manager/scheduler/execution.ts
|
|
5167
5198
|
import { createHash as createHash10 } from "crypto";
|
|
5168
|
-
import { homedir as
|
|
5169
|
-
import { join as
|
|
5199
|
+
import { homedir as homedir8 } from "os";
|
|
5200
|
+
import { join as join16 } from "path";
|
|
5170
5201
|
function claudePidFilePath() {
|
|
5171
|
-
return
|
|
5202
|
+
return join16(homedir8(), ".augmented", "manager-claude-pids.json");
|
|
5172
5203
|
}
|
|
5173
5204
|
var inFlightClaudePids = /* @__PURE__ */ new Map();
|
|
5174
5205
|
function registerClaudeSpawn(record) {
|
|
@@ -5368,15 +5399,15 @@ function partitionActionableByPoison(actionable, states, config2) {
|
|
|
5368
5399
|
}
|
|
5369
5400
|
|
|
5370
5401
|
// src/lib/restart-flags.ts
|
|
5371
|
-
import { existsSync as existsSync8, mkdirSync as mkdirSync6, readdirSync as readdirSync4, readFileSync as readFileSync14, renameSync, rmSync as rmSync3, writeFileSync as
|
|
5372
|
-
import { homedir as
|
|
5373
|
-
import { join as
|
|
5402
|
+
import { existsSync as existsSync8, mkdirSync as mkdirSync6, readdirSync as readdirSync4, readFileSync as readFileSync14, renameSync as renameSync2, rmSync as rmSync3, writeFileSync as writeFileSync7 } from "fs";
|
|
5403
|
+
import { homedir as homedir9 } from "os";
|
|
5404
|
+
import { join as join17 } from "path";
|
|
5374
5405
|
import { randomUUID } from "crypto";
|
|
5375
5406
|
function restartFlagsDir() {
|
|
5376
|
-
return
|
|
5407
|
+
return join17(homedir9(), ".augmented", "restart-flags");
|
|
5377
5408
|
}
|
|
5378
5409
|
function flagPath(codeName) {
|
|
5379
|
-
return
|
|
5410
|
+
return join17(restartFlagsDir(), `${codeName}.flag`);
|
|
5380
5411
|
}
|
|
5381
5412
|
function readRestartFlags() {
|
|
5382
5413
|
const dir = restartFlagsDir();
|
|
@@ -5385,7 +5416,7 @@ function readRestartFlags() {
|
|
|
5385
5416
|
for (const entry of readdirSync4(dir)) {
|
|
5386
5417
|
if (!entry.endsWith(".flag")) continue;
|
|
5387
5418
|
try {
|
|
5388
|
-
const raw = readFileSync14(
|
|
5419
|
+
const raw = readFileSync14(join17(dir, entry), "utf8");
|
|
5389
5420
|
const parsed = JSON.parse(raw);
|
|
5390
5421
|
if (typeof parsed.codeName !== "string" || parsed.codeName.length === 0) {
|
|
5391
5422
|
parsed.codeName = entry.replace(/\.flag$/, "");
|
|
@@ -6616,7 +6647,7 @@ var runningChannelSecretHashes = /* @__PURE__ */ new Map();
|
|
|
6616
6647
|
var sessionLaunchManagedStructure = /* @__PURE__ */ new Map();
|
|
6617
6648
|
function projectMcpHash(_codeName, projectDir) {
|
|
6618
6649
|
try {
|
|
6619
|
-
const raw = readFileSync15(
|
|
6650
|
+
const raw = readFileSync15(join18(projectDir, ".mcp.json"), "utf-8");
|
|
6620
6651
|
return createHash11("sha256").update(canonicalJson(JSON.parse(raw))).digest("hex");
|
|
6621
6652
|
} catch {
|
|
6622
6653
|
return null;
|
|
@@ -6624,7 +6655,7 @@ function projectMcpHash(_codeName, projectDir) {
|
|
|
6624
6655
|
}
|
|
6625
6656
|
function projectMcpKeys(_codeName, projectDir) {
|
|
6626
6657
|
try {
|
|
6627
|
-
const raw = readFileSync15(
|
|
6658
|
+
const raw = readFileSync15(join18(projectDir, ".mcp.json"), "utf-8");
|
|
6628
6659
|
const parsed = JSON.parse(raw);
|
|
6629
6660
|
const servers = parsed.mcpServers;
|
|
6630
6661
|
if (!servers || typeof servers !== "object") return /* @__PURE__ */ new Set();
|
|
@@ -6642,7 +6673,7 @@ function seedSessionLaunchBaselines(codeName, projectDir) {
|
|
|
6642
6673
|
else runningMcpServerKeys.delete(codeName);
|
|
6643
6674
|
let launchStructure = null;
|
|
6644
6675
|
try {
|
|
6645
|
-
const raw = readFileSync15(
|
|
6676
|
+
const raw = readFileSync15(join18(projectDir, ".mcp.json"), "utf-8");
|
|
6646
6677
|
launchStructure = managedMcpStructureHashFromFile(
|
|
6647
6678
|
JSON.parse(raw),
|
|
6648
6679
|
isManagedMcpServerKey
|
|
@@ -6742,7 +6773,7 @@ async function runAgentSessionToolBindProbes(agent, integrations, projectDir, op
|
|
|
6742
6773
|
if (result && result.rebindCandidates.length > 0 && hostFlagStore().getBoolean("session-tool-rebind")) {
|
|
6743
6774
|
let mcpJsonForRebind = null;
|
|
6744
6775
|
try {
|
|
6745
|
-
mcpJsonForRebind = JSON.parse(readFileSync15(
|
|
6776
|
+
mcpJsonForRebind = JSON.parse(readFileSync15(join18(projectDir, ".mcp.json"), "utf-8"));
|
|
6746
6777
|
} catch {
|
|
6747
6778
|
mcpJsonForRebind = null;
|
|
6748
6779
|
}
|
|
@@ -6871,7 +6902,7 @@ function checkMcpConfigDriftAndScheduleRestart(codeName, projectDir) {
|
|
|
6871
6902
|
function projectChannelSecretHash(projectDir) {
|
|
6872
6903
|
try {
|
|
6873
6904
|
const entries = parseEnvIntegrations(
|
|
6874
|
-
readFileSync15(
|
|
6905
|
+
readFileSync15(join18(projectDir, ".env.integrations"), "utf-8")
|
|
6875
6906
|
);
|
|
6876
6907
|
return channelSecretValueHash(entries, CHANNEL_SECRET_ENV_KEYS);
|
|
6877
6908
|
} catch {
|
|
@@ -6958,7 +6989,7 @@ var agentRestartTimezoneInputs = /* @__PURE__ */ new Map();
|
|
|
6958
6989
|
var lastVersionCheckAt = 0;
|
|
6959
6990
|
var VERSION_CHECK_INTERVAL_MS = 5 * 60 * 1e3;
|
|
6960
6991
|
var lastResponsivenessProbeAt = 0;
|
|
6961
|
-
var agtCliVersion = true ? "0.28.
|
|
6992
|
+
var agtCliVersion = true ? "0.28.301" : "dev";
|
|
6962
6993
|
function resolveBrewPath(execFileSync2) {
|
|
6963
6994
|
try {
|
|
6964
6995
|
const out = execFileSync2("which", ["brew"], { timeout: 5e3 }).toString().trim();
|
|
@@ -7154,7 +7185,7 @@ function ensureClaudeManagedSettings(path = claudeManagedSettingsPath()) {
|
|
|
7154
7185
|
if (settings.channelsEnabled === true) return "ok";
|
|
7155
7186
|
settings.channelsEnabled = true;
|
|
7156
7187
|
mkdirSync7(dirname6(path), { recursive: true });
|
|
7157
|
-
|
|
7188
|
+
writeFileSync8(path, `${JSON.stringify(settings, null, 2)}
|
|
7158
7189
|
`);
|
|
7159
7190
|
log(`[managed-settings] set channelsEnabled:true in ${path} (ENG-5786 \u2014 unblocks Claude Code channels)`);
|
|
7160
7191
|
return "ok";
|
|
@@ -7255,7 +7286,7 @@ ${r.stderr}`;
|
|
|
7255
7286
|
}
|
|
7256
7287
|
var UPDATE_CHECK_INTERVAL_MS = 5 * 60 * 1e3;
|
|
7257
7288
|
function selfUpdateAppliedMarkerPath() {
|
|
7258
|
-
return
|
|
7289
|
+
return join18(homedir10(), ".augmented", ".last-self-update-applied");
|
|
7259
7290
|
}
|
|
7260
7291
|
var selfUpdateUpToDateLogged = false;
|
|
7261
7292
|
var restartAfterUpgrade = false;
|
|
@@ -7279,7 +7310,7 @@ async function checkAndUpdateCli(opts) {
|
|
|
7279
7310
|
const isNpmGlobal = !isBrewFormula && resolvedPath.includes("node_modules");
|
|
7280
7311
|
if (!isBrewFormula && !isNpmGlobal) return "noop";
|
|
7281
7312
|
const { readFileSync: readF, writeFileSync: writeF } = await import("fs");
|
|
7282
|
-
const markerPath =
|
|
7313
|
+
const markerPath = join18(homedir10(), ".augmented", ".last-update-check");
|
|
7283
7314
|
if (!force) {
|
|
7284
7315
|
try {
|
|
7285
7316
|
const lastCheck = parseInt(readF(markerPath, "utf-8").trim(), 10);
|
|
@@ -7558,13 +7589,13 @@ async function checkClaudeAuth() {
|
|
|
7558
7589
|
var evalEmptyMcpConfigPath = null;
|
|
7559
7590
|
function ensureEvalEmptyMcpConfig() {
|
|
7560
7591
|
if (evalEmptyMcpConfigPath && existsSync9(evalEmptyMcpConfigPath)) return evalEmptyMcpConfigPath;
|
|
7561
|
-
const dir =
|
|
7592
|
+
const dir = join18(homedir10(), ".augmented");
|
|
7562
7593
|
try {
|
|
7563
7594
|
mkdirSync7(dir, { recursive: true });
|
|
7564
7595
|
} catch {
|
|
7565
7596
|
}
|
|
7566
|
-
const p =
|
|
7567
|
-
|
|
7597
|
+
const p = join18(dir, ".eval-empty-mcp.json");
|
|
7598
|
+
writeFileSync8(p, JSON.stringify({ mcpServers: {} }));
|
|
7568
7599
|
evalEmptyMcpConfigPath = p;
|
|
7569
7600
|
return p;
|
|
7570
7601
|
}
|
|
@@ -7589,7 +7620,7 @@ async function runEvalClaude(prompt, model) {
|
|
|
7589
7620
|
""
|
|
7590
7621
|
];
|
|
7591
7622
|
const { stdout } = await execFilePromiseLong(resolveClaudeBinary(), args, {
|
|
7592
|
-
cwd:
|
|
7623
|
+
cwd: homedir10(),
|
|
7593
7624
|
timeout: 12e4,
|
|
7594
7625
|
stdin: "ignore",
|
|
7595
7626
|
env: childEnv,
|
|
@@ -7655,10 +7686,10 @@ function resolveConversationEvalBackend() {
|
|
|
7655
7686
|
return conversationEvalBackend;
|
|
7656
7687
|
}
|
|
7657
7688
|
function getStateFile() {
|
|
7658
|
-
return
|
|
7689
|
+
return join18(config?.configDir ?? join18(process.env["HOME"] ?? "/tmp", ".augmented"), "manager-state.json");
|
|
7659
7690
|
}
|
|
7660
7691
|
function channelHashCacheDir() {
|
|
7661
|
-
return config?.configDir ??
|
|
7692
|
+
return config?.configDir ?? join18(process.env["HOME"] ?? "/tmp", ".augmented");
|
|
7662
7693
|
}
|
|
7663
7694
|
function loadChannelHashCache2() {
|
|
7664
7695
|
loadChannelHashCache(agentState.knownChannelConfigHashes, channelHashCacheDir());
|
|
@@ -7669,7 +7700,7 @@ function saveChannelHashCache2() {
|
|
|
7669
7700
|
var _channelQuarantineStore = null;
|
|
7670
7701
|
function channelQuarantineStore() {
|
|
7671
7702
|
if (!_channelQuarantineStore) {
|
|
7672
|
-
const dir = config?.configDir ??
|
|
7703
|
+
const dir = config?.configDir ?? join18(process.env["HOME"] ?? "/tmp", ".augmented");
|
|
7673
7704
|
_channelQuarantineStore = new ChannelQuarantineStore(defaultQuarantinePath(dir));
|
|
7674
7705
|
}
|
|
7675
7706
|
return _channelQuarantineStore;
|
|
@@ -7677,7 +7708,7 @@ function channelQuarantineStore() {
|
|
|
7677
7708
|
var _hostFlagStore = null;
|
|
7678
7709
|
function hostFlagStore() {
|
|
7679
7710
|
if (!_hostFlagStore) {
|
|
7680
|
-
const dir = config?.configDir ??
|
|
7711
|
+
const dir = config?.configDir ?? join18(process.env["HOME"] ?? "/tmp", ".augmented");
|
|
7681
7712
|
_hostFlagStore = new HostFlagStore({ cachePath: defaultFlagsCachePath(dir), log });
|
|
7682
7713
|
}
|
|
7683
7714
|
return _hostFlagStore;
|
|
@@ -7744,13 +7775,13 @@ function parseSkillFrontmatter(content) {
|
|
|
7744
7775
|
return out;
|
|
7745
7776
|
}
|
|
7746
7777
|
async function refreshSkillsIndexInClaudeMd(configDir, codeName, log2) {
|
|
7747
|
-
const { readdirSync: readdirSync6, readFileSync: rfs, existsSync: ex, writeFileSync:
|
|
7748
|
-
const skillsDir =
|
|
7749
|
-
const claudeMdPath =
|
|
7778
|
+
const { readdirSync: readdirSync6, readFileSync: rfs, existsSync: ex, writeFileSync: writeFileSync9 } = await import("fs");
|
|
7779
|
+
const skillsDir = join18(configDir, codeName, "project", ".claude", "skills");
|
|
7780
|
+
const claudeMdPath = join18(configDir, codeName, "project", "CLAUDE.md");
|
|
7750
7781
|
if (!ex(skillsDir) || !ex(claudeMdPath)) return;
|
|
7751
7782
|
const entries = [];
|
|
7752
7783
|
for (const dir of readdirSync6(skillsDir).sort()) {
|
|
7753
|
-
const skillFile =
|
|
7784
|
+
const skillFile = join18(skillsDir, dir, "SKILL.md");
|
|
7754
7785
|
if (!ex(skillFile)) continue;
|
|
7755
7786
|
try {
|
|
7756
7787
|
const { name, description } = parseSkillFrontmatter(rfs(skillFile, "utf-8"));
|
|
@@ -7792,7 +7823,7 @@ ${SKILLS_INDEX_END}`;
|
|
|
7792
7823
|
next = current.trimEnd() + "\n\n" + section + "\n";
|
|
7793
7824
|
}
|
|
7794
7825
|
if (next !== current) {
|
|
7795
|
-
|
|
7826
|
+
writeFileSync9(claudeMdPath, next, "utf-8");
|
|
7796
7827
|
log2(`Refreshed skills index in CLAUDE.md for '${codeName}' (${entries.length} skills)`);
|
|
7797
7828
|
}
|
|
7798
7829
|
}
|
|
@@ -7813,7 +7844,7 @@ function flushRestartedAgentDiagnostics(hostId, codeNames) {
|
|
|
7813
7844
|
if (codeNames.length === 0) return;
|
|
7814
7845
|
void (async () => {
|
|
7815
7846
|
try {
|
|
7816
|
-
const { collectDiagnostics } = await import("../persistent-session-
|
|
7847
|
+
const { collectDiagnostics } = await import("../persistent-session-HWVIMZAY.js");
|
|
7817
7848
|
await api.post("/host/heartbeat", {
|
|
7818
7849
|
host_id: hostId,
|
|
7819
7850
|
agent_diagnostics: collectDiagnostics(codeNames)
|
|
@@ -7911,7 +7942,7 @@ async function pollCycle() {
|
|
|
7911
7942
|
}
|
|
7912
7943
|
try {
|
|
7913
7944
|
const { detectHostSecurity } = await import("../host-security-6PDFG7F5.js");
|
|
7914
|
-
const { collectDiagnostics } = await import("../persistent-session-
|
|
7945
|
+
const { collectDiagnostics } = await import("../persistent-session-HWVIMZAY.js");
|
|
7915
7946
|
const diagCodeNames = [...agentState.persistentSessionAgents];
|
|
7916
7947
|
const agentDiagnostics = diagCodeNames.length > 0 ? collectDiagnostics(diagCodeNames) : void 0;
|
|
7917
7948
|
let tailscaleHostname;
|
|
@@ -8059,7 +8090,7 @@ async function pollCycle() {
|
|
|
8059
8090
|
const {
|
|
8060
8091
|
collectResponsivenessProbes,
|
|
8061
8092
|
getResponsivenessIntervalMs
|
|
8062
|
-
} = await import("../responsiveness-probe-
|
|
8093
|
+
} = await import("../responsiveness-probe-WFO4SRHV.js");
|
|
8063
8094
|
const probeIntervalMs = getResponsivenessIntervalMs();
|
|
8064
8095
|
if (now - lastResponsivenessProbeAt > probeIntervalMs) {
|
|
8065
8096
|
const probeCodeNames = [...agentState.persistentSessionAgents];
|
|
@@ -8091,7 +8122,7 @@ async function pollCycle() {
|
|
|
8091
8122
|
collectResponsivenessProbes,
|
|
8092
8123
|
livePendingInboundOldestAgeSeconds,
|
|
8093
8124
|
parkPendingInbound
|
|
8094
|
-
} = await import("../responsiveness-probe-
|
|
8125
|
+
} = await import("../responsiveness-probe-WFO4SRHV.js");
|
|
8095
8126
|
const { getProjectDir: wedgeProjectDir } = await import("../claude-scheduler-FATCLHDM.js");
|
|
8096
8127
|
const wedgeNow = /* @__PURE__ */ new Date();
|
|
8097
8128
|
const liveAgents = agentState.persistentSessionAgents;
|
|
@@ -8183,10 +8214,10 @@ async function pollCycle() {
|
|
|
8183
8214
|
const paneTail = readFileSync15(paneLogPath(codeName), "utf8").slice(-65536);
|
|
8184
8215
|
const transient = detectTransientApiErrorInLog(paneTail);
|
|
8185
8216
|
if (transient) {
|
|
8186
|
-
const wedgeHome =
|
|
8217
|
+
const wedgeHome = join18(homedir10(), ".augmented", codeName);
|
|
8187
8218
|
if (existsSync9(wedgeHome)) {
|
|
8188
8219
|
atomicWriteFileSync(
|
|
8189
|
-
|
|
8220
|
+
join18(wedgeHome, "watchdog-give-up.json"),
|
|
8190
8221
|
JSON.stringify({
|
|
8191
8222
|
gave_up_at: wedgeNow.toISOString(),
|
|
8192
8223
|
reason: "transient_overload"
|
|
@@ -8435,7 +8466,7 @@ async function pollCycle() {
|
|
|
8435
8466
|
} catch {
|
|
8436
8467
|
}
|
|
8437
8468
|
killAgentChannelProcesses(prev.codeName, { log });
|
|
8438
|
-
const agentDir =
|
|
8469
|
+
const agentDir = join18(adapter.getAgentDir(prev.codeName), "provision");
|
|
8439
8470
|
await cleanupAgentFiles(prev.codeName, agentDir);
|
|
8440
8471
|
clearAgentCaches(prev.agentId, prev.codeName);
|
|
8441
8472
|
}
|
|
@@ -8522,10 +8553,10 @@ async function pollCycle() {
|
|
|
8522
8553
|
// pending-inbound marker. Best-effort: a write failure is logged by
|
|
8523
8554
|
// the watchdog, never fails the poll cycle.
|
|
8524
8555
|
signalGiveUp: (codeName) => {
|
|
8525
|
-
const dir =
|
|
8556
|
+
const dir = join18(homedir10(), ".augmented", codeName);
|
|
8526
8557
|
if (!existsSync9(dir)) return;
|
|
8527
8558
|
atomicWriteFileSync(
|
|
8528
|
-
|
|
8559
|
+
join18(dir, "watchdog-give-up.json"),
|
|
8529
8560
|
JSON.stringify({ gave_up_at: (/* @__PURE__ */ new Date()).toISOString() })
|
|
8530
8561
|
);
|
|
8531
8562
|
}
|
|
@@ -8655,7 +8686,7 @@ async function processAgent(agent, agentStates) {
|
|
|
8655
8686
|
}
|
|
8656
8687
|
const now = (/* @__PURE__ */ new Date()).toISOString();
|
|
8657
8688
|
const adapter = resolveAgentFramework(agent.code_name);
|
|
8658
|
-
let agentDir =
|
|
8689
|
+
let agentDir = join18(adapter.getAgentDir(agent.code_name), "provision");
|
|
8659
8690
|
if (agent.status === "draft" || agent.status === "paused") {
|
|
8660
8691
|
if (previousKnownStatus !== agent.status) {
|
|
8661
8692
|
log(`Agent '${agent.code_name}' is ${agent.status}, skipping provisioning`);
|
|
@@ -8839,7 +8870,7 @@ async function processAgent(agent, agentStates) {
|
|
|
8839
8870
|
const frameworkId = refreshData.agent.framework ?? DEFAULT_FRAMEWORK;
|
|
8840
8871
|
agentFrameworkCache.set(agent.code_name, frameworkId);
|
|
8841
8872
|
const frameworkAdapter = getFramework(frameworkId);
|
|
8842
|
-
agentDir =
|
|
8873
|
+
agentDir = join18(frameworkAdapter.getAgentDir(agent.code_name), "provision");
|
|
8843
8874
|
cacheAgentDeliveryMetadata(agent.code_name, refreshData);
|
|
8844
8875
|
agentRestartTimezoneInputs.set(agent.code_name, {
|
|
8845
8876
|
agentTimezone: typeof refreshData.agent.timezone === "string" ? refreshData.agent.timezone : null,
|
|
@@ -8886,7 +8917,7 @@ async function processAgent(agent, agentStates) {
|
|
|
8886
8917
|
const changedFiles = [];
|
|
8887
8918
|
mkdirSync7(agentDir, { recursive: true });
|
|
8888
8919
|
for (const artifact of artifacts) {
|
|
8889
|
-
const filePath =
|
|
8920
|
+
const filePath = join18(agentDir, artifact.relativePath);
|
|
8890
8921
|
let existingHash;
|
|
8891
8922
|
let newHash;
|
|
8892
8923
|
let writeContent = artifact.content;
|
|
@@ -8905,7 +8936,7 @@ async function processAgent(agent, agentStates) {
|
|
|
8905
8936
|
};
|
|
8906
8937
|
newHash = sha256(stripDynamicSections(artifact.content));
|
|
8907
8938
|
try {
|
|
8908
|
-
const projectClaudeMd =
|
|
8939
|
+
const projectClaudeMd = join18(config.configDir, agent.code_name, "project", "CLAUDE.md");
|
|
8909
8940
|
const existing = readFileSync15(projectClaudeMd, "utf-8");
|
|
8910
8941
|
existingHash = sha256(stripDynamicSections(existing));
|
|
8911
8942
|
} catch {
|
|
@@ -8946,26 +8977,26 @@ async function processAgent(agent, agentStates) {
|
|
|
8946
8977
|
}
|
|
8947
8978
|
}
|
|
8948
8979
|
if (changedFiles.length > 0) {
|
|
8949
|
-
const isFirst = !existsSync9(
|
|
8980
|
+
const isFirst = !existsSync9(join18(agentDir, "CHARTER.md"));
|
|
8950
8981
|
const verb = isFirst ? "Provisioning" : "Updating";
|
|
8951
8982
|
const fileNames = changedFiles.map((f) => f.relativePath).join(", ");
|
|
8952
8983
|
log(`${verb} '${agent.code_name}': ${fileNames}`);
|
|
8953
8984
|
for (const file of changedFiles) {
|
|
8954
|
-
const filePath =
|
|
8985
|
+
const filePath = join18(agentDir, file.relativePath);
|
|
8955
8986
|
mkdirSync7(dirname6(filePath), { recursive: true });
|
|
8956
8987
|
if (file.relativePath === ".mcp.json") {
|
|
8957
8988
|
safeWriteJsonAtomic(filePath, file.content, { mode: 384 });
|
|
8958
8989
|
} else {
|
|
8959
|
-
|
|
8990
|
+
writeFileSync8(filePath, file.content);
|
|
8960
8991
|
}
|
|
8961
8992
|
}
|
|
8962
8993
|
try {
|
|
8963
|
-
const provSkillsDir =
|
|
8994
|
+
const provSkillsDir = join18(agentDir, ".claude", "skills");
|
|
8964
8995
|
if (existsSync9(provSkillsDir)) {
|
|
8965
8996
|
for (const folder of readdirSync5(provSkillsDir)) {
|
|
8966
8997
|
if (folder.startsWith("knowledge-")) {
|
|
8967
8998
|
try {
|
|
8968
|
-
rmSync4(
|
|
8999
|
+
rmSync4(join18(provSkillsDir, folder), { recursive: true });
|
|
8969
9000
|
} catch {
|
|
8970
9001
|
}
|
|
8971
9002
|
}
|
|
@@ -8978,7 +9009,7 @@ async function processAgent(agent, agentStates) {
|
|
|
8978
9009
|
const trackedFiles2 = frameworkAdapter.driftTrackedFiles();
|
|
8979
9010
|
const hashes = /* @__PURE__ */ new Map();
|
|
8980
9011
|
for (const file of trackedFiles2) {
|
|
8981
|
-
const h = hashFile(
|
|
9012
|
+
const h = hashFile(join18(agentDir, file));
|
|
8982
9013
|
if (h) hashes.set(file, h);
|
|
8983
9014
|
}
|
|
8984
9015
|
agentState.writtenHashes.set(agent.agent_id, hashes);
|
|
@@ -8996,14 +9027,14 @@ async function processAgent(agent, agentStates) {
|
|
|
8996
9027
|
}
|
|
8997
9028
|
if (Array.isArray(refreshData.workflows)) {
|
|
8998
9029
|
try {
|
|
8999
|
-
const provWorkflowsDir =
|
|
9030
|
+
const provWorkflowsDir = join18(agentDir, ".claude", "workflows");
|
|
9000
9031
|
if (existsSync9(provWorkflowsDir)) {
|
|
9001
9032
|
const expected = new Set(refreshData.workflows.map((w) => `${w.name}.js`));
|
|
9002
9033
|
for (const file of readdirSync5(provWorkflowsDir)) {
|
|
9003
9034
|
if (!file.endsWith(".js")) continue;
|
|
9004
9035
|
if (expected.has(file)) continue;
|
|
9005
9036
|
try {
|
|
9006
|
-
rmSync4(
|
|
9037
|
+
rmSync4(join18(provWorkflowsDir, file));
|
|
9007
9038
|
} catch {
|
|
9008
9039
|
}
|
|
9009
9040
|
}
|
|
@@ -9063,7 +9094,7 @@ async function processAgent(agent, agentStates) {
|
|
|
9063
9094
|
if (written && existsSync9(agentDir)) {
|
|
9064
9095
|
const driftedFiles = [];
|
|
9065
9096
|
for (const [file, expectedHash] of written) {
|
|
9066
|
-
const localHash = hashFile(
|
|
9097
|
+
const localHash = hashFile(join18(agentDir, file));
|
|
9067
9098
|
if (localHash && localHash !== expectedHash) {
|
|
9068
9099
|
driftedFiles.push(file);
|
|
9069
9100
|
}
|
|
@@ -9074,7 +9105,7 @@ async function processAgent(agent, agentStates) {
|
|
|
9074
9105
|
try {
|
|
9075
9106
|
const localHashes = {};
|
|
9076
9107
|
for (const file of driftedFiles) {
|
|
9077
|
-
localHashes[file] = hashFile(
|
|
9108
|
+
localHashes[file] = hashFile(join18(agentDir, file));
|
|
9078
9109
|
}
|
|
9079
9110
|
await api.post("/host/drift", {
|
|
9080
9111
|
agent_id: agent.agent_id,
|
|
@@ -9261,7 +9292,7 @@ async function processAgent(agent, agentStates) {
|
|
|
9261
9292
|
const addedChannels = [...restartDecision.added];
|
|
9262
9293
|
const writeDmNoticeMarkers = isChannelAddRestart ? () => {
|
|
9263
9294
|
try {
|
|
9264
|
-
const agentAugmentedDir =
|
|
9295
|
+
const agentAugmentedDir = join18(homedir10(), ".augmented", agent.code_name);
|
|
9265
9296
|
mkdirSync7(agentAugmentedDir, { recursive: true });
|
|
9266
9297
|
const markerJson = JSON.stringify({
|
|
9267
9298
|
version: 1,
|
|
@@ -9269,7 +9300,7 @@ async function processAgent(agent, agentStates) {
|
|
|
9269
9300
|
added: addedChannels
|
|
9270
9301
|
});
|
|
9271
9302
|
for (const file of ["slack-channel-add-restart.json", "telegram-channel-add-restart.json"]) {
|
|
9272
|
-
atomicWriteFileSync(
|
|
9303
|
+
atomicWriteFileSync(join18(agentAugmentedDir, file), markerJson);
|
|
9273
9304
|
}
|
|
9274
9305
|
} catch (err) {
|
|
9275
9306
|
log(`[hot-reload] channel-add DM-notice marker write failed for '${agent.code_name}' (non-fatal): ${err.message}`);
|
|
@@ -9422,18 +9453,18 @@ async function processAgent(agent, agentStates) {
|
|
|
9422
9453
|
if (agentSessionMode === "persistent" && (agentFrameworkCache.get(agent.code_name) ?? DEFAULT_FRAMEWORK) === "claude-code") {
|
|
9423
9454
|
try {
|
|
9424
9455
|
const agentProvisionDir = agentDir;
|
|
9425
|
-
const projectDir =
|
|
9456
|
+
const projectDir = join18(homedir10(), ".augmented", agent.code_name, "project");
|
|
9426
9457
|
mkdirSync7(agentProvisionDir, { recursive: true });
|
|
9427
9458
|
mkdirSync7(projectDir, { recursive: true });
|
|
9428
|
-
const provisionMcpPath =
|
|
9429
|
-
const projectMcpPath =
|
|
9459
|
+
const provisionMcpPath = join18(agentProvisionDir, ".mcp.json");
|
|
9460
|
+
const projectMcpPath = join18(projectDir, ".mcp.json");
|
|
9430
9461
|
let mcpConfig = { mcpServers: {} };
|
|
9431
9462
|
try {
|
|
9432
9463
|
mcpConfig = JSON.parse(readFileSync15(provisionMcpPath, "utf-8"));
|
|
9433
9464
|
if (!mcpConfig.mcpServers) mcpConfig.mcpServers = {};
|
|
9434
9465
|
} catch {
|
|
9435
9466
|
}
|
|
9436
|
-
const localDirectChatChannel =
|
|
9467
|
+
const localDirectChatChannel = join18(homedir10(), ".augmented", "_mcp", "direct-chat-channel.js");
|
|
9437
9468
|
const directChatTeamSettings = refreshData.team?.settings;
|
|
9438
9469
|
const directChatTz = (() => {
|
|
9439
9470
|
const tz = directChatTeamSettings?.["timezone"];
|
|
@@ -9459,7 +9490,7 @@ async function processAgent(agent, agentStates) {
|
|
|
9459
9490
|
// ~/.augmented/<codeName>/.current-turn-initiator.json. Note getAgentDir
|
|
9460
9491
|
// returns the agent root (NOT the /provision subdir `agentDir` points at),
|
|
9461
9492
|
// so it byte-matches the broker readers' path.
|
|
9462
|
-
AGT_TURN_INITIATOR_FILE:
|
|
9493
|
+
AGT_TURN_INITIATOR_FILE: join18(
|
|
9463
9494
|
frameworkAdapter.getAgentDir(agent.code_name),
|
|
9464
9495
|
".current-turn-initiator.json"
|
|
9465
9496
|
)
|
|
@@ -9479,7 +9510,7 @@ async function processAgent(agent, agentStates) {
|
|
|
9479
9510
|
log(`Channel credentials written for '${agent.code_name}/direct-chat'`);
|
|
9480
9511
|
}
|
|
9481
9512
|
}
|
|
9482
|
-
const staleChannelsPath =
|
|
9513
|
+
const staleChannelsPath = join18(projectDir, ".mcp-channels.json");
|
|
9483
9514
|
if (existsSync9(staleChannelsPath)) {
|
|
9484
9515
|
try {
|
|
9485
9516
|
rmSync4(staleChannelsPath, { force: true });
|
|
@@ -9551,7 +9582,7 @@ async function processAgent(agent, agentStates) {
|
|
|
9551
9582
|
}
|
|
9552
9583
|
if (hostFlagStore().getBoolean("connectivity-probe")) {
|
|
9553
9584
|
try {
|
|
9554
|
-
const probeProjectDir =
|
|
9585
|
+
const probeProjectDir = join18(homedir10(), ".augmented", agent.code_name, "project");
|
|
9555
9586
|
await runAgentConnectivityProbes(agent, integrations, probeProjectDir);
|
|
9556
9587
|
} catch (err) {
|
|
9557
9588
|
log(`Connectivity probe failed for '${agent.code_name}': ${err.message}`);
|
|
@@ -9562,7 +9593,7 @@ async function processAgent(agent, agentStates) {
|
|
|
9562
9593
|
const forceDue = attemptsLeft > 0;
|
|
9563
9594
|
let probeRan = false;
|
|
9564
9595
|
try {
|
|
9565
|
-
const probeProjectDir =
|
|
9596
|
+
const probeProjectDir = join18(homedir10(), ".augmented", agent.code_name, "project");
|
|
9566
9597
|
probeRan = await runAgentSessionToolBindProbes(agent, integrations, probeProjectDir, { forceDue });
|
|
9567
9598
|
} catch (err) {
|
|
9568
9599
|
log(`Session-tool-bind probe failed for '${agent.code_name}': ${err.message}`);
|
|
@@ -9602,8 +9633,8 @@ async function processAgent(agent, agentStates) {
|
|
|
9602
9633
|
recordConfigChurnEvent(agent.agent_id, agent.code_name, FLAP_CHANNEL_INTEGRATIONS, intMembership);
|
|
9603
9634
|
}
|
|
9604
9635
|
if (intHash !== prevIntHash) {
|
|
9605
|
-
const projectDir =
|
|
9606
|
-
const envIntPath =
|
|
9636
|
+
const projectDir = join18(homedir10(), ".augmented", agent.code_name, "project");
|
|
9637
|
+
const envIntPath = join18(projectDir, ".env.integrations");
|
|
9607
9638
|
let preWriteEnv;
|
|
9608
9639
|
try {
|
|
9609
9640
|
preWriteEnv = readFileSync15(envIntPath, "utf-8");
|
|
@@ -9618,7 +9649,7 @@ async function processAgent(agent, agentStates) {
|
|
|
9618
9649
|
let rotationHandled = true;
|
|
9619
9650
|
if (fw === "claude-code" && isSessionHealthy(agent.code_name)) {
|
|
9620
9651
|
try {
|
|
9621
|
-
const projectMcpPath =
|
|
9652
|
+
const projectMcpPath = join18(projectDir, ".mcp.json");
|
|
9622
9653
|
const postWriteEnv = readFileSync15(envIntPath, "utf-8");
|
|
9623
9654
|
const mcpContent = readFileSync15(projectMcpPath, "utf-8");
|
|
9624
9655
|
const changedVars = diffEnvIntegrations(preWriteEnv, postWriteEnv);
|
|
@@ -9865,16 +9896,16 @@ async function processAgent(agent, agentStates) {
|
|
|
9865
9896
|
}
|
|
9866
9897
|
try {
|
|
9867
9898
|
const { readdirSync: readdirSync6, rmSync: rmSync5 } = await import("fs");
|
|
9868
|
-
const { homedir:
|
|
9899
|
+
const { homedir: homedir11 } = await import("os");
|
|
9869
9900
|
const frameworkId2 = frameworkAdapter.id;
|
|
9870
9901
|
const candidateSkillDirs = [
|
|
9871
9902
|
// Claude Code — framework runtime tree
|
|
9872
|
-
|
|
9903
|
+
join18(homedir11(), ".augmented", agent.code_name, "skills"),
|
|
9873
9904
|
// Claude Code — project tree
|
|
9874
|
-
|
|
9905
|
+
join18(homedir11(), ".augmented", agent.code_name, "project", ".claude", "skills"),
|
|
9875
9906
|
// Defensive: legacy provision-side path, not currently an
|
|
9876
9907
|
// install target but cheap to sweep.
|
|
9877
|
-
|
|
9908
|
+
join18(agentDir, ".claude", "skills")
|
|
9878
9909
|
];
|
|
9879
9910
|
const existingDirs = candidateSkillDirs.filter((d) => existsSync9(d));
|
|
9880
9911
|
const discoveredEntries = /* @__PURE__ */ new Set();
|
|
@@ -9890,7 +9921,7 @@ async function processAgent(agent, agentStates) {
|
|
|
9890
9921
|
}
|
|
9891
9922
|
const removeSkillFolder = (entry, reason) => {
|
|
9892
9923
|
for (const dir of existingDirs) {
|
|
9893
|
-
const p =
|
|
9924
|
+
const p = join18(dir, entry);
|
|
9894
9925
|
if (existsSync9(p)) {
|
|
9895
9926
|
rmSync5(p, { recursive: true, force: true });
|
|
9896
9927
|
}
|
|
@@ -9910,7 +9941,7 @@ async function processAgent(agent, agentStates) {
|
|
|
9910
9941
|
const sharedSkillsPayload = refreshAny.shared_skills;
|
|
9911
9942
|
const desiredResolved = globalSkillsPayload !== void 0 || sharedSkillsPayload !== void 0;
|
|
9912
9943
|
const manifestPath = managedSkillManifestPath(
|
|
9913
|
-
|
|
9944
|
+
join18(homedir10(), ".augmented", agent.code_name)
|
|
9914
9945
|
);
|
|
9915
9946
|
const prevIds = /* @__PURE__ */ new Set([
|
|
9916
9947
|
...agentState.knownGlobalSkillIds.get(agent.agent_id) ?? /* @__PURE__ */ new Set(),
|
|
@@ -9930,15 +9961,15 @@ async function processAgent(agent, agentStates) {
|
|
|
9930
9961
|
}
|
|
9931
9962
|
if (plan.removes.length) {
|
|
9932
9963
|
const globalSkillDirs = [
|
|
9933
|
-
|
|
9934
|
-
|
|
9935
|
-
|
|
9964
|
+
join18(homedir10(), ".augmented", agent.code_name, "skills"),
|
|
9965
|
+
join18(homedir10(), ".augmented", agent.code_name, "project", ".claude", "skills"),
|
|
9966
|
+
join18(agentDir, ".claude", "skills")
|
|
9936
9967
|
];
|
|
9937
9968
|
for (const id of plan.removes) {
|
|
9938
9969
|
let prunedAny = false;
|
|
9939
9970
|
for (const dir of globalSkillDirs) {
|
|
9940
|
-
const p =
|
|
9941
|
-
if (existsSync9(p) && existsSync9(
|
|
9971
|
+
const p = join18(dir, id);
|
|
9972
|
+
if (existsSync9(p) && existsSync9(join18(p, "SKILL.md"))) {
|
|
9942
9973
|
rmSync4(p, { recursive: true, force: true });
|
|
9943
9974
|
prunedAny = true;
|
|
9944
9975
|
}
|
|
@@ -10135,7 +10166,7 @@ async function processAgent(agent, agentStates) {
|
|
|
10135
10166
|
const sess = getSessionState(agent.code_name);
|
|
10136
10167
|
let mcpJsonParsed = null;
|
|
10137
10168
|
try {
|
|
10138
|
-
const mcpPath =
|
|
10169
|
+
const mcpPath = join18(getProjectDir(agent.code_name), ".mcp.json");
|
|
10139
10170
|
mcpJsonParsed = JSON.parse(readFileSync15(mcpPath, "utf-8"));
|
|
10140
10171
|
} catch {
|
|
10141
10172
|
}
|
|
@@ -10457,7 +10488,7 @@ In progress for ${age} minutes \u2014 auto-failed`).catch(() => {
|
|
|
10457
10488
|
if (trackedFiles.length > 0 && existsSync9(agentDir)) {
|
|
10458
10489
|
const hashes = /* @__PURE__ */ new Map();
|
|
10459
10490
|
for (const file of trackedFiles) {
|
|
10460
|
-
const h = hashFile(
|
|
10491
|
+
const h = hashFile(join18(agentDir, file));
|
|
10461
10492
|
if (h) hashes.set(file, h);
|
|
10462
10493
|
}
|
|
10463
10494
|
agentState.writtenHashes.set(agent.agent_id, hashes);
|
|
@@ -10472,7 +10503,7 @@ In progress for ${age} minutes \u2014 auto-failed`).catch(() => {
|
|
|
10472
10503
|
refreshData.agent.onboarding_state
|
|
10473
10504
|
);
|
|
10474
10505
|
const obStep = obState.step;
|
|
10475
|
-
const markerPath =
|
|
10506
|
+
const markerPath = join18(homedir10(), ".augmented", agent.code_name, "onboarding-drive.json");
|
|
10476
10507
|
const marker = readOnboardingDriveMarker(markerPath);
|
|
10477
10508
|
const decision = decideOnboardingDrive(obStep, marker, Date.now(), obState.generation ?? 0);
|
|
10478
10509
|
if (decision.clearMarker) {
|
|
@@ -10536,8 +10567,8 @@ var egressAllowlistEqual = (a, b) => a.length === b.length && a.every((d, i) =>
|
|
|
10536
10567
|
async function ensurePersistentSession(agent, tasks, boardItems, refreshData) {
|
|
10537
10568
|
const codeName = agent.code_name;
|
|
10538
10569
|
const projectDir = getProjectDir(codeName);
|
|
10539
|
-
const mcpConfigPath =
|
|
10540
|
-
const claudeMdPath =
|
|
10570
|
+
const mcpConfigPath = join18(projectDir, ".mcp.json");
|
|
10571
|
+
const claudeMdPath = join18(projectDir, "CLAUDE.md");
|
|
10541
10572
|
if (restartBreaker.isTripped(codeName)) {
|
|
10542
10573
|
const trip = restartBreaker.getTrip(codeName);
|
|
10543
10574
|
return {
|
|
@@ -10802,6 +10833,11 @@ ${truncateForLog(ctx.tail)}` : `; pane_tail_hash=sha256:${createHash11("sha256")
|
|
|
10802
10833
|
// (AGT_KANBAN_WAITING_ENABLED) so the stdio kanban MCP exposes the `waiting`
|
|
10803
10834
|
// option. Host-grained (HostFlagStore); the per-org API gate is authoritative.
|
|
10804
10835
|
kanbanWaitingEnabled: hostFlagStore().getBoolean("kanban-waiting-status"),
|
|
10836
|
+
// ENG-7682 (notify Slice 1): materialize notify-dispatch into the spawn env
|
|
10837
|
+
// (AGT_NOTIFY_DISPATCH) so the Slack channel MCP admits non-@mention channel
|
|
10838
|
+
// messages in member channels (membership mode). Host-grained (HostFlagStore);
|
|
10839
|
+
// the launcher injects it unless an operator env override is already present.
|
|
10840
|
+
notifyDispatchMode: hostFlagStore().getString("notify-dispatch"),
|
|
10805
10841
|
egressAllowlist,
|
|
10806
10842
|
log
|
|
10807
10843
|
});
|
|
@@ -11063,7 +11099,7 @@ async function handleRestartDoorbell(agentId, requestedAt, restartReason) {
|
|
|
11063
11099
|
void api.post("/host/restart-ack", { host_id: hostId, agent_id: agentId, restart_requested_at: requestedAt }).catch((err) => log(`[restart-lane] ack failed for '${codeName}': ${err.message}`));
|
|
11064
11100
|
void (async () => {
|
|
11065
11101
|
try {
|
|
11066
|
-
const { collectDiagnostics } = await import("../persistent-session-
|
|
11102
|
+
const { collectDiagnostics } = await import("../persistent-session-HWVIMZAY.js");
|
|
11067
11103
|
await api.post("/host/heartbeat", {
|
|
11068
11104
|
host_id: hostId,
|
|
11069
11105
|
agent_diagnostics: collectDiagnostics([codeName])
|
|
@@ -11113,7 +11149,7 @@ async function respawnAgentAfterMcpStop(codeName, reason) {
|
|
|
11113
11149
|
}
|
|
11114
11150
|
try {
|
|
11115
11151
|
const hostId = await getHostId();
|
|
11116
|
-
const { collectDiagnostics } = await import("../persistent-session-
|
|
11152
|
+
const { collectDiagnostics } = await import("../persistent-session-HWVIMZAY.js");
|
|
11117
11153
|
await api.post("/host/heartbeat", {
|
|
11118
11154
|
host_id: hostId,
|
|
11119
11155
|
agent_diagnostics: collectDiagnostics([codeName])
|
|
@@ -11354,9 +11390,9 @@ async function processDirectChatMessage(agent, msg) {
|
|
|
11354
11390
|
const useDoorbell = hostFlagStore().getBoolean("direct-chat-doorbell") || isolationMode(agent.codeName) === "docker";
|
|
11355
11391
|
if (useDoorbell) {
|
|
11356
11392
|
try {
|
|
11357
|
-
const doorbell = directChatDoorbellPath(agent.agentId,
|
|
11393
|
+
const doorbell = directChatDoorbellPath(agent.agentId, homedir10());
|
|
11358
11394
|
mkdirSync7(dirname6(doorbell), { recursive: true });
|
|
11359
|
-
|
|
11395
|
+
writeFileSync8(doorbell, String(Date.now()));
|
|
11360
11396
|
log(`[direct-chat] Doorbell rung for '${agent.codeName}' (msg=${msg.id}) \u2014 in-session MCP will pull via the cursor`);
|
|
11361
11397
|
return;
|
|
11362
11398
|
} catch (err) {
|
|
@@ -11436,9 +11472,9 @@ ${formatRunMarker(run_id)}` : KANBAN_CHECK_COMMAND;
|
|
|
11436
11472
|
}
|
|
11437
11473
|
if (run_id) openInjectedRunByCode.set(codeName, run_id);
|
|
11438
11474
|
try {
|
|
11439
|
-
const doorbell = directChatDoorbellPath(agentId,
|
|
11475
|
+
const doorbell = directChatDoorbellPath(agentId, homedir10());
|
|
11440
11476
|
mkdirSync7(dirname6(doorbell), { recursive: true });
|
|
11441
|
-
|
|
11477
|
+
writeFileSync8(doorbell, String(Date.now()));
|
|
11442
11478
|
} catch (err) {
|
|
11443
11479
|
log(`[kanban] doorbell ring failed for '${codeName}': ${err.message} (notice still queued)`);
|
|
11444
11480
|
}
|
|
@@ -11518,7 +11554,7 @@ async function processClaudePairSessions(agents) {
|
|
|
11518
11554
|
killPairSession,
|
|
11519
11555
|
pairTmuxSession,
|
|
11520
11556
|
finalizeClaudePairOnboarding
|
|
11521
|
-
} = await import("../claude-pair-runtime-
|
|
11557
|
+
} = await import("../claude-pair-runtime-BEUY5L6C.js");
|
|
11522
11558
|
for (const pairId of pendingResp.cancelled_pair_ids ?? []) {
|
|
11523
11559
|
log(`[claude-pair] sweeping orphan tmux session for pair ${pairId.slice(0, 8)}`);
|
|
11524
11560
|
const killed = await killPairSession(pairTmuxSession(pairId));
|
|
@@ -11761,8 +11797,8 @@ function parseMemoryFile(raw, fallbackName) {
|
|
|
11761
11797
|
};
|
|
11762
11798
|
}
|
|
11763
11799
|
async function syncMemories(agent, configDir, log2) {
|
|
11764
|
-
const projectDir =
|
|
11765
|
-
const memoryDir =
|
|
11800
|
+
const projectDir = join18(configDir, agent.code_name, "project");
|
|
11801
|
+
const memoryDir = join18(projectDir, "memory");
|
|
11766
11802
|
const isFreshSync = pendingFreshMemorySync.has(agent.agent_id);
|
|
11767
11803
|
if (isFreshSync) {
|
|
11768
11804
|
log2(`[memory-sync] Fresh-sync requested for '${agent.code_name}' \u2014 pulling DB first`);
|
|
@@ -11780,7 +11816,7 @@ async function syncMemories(agent, configDir, log2) {
|
|
|
11780
11816
|
for (const file of readdirSync5(memoryDir)) {
|
|
11781
11817
|
if (!file.endsWith(".md")) continue;
|
|
11782
11818
|
try {
|
|
11783
|
-
const raw = readFileSync15(
|
|
11819
|
+
const raw = readFileSync15(join18(memoryDir, file), "utf-8");
|
|
11784
11820
|
const fileHash = createHash11("sha256").update(raw).digest("hex").slice(0, 16);
|
|
11785
11821
|
currentHashes.set(file, fileHash);
|
|
11786
11822
|
if (prevHashes.get(file) === fileHash) continue;
|
|
@@ -11805,7 +11841,7 @@ async function syncMemories(agent, configDir, log2) {
|
|
|
11805
11841
|
} catch (err) {
|
|
11806
11842
|
for (const mem of changedMemories) {
|
|
11807
11843
|
for (const [file] of currentHashes) {
|
|
11808
|
-
const parsed = parseMemoryFile(readFileSync15(
|
|
11844
|
+
const parsed = parseMemoryFile(readFileSync15(join18(memoryDir, file), "utf-8"), file.replace(/\.md$/, ""));
|
|
11809
11845
|
if (parsed?.name === mem.name) currentHashes.delete(file);
|
|
11810
11846
|
}
|
|
11811
11847
|
}
|
|
@@ -11840,7 +11876,7 @@ async function downloadMemories(agent, memoryDir, log2, { force }) {
|
|
|
11840
11876
|
const mem = dbMemories.memories[i];
|
|
11841
11877
|
const rawSlug = mem.name.toLowerCase().replace(/[^a-z0-9]+/g, "-").replace(/(^-|-$)/g, "").slice(0, 60);
|
|
11842
11878
|
const slug = rawSlug || `memory-${i}`;
|
|
11843
|
-
const filePath =
|
|
11879
|
+
const filePath = join18(memoryDir, `${slug}.md`);
|
|
11844
11880
|
const desired = `---
|
|
11845
11881
|
name: ${JSON.stringify(mem.name)}
|
|
11846
11882
|
type: ${mem.type}
|
|
@@ -11856,10 +11892,10 @@ ${mem.content}
|
|
|
11856
11892
|
} catch {
|
|
11857
11893
|
}
|
|
11858
11894
|
if (existing === desired) continue;
|
|
11859
|
-
|
|
11895
|
+
writeFileSync8(filePath, desired);
|
|
11860
11896
|
overwritten++;
|
|
11861
11897
|
} else {
|
|
11862
|
-
|
|
11898
|
+
writeFileSync8(filePath, desired);
|
|
11863
11899
|
written++;
|
|
11864
11900
|
}
|
|
11865
11901
|
}
|
|
@@ -12137,7 +12173,7 @@ function startManager(opts) {
|
|
|
12137
12173
|
log(`[startup] state rehydration failed (continuing with empty state): ${err.message}`);
|
|
12138
12174
|
}
|
|
12139
12175
|
log(
|
|
12140
|
-
`[startup] worker pid=${process.pid} ppid=${process.ppid} node=${process.version} log=${
|
|
12176
|
+
`[startup] worker pid=${process.pid} ppid=${process.ppid} node=${process.version} log=${join18(homedir10(), ".augmented", "manager.log")}`
|
|
12141
12177
|
);
|
|
12142
12178
|
deployMcpAssets();
|
|
12143
12179
|
reapOrphanChannelMcps({ log });
|
|
@@ -12255,14 +12291,14 @@ function restartRunningChannelMcps(basenames) {
|
|
|
12255
12291
|
}
|
|
12256
12292
|
}
|
|
12257
12293
|
function deployMcpAssets() {
|
|
12258
|
-
const targetDir =
|
|
12294
|
+
const targetDir = join18(homedir10(), ".augmented", "_mcp");
|
|
12259
12295
|
mkdirSync7(targetDir, { recursive: true });
|
|
12260
12296
|
const moduleDir = dirname6(fileURLToPath(import.meta.url));
|
|
12261
12297
|
let mcpSourceDir = "";
|
|
12262
12298
|
let dir = moduleDir;
|
|
12263
12299
|
for (let i = 0; i < 6; i++) {
|
|
12264
|
-
const candidate =
|
|
12265
|
-
if (existsSync9(
|
|
12300
|
+
const candidate = join18(dir, "dist", "mcp");
|
|
12301
|
+
if (existsSync9(join18(candidate, "index.js"))) {
|
|
12266
12302
|
mcpSourceDir = candidate;
|
|
12267
12303
|
break;
|
|
12268
12304
|
}
|
|
@@ -12342,8 +12378,8 @@ function deployMcpAssets() {
|
|
|
12342
12378
|
// needs restarting to pick up a token rotation.
|
|
12343
12379
|
"xero.js"
|
|
12344
12380
|
]) {
|
|
12345
|
-
const src =
|
|
12346
|
-
const dst =
|
|
12381
|
+
const src = join18(mcpSourceDir, file);
|
|
12382
|
+
const dst = join18(targetDir, file);
|
|
12347
12383
|
if (!existsSync9(src)) continue;
|
|
12348
12384
|
const before = fileHash(dst);
|
|
12349
12385
|
try {
|
|
@@ -12361,14 +12397,14 @@ function deployMcpAssets() {
|
|
|
12361
12397
|
log(`[manager] Bundle(s) updated: ${changedBasenames.join(", ")} \u2014 signalling running instances to restart`);
|
|
12362
12398
|
restartRunningChannelMcps(changedBasenames);
|
|
12363
12399
|
}
|
|
12364
|
-
const localMcpPath =
|
|
12400
|
+
const localMcpPath = join18(targetDir, "index.js");
|
|
12365
12401
|
try {
|
|
12366
|
-
const agentsDir =
|
|
12402
|
+
const agentsDir = join18(homedir10(), ".augmented", "agents");
|
|
12367
12403
|
if (existsSync9(agentsDir)) {
|
|
12368
12404
|
for (const entry of readdirSync5(agentsDir, { withFileTypes: true })) {
|
|
12369
12405
|
if (!entry.isDirectory()) continue;
|
|
12370
12406
|
for (const subdir of ["provision", "project"]) {
|
|
12371
|
-
const mcpJsonPath =
|
|
12407
|
+
const mcpJsonPath = join18(agentsDir, entry.name, subdir, ".mcp.json");
|
|
12372
12408
|
try {
|
|
12373
12409
|
const raw = readFileSync15(mcpJsonPath, "utf-8");
|
|
12374
12410
|
if (!raw.includes("@integrity-labs/augmented-mcp")) continue;
|
|
@@ -12377,7 +12413,7 @@ function deployMcpAssets() {
|
|
|
12377
12413
|
if (!augServer) continue;
|
|
12378
12414
|
augServer.command = "node";
|
|
12379
12415
|
augServer.args = [localMcpPath];
|
|
12380
|
-
|
|
12416
|
+
writeFileSync8(mcpJsonPath, JSON.stringify(mcpConfig, null, 2));
|
|
12381
12417
|
log(`[manager] Patched ${entry.name}/${subdir}/.mcp.json: npx \u2192 node`);
|
|
12382
12418
|
} catch {
|
|
12383
12419
|
}
|