feat: 按上游计费倍率调度 OpenAI 账号

This commit is contained in:
Tian Lee
2026-07-16 00:40:46 +08:00
parent 0765d10c1d
commit 90ee85f3ef
34 changed files with 2299 additions and 252 deletions
@@ -863,10 +863,18 @@ func filterSchedulerExtra(extra map[string]any) map[string]any {
"auto_pause_5h_disabled",
"auto_pause_7d_disabled",
"model_rate_limits",
service.UpstreamBillingProbeExtraKey,
}
filtered := make(map[string]any)
for _, key := range keys {
if value, ok := extra[key]; ok && value != nil {
if key == service.UpstreamBillingProbeExtraKey {
filteredProbe := filterSchedulerUpstreamBillingProbe(value)
if filteredProbe == nil {
continue
}
value = filteredProbe
}
filtered[key] = value
}
}
@@ -875,3 +883,43 @@ func filterSchedulerExtra(extra map[string]any) map[string]any {
}
return filtered
}
func filterSchedulerUpstreamBillingProbe(value any) map[string]any {
source, ok := value.(map[string]any)
if !ok {
return nil
}
status, ok := source["status"].(string)
if !ok || status == "" {
return nil
}
filtered := map[string]any{"status": status}
for _, key := range []string{"received_at", "fresh_until", "next_probe_at"} {
if field, exists := source[key]; exists && field != nil {
filtered[key] = field
}
}
data, ok := source["data"].(map[string]any)
if !ok {
return filtered
}
filteredData := make(map[string]any)
for _, key := range []string{
"billing_scope",
"resolved_rate_multiplier",
"peak_rate_enabled",
"peak_start",
"peak_end",
"peak_rate_multiplier",
"timezone",
} {
if field, exists := data[key]; exists && field != nil {
filteredData[key] = field
}
}
if len(filteredData) > 0 {
filtered["data"] = filteredData
}
return filtered
}
@@ -1,6 +1,7 @@
package repository
import (
"strings"
"testing"
"github.com/Wei-Shaw/sub2api/internal/service"
@@ -35,3 +36,75 @@ func TestSchedulerMetadataAccountKeepsOpenAISubscriptionIdentity(t *testing.T) {
require.True(t, metadata.IsOpenAIChatGPTSubscription())
require.Empty(t, metadata.GetCredential("access_token"))
}
func TestSchedulerMetadataAccountProjectsUpstreamBillingProbe(t *testing.T) {
lastError := strings.Repeat("upstream diagnostic ", 512)
probe := map[string]any{
"status": "ok",
"data": map[string]any{
"billing_scope": "token",
"resolved_rate_multiplier": 0.03,
"peak_rate_enabled": true,
"peak_start": "09:00",
"peak_end": "18:00",
"peak_rate_multiplier": 2.0,
"timezone": "Asia/Shanghai",
"effective_rate_multiplier": 0.03,
"remote_diagnostic": lastError,
},
"received_at": "2026-07-13T10:00:00Z",
"fresh_until": "2026-07-13T11:00:00Z",
"next_probe_at": "2026-07-13T10:30:00Z",
"http_status": 502,
"last_error": lastError,
}
account := service.Account{
ID: 42,
Extra: map[string]any{
"upstream_billing_probe": probe,
"unused_large_field": "drop-me",
},
}
metadata := buildSchedulerMetadataAccount(account)
fullPayload, metaPayload, err := marshalSchedulerCacheAccount(account)
require.NoError(t, err)
filtered, ok := metadata.Extra["upstream_billing_probe"].(map[string]any)
require.True(t, ok)
require.Equal(t, "ok", filtered["status"])
require.Equal(t, "2026-07-13T10:00:00Z", filtered["received_at"])
require.Equal(t, "2026-07-13T11:00:00Z", filtered["fresh_until"])
require.Equal(t, "2026-07-13T10:30:00Z", filtered["next_probe_at"])
require.NotContains(t, filtered, "http_status")
require.NotContains(t, filtered, "last_error")
filteredData, ok := filtered["data"].(map[string]any)
require.True(t, ok)
require.Equal(t, "token", filteredData["billing_scope"])
require.Equal(t, 0.03, filteredData["resolved_rate_multiplier"])
require.Equal(t, true, filteredData["peak_rate_enabled"])
require.Equal(t, "09:00", filteredData["peak_start"])
require.Equal(t, "18:00", filteredData["peak_end"])
require.Equal(t, 2.0, filteredData["peak_rate_multiplier"])
require.Equal(t, "Asia/Shanghai", filteredData["timezone"])
require.NotContains(t, filteredData, "effective_rate_multiplier")
require.NotContains(t, filteredData, "remote_diagnostic")
require.NotContains(t, metadata.Extra, "unused_large_field")
require.Contains(t, string(fullPayload), lastError)
require.NotContains(t, string(metaPayload), "last_error")
require.Less(t, len(metaPayload)*4, len(fullPayload))
}
func TestSchedulerMetadataAccountDropsInvalidUpstreamBillingProbe(t *testing.T) {
for _, probe := range []any{
"invalid",
map[string]any{},
map[string]any{"status": ""},
} {
metadata := buildSchedulerMetadataAccount(service.Account{
Extra: map[string]any{service.UpstreamBillingProbeExtraKey: probe},
})
require.NotContains(t, metadata.Extra, service.UpstreamBillingProbeExtraKey)
}
}