Skip to content

Commit d68ba5e

Browse files
Suppress expired exec approval followup warnings (#66685)
* fix(agents): suppress expired approval followup warnings * fix(agents): suppress expired approval followup warnings --------- Co-authored-by: openclaw-clownfish[bot] <280122609+openclaw-clownfish[bot]@users.noreply.github.com>
1 parent d0f6558 commit d68ba5e

2 files changed

Lines changed: 37 additions & 0 deletions

File tree

src/agents/bash-tools.exec-host-shared.test.ts

Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -167,6 +167,39 @@ describe("sendExecApprovalFollowupResult", () => {
167167
);
168168
});
169169

170+
it.each([
171+
{
172+
name: "direct gateway code",
173+
error: Object.assign(new Error("approval not found"), {
174+
gatewayCode: "APPROVAL_NOT_FOUND",
175+
}),
176+
},
177+
{
178+
name: "structured invalid-request details",
179+
error: Object.assign(new Error("approval not found"), {
180+
gatewayCode: "INVALID_REQUEST",
181+
details: { reason: "APPROVAL_NOT_FOUND" },
182+
}),
183+
},
184+
{
185+
name: "legacy message-only error",
186+
error: new Error("unknown or expired approval id"),
187+
},
188+
])("suppresses approval-not-found followup dispatch failures ($name)", async ({ error }) => {
189+
sendExecApprovalFollowup.mockRejectedValue(error);
190+
191+
await sendExecApprovalFollowupResult(
192+
{
193+
approvalId: "approval-expired",
194+
sessionKey: "agent:main:main",
195+
},
196+
"Exec finished",
197+
{ sendExecApprovalFollowup, logWarn },
198+
);
199+
200+
expect(logWarn).not.toHaveBeenCalled();
201+
});
202+
170203
it("evicts oldest followup failure dedupe keys after reaching the cap", async () => {
171204
sendExecApprovalFollowup.mockRejectedValue(new Error("Channel is required"));
172205
const deps = { sendExecApprovalFollowup, logWarn };

src/agents/bash-tools.exec-host-shared.ts

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
*/
66
import crypto from "node:crypto";
77
import { resolveExpiresAtMsFromDurationMs } from "@openclaw/normalization-core/number-coercion";
8+
import { isApprovalNotFoundError } from "../infra/approval-errors.js";
89
import { formatErrorMessage } from "../infra/errors.js";
910
import { buildExecApprovalUnavailableReplyPayload } from "../infra/exec-approval-reply.js";
1011
import {
@@ -481,6 +482,9 @@ export async function sendExecApprovalFollowupResult(
481482
}
482483
: {}),
483484
}).catch((error: unknown) => {
485+
if (isApprovalNotFoundError(error)) {
486+
return;
487+
}
484488
const message = formatErrorMessage(error);
485489
const key = `${target.approvalId}:${message}`;
486490
if (!rememberExecApprovalFollowupFailureKey(key)) {

0 commit comments

Comments
 (0)