When an auth profile hits a rate limit, `errorCount` is incremented and `cooldownUntil` is set with exponential backoff. After the cooldown expires, the time-based check correctly returns false — but `errorCount` persists. The next transient failure immediately escalates to a much longer cooldown because the backoff formula uses the stale count: 60s × 5^(errorCount-1), max 1h This creates a positive feedback loop where profiles appear permanently stuck after rate limits, requiring manual JSON editing to recover. Add `clearExpiredCooldowns()` which sweeps all profiles on every call to `resolveAuthProfileOrder()` and clears expired `cooldownUntil` / `disabledUntil` values along with resetting `errorCount` and `failureCounts` — giving the profile a fair retry window (circuit-breaker half-open → closed transition). Key design decisions: - `cooldownUntil` and `disabledUntil` handled independently (a profile can have both; only the expired one is cleared) - `errorCount` reset only when ALL unusable windows have expired - `lastFailureAt` preserved for the existing failureWindowMs decay logic - In-memory mutation; disk persistence happens lazily on the next store write, matching the existing save pattern Fixes #3604 Related: #13623, #15851, #11972, #8434
44 lines
1.3 KiB
TypeScript
44 lines
1.3 KiB
TypeScript
export { CLAUDE_CLI_PROFILE_ID, CODEX_CLI_PROFILE_ID } from "./auth-profiles/constants.js";
|
|
export { resolveAuthProfileDisplayLabel } from "./auth-profiles/display.js";
|
|
export { formatAuthDoctorHint } from "./auth-profiles/doctor.js";
|
|
export { resolveApiKeyForProfile } from "./auth-profiles/oauth.js";
|
|
export { resolveAuthProfileOrder } from "./auth-profiles/order.js";
|
|
export { resolveAuthStorePathForDisplay } from "./auth-profiles/paths.js";
|
|
export {
|
|
listProfilesForProvider,
|
|
markAuthProfileGood,
|
|
setAuthProfileOrder,
|
|
upsertAuthProfile,
|
|
upsertAuthProfileWithLock,
|
|
} from "./auth-profiles/profiles.js";
|
|
export {
|
|
repairOAuthProfileIdMismatch,
|
|
suggestOAuthProfileIdForLegacyDefault,
|
|
} from "./auth-profiles/repair.js";
|
|
export {
|
|
ensureAuthProfileStore,
|
|
loadAuthProfileStore,
|
|
saveAuthProfileStore,
|
|
} from "./auth-profiles/store.js";
|
|
export type {
|
|
ApiKeyCredential,
|
|
AuthProfileCredential,
|
|
AuthProfileFailureReason,
|
|
AuthProfileIdRepairResult,
|
|
AuthProfileStore,
|
|
OAuthCredential,
|
|
ProfileUsageStats,
|
|
TokenCredential,
|
|
} from "./auth-profiles/types.js";
|
|
export {
|
|
calculateAuthProfileCooldownMs,
|
|
clearAuthProfileCooldown,
|
|
clearExpiredCooldowns,
|
|
getSoonestCooldownExpiry,
|
|
isProfileInCooldown,
|
|
markAuthProfileCooldown,
|
|
markAuthProfileFailure,
|
|
markAuthProfileUsed,
|
|
resolveProfileUnusableUntilForDisplay,
|
|
} from "./auth-profiles/usage.js";
|