From 2dd093a32e8fae75f3621afe29fad1f7f631a436 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E4=B8=96=E7=95=8C?= Date: Sun, 15 Mar 2026 21:09:08 +0800 Subject: [PATCH] ccm,ocm: fix data race, remove dead code, clean up inefficiencies --- service/ccm/credential_default.go | 3 ++- service/ccm/credential_provider.go | 8 ++++++++ service/ccm/service.go | 6 ++---- service/ccm/service_usage.go | 2 +- service/ocm/credential_default.go | 7 +------ service/ocm/credential_provider.go | 8 ++++++++ service/ocm/service_usage.go | 2 +- 7 files changed, 23 insertions(+), 13 deletions(-) diff --git a/service/ccm/credential_default.go b/service/ccm/credential_default.go index 021df5d27..50791064b 100644 --- a/service/ccm/credential_default.go +++ b/service/ccm/credential_default.go @@ -642,8 +642,9 @@ func (c *defaultCredential) fetchProfile(ctx context.Context, httpClient *http.C if rateLimitTier != "" { c.state.rateLimitTier = rateLimitTier } + resolvedAccountType := c.state.accountType c.stateAccess.Unlock() - c.logger.Info("fetched profile for ", c.tag, ": type=", c.state.accountType, ", tier=", rateLimitTier, ", weight=", ccmPlanWeight(c.state.accountType, rateLimitTier)) + c.logger.Info("fetched profile for ", c.tag, ": type=", resolvedAccountType, ", tier=", rateLimitTier, ", weight=", ccmPlanWeight(resolvedAccountType, rateLimitTier)) } func (c *defaultCredential) close() { diff --git a/service/ccm/credential_provider.go b/service/ccm/credential_provider.go index 5500df6a1..d4f5abe2f 100644 --- a/service/ccm/credential_provider.go +++ b/service/ccm/credential_provider.go @@ -348,6 +348,14 @@ func (p *balancerProvider) pollIfStale(ctx context.Context) { } p.sessionAccess.Unlock() + p.interruptAccess.Lock() + for key, entry := range p.credentialInterrupts { + if entry.context.Err() != nil { + delete(p.credentialInterrupts, key) + } + } + p.interruptAccess.Unlock() + for _, credential := range p.credentials { if time.Since(credential.lastUpdatedTime()) > credential.pollBackoff(p.pollInterval) { credential.pollUsage(ctx) diff --git a/service/ccm/service.go b/service/ccm/service.go index 74952173c..b1c637d14 100644 --- a/service/ccm/service.go +++ b/service/ccm/service.go @@ -5,7 +5,7 @@ import ( "encoding/json" "net/http" "strings" - "sync" + "github.com/sagernet/sing-box/adapter" boxService "github.com/sagernet/sing-box/adapter/service" @@ -157,9 +157,7 @@ type Service struct { listener *listener.Listener tlsConfig tls.ServerConfig httpServer *http.Server - userManager *UserManager - trackingGroup sync.WaitGroup - shuttingDown bool + userManager *UserManager providers map[string]credentialProvider allCredentials []Credential diff --git a/service/ccm/service_usage.go b/service/ccm/service_usage.go index e23db6654..ff14b0543 100644 --- a/service/ccm/service_usage.go +++ b/service/ccm/service_usage.go @@ -652,7 +652,7 @@ func (u *AggregatedUsage) AddUsageWithCycleHint( addUsageToCombinations(&u.Combinations, model, contextWindow, weekStartUnix, messagesCount, inputTokens, outputTokens, cacheReadTokens, cacheCreationTokens, cacheCreation5MinuteTokens, cacheCreation1HourTokens, user) - go u.scheduleSave() + u.scheduleSave() return nil } diff --git a/service/ocm/credential_default.go b/service/ocm/credential_default.go index 18612a569..ed4214fab 100644 --- a/service/ocm/credential_default.go +++ b/service/ocm/credential_default.go @@ -587,12 +587,7 @@ func (c *defaultCredential) pollUsage(ctx context.Context) { return } - var usageURL string - if c.isAPIKeyMode() { - usageURL = openaiAPIBaseURL + "/api/codex/usage" - } else { - usageURL = strings.TrimSuffix(chatGPTBackendURL, "/codex") + "/wham/usage" - } + usageURL := strings.TrimSuffix(chatGPTBackendURL, "/codex") + "/wham/usage" accountID := c.getAccountID() pollClient := &http.Client{ diff --git a/service/ocm/credential_provider.go b/service/ocm/credential_provider.go index 6f3da6b43..092b40c67 100644 --- a/service/ocm/credential_provider.go +++ b/service/ocm/credential_provider.go @@ -375,6 +375,14 @@ func (p *balancerProvider) pollIfStale(ctx context.Context) { } p.sessionAccess.Unlock() + p.interruptAccess.Lock() + for key, entry := range p.credentialInterrupts { + if entry.context.Err() != nil { + delete(p.credentialInterrupts, key) + } + } + p.interruptAccess.Unlock() + for _, credential := range p.credentials { if time.Since(credential.lastUpdatedTime()) > credential.pollBackoff(p.pollInterval) { credential.pollUsage(ctx) diff --git a/service/ocm/service_usage.go b/service/ocm/service_usage.go index 19a853a7c..10ebc2355 100644 --- a/service/ocm/service_usage.go +++ b/service/ocm/service_usage.go @@ -1148,7 +1148,7 @@ func (u *AggregatedUsage) AddUsageWithCycleHint(model string, contextWindow int, addUsageToCombinations(&u.Combinations, model, normalizedServiceTier, contextWindow, weekStartUnix, user, inputTokens, outputTokens, cachedTokens) - go u.scheduleSave() + u.scheduleSave() return nil }