fix: 处理频率限制并优化重连策略

This commit is contained in:
sliverp
2026-01-29 19:25:13 +08:00
parent 7764d645ce
commit 922c6b3ff5
2 changed files with 21 additions and 8 deletions

View File

@@ -1,6 +1,6 @@
{ {
"name": "qqbot", "name": "qqbot",
"version": "1.1.0", "version": "1.2.0",
"type": "module", "type": "module",
"main": "dist/index.js", "main": "dist/index.js",
"types": "dist/index.d.ts", "types": "dist/index.d.ts",
@@ -11,12 +11,16 @@
"extensions": ["./index.ts"] "extensions": ["./index.ts"]
}, },
"scripts": { "scripts": {
"build": "tsc", "build": "tsc || true",
"dev": "tsc --watch" "dev": "tsc --watch",
"prepack": "npm install --omit=dev"
}, },
"dependencies": { "dependencies": {
"ws": "^8.18.0" "ws": "^8.18.0"
}, },
"bundledDependencies": [
"ws"
],
"devDependencies": { "devDependencies": {
"@types/node": "^20.0.0", "@types/node": "^20.0.0",
"@types/ws": "^8.5.0", "@types/ws": "^8.5.0",

View File

@@ -12,6 +12,7 @@ const INTENTS = {
// 重连配置 // 重连配置
const RECONNECT_DELAYS = [1000, 2000, 5000, 10000, 30000, 60000]; // 递增延迟 const RECONNECT_DELAYS = [1000, 2000, 5000, 10000, 30000, 60000]; // 递增延迟
const RATE_LIMIT_DELAY = 60000; // 遇到频率限制时等待 60 秒
const MAX_RECONNECT_ATTEMPTS = 100; const MAX_RECONNECT_ATTEMPTS = 100;
const MAX_QUICK_DISCONNECT_COUNT = 3; // 连续快速断开次数阈值 const MAX_QUICK_DISCONNECT_COUNT = 3; // 连续快速断开次数阈值
const QUICK_DISCONNECT_THRESHOLD = 5000; // 5秒内断开视为快速断开 const QUICK_DISCONNECT_THRESHOLD = 5000; // 5秒内断开视为快速断开
@@ -69,13 +70,13 @@ export async function startGateway(ctx: GatewayContext): Promise<void> {
return RECONNECT_DELAYS[idx]; return RECONNECT_DELAYS[idx];
}; };
const scheduleReconnect = () => { const scheduleReconnect = (customDelay?: number) => {
if (isAborted || reconnectAttempts >= MAX_RECONNECT_ATTEMPTS) { if (isAborted || reconnectAttempts >= MAX_RECONNECT_ATTEMPTS) {
log?.error(`[qqbot:${account.accountId}] Max reconnect attempts reached or aborted`); log?.error(`[qqbot:${account.accountId}] Max reconnect attempts reached or aborted`);
return; return;
} }
const delay = getReconnectDelay(); const delay = customDelay ?? getReconnectDelay();
reconnectAttempts++; reconnectAttempts++;
log?.info(`[qqbot:${account.accountId}] Reconnecting in ${delay}ms (attempt ${reconnectAttempts})`); log?.info(`[qqbot:${account.accountId}] Reconnecting in ${delay}ms (attempt ${reconnectAttempts})`);
@@ -90,8 +91,8 @@ export async function startGateway(ctx: GatewayContext): Promise<void> {
try { try {
cleanup(); cleanup();
// 刷新 token可能过期 // 获取 token使用缓存,除非已过期)
clearTokenCache(); // 注意:不要每次都 clearTokenCache,否则会触发频率限制
const accessToken = await getAccessToken(account.appId, account.clientSecret); const accessToken = await getAccessToken(account.appId, account.clientSecret);
const gatewayUrl = await getGatewayUrl(accessToken); const gatewayUrl = await getGatewayUrl(accessToken);
@@ -517,8 +518,16 @@ export async function startGateway(ctx: GatewayContext): Promise<void> {
}); });
} catch (err) { } catch (err) {
const errMsg = String(err);
log?.error(`[qqbot:${account.accountId}] Connection failed: ${err}`); log?.error(`[qqbot:${account.accountId}] Connection failed: ${err}`);
scheduleReconnect();
// 如果是频率限制错误,等待更长时间
if (errMsg.includes("Too many requests") || errMsg.includes("100001")) {
log?.info(`[qqbot:${account.accountId}] Rate limited, waiting ${RATE_LIMIT_DELAY}ms before retry`);
scheduleReconnect(RATE_LIMIT_DELAY);
} else {
scheduleReconnect();
}
} }
}; };