fix(agents): suppress exec/bash exit code errors from user display
Exec/bash tool errors with non-zero exit codes (e.g., grep no matches, command not found) are now treated as internal/recoverable errors and not displayed to users. These errors are expected workflow results that the model should handle internally, not technical failures that need user attention. Fixes #3765
This commit is contained in:
parent
6372242da7
commit
9a806956a5
@ -171,10 +171,41 @@ describe("buildEmbeddedRunPayloads", () => {
|
|||||||
toolResultFormat: "plain",
|
toolResultFormat: "plain",
|
||||||
});
|
});
|
||||||
|
|
||||||
expect(payloads).toHaveLength(1);
|
// Exec exit code errors are now suppressed as internal/recoverable errors
|
||||||
expect(payloads[0]?.isError).toBe(true);
|
expect(payloads).toHaveLength(0);
|
||||||
expect(payloads[0]?.text).toContain("Exec");
|
});
|
||||||
expect(payloads[0]?.text).toContain("code 1");
|
|
||||||
|
it("suppresses exec exit code errors (grep no matches, etc.)", () => {
|
||||||
|
const payloads = buildEmbeddedRunPayloads({
|
||||||
|
assistantTexts: [],
|
||||||
|
toolMetas: [],
|
||||||
|
lastAssistant: undefined,
|
||||||
|
lastToolError: { toolName: "exec", error: "Command exited with code 1" },
|
||||||
|
sessionKey: "session:telegram",
|
||||||
|
inlineToolResultsAllowed: false,
|
||||||
|
verboseLevel: "off",
|
||||||
|
reasoningLevel: "off",
|
||||||
|
toolResultFormat: "plain",
|
||||||
|
});
|
||||||
|
|
||||||
|
// Exec/bash exit code errors should not be sent to the user
|
||||||
|
expect(payloads).toHaveLength(0);
|
||||||
|
});
|
||||||
|
|
||||||
|
it("suppresses bash exit code errors", () => {
|
||||||
|
const payloads = buildEmbeddedRunPayloads({
|
||||||
|
assistantTexts: [],
|
||||||
|
toolMetas: [],
|
||||||
|
lastAssistant: undefined,
|
||||||
|
lastToolError: { toolName: "bash", error: "Command exited with code 127" },
|
||||||
|
sessionKey: "session:telegram",
|
||||||
|
inlineToolResultsAllowed: false,
|
||||||
|
verboseLevel: "off",
|
||||||
|
reasoningLevel: "off",
|
||||||
|
toolResultFormat: "plain",
|
||||||
|
});
|
||||||
|
|
||||||
|
expect(payloads).toHaveLength(0);
|
||||||
});
|
});
|
||||||
|
|
||||||
it("suppresses recoverable tool errors containing 'required'", () => {
|
it("suppresses recoverable tool errors containing 'required'", () => {
|
||||||
|
|||||||
@ -182,7 +182,13 @@ export function buildEmbeddedRunPayloads(params: {
|
|||||||
// Check if this is a recoverable/internal tool error that shouldn't be shown to users
|
// Check if this is a recoverable/internal tool error that shouldn't be shown to users
|
||||||
// when there's already a user-facing reply (the model should have retried).
|
// when there's already a user-facing reply (the model should have retried).
|
||||||
const errorLower = (params.lastToolError.error ?? "").toLowerCase();
|
const errorLower = (params.lastToolError.error ?? "").toLowerCase();
|
||||||
|
const toolNameLower = (params.lastToolError.toolName ?? "").toLowerCase();
|
||||||
|
const isExecTool = toolNameLower === "exec" || toolNameLower === "bash";
|
||||||
|
// Exec/bash non-zero exit codes are internal errors (e.g., grep no matches) that
|
||||||
|
// the model should handle, not surface to users.
|
||||||
|
const isExecExitCodeError = isExecTool && errorLower.includes("exited with code");
|
||||||
const isRecoverableError =
|
const isRecoverableError =
|
||||||
|
isExecExitCodeError ||
|
||||||
errorLower.includes("required") ||
|
errorLower.includes("required") ||
|
||||||
errorLower.includes("missing") ||
|
errorLower.includes("missing") ||
|
||||||
errorLower.includes("invalid") ||
|
errorLower.includes("invalid") ||
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user