From 2b8cb628b6b7ffe7521446692516c77d41c9b18c Mon Sep 17 00:00:00 2001 From: Ritel-T Date: Sun, 30 Aug 2026 13:06:45 +0900 Subject: [PATCH] fix(openai): preserve tiers in messages chat fallback --- .../openai_gateway_messages_chat_fallback.go | 65 ++++++++++--------- ...nai_gateway_messages_chat_fallback_test.go | 4 +- 2 files changed, 37 insertions(+), 32 deletions(-) diff --git a/backend/internal/service/openai_gateway_messages_chat_fallback.go b/backend/internal/service/openai_gateway_messages_chat_fallback.go index 31dccb969b..9a9dfc611f 100644 --- a/backend/internal/service/openai_gateway_messages_chat_fallback.go +++ b/backend/internal/service/openai_gateway_messages_chat_fallback.go @@ -152,15 +152,16 @@ func (s *OpenAIGatewayService) bufferChatCompletionsAsAnthropic( c.JSON(http.StatusOK, anthropicResp) return &OpenAIForwardResult{ - RequestID: requestID, - Usage: usage, - Model: originalModel, - BillingModel: billingModel, - UpstreamModel: upstreamModel, - ReasoningEffort: reasoningEffort, - ServiceTier: resolvedOpenAIUpstreamServiceTier(c, serviceTier), - Stream: false, - Duration: time.Since(startTime), + RequestID: requestID, + Usage: usage, + Model: originalModel, + BillingModel: billingModel, + UpstreamModel: upstreamModel, + ReasoningEffort: reasoningEffort, + UpstreamResponseServiceTier: observedUpstreamResponseServiceTier(c), + ServiceTier: resolvedOpenAIUpstreamServiceTier(c, serviceTier), + Stream: false, + Duration: time.Since(startTime), }, nil } @@ -212,17 +213,18 @@ func (s *OpenAIGatewayService) streamChatCompletionsAsAnthropic( // masks the truncation, and surface the error to flag usage incomplete // (mirrors forwardResponsesViaRawChatCompletions). return &OpenAIForwardResult{ - RequestID: requestID, - Usage: usage, - Model: originalModel, - BillingModel: billingModel, - UpstreamModel: upstreamModel, - ReasoningEffort: reasoningEffort, - ServiceTier: resolvedOpenAIUpstreamServiceTier(c, serviceTier), - Stream: true, - Duration: time.Since(startTime), - FirstTokenMs: scan.FirstTokenMs, - ClientDisconnect: clientDisconnected, + RequestID: requestID, + Usage: usage, + Model: originalModel, + BillingModel: billingModel, + UpstreamModel: upstreamModel, + ReasoningEffort: reasoningEffort, + UpstreamResponseServiceTier: observedUpstreamResponseServiceTier(c), + ServiceTier: resolvedOpenAIUpstreamServiceTier(c, serviceTier), + Stream: true, + Duration: time.Since(startTime), + FirstTokenMs: scan.FirstTokenMs, + ClientDisconnect: clientDisconnected, }, fmt.Errorf("stream usage incomplete: %w", scan.Err) } @@ -247,16 +249,17 @@ func (s *OpenAIGatewayService) streamChatCompletionsAsAnthropic( } return &OpenAIForwardResult{ - RequestID: requestID, - Usage: usage, - Model: originalModel, - BillingModel: billingModel, - UpstreamModel: upstreamModel, - ReasoningEffort: reasoningEffort, - ServiceTier: resolvedOpenAIUpstreamServiceTier(c, serviceTier), - Stream: true, - Duration: time.Since(startTime), - FirstTokenMs: scan.FirstTokenMs, - ClientDisconnect: clientDisconnected, + RequestID: requestID, + Usage: usage, + Model: originalModel, + BillingModel: billingModel, + UpstreamModel: upstreamModel, + ReasoningEffort: reasoningEffort, + UpstreamResponseServiceTier: observedUpstreamResponseServiceTier(c), + ServiceTier: resolvedOpenAIUpstreamServiceTier(c, serviceTier), + Stream: true, + Duration: time.Since(startTime), + FirstTokenMs: scan.FirstTokenMs, + ClientDisconnect: clientDisconnected, }, nil } diff --git a/backend/internal/service/openai_gateway_messages_chat_fallback_test.go b/backend/internal/service/openai_gateway_messages_chat_fallback_test.go index dd5c1ed9c0..43c453376c 100644 --- a/backend/internal/service/openai_gateway_messages_chat_fallback_test.go +++ b/backend/internal/service/openai_gateway_messages_chat_fallback_test.go @@ -140,7 +140,7 @@ func TestForwardAsAnthropic_ForceChatCompletionsNonStreaming(t *testing.T) { StatusCode: http.StatusOK, Header: http.Header{"Content-Type": []string{"application/json"}, "x-request-id": []string{"rid_msg_chat_json"}}, Body: io.NopCloser(strings.NewReader( - `{"id":"chatcmpl_json","object":"chat.completion","model":"gpt-5.4","choices":[{"index":0,"message":{"role":"assistant","content":"ok"},"finish_reason":"stop"}],"usage":{"prompt_tokens":3,"completion_tokens":2,"total_tokens":5,"prompt_tokens_details":{"cached_tokens":1}}}`, + `{"id":"chatcmpl_json","object":"chat.completion","model":"gpt-5.4","service_tier":"priority","choices":[{"index":0,"message":{"role":"assistant","content":"ok"},"finish_reason":"stop"}],"usage":{"prompt_tokens":3,"completion_tokens":2,"total_tokens":5,"prompt_tokens_details":{"cached_tokens":1}}}`, )), }} svc := &OpenAIGatewayService{ @@ -162,6 +162,8 @@ func TestForwardAsAnthropic_ForceChatCompletionsNonStreaming(t *testing.T) { require.Equal(t, 3, result.Usage.InputTokens) require.Equal(t, 2, result.Usage.OutputTokens) require.Equal(t, 1, result.Usage.CacheReadInputTokens) + require.Nil(t, result.ServiceTier) + require.Equal(t, "priority", result.UpstreamResponseServiceTier) require.False(t, result.Stream) }