refactor(channel): 抽取渠道映射公共函数 + OpenAI映射到body + 空响应修复 + 清理日志
- 抽取 ResolveChannelMappingAndRestrict 统一入口(5处→1个方法) - 抽取 BuildModelMappingChain 到 ChannelMappingResult 方法(5处→1行调用) - OpenAI 三入口 Forward 前应用渠道映射到请求体 - OpenAI Responses/Messages 限制检查添加错误响应 - 清理前端 3 处 console.log 调试日志
This commit is contained in:
@@ -92,6 +92,23 @@ type ChannelMappingResult struct {
|
||||
BillingModelSource string // 计费模型来源("requested" / "upstream")
|
||||
}
|
||||
|
||||
// BuildModelMappingChain 根据映射结果和上游实际模型构建映射链描述。
|
||||
// reqModel: 客户端请求的原始模型名。
|
||||
// upstreamModel: 上游实际使用的模型名(ForwardResult.UpstreamModel)。
|
||||
// 返回空字符串表示无映射。
|
||||
func (r ChannelMappingResult) BuildModelMappingChain(reqModel, upstreamModel string) string {
|
||||
if !r.Mapped {
|
||||
if upstreamModel != "" && upstreamModel != reqModel {
|
||||
return reqModel + "→" + upstreamModel
|
||||
}
|
||||
return ""
|
||||
}
|
||||
if upstreamModel != "" && upstreamModel != r.MappedModel {
|
||||
return reqModel + "→" + r.MappedModel + "→" + upstreamModel
|
||||
}
|
||||
return reqModel + "→" + r.MappedModel
|
||||
}
|
||||
|
||||
const (
|
||||
channelCacheTTL = 60 * time.Second
|
||||
channelErrorTTL = 5 * time.Second // DB 错误时的短缓存
|
||||
|
||||
@@ -8195,6 +8195,19 @@ func (s *GatewayService) IsModelRestricted(ctx context.Context, groupID int64, m
|
||||
return s.channelService.IsModelRestricted(ctx, groupID, model)
|
||||
}
|
||||
|
||||
// ResolveChannelMappingAndRestrict 解析渠道映射并检查模型限制。
|
||||
// 返回映射结果和是否被限制。
|
||||
func (s *GatewayService) ResolveChannelMappingAndRestrict(ctx context.Context, groupID *int64, model string) (ChannelMappingResult, bool) {
|
||||
var mapping ChannelMappingResult
|
||||
mapping.MappedModel = model
|
||||
if groupID == nil {
|
||||
return mapping, false
|
||||
}
|
||||
mapping = s.ResolveChannelMapping(ctx, *groupID, model)
|
||||
restricted := s.IsModelRestricted(ctx, *groupID, mapping.MappedModel)
|
||||
return mapping, restricted
|
||||
}
|
||||
|
||||
// ForwardCountTokens 转发 count_tokens 请求到上游 API
|
||||
// 特点:不记录使用量、仅支持非流式响应
|
||||
func (s *GatewayService) ForwardCountTokens(ctx context.Context, c *gin.Context, account *Account, parsed *ParsedRequest) error {
|
||||
|
||||
@@ -413,6 +413,34 @@ func (s *OpenAIGatewayService) IsModelRestricted(ctx context.Context, groupID in
|
||||
return s.channelService.IsModelRestricted(ctx, groupID, model)
|
||||
}
|
||||
|
||||
// ResolveChannelMappingAndRestrict 解析渠道映射并检查模型限制。
|
||||
// 返回映射结果和是否被限制。
|
||||
func (s *OpenAIGatewayService) ResolveChannelMappingAndRestrict(ctx context.Context, groupID *int64, model string) (ChannelMappingResult, bool) {
|
||||
var mapping ChannelMappingResult
|
||||
mapping.MappedModel = model
|
||||
if groupID == nil {
|
||||
return mapping, false
|
||||
}
|
||||
mapping = s.ResolveChannelMapping(ctx, *groupID, model)
|
||||
restricted := s.IsModelRestricted(ctx, *groupID, mapping.MappedModel)
|
||||
return mapping, restricted
|
||||
}
|
||||
|
||||
// ReplaceModelInBody 替换请求体中的 JSON model 字段(通用 gjson/sjson 实现)。
|
||||
func (s *OpenAIGatewayService) ReplaceModelInBody(body []byte, newModel string) []byte {
|
||||
if len(body) == 0 {
|
||||
return body
|
||||
}
|
||||
if current := gjson.GetBytes(body, "model"); current.Exists() && current.String() == newModel {
|
||||
return body
|
||||
}
|
||||
newBody, err := sjson.SetBytes(body, "model", newModel)
|
||||
if err != nil {
|
||||
return body
|
||||
}
|
||||
return newBody
|
||||
}
|
||||
|
||||
func (s *OpenAIGatewayService) getCodexSnapshotThrottle() *accountWriteThrottle {
|
||||
if s != nil && s.codexSnapshotThrottle != nil {
|
||||
return s.codexSnapshotThrottle
|
||||
|
||||
Reference in New Issue
Block a user