@integrity-labs/agt-cli 0.28.829 → 0.28.831
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 +5 -5
- package/dist/{chunk-GJY3KZG6.js → chunk-4ZPOP7EW.js} +36 -11
- package/dist/{chunk-GJY3KZG6.js.map → chunk-4ZPOP7EW.js.map} +1 -1
- package/dist/{chunk-6HTCP6D5.js → chunk-N4QVPPYS.js} +2 -2
- package/dist/{chunk-E75YCJTE.js → chunk-PODKITVQ.js} +4 -4
- package/dist/{claude-pair-runtime-UTDZXJKO.js → claude-pair-runtime-PUWAIK73.js} +2 -2
- package/dist/lib/manager-worker.js +13 -13
- package/dist/mcp/augmented-admin.js +1 -1
- package/dist/mcp/direct-chat-channel.js +88 -13
- package/dist/mcp/index.js +35 -10
- package/dist/mcp/origami.js +35 -10
- package/dist/mcp/slack-channel.js +115 -13
- package/dist/mcp/telegram-channel.js +107 -13
- package/dist/{persistent-session-6YTEDS3H.js → persistent-session-W23U7GQU.js} +3 -3
- package/dist/{responsiveness-probe-5B2WA5G3.js → responsiveness-probe-IRQKIEBW.js} +3 -3
- package/dist/{session-auth-dead-LFNU6AUU.js → session-auth-dead-VDDXVJTX.js} +2 -2
- package/package.json +1 -1
- /package/dist/{chunk-6HTCP6D5.js.map → chunk-N4QVPPYS.js.map} +0 -0
- /package/dist/{chunk-E75YCJTE.js.map → chunk-PODKITVQ.js.map} +0 -0
- /package/dist/{claude-pair-runtime-UTDZXJKO.js.map → claude-pair-runtime-PUWAIK73.js.map} +0 -0
- /package/dist/{persistent-session-6YTEDS3H.js.map → persistent-session-W23U7GQU.js.map} +0 -0
- /package/dist/{responsiveness-probe-5B2WA5G3.js.map → responsiveness-probe-IRQKIEBW.js.map} +0 -0
- /package/dist/{session-auth-dead-LFNU6AUU.js.map → session-auth-dead-VDDXVJTX.js.map} +0 -0
|
@@ -36911,7 +36911,7 @@ var FLAG_REGISTRY = [
|
|
|
36911
36911
|
},
|
|
36912
36912
|
{
|
|
36913
36913
|
key: "auto-resume-enabled",
|
|
36914
|
-
description: "
|
|
36914
|
+
description: "Bounded BLIND auto-resume for circuit-breaker pauses (ENG-6088): at most one unattended resume per trip cycle, fired once the trip driver has been quiet for the configured window and only for provisioning-reload trips (the ENG-7577 class gate \u2014 a crash-class trip still needs an operator). Superseded wherever `resume-reconciler` is on: that path proves the dependency recovered instead of assuming it, and the blind timer is its flag-off fallback. Boolean gate; ships dark. ENG-8395 promoted this from a raw host env var because AGT_AUTO_RESUME_ENABLED lives in the host env file, so its grain is per-HOST \u2014 one flip arms every agent that host runs (agt-aws-1 carries 14), which made the canary-then-fleet rollout its own documentation prescribes impossible. As a registry flag it resolves per org/team/host/AGENT, so one agent can genuinely be cut over first. Read host-side by the manager (agt-cli), not centrally.",
|
|
36915
36915
|
flagType: "boolean",
|
|
36916
36916
|
// Declared safe value is `false` — identical to today's behaviour on a host
|
|
36917
36917
|
// that has never set the env var. Fail-safe direction on a flag-DB read
|
|
@@ -36928,16 +36928,41 @@ var FLAG_REGISTRY = [
|
|
|
36928
36928
|
// An unattended resume is a real availability change — the agent starts
|
|
36929
36929
|
// spawning sessions again with no human in the loop — so arming it is a
|
|
36930
36930
|
// deliberate, confirmed write (ADR-0022 sensitive-flag confirm).
|
|
36931
|
-
sensitive: true
|
|
36932
|
-
// ENG-
|
|
36933
|
-
//
|
|
36934
|
-
//
|
|
36935
|
-
//
|
|
36936
|
-
//
|
|
36937
|
-
//
|
|
36938
|
-
//
|
|
36939
|
-
//
|
|
36931
|
+
sensitive: true,
|
|
36932
|
+
// ENG-10034: bisected from the PUBLISHED agt-cli dists, not from git history —
|
|
36933
|
+
// auto-resume.ts is host-side, so what matters is the first ARTIFACT a host
|
|
36934
|
+
// could be running that contains a consumer for this flag.
|
|
36935
|
+
//
|
|
36936
|
+
// METHOD, so it can be re-run rather than trusted: download each candidate
|
|
36937
|
+
// tarball from the npm registry and grep its contents for the flag-specific
|
|
36938
|
+
// wiring. Binary search over the 22 versions published either side of
|
|
36939
|
+
// ENG-8395's merge gave a clean one-release boundary, eight minutes wide:
|
|
36940
|
+
//
|
|
36941
|
+
// 0.28.506 2026-08-03T22:29:22Z readAutoResumeEnvOverride ✗ AUTO_RESUME_FLAG_KEY ✗ 'auto-resume-enabled' ✗
|
|
36942
|
+
// 0.28.507 2026-08-03T22:37:00Z readAutoResumeEnvOverride ✓ AUTO_RESUME_FLAG_KEY ✓ 'auto-resume-enabled' ✓
|
|
36943
|
+
//
|
|
36944
|
+
// All three symbols are checked rather than one. `getBooleanForAgent` alone
|
|
36945
|
+
// would have been the wrong probe — it is present in BOTH builds, because the
|
|
36946
|
+
// generic resolver long predates this flag. A `since` bisected on a symbol the
|
|
36947
|
+
// flag does not depend on is a number that looks rigorous and is not.
|
|
36948
|
+
//
|
|
36949
|
+
// ENG-8395 AC5 left this unset on purpose and said why: an unset `since` makes
|
|
36950
|
+
// the flip-reach estimate report FULL reach for a host-side reader, promising
|
|
36951
|
+
// reach it does not have (the defect caught on ENG-8344 / PR #4014). The
|
|
36952
|
+
// follow-up it was waiting on was never filed, so the flag sat un-armable for
|
|
36953
|
+
// a month and ENG-6088's bounded auto-resume stayed dark fleet-wide — a
|
|
36954
|
+
// customer agent sat breaker-paused 2h08m on 2026-09-05 with the recovery path
|
|
36955
|
+
// silently disabled. That is what an administrative blocker recorded only in a
|
|
36956
|
+
// code comment costs.
|
|
36957
|
+
//
|
|
36958
|
+
// Same method as its precedents: slack-hot-thread-guard = 0.28.339,
|
|
36959
|
+
// slack-scheduled-channel-guard = 0.28.421 (ENG-8149). Setting it now is safe:
|
|
36960
|
+
// `since` is excluded from projectDefinition, so it does not roll
|
|
36940
36961
|
// FLAGS_SCHEMA_VERSION.
|
|
36962
|
+
//
|
|
36963
|
+
// This does NOT arm the flag. defaultValue stays false and `sensitive` stays
|
|
36964
|
+
// true; arming is a separate, deliberate decision that belongs to ENG-6066.
|
|
36965
|
+
since: "0.28.507"
|
|
36941
36966
|
},
|
|
36942
36967
|
{
|
|
36943
36968
|
key: "host-poll-rate-alarm",
|
|
@@ -38389,10 +38414,19 @@ function undeliverableNoticeEligible(shouldEngage) {
|
|
|
38389
38414
|
function shouldPostUndeliverableNotice(lastNoticeAtMs, nowMs, throttleMs = UNDELIVERABLE_NOTICE_THROTTLE_MS) {
|
|
38390
38415
|
return lastNoticeAtMs == null || nowMs - lastNoticeAtMs >= throttleMs;
|
|
38391
38416
|
}
|
|
38392
|
-
function undeliverableNoticeText(replay
|
|
38393
|
-
|
|
38417
|
+
function undeliverableNoticeText(replay) {
|
|
38418
|
+
const honest = noticePromiseIsHonest(replay);
|
|
38419
|
+
return honest ? "\u23F3 I can't get to this right now \u2014 no need to resend; I'll pick it up automatically as soon as I'm free." : "\u23F3 I can't get to this right now. Please resend in a few minutes \u2014 I may not see this one.";
|
|
38420
|
+
}
|
|
38421
|
+
function undeliverableNoticeTextForRepeat(i) {
|
|
38422
|
+
if (i.priorNotices <= 0) return undeliverableNoticeText(i.replay);
|
|
38423
|
+
if (i.priorNotices === 1) {
|
|
38424
|
+
return noticePromiseIsHonest(i.replay) ? "\u23F3 Still stuck on this one \u2014 the automatic pickup I mentioned has not happened. Please resend when you can." : "\u23F3 Still stuck on this one, and I still have not picked it up. Resending is the reliable way through.";
|
|
38425
|
+
}
|
|
38426
|
+
return null;
|
|
38394
38427
|
}
|
|
38395
38428
|
function noticePromiseIsHonest(replay) {
|
|
38429
|
+
if (replay === void 0) return false;
|
|
38396
38430
|
if (typeof replay === "boolean") return replay;
|
|
38397
38431
|
return markerReplayable({
|
|
38398
38432
|
enabled: replay.enabled ?? channelReplayEnabled(),
|
|
@@ -38427,6 +38461,13 @@ var UndeliverableNoticeScheduler = class {
|
|
|
38427
38461
|
}
|
|
38428
38462
|
/** decision-time stamps, keyed by conversation. Shared with other one-per-window system notices. */
|
|
38429
38463
|
stamps = /* @__PURE__ */ new Map();
|
|
38464
|
+
/**
|
|
38465
|
+
* ENG-9413 AC4 — how many notices have actually been POSTED for this
|
|
38466
|
+
* conversation. Distinct from `stamps`, which is a decision-time throttle and
|
|
38467
|
+
* is dropped by `cancel()`: a notice that was scheduled and cancelled was
|
|
38468
|
+
* never seen by anyone and must not count toward escalation.
|
|
38469
|
+
*/
|
|
38470
|
+
sent = /* @__PURE__ */ new Map();
|
|
38430
38471
|
/** scheduled-but-unsent notices, keyed by conversation. */
|
|
38431
38472
|
timers = /* @__PURE__ */ new Map();
|
|
38432
38473
|
/** is a notice scheduled but not yet sent for this conversation? */
|
|
@@ -38437,6 +38478,30 @@ var UndeliverableNoticeScheduler = class {
|
|
|
38437
38478
|
stampedAt(key2) {
|
|
38438
38479
|
return this.stamps.get(key2);
|
|
38439
38480
|
}
|
|
38481
|
+
/**
|
|
38482
|
+
* ENG-9413 AC4 — notices already POSTED for this conversation. Read by the
|
|
38483
|
+
* channel's send callback to pick escalated copy, or to say nothing at all.
|
|
38484
|
+
* The count is incremented AFTER `send` runs, so inside the callback this is
|
|
38485
|
+
* the number of PRIOR notices.
|
|
38486
|
+
*/
|
|
38487
|
+
noticeCount(key2) {
|
|
38488
|
+
return this.sent.get(key2) ?? 0;
|
|
38489
|
+
}
|
|
38490
|
+
/**
|
|
38491
|
+
* ENG-9413 AC4 — record that a notice was CONFIRMED delivered.
|
|
38492
|
+
*
|
|
38493
|
+
* Called by the channel, not by `dispatch`, and that is the correction.
|
|
38494
|
+
* `dispatch`'s `send` is `() => void`: it returns before the Slack or Telegram
|
|
38495
|
+
* request completes, so incrementing there counted posts that never landed. A
|
|
38496
|
+
* failed post would then advance the escalation — the user's SECOND notice
|
|
38497
|
+
* would arrive worded as though they had already seen a first, and their third
|
|
38498
|
+
* would be suppressed entirely, on the strength of notices that were never
|
|
38499
|
+
* delivered. Raised in review on this PR; direct chat already got this right
|
|
38500
|
+
* by incrementing only on `ok`, and the shared scheduler now matches it.
|
|
38501
|
+
*/
|
|
38502
|
+
noteDelivered(key2) {
|
|
38503
|
+
this.sent.set(key2, this.noticeCount(key2) + 1);
|
|
38504
|
+
}
|
|
38440
38505
|
/**
|
|
38441
38506
|
* ENG-6025: claim this conversation's one-notice-per-window slot for a
|
|
38442
38507
|
* DIFFERENT system notice (the watchdog give-up line). Returns false when the
|
|
@@ -38508,6 +38573,7 @@ var UndeliverableNoticeScheduler = class {
|
|
|
38508
38573
|
for (const timer of this.timers.values()) clearTimeout(timer);
|
|
38509
38574
|
this.timers.clear();
|
|
38510
38575
|
this.stamps.clear();
|
|
38576
|
+
this.sent.clear();
|
|
38511
38577
|
}
|
|
38512
38578
|
clearTimer(key2) {
|
|
38513
38579
|
const timer = this.timers.get(key2);
|
|
@@ -38681,6 +38747,13 @@ function channelReplayEnabled() {
|
|
|
38681
38747
|
defaultValue: true
|
|
38682
38748
|
});
|
|
38683
38749
|
}
|
|
38750
|
+
function combineMarkerReplayFacts(markers) {
|
|
38751
|
+
if (markers.length === 0) return null;
|
|
38752
|
+
return {
|
|
38753
|
+
hasPayload: markers.every((m) => m.hasPayload),
|
|
38754
|
+
discretionary: markers.some((m) => m.discretionary === true)
|
|
38755
|
+
};
|
|
38756
|
+
}
|
|
38684
38757
|
function markerReplayable(i) {
|
|
38685
38758
|
if (!i.enabled) return false;
|
|
38686
38759
|
if (!i.hasPayload) return false;
|
|
@@ -43799,8 +43872,36 @@ function postUndeliverableNotice(channel, threadTs, isThreadReply, cause = "unkn
|
|
|
43799
43872
|
send: () => sendUndeliverableNotice(channel, threadTs, conversationKey)
|
|
43800
43873
|
});
|
|
43801
43874
|
}
|
|
43875
|
+
function slackConversationReplayFacts(channel, threadTs) {
|
|
43876
|
+
if (!threadTs || !SLACK_PENDING_INBOUND_DIR) return null;
|
|
43877
|
+
const found = [];
|
|
43878
|
+
try {
|
|
43879
|
+
markSeenAllSlackPendingMarkersForThread(
|
|
43880
|
+
SLACK_PENDING_INBOUND_DIR,
|
|
43881
|
+
channel,
|
|
43882
|
+
threadTs,
|
|
43883
|
+
(fullPath) => {
|
|
43884
|
+
try {
|
|
43885
|
+
const marker = JSON.parse(readFileSync18(fullPath, "utf-8"));
|
|
43886
|
+
found.push({ hasPayload: Boolean(marker.payload), discretionary: marker.discretionary });
|
|
43887
|
+
} catch {
|
|
43888
|
+
found.push({ hasPayload: false });
|
|
43889
|
+
}
|
|
43890
|
+
}
|
|
43891
|
+
);
|
|
43892
|
+
} catch {
|
|
43893
|
+
return null;
|
|
43894
|
+
}
|
|
43895
|
+
const facts = combineMarkerReplayFacts(found);
|
|
43896
|
+
return facts ? { enabled: channelReplayEnabled(), ...facts } : null;
|
|
43897
|
+
}
|
|
43802
43898
|
function sendUndeliverableNotice(channel, threadTs, conversationKey) {
|
|
43803
43899
|
if (!BOT_TOKEN || !channel) return;
|
|
43900
|
+
const text = undeliverableNoticeTextForRepeat({
|
|
43901
|
+
replay: slackConversationReplayFacts(channel, threadTs) ?? void 0,
|
|
43902
|
+
priorNotices: slackUndeliverableNotices.noticeCount(conversationKey)
|
|
43903
|
+
});
|
|
43904
|
+
if (text === null) return;
|
|
43804
43905
|
fetch("https://slack.com/api/chat.postMessage", {
|
|
43805
43906
|
method: "POST",
|
|
43806
43907
|
headers: {
|
|
@@ -43809,12 +43910,13 @@ function sendUndeliverableNotice(channel, threadTs, conversationKey) {
|
|
|
43809
43910
|
},
|
|
43810
43911
|
body: JSON.stringify({
|
|
43811
43912
|
channel,
|
|
43812
|
-
text
|
|
43913
|
+
text,
|
|
43813
43914
|
...threadTs ? { thread_ts: threadTs } : {}
|
|
43814
43915
|
})
|
|
43815
43916
|
}).then((res) => res.json()).then((data) => {
|
|
43816
43917
|
if (data?.ok === true && typeof data.ts === "string" && data.ts) {
|
|
43817
43918
|
lastSlackUndeliverableNoticeInfo.set(conversationKey, { channel, ts: data.ts });
|
|
43919
|
+
slackUndeliverableNotices.noteDelivered(conversationKey);
|
|
43818
43920
|
}
|
|
43819
43921
|
}).catch(() => {
|
|
43820
43922
|
});
|
|
@@ -37043,7 +37043,7 @@ var FLAG_REGISTRY = [
|
|
|
37043
37043
|
},
|
|
37044
37044
|
{
|
|
37045
37045
|
key: "auto-resume-enabled",
|
|
37046
|
-
description: "
|
|
37046
|
+
description: "Bounded BLIND auto-resume for circuit-breaker pauses (ENG-6088): at most one unattended resume per trip cycle, fired once the trip driver has been quiet for the configured window and only for provisioning-reload trips (the ENG-7577 class gate \u2014 a crash-class trip still needs an operator). Superseded wherever `resume-reconciler` is on: that path proves the dependency recovered instead of assuming it, and the blind timer is its flag-off fallback. Boolean gate; ships dark. ENG-8395 promoted this from a raw host env var because AGT_AUTO_RESUME_ENABLED lives in the host env file, so its grain is per-HOST \u2014 one flip arms every agent that host runs (agt-aws-1 carries 14), which made the canary-then-fleet rollout its own documentation prescribes impossible. As a registry flag it resolves per org/team/host/AGENT, so one agent can genuinely be cut over first. Read host-side by the manager (agt-cli), not centrally.",
|
|
37047
37047
|
flagType: "boolean",
|
|
37048
37048
|
// Declared safe value is `false` — identical to today's behaviour on a host
|
|
37049
37049
|
// that has never set the env var. Fail-safe direction on a flag-DB read
|
|
@@ -37060,16 +37060,41 @@ var FLAG_REGISTRY = [
|
|
|
37060
37060
|
// An unattended resume is a real availability change — the agent starts
|
|
37061
37061
|
// spawning sessions again with no human in the loop — so arming it is a
|
|
37062
37062
|
// deliberate, confirmed write (ADR-0022 sensitive-flag confirm).
|
|
37063
|
-
sensitive: true
|
|
37064
|
-
// ENG-
|
|
37065
|
-
//
|
|
37066
|
-
//
|
|
37067
|
-
//
|
|
37068
|
-
//
|
|
37069
|
-
//
|
|
37070
|
-
//
|
|
37071
|
-
//
|
|
37063
|
+
sensitive: true,
|
|
37064
|
+
// ENG-10034: bisected from the PUBLISHED agt-cli dists, not from git history —
|
|
37065
|
+
// auto-resume.ts is host-side, so what matters is the first ARTIFACT a host
|
|
37066
|
+
// could be running that contains a consumer for this flag.
|
|
37067
|
+
//
|
|
37068
|
+
// METHOD, so it can be re-run rather than trusted: download each candidate
|
|
37069
|
+
// tarball from the npm registry and grep its contents for the flag-specific
|
|
37070
|
+
// wiring. Binary search over the 22 versions published either side of
|
|
37071
|
+
// ENG-8395's merge gave a clean one-release boundary, eight minutes wide:
|
|
37072
|
+
//
|
|
37073
|
+
// 0.28.506 2026-08-03T22:29:22Z readAutoResumeEnvOverride ✗ AUTO_RESUME_FLAG_KEY ✗ 'auto-resume-enabled' ✗
|
|
37074
|
+
// 0.28.507 2026-08-03T22:37:00Z readAutoResumeEnvOverride ✓ AUTO_RESUME_FLAG_KEY ✓ 'auto-resume-enabled' ✓
|
|
37075
|
+
//
|
|
37076
|
+
// All three symbols are checked rather than one. `getBooleanForAgent` alone
|
|
37077
|
+
// would have been the wrong probe — it is present in BOTH builds, because the
|
|
37078
|
+
// generic resolver long predates this flag. A `since` bisected on a symbol the
|
|
37079
|
+
// flag does not depend on is a number that looks rigorous and is not.
|
|
37080
|
+
//
|
|
37081
|
+
// ENG-8395 AC5 left this unset on purpose and said why: an unset `since` makes
|
|
37082
|
+
// the flip-reach estimate report FULL reach for a host-side reader, promising
|
|
37083
|
+
// reach it does not have (the defect caught on ENG-8344 / PR #4014). The
|
|
37084
|
+
// follow-up it was waiting on was never filed, so the flag sat un-armable for
|
|
37085
|
+
// a month and ENG-6088's bounded auto-resume stayed dark fleet-wide — a
|
|
37086
|
+
// customer agent sat breaker-paused 2h08m on 2026-09-05 with the recovery path
|
|
37087
|
+
// silently disabled. That is what an administrative blocker recorded only in a
|
|
37088
|
+
// code comment costs.
|
|
37089
|
+
//
|
|
37090
|
+
// Same method as its precedents: slack-hot-thread-guard = 0.28.339,
|
|
37091
|
+
// slack-scheduled-channel-guard = 0.28.421 (ENG-8149). Setting it now is safe:
|
|
37092
|
+
// `since` is excluded from projectDefinition, so it does not roll
|
|
37072
37093
|
// FLAGS_SCHEMA_VERSION.
|
|
37094
|
+
//
|
|
37095
|
+
// This does NOT arm the flag. defaultValue stays false and `sensitive` stays
|
|
37096
|
+
// true; arming is a separate, deliberate decision that belongs to ENG-6066.
|
|
37097
|
+
since: "0.28.507"
|
|
37073
37098
|
},
|
|
37074
37099
|
{
|
|
37075
37100
|
key: "host-poll-rate-alarm",
|
|
@@ -41127,10 +41152,19 @@ var UNDELIVERABLE_NOTICE_THROTTLE_MS = 5 * 60 * 1e3;
|
|
|
41127
41152
|
function shouldPostUndeliverableNotice(lastNoticeAtMs, nowMs, throttleMs = UNDELIVERABLE_NOTICE_THROTTLE_MS) {
|
|
41128
41153
|
return lastNoticeAtMs == null || nowMs - lastNoticeAtMs >= throttleMs;
|
|
41129
41154
|
}
|
|
41130
|
-
function undeliverableNoticeText(replay
|
|
41131
|
-
|
|
41155
|
+
function undeliverableNoticeText(replay) {
|
|
41156
|
+
const honest = noticePromiseIsHonest(replay);
|
|
41157
|
+
return honest ? "\u23F3 I can't get to this right now \u2014 no need to resend; I'll pick it up automatically as soon as I'm free." : "\u23F3 I can't get to this right now. Please resend in a few minutes \u2014 I may not see this one.";
|
|
41158
|
+
}
|
|
41159
|
+
function undeliverableNoticeTextForRepeat(i) {
|
|
41160
|
+
if (i.priorNotices <= 0) return undeliverableNoticeText(i.replay);
|
|
41161
|
+
if (i.priorNotices === 1) {
|
|
41162
|
+
return noticePromiseIsHonest(i.replay) ? "\u23F3 Still stuck on this one \u2014 the automatic pickup I mentioned has not happened. Please resend when you can." : "\u23F3 Still stuck on this one, and I still have not picked it up. Resending is the reliable way through.";
|
|
41163
|
+
}
|
|
41164
|
+
return null;
|
|
41132
41165
|
}
|
|
41133
41166
|
function noticePromiseIsHonest(replay) {
|
|
41167
|
+
if (replay === void 0) return false;
|
|
41134
41168
|
if (typeof replay === "boolean") return replay;
|
|
41135
41169
|
return markerReplayable({
|
|
41136
41170
|
enabled: replay.enabled ?? channelReplayEnabled(),
|
|
@@ -41165,6 +41199,13 @@ var UndeliverableNoticeScheduler = class {
|
|
|
41165
41199
|
}
|
|
41166
41200
|
/** decision-time stamps, keyed by conversation. Shared with other one-per-window system notices. */
|
|
41167
41201
|
stamps = /* @__PURE__ */ new Map();
|
|
41202
|
+
/**
|
|
41203
|
+
* ENG-9413 AC4 — how many notices have actually been POSTED for this
|
|
41204
|
+
* conversation. Distinct from `stamps`, which is a decision-time throttle and
|
|
41205
|
+
* is dropped by `cancel()`: a notice that was scheduled and cancelled was
|
|
41206
|
+
* never seen by anyone and must not count toward escalation.
|
|
41207
|
+
*/
|
|
41208
|
+
sent = /* @__PURE__ */ new Map();
|
|
41168
41209
|
/** scheduled-but-unsent notices, keyed by conversation. */
|
|
41169
41210
|
timers = /* @__PURE__ */ new Map();
|
|
41170
41211
|
/** is a notice scheduled but not yet sent for this conversation? */
|
|
@@ -41175,6 +41216,30 @@ var UndeliverableNoticeScheduler = class {
|
|
|
41175
41216
|
stampedAt(key2) {
|
|
41176
41217
|
return this.stamps.get(key2);
|
|
41177
41218
|
}
|
|
41219
|
+
/**
|
|
41220
|
+
* ENG-9413 AC4 — notices already POSTED for this conversation. Read by the
|
|
41221
|
+
* channel's send callback to pick escalated copy, or to say nothing at all.
|
|
41222
|
+
* The count is incremented AFTER `send` runs, so inside the callback this is
|
|
41223
|
+
* the number of PRIOR notices.
|
|
41224
|
+
*/
|
|
41225
|
+
noticeCount(key2) {
|
|
41226
|
+
return this.sent.get(key2) ?? 0;
|
|
41227
|
+
}
|
|
41228
|
+
/**
|
|
41229
|
+
* ENG-9413 AC4 — record that a notice was CONFIRMED delivered.
|
|
41230
|
+
*
|
|
41231
|
+
* Called by the channel, not by `dispatch`, and that is the correction.
|
|
41232
|
+
* `dispatch`'s `send` is `() => void`: it returns before the Slack or Telegram
|
|
41233
|
+
* request completes, so incrementing there counted posts that never landed. A
|
|
41234
|
+
* failed post would then advance the escalation — the user's SECOND notice
|
|
41235
|
+
* would arrive worded as though they had already seen a first, and their third
|
|
41236
|
+
* would be suppressed entirely, on the strength of notices that were never
|
|
41237
|
+
* delivered. Raised in review on this PR; direct chat already got this right
|
|
41238
|
+
* by incrementing only on `ok`, and the shared scheduler now matches it.
|
|
41239
|
+
*/
|
|
41240
|
+
noteDelivered(key2) {
|
|
41241
|
+
this.sent.set(key2, this.noticeCount(key2) + 1);
|
|
41242
|
+
}
|
|
41178
41243
|
/**
|
|
41179
41244
|
* ENG-6025: claim this conversation's one-notice-per-window slot for a
|
|
41180
41245
|
* DIFFERENT system notice (the watchdog give-up line). Returns false when the
|
|
@@ -41246,6 +41311,7 @@ var UndeliverableNoticeScheduler = class {
|
|
|
41246
41311
|
for (const timer of this.timers.values()) clearTimeout(timer);
|
|
41247
41312
|
this.timers.clear();
|
|
41248
41313
|
this.stamps.clear();
|
|
41314
|
+
this.sent.clear();
|
|
41249
41315
|
}
|
|
41250
41316
|
clearTimer(key2) {
|
|
41251
41317
|
const timer = this.timers.get(key2);
|
|
@@ -41412,6 +41478,13 @@ function channelReplayEnabled() {
|
|
|
41412
41478
|
defaultValue: true
|
|
41413
41479
|
});
|
|
41414
41480
|
}
|
|
41481
|
+
function combineMarkerReplayFacts(markers) {
|
|
41482
|
+
if (markers.length === 0) return null;
|
|
41483
|
+
return {
|
|
41484
|
+
hasPayload: markers.every((m) => m.hasPayload),
|
|
41485
|
+
discretionary: markers.some((m) => m.discretionary === true)
|
|
41486
|
+
};
|
|
41487
|
+
}
|
|
41415
41488
|
function markerReplayable(i) {
|
|
41416
41489
|
if (!i.enabled) return false;
|
|
41417
41490
|
if (!i.hasPayload) return false;
|
|
@@ -42039,19 +42112,40 @@ function notifyUndeliverable(chatId, messageId, cause = "unknown") {
|
|
|
42039
42112
|
send: () => void sendUndeliverableNotice(chatId, messageId)
|
|
42040
42113
|
});
|
|
42041
42114
|
}
|
|
42115
|
+
function telegramMarkerReplayFacts(chatId, messageId) {
|
|
42116
|
+
const path = pendingInboundPath(chatId, messageId);
|
|
42117
|
+
if (!path || !existsSync9(path)) return null;
|
|
42118
|
+
try {
|
|
42119
|
+
const marker = JSON.parse(readFileSync14(path, "utf-8"));
|
|
42120
|
+
const facts = combineMarkerReplayFacts([
|
|
42121
|
+
{ hasPayload: Boolean(marker.payload), discretionary: marker.discretionary }
|
|
42122
|
+
]);
|
|
42123
|
+
return facts ? { enabled: channelReplayEnabled(), ...facts } : null;
|
|
42124
|
+
} catch {
|
|
42125
|
+
return null;
|
|
42126
|
+
}
|
|
42127
|
+
}
|
|
42042
42128
|
async function sendUndeliverableNotice(chatId, messageId) {
|
|
42129
|
+
const text = undeliverableNoticeTextForRepeat({
|
|
42130
|
+
replay: telegramMarkerReplayFacts(String(chatId), String(messageId)) ?? void 0,
|
|
42131
|
+
priorNotices: telegramUndeliverableNotices.noticeCount(String(chatId))
|
|
42132
|
+
});
|
|
42133
|
+
if (text === null) return;
|
|
42043
42134
|
try {
|
|
42044
42135
|
const resp = await telegramApiCall(
|
|
42045
42136
|
"sendMessage",
|
|
42046
42137
|
{
|
|
42047
42138
|
chat_id: chatId,
|
|
42048
42139
|
// ENG-6025: shared copy with the Slack undeliverable notice.
|
|
42049
|
-
text
|
|
42140
|
+
text,
|
|
42050
42141
|
reply_to_message_id: Number(messageId),
|
|
42051
42142
|
allow_sending_without_reply: true
|
|
42052
42143
|
},
|
|
42053
42144
|
1e4
|
|
42054
42145
|
);
|
|
42146
|
+
if (resp.ok) {
|
|
42147
|
+
telegramUndeliverableNotices.noteDelivered(String(chatId));
|
|
42148
|
+
}
|
|
42055
42149
|
if (!resp.ok) {
|
|
42056
42150
|
process.stderr.write(
|
|
42057
42151
|
`telegram-channel(${AGENT_CODE_NAME}): undeliverable notice failed (chat=${redactId(chatId)}): ${resp.description ?? "unknown"}
|
|
@@ -49,8 +49,8 @@ import {
|
|
|
49
49
|
writeDirectChatSessionState,
|
|
50
50
|
writeEgressAllowlist,
|
|
51
51
|
writePersistentClaudeWrapper
|
|
52
|
-
} from "./chunk-
|
|
53
|
-
import "./chunk-
|
|
52
|
+
} from "./chunk-N4QVPPYS.js";
|
|
53
|
+
import "./chunk-4ZPOP7EW.js";
|
|
54
54
|
import "./chunk-XWVM4KPK.js";
|
|
55
55
|
export {
|
|
56
56
|
EGRESS_BASELINE_DOMAINS,
|
|
@@ -104,4 +104,4 @@ export {
|
|
|
104
104
|
writeEgressAllowlist,
|
|
105
105
|
writePersistentClaudeWrapper
|
|
106
106
|
};
|
|
107
|
-
//# sourceMappingURL=persistent-session-
|
|
107
|
+
//# sourceMappingURL=persistent-session-W23U7GQU.js.map
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import {
|
|
2
2
|
paneLogPath
|
|
3
|
-
} from "./chunk-
|
|
4
|
-
import "./chunk-
|
|
3
|
+
} from "./chunk-N4QVPPYS.js";
|
|
4
|
+
import "./chunk-4ZPOP7EW.js";
|
|
5
5
|
import "./chunk-XWVM4KPK.js";
|
|
6
6
|
|
|
7
7
|
// src/lib/responsiveness-probe.ts
|
|
@@ -739,4 +739,4 @@ export {
|
|
|
739
739
|
readAndResetSlackReplyBindingClassifications,
|
|
740
740
|
readAndResetSlackReplyTargetClassifications
|
|
741
741
|
};
|
|
742
|
-
//# sourceMappingURL=responsiveness-probe-
|
|
742
|
+
//# sourceMappingURL=responsiveness-probe-IRQKIEBW.js.map
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import {
|
|
2
2
|
sessionTranscriptDir
|
|
3
|
-
} from "./chunk-
|
|
3
|
+
} from "./chunk-4ZPOP7EW.js";
|
|
4
4
|
|
|
5
5
|
// src/lib/session-auth-dead.ts
|
|
6
6
|
import { closeSync, openSync, readSync, readdirSync, statSync } from "fs";
|
|
@@ -203,4 +203,4 @@ export {
|
|
|
203
203
|
decideSessionAuthState,
|
|
204
204
|
probeSessionAuth
|
|
205
205
|
};
|
|
206
|
-
//# sourceMappingURL=session-auth-dead-
|
|
206
|
+
//# sourceMappingURL=session-auth-dead-VDDXVJTX.js.map
|
package/package.json
CHANGED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|