feat: sync deployed v1.0.0-rc.38-custom.42
Sync production source including routing, billing, Astra detection and public uptime. Update custom build instructions and license packaging.
This commit is contained in:
1 parent
aa6c3f50f4
commit
ceddfd3d6b
828 files changed
+122253
-13702
No files matched your search
+27
-13
@@ -12,14 +12,12 @@ import (
|
||||
"github.com/QuantumNous/new-api/logger"
|
||||
"github.com/QuantumNous/new-api/model"
|
||||
"github.com/QuantumNous/new-api/pkg/billingexpr"
|
||||
perfmetrics "github.com/QuantumNous/new-api/pkg/perf_metrics"
|
||||
relaycommon "github.com/QuantumNous/new-api/relay/common"
|
||||
relayconstant "github.com/QuantumNous/new-api/relay/constant"
|
||||
"github.com/QuantumNous/new-api/relaykit/dto"
|
||||
"github.com/QuantumNous/new-api/relaykit/types"
|
||||
"github.com/QuantumNous/new-api/setting/operation_setting"
|
||||
|
||||
"github.com/bytedance/gopkg/util/gopool"
|
||||
"github.com/gin-gonic/gin"
|
||||
"github.com/shopspring/decimal"
|
||||
)
|
||||
@@ -66,6 +64,7 @@ type textQuotaSummary struct {
|
||||
AudioInputPrice float64
|
||||
ToolSurchargeItems []ToolSurchargeItem
|
||||
ToolCallSurchargeQuota decimal.Decimal
|
||||
FixedPriceBilling bool
|
||||
}
|
||||
|
||||
// hasBillableUsage reports whether this request should incur any charge.
|
||||
@@ -73,7 +72,7 @@ type textQuotaSummary struct {
|
||||
// surcharge (e.g. /v1/alpha/search returns no usage but bills one web_search
|
||||
// call), so token count alone is not sufficient to decide.
|
||||
func (s *textQuotaSummary) hasBillableUsage() bool {
|
||||
return s.TotalTokens > 0 || !s.ToolCallSurchargeQuota.IsZero()
|
||||
return s.FixedPriceBilling || s.TotalTokens > 0 || !s.ToolCallSurchargeQuota.IsZero()
|
||||
}
|
||||
|
||||
func cacheWriteTokensTotal(summary textQuotaSummary) int {
|
||||
@@ -397,7 +396,7 @@ func PostTextConsumeQuota(ctx *gin.Context, relayInfo *relaycommon.RelayInfo, us
|
||||
if usage == nil {
|
||||
extraContent = append(extraContent, "上游无计费信息")
|
||||
}
|
||||
if originUsage != nil {
|
||||
if originUsage != nil && !ctx.GetBool("attempt_checkpoint") {
|
||||
ObserveChannelAffinityUsageCacheByRelayFormat(ctx, billingUsage, relayInfo.GetFinalRequestRelayFormat())
|
||||
}
|
||||
|
||||
@@ -405,17 +404,30 @@ func PostTextConsumeQuota(ctx *gin.Context, relayInfo *relaycommon.RelayInfo, us
|
||||
summary := calculateTextQuotaSummary(ctx, relayInfo, billingUsage)
|
||||
|
||||
var tieredResult *billingexpr.TieredResult
|
||||
var tieredTokens billingexpr.TokenParams
|
||||
tieredBillingApplied := false
|
||||
if originUsage != nil {
|
||||
snap := relayInfo.TieredBillingSnapshot
|
||||
// Providers normally estimate missing usage before settlement. Preserve the
|
||||
// same prompt estimate when a fixed-price expression reaches us without it;
|
||||
// its conditions must still run and may select a token-priced fallback.
|
||||
if billingUsage == nil && snap != nil && billingexpr.UsesFixedPricingByHash(snap.ExprString, snap.ExprHash) {
|
||||
billingUsage = &dto.Usage{PromptTokens: summary.PromptTokens, CompletionTokens: summary.CompletionTokens, TotalTokens: summary.TotalTokens}
|
||||
}
|
||||
if billingUsage != nil {
|
||||
var tieredUsedVars map[string]bool
|
||||
if snap := relayInfo.TieredBillingSnapshot; snap != nil {
|
||||
tieredUsedVars = billingexpr.UsedVars(snap.ExprString)
|
||||
tieredUsedVars = billingexpr.UsedVarsByHash(snap.ExprString, snap.ExprHash)
|
||||
}
|
||||
tieredOk, tieredQuota, tieredRes := TryTieredSettle(relayInfo, BuildTieredTokenParams(billingUsage, summary.IsClaudeUsageSemantic, tieredUsedVars))
|
||||
tieredTokens = BuildTieredTokenParams(billingUsage, summary.IsClaudeUsageSemantic, tieredUsedVars)
|
||||
tieredOk, tieredQuota, tieredRes := TryTieredSettle(relayInfo, tieredTokens)
|
||||
if tieredOk {
|
||||
tieredBillingApplied = true
|
||||
tieredResult = tieredRes
|
||||
summary.Quota = composeTieredTextQuota(relayInfo, summary, tieredQuota, tieredRes)
|
||||
summary.FixedPriceBilling = isFixedPriceSettlement(relayInfo, tieredRes)
|
||||
if summary.FixedPriceBilling {
|
||||
summary.AudioInputPrice = 0
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -440,14 +452,16 @@ func PostTextConsumeQuota(ctx *gin.Context, relayInfo *relaycommon.RelayInfo, us
|
||||
if !summary.hasBillableUsage() {
|
||||
extraContent = append(extraContent, "上游没有返回计费信息,无法扣费(可能是上游超时)")
|
||||
logger.LogError(ctx, fmt.Sprintf("total tokens is 0, cannot consume quota, userId %d, channelId %d, tokenId %d, model %s, pre-consumed quota %d", relayInfo.UserId, relayInfo.ChannelId, relayInfo.TokenId, summary.ModelName, relayInfo.FinalPreConsumedQuota))
|
||||
} else {
|
||||
} else if relayInfo.DurableAttemptID == 0 {
|
||||
model.UpdateUserUsedQuotaAndRequestCount(relayInfo.UserId, summary.Quota)
|
||||
model.UpdateChannelUsedQuota(relayInfo.ChannelId, summary.Quota)
|
||||
}
|
||||
|
||||
if relayInfo.DurableAttemptID == 0 {
|
||||
if err := SettleBilling(ctx, relayInfo, summary.Quota); err != nil {
|
||||
logger.LogError(ctx, "error settling billing: "+err.Error())
|
||||
}
|
||||
}
|
||||
|
||||
logModel := summary.ModelName
|
||||
if strings.HasPrefix(logModel, "gpt-4-gizmo") {
|
||||
@@ -516,11 +530,12 @@ func PostTextConsumeQuota(ctx *gin.Context, relayInfo *relaycommon.RelayInfo, us
|
||||
}
|
||||
if tieredBillingApplied {
|
||||
InjectTieredBillingInfo(other, relayInfo, tieredResult)
|
||||
|
||||
}
|
||||
|
||||
attachQuotaSaturation(ctx, relayInfo, other)
|
||||
|
||||
model.RecordConsumeLog(ctx, relayInfo.UserId, model.RecordConsumeLogParams{
|
||||
logParams := model.RecordConsumeLogParams{
|
||||
ChannelId: relayInfo.ChannelId,
|
||||
PromptTokens: summary.PromptTokens,
|
||||
CompletionTokens: summary.CompletionTokens,
|
||||
@@ -533,8 +548,7 @@ func PostTextConsumeQuota(ctx *gin.Context, relayInfo *relaycommon.RelayInfo, us
|
||||
IsStream: relayInfo.IsStream,
|
||||
Group: relayInfo.UsingGroup,
|
||||
Other: other,
|
||||
})
|
||||
gopool.Go(func() {
|
||||
perfmetrics.RecordRelaySample(relayInfo, true, int64(summary.CompletionTokens))
|
||||
})
|
||||
}
|
||||
if relayInfo.DurableAttemptID != 0 { recordDurableAttempt(ctx,relayInfo,billingUsage,logParams) } else { model.RecordConsumeLog(ctx,relayInfo.UserId,logParams) }
|
||||
relayInfo.PerformanceOutputTokens = int64(summary.CompletionTokens)
|
||||
}
|
||||
Reference in new issue
Block a user