mirror of
https://github.com/Wei-Shaw/claude-relay-service.git
synced 2026-01-23 18:19:17 +00:00
@@ -504,6 +504,9 @@ async function getAllAccounts() {
|
||||
for (const key of keys) {
|
||||
const accountData = await client.hgetall(key)
|
||||
if (accountData && Object.keys(accountData).length > 0) {
|
||||
// 获取限流状态信息
|
||||
const rateLimitInfo = await getAccountRateLimitInfo(accountData.id)
|
||||
|
||||
// 解析代理配置
|
||||
if (accountData.proxy) {
|
||||
try {
|
||||
@@ -519,7 +522,19 @@ async function getAllAccounts() {
|
||||
...accountData,
|
||||
geminiOauth: accountData.geminiOauth ? '[ENCRYPTED]' : '',
|
||||
accessToken: accountData.accessToken ? '[ENCRYPTED]' : '',
|
||||
refreshToken: accountData.refreshToken ? '[ENCRYPTED]' : ''
|
||||
refreshToken: accountData.refreshToken ? '[ENCRYPTED]' : '',
|
||||
// 添加限流状态信息(统一格式)
|
||||
rateLimitStatus: rateLimitInfo
|
||||
? {
|
||||
isRateLimited: rateLimitInfo.isRateLimited,
|
||||
rateLimitedAt: rateLimitInfo.rateLimitedAt,
|
||||
minutesRemaining: rateLimitInfo.minutesRemaining
|
||||
}
|
||||
: {
|
||||
isRateLimited: false,
|
||||
rateLimitedAt: null,
|
||||
minutesRemaining: 0
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
@@ -774,6 +789,45 @@ async function setAccountRateLimited(accountId, isLimited = true) {
|
||||
await updateAccount(accountId, updates)
|
||||
}
|
||||
|
||||
// 获取账户的限流信息(参考 claudeAccountService 的实现)
|
||||
async function getAccountRateLimitInfo(accountId) {
|
||||
try {
|
||||
const account = await getAccount(accountId)
|
||||
if (!account) {
|
||||
return null
|
||||
}
|
||||
|
||||
if (account.rateLimitStatus === 'limited' && account.rateLimitedAt) {
|
||||
const rateLimitedAt = new Date(account.rateLimitedAt)
|
||||
const now = new Date()
|
||||
const minutesSinceRateLimit = Math.floor((now - rateLimitedAt) / (1000 * 60))
|
||||
|
||||
// Gemini 限流持续时间为 1 小时
|
||||
const minutesRemaining = Math.max(0, 60 - minutesSinceRateLimit)
|
||||
const rateLimitEndAt = new Date(rateLimitedAt.getTime() + 60 * 60 * 1000).toISOString()
|
||||
|
||||
return {
|
||||
isRateLimited: minutesRemaining > 0,
|
||||
rateLimitedAt: account.rateLimitedAt,
|
||||
minutesSinceRateLimit,
|
||||
minutesRemaining,
|
||||
rateLimitEndAt
|
||||
}
|
||||
}
|
||||
|
||||
return {
|
||||
isRateLimited: false,
|
||||
rateLimitedAt: null,
|
||||
minutesSinceRateLimit: 0,
|
||||
minutesRemaining: 0,
|
||||
rateLimitEndAt: null
|
||||
}
|
||||
} catch (error) {
|
||||
logger.error(`❌ Failed to get rate limit info for Gemini account: ${accountId}`, error)
|
||||
return null
|
||||
}
|
||||
}
|
||||
|
||||
// 获取配置的OAuth客户端 - 参考GeminiCliSimulator的getOauthClient方法
|
||||
async function getOauthClient(accessToken, refreshToken) {
|
||||
const client = new OAuth2Client({
|
||||
@@ -1137,6 +1191,7 @@ module.exports = {
|
||||
refreshAccountToken,
|
||||
markAccountUsed,
|
||||
setAccountRateLimited,
|
||||
getAccountRateLimitInfo,
|
||||
isTokenExpired,
|
||||
getOauthClient,
|
||||
loadCodeAssist,
|
||||
|
||||
Reference in New Issue
Block a user