源码快照 @ 2026-09-01 (source-only, 剔除非源码素材)
Publish Claude Code Binaries / Stage and publish binaries (push) Canceled after 0s
Publish Tutti App Runtime / Build darwin-arm64 (push) Canceled after 0s
Publish Tutti App Runtime / Build darwin-amd64 (push) Canceled after 0s
Publish Tutti App Runtime / Build linux-amd64 (push) Canceled after 0s
Publish Tutti App Runtime / Build windows-amd64 (push) Canceled after 0s
Sync Tutti Agent Skills / sync (push) Canceled after 0s
Windows Agent Adapters / Test Windows agent adapters (push) Canceled after 0s
Windows Daemon Adapters / Test Windows daemon adapters (push) Canceled after 0s
Publish Tutti App Runtime / Publish runtime catalog (push) Canceled after 0s
Publish Claude Code Binaries / Stage and publish binaries (push) Canceled after 0s
Publish Tutti App Runtime / Build darwin-arm64 (push) Canceled after 0s
Publish Tutti App Runtime / Build darwin-amd64 (push) Canceled after 0s
Publish Tutti App Runtime / Build linux-amd64 (push) Canceled after 0s
Publish Tutti App Runtime / Build windows-amd64 (push) Canceled after 0s
Sync Tutti Agent Skills / sync (push) Canceled after 0s
Windows Agent Adapters / Test Windows agent adapters (push) Canceled after 0s
Windows Daemon Adapters / Test Windows daemon adapters (push) Canceled after 0s
Publish Tutti App Runtime / Publish runtime catalog (push) Canceled after 0s
This commit is contained in:
+45
@@ -0,0 +1,45 @@
|
||||
import { describe, expect, it } from "vitest";
|
||||
import { conversationRailRetryMode } from "./agentGuiConversationRailRequestRetry";
|
||||
|
||||
describe("conversationRailRetryMode", () => {
|
||||
it("retries transient upstream failures even when an adapter defaulted retryable to false", () => {
|
||||
expect(
|
||||
conversationRailRetryMode(
|
||||
Object.assign(new Error("upstream unavailable"), {
|
||||
retryable: false,
|
||||
status: 520
|
||||
})
|
||||
)
|
||||
).toBe("foreground");
|
||||
});
|
||||
|
||||
it("does not retry authorization, parameter, or cancellation failures", () => {
|
||||
expect(conversationRailRetryMode({ status: 400 })).toBeNull();
|
||||
expect(conversationRailRetryMode({ statusCode: 403 })).toBeNull();
|
||||
expect(
|
||||
conversationRailRetryMode({
|
||||
code: "common.invalid_input",
|
||||
name: "TshAppError"
|
||||
})
|
||||
).toBeNull();
|
||||
expect(
|
||||
conversationRailRetryMode({ code: "control_surface.unauthorized" })
|
||||
).toBeNull();
|
||||
expect(conversationRailRetryMode({ name: "AbortError" })).toBeNull();
|
||||
expect(conversationRailRetryMode(new Error("mapper failed"))).toBeNull();
|
||||
});
|
||||
|
||||
it("retries only errors with explicit transport or retryable evidence", () => {
|
||||
expect(conversationRailRetryMode(new TypeError("fetch failed"))).toBe(
|
||||
"foreground"
|
||||
);
|
||||
expect(conversationRailRetryMode({ retryable: true })).toBe("foreground");
|
||||
});
|
||||
|
||||
it("defers a second request after the first request timed out", () => {
|
||||
expect(conversationRailRetryMode({ name: "TimeoutError" })).toBe(
|
||||
"background"
|
||||
);
|
||||
expect(conversationRailRetryMode({ status: 504 })).toBe("background");
|
||||
});
|
||||
});
|
||||
Reference in New Issue
Block a user