fix: add optimistic reset for transient 429 rate limit errors
Fixes issue #71 - 'No accounts available' error when API returns 429 The Google Cloud Code API can return 429 RESOURCE_EXHAUSTED errors even when accounts have quota available due to: - Temporary API load/throttling - Per-minute request limits (not per-day quota) - Transient backend issues This fix adds: 1. A 500ms buffer after waiting for rate limits to expire 2. Optimistic rate limit reset when all accounts appear stuck 3. Retry logic that clears rate limits and tries again The fix works in conjunction with the server-level optimistic reset that already exists, providing multiple layers of protection against false 'No accounts available' errors. Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
@@ -72,8 +72,19 @@ export async function sendMessage(anthropicRequest, accountManager, fallbackEnab
|
|||||||
const accountCount = accountManager.getAccountCount();
|
const accountCount = accountManager.getAccountCount();
|
||||||
logger.warn(`[CloudCode] All ${accountCount} account(s) rate-limited. Waiting ${formatDuration(allWaitMs)}...`);
|
logger.warn(`[CloudCode] All ${accountCount} account(s) rate-limited. Waiting ${formatDuration(allWaitMs)}...`);
|
||||||
await sleep(allWaitMs);
|
await sleep(allWaitMs);
|
||||||
|
|
||||||
|
// Add small buffer after waiting to ensure rate limits have truly expired
|
||||||
|
await sleep(500);
|
||||||
accountManager.clearExpiredLimits();
|
accountManager.clearExpiredLimits();
|
||||||
account = accountManager.pickNext(model);
|
account = accountManager.pickNext(model);
|
||||||
|
|
||||||
|
// If still no account after waiting, try optimistic reset
|
||||||
|
// This handles cases where the API rate limit is transient
|
||||||
|
if (!account) {
|
||||||
|
logger.warn('[CloudCode] No account available after wait, attempting optimistic reset...');
|
||||||
|
accountManager.resetAllRateLimits();
|
||||||
|
account = accountManager.pickNext(model);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!account) {
|
if (!account) {
|
||||||
|
|||||||
@@ -71,8 +71,19 @@ export async function* sendMessageStream(anthropicRequest, accountManager, fallb
|
|||||||
const accountCount = accountManager.getAccountCount();
|
const accountCount = accountManager.getAccountCount();
|
||||||
logger.warn(`[CloudCode] All ${accountCount} account(s) rate-limited. Waiting ${formatDuration(allWaitMs)}...`);
|
logger.warn(`[CloudCode] All ${accountCount} account(s) rate-limited. Waiting ${formatDuration(allWaitMs)}...`);
|
||||||
await sleep(allWaitMs);
|
await sleep(allWaitMs);
|
||||||
|
|
||||||
|
// Add small buffer after waiting to ensure rate limits have truly expired
|
||||||
|
await sleep(500);
|
||||||
accountManager.clearExpiredLimits();
|
accountManager.clearExpiredLimits();
|
||||||
account = accountManager.pickNext(model);
|
account = accountManager.pickNext(model);
|
||||||
|
|
||||||
|
// If still no account after waiting, try optimistic reset
|
||||||
|
// This handles cases where the API rate limit is transient
|
||||||
|
if (!account) {
|
||||||
|
logger.warn('[CloudCode] No account available after wait, attempting optimistic reset...');
|
||||||
|
accountManager.resetAllRateLimits();
|
||||||
|
account = accountManager.pickNext(model);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!account) {
|
if (!account) {
|
||||||
|
|||||||
Reference in New Issue
Block a user