From 21b6f2d593a3dce45abdfe491974634842698f08 Mon Sep 17 00:00:00 2001 From: erio Date: Fri, 20 Mar 2026 00:04:01 +0800 Subject: [PATCH] fix(antigravity): correctly mark credits exhausted on "Resource has been exhausted" 429 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit shouldMarkCreditsExhausted was blocked by isURLLevelRateLimit check when credit overages retry returned "Resource has been exhausted (e.g. check quota).", causing credits to never be marked as exhausted. This led to an infinite loop where each request injected credits, bypassed model rate limits, and failed again. - Remove isURLLevelRateLimit guard from shouldMarkCreditsExhausted (only called for credit retry responses — if credits retry fails, mark exhausted) - Add "resource has been exhausted" to creditsExhaustedKeywords - Update tests to match corrected behavior --- .../internal/service/antigravity_credits_overages.go | 7 ++++--- .../service/antigravity_credits_overages_test.go | 10 ++++++++-- 2 files changed, 12 insertions(+), 5 deletions(-) diff --git a/backend/internal/service/antigravity_credits_overages.go b/backend/internal/service/antigravity_credits_overages.go index 1521dfcd..ec365085 100644 --- a/backend/internal/service/antigravity_credits_overages.go +++ b/backend/internal/service/antigravity_credits_overages.go @@ -45,6 +45,7 @@ var ( "minimumcreditamountforusage", "minimum credit amount for usage", "minimum credit", + "resource has been exhausted", } ) @@ -147,9 +148,9 @@ func shouldMarkCreditsExhausted(resp *http.Response, respBody []byte, reqErr err if resp.StatusCode >= 500 || resp.StatusCode == http.StatusRequestTimeout { return false } - if isURLLevelRateLimit(respBody) { - return false - } + // 注意:不再检查 isURLLevelRateLimit。此函数仅在积分重试失败后调用, + // 如果注入 enabledCreditTypes 后仍返回 "Resource has been exhausted", + // 说明积分也已耗尽,应该标记。clearCreditsExhausted 会在后续成功时自动清除。 if info := parseAntigravitySmartRetryInfo(respBody); info != nil { return false } diff --git a/backend/internal/service/antigravity_credits_overages_test.go b/backend/internal/service/antigravity_credits_overages_test.go index bc679494..7a5224da 100644 --- a/backend/internal/service/antigravity_credits_overages_test.go +++ b/backend/internal/service/antigravity_credits_overages_test.go @@ -406,10 +406,16 @@ func TestShouldMarkCreditsExhausted(t *testing.T) { require.False(t, shouldMarkCreditsExhausted(resp, []byte(`{"error":"Insufficient credits"}`), nil)) }) - t.Run("URL 级限流不标记", func(t *testing.T) { + t.Run("Resource has been exhausted 应标记为积分耗尽", func(t *testing.T) { resp := &http.Response{StatusCode: http.StatusTooManyRequests} body := []byte(`{"error":{"message":"Resource has been exhausted"}}`) - require.False(t, shouldMarkCreditsExhausted(resp, body, nil)) + require.True(t, shouldMarkCreditsExhausted(resp, body, nil)) + }) + + t.Run("Resource has been exhausted (check quota) 完整格式应标记", func(t *testing.T) { + resp := &http.Response{StatusCode: http.StatusTooManyRequests} + body := []byte(`{"error":{"code":429,"message":"Resource has been exhausted (e.g. check quota).","status":"RESOURCE_EXHAUSTED"}}`) + require.True(t, shouldMarkCreditsExhausted(resp, body, nil)) }) t.Run("结构化限流不标记", func(t *testing.T) {