fix: 优化凭证刷新和重试机制以避免并发冲突

- 移除 Gemini 服务中不必要的过期检查逻辑
- 在凭证刷新时添加随机延迟和最大重试次数限制
- 在流式和非流式请求重试时添加随机延迟
This commit is contained in:
hex2077 2026-01-18 00:04:22 +08:00
parent 5f2a7c10a7
commit be814c5a56
3 changed files with 23 additions and 5 deletions

View file

@ -285,7 +285,7 @@ export class GeminiApiService {
async initializeAuth(forceRefresh = false) {
// 检查是否需要刷新 Token
const needsRefresh = forceRefresh || this.isExpiryDateNear();
const needsRefresh = forceRefresh
if (this.authClient.credentials.access_token && !needsRefresh) {
// Token 有效且不需要刷新

View file

@ -252,10 +252,22 @@ export class ProviderPoolManager {
*/
async _refreshNodeToken(providerType, providerStatus, force = false) {
const config = providerStatus.config;
this._log('info', `Starting token refresh for node ${providerStatus.uuid} (${providerType})`);
// 检查刷新次数是否已达上限最大3次
const currentRefreshCount = config.refreshCount || 0;
if (currentRefreshCount >= 3 && !force) {
this._log('warn', `Node ${providerStatus.uuid} has reached maximum refresh count (3), skipping refresh`);
return;
}
// 添加5秒内的随机等待时间避免并发刷新时的冲突
const randomDelay = Math.floor(Math.random() * 5000);
this._log('info', `Starting token refresh for node ${providerStatus.uuid} (${providerType}) with ${randomDelay}ms delay`);
await new Promise(resolve => setTimeout(resolve, randomDelay));
try {
config.refreshCount = (config.refreshCount || 0) + 1;
// 增加刷新计数
config.refreshCount = currentRefreshCount + 1;
// 使用适配器进行刷新
const tempConfig = {

View file

@ -345,7 +345,10 @@ export async function handleStreamRequest(res, service, model, requestBody, from
// 凭证已被标记为不健康后,尝试切换到新凭证重试
// 不再依赖状态码判断,只要凭证被标记不健康且可以重试,就尝试切换
if (credentialMarkedUnhealthy && currentRetry < maxRetries && providerPoolManager && CONFIG) {
console.log(`[Stream Retry] Credential marked unhealthy. Attempting retry ${currentRetry + 1}/${maxRetries} with different credential...`);
// 增加10秒内的随机等待时间避免所有请求同时切换凭证
const randomDelay = Math.floor(Math.random() * 10000); // 0-10000毫秒
console.log(`[Stream Retry] Credential marked unhealthy. Waiting ${randomDelay}ms before retry ${currentRetry + 1}/${maxRetries} with different credential...`);
await new Promise(resolve => setTimeout(resolve, randomDelay));
try {
// 动态导入以避免循环依赖
@ -475,7 +478,10 @@ export async function handleUnaryRequest(res, service, model, requestBody, fromP
// 凭证已被标记为不健康后,尝试切换到新凭证重试
// 不再依赖状态码判断,只要凭证被标记不健康且可以重试,就尝试切换
if (credentialMarkedUnhealthy && currentRetry < maxRetries && providerPoolManager && CONFIG) {
console.log(`[Unary Retry] Credential marked unhealthy. Attempting retry ${currentRetry + 1}/${maxRetries} with different credential...`);
// 增加10秒内的随机等待时间避免所有请求同时切换凭证
const randomDelay = Math.floor(Math.random() * 10000); // 0-10000毫秒
console.log(`[Unary Retry] Credential marked unhealthy. Waiting ${randomDelay}ms before retry ${currentRetry + 1}/${maxRetries} with different credential...`);
await new Promise(resolve => setTimeout(resolve, randomDelay));
try {
// 动态导入以避免循环依赖