Skip to content

Commit 5f56187

Browse files
fix: improve json error detection and remove invalid rerank path header (#1591)
**Description** Makes the JSON detection in ResponseError translator more robust: if the upstream content-type contains application/json (e.g., application/json; charset=utf-8), it now passes the upstream error body through unchanged instead of wrapping it again. Removes invalid `:path` pseudo-header from error response translation for rerank to prevent Envoy stream aborts, yielding a 500 with an empty body. --------- Signed-off-by: ayush <[email protected]> Co-authored-by: Takeshi Yoneda <[email protected]>
1 parent 695b823 commit 5f56187

File tree

6 files changed

+13
-10
lines changed

6 files changed

+13
-10
lines changed

internal/translator/cohere_rerank_v2.go

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@ import (
1111
"io"
1212
"path"
1313
"strconv"
14+
"strings"
1415

1516
"github.com/tidwall/sjson"
1617

@@ -111,7 +112,7 @@ func (t *cohereToCohereTranslatorV2Rerank) ResponseBody(_ map[string]string, bod
111112
func (t *cohereToCohereTranslatorV2Rerank) ResponseError(respHeaders map[string]string, body io.Reader) (
112113
newHeaders []internalapi.Header, newBody []byte, err error,
113114
) {
114-
if v, ok := respHeaders[contentTypeHeaderName]; ok && v != jsonContentType {
115+
if v, ok := respHeaders[contentTypeHeaderName]; ok && !strings.Contains(v, jsonContentType) {
115116
buf, err := io.ReadAll(body)
116117
if err != nil {
117118
return nil, nil, fmt.Errorf("failed to read error body: %w", err)
@@ -125,10 +126,10 @@ func (t *cohereToCohereTranslatorV2Rerank) ResponseError(respHeaders map[string]
125126
if err != nil {
126127
return nil, nil, fmt.Errorf("failed to marshal error body: %w", err)
127128
}
128-
newHeaders = []internalapi.Header{
129-
{pathHeaderName, t.path},
130-
{contentTypeHeaderName, jsonContentType},
131-
}
129+
newHeaders = append(newHeaders,
130+
internalapi.Header{contentTypeHeaderName, jsonContentType},
131+
internalapi.Header{contentLengthHeaderName, strconv.Itoa(len(newBody))},
132+
)
132133
}
133134
return
134135
}

internal/translator/openai_awsbedrock.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -562,7 +562,7 @@ func (o *openAIToAWSBedrockTranslatorV1ChatCompletion) ResponseError(respHeaders
562562
) {
563563
statusCode := respHeaders[statusHeaderName]
564564
var openaiError openai.Error
565-
if v, ok := respHeaders[contentTypeHeaderName]; ok && v == jsonContentType {
565+
if v, ok := respHeaders[contentTypeHeaderName]; ok && strings.Contains(v, jsonContentType) {
566566
var bedrockError awsbedrock.BedrockException
567567
if err = json.NewDecoder(body).Decode(&bedrockError); err != nil {
568568
return nil, nil, fmt.Errorf("failed to unmarshal error body: %w", err)

internal/translator/openai_embeddings.go

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@ import (
1111
"io"
1212
"path"
1313
"strconv"
14+
"strings"
1415

1516
"github.com/tidwall/sjson"
1617

@@ -94,7 +95,7 @@ func (o *openAIToOpenAITranslatorV1Embedding) ResponseError(respHeaders map[stri
9495
newHeaders []internalapi.Header, newBody []byte, err error,
9596
) {
9697
statusCode := respHeaders[statusHeaderName]
97-
if v, ok := respHeaders[contentTypeHeaderName]; ok && v != jsonContentType {
98+
if v, ok := respHeaders[contentTypeHeaderName]; ok && !strings.Contains(v, jsonContentType) {
9899
var openaiError openai.Error
99100
buf, err := io.ReadAll(body)
100101
if err != nil {

internal/translator/openai_openai.go

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ import (
1313
"io"
1414
"path"
1515
"strconv"
16+
"strings"
1617

1718
"github.com/tidwall/sjson"
1819

@@ -82,7 +83,7 @@ func (o *openAIToOpenAITranslatorV1ChatCompletion) ResponseError(respHeaders map
8283
newHeaders []internalapi.Header, newBody []byte, err error,
8384
) {
8485
statusCode := respHeaders[statusHeaderName]
85-
if v, ok := respHeaders[contentTypeHeaderName]; ok && v != jsonContentType {
86+
if v, ok := respHeaders[contentTypeHeaderName]; ok && !strings.Contains(v, jsonContentType) {
8687
var openaiError openai.Error
8788
buf, err := io.ReadAll(body)
8889
if err != nil {

tests/extproc/vcr/chat_completions_test.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -67,7 +67,7 @@ func TestOpenAIChatCompletions(t *testing.T) {
6767
},
6868
{
6969
name: testopenai.CassetteChatUnknownModel,
70-
expectResponseBody: `{"type":"error","error":{"type":"OpenAIBackendError","code":"404","message":"{\n \"error\": {\n \"message\": \"The model ` + "`gpt-4.1-nano-wrong`" + ` does not exist or you do not have access to it.\",\n \"type\": \"invalid_request_error\",\n \"param\": null,\n \"code\": \"model_not_found\"\n }\n}\n"}}`,
70+
expectResponseBody: "{\n \"error\": {\n \"message\": \"The model `gpt-4.1-nano-wrong` does not exist or you do not have access to it.\",\n \"type\": \"invalid_request_error\",\n \"param\": null,\n \"code\": \"model_not_found\"\n }\n}\n",
7171
expectStatusCode: http.StatusNotFound,
7272
},
7373
{

tests/extproc/vcr/embeddings_test.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -47,7 +47,7 @@ func TestOpenAIEmbeddings(t *testing.T) {
4747
},
4848
{
4949
name: testopenai.CassetteEmbeddingsUnknownModel,
50-
expectResponseBody: `{"type":"error","error":{"type":"OpenAIBackendError","code":"404","message":"{\n \"error\": {\n \"message\": \"The model ` + "`text-embedding-4-ultra`" + ` does not exist or you do not have access to it.\",\n \"type\": \"invalid_request_error\",\n \"param\": null,\n \"code\": \"model_not_found\"\n }\n}\n"}}`,
50+
expectResponseBody: "{\n \"error\": {\n \"message\": \"The model `text-embedding-4-ultra` does not exist or you do not have access to it.\",\n \"type\": \"invalid_request_error\",\n \"param\": null,\n \"code\": \"model_not_found\"\n }\n}\n",
5151
expectStatusCode: http.StatusNotFound,
5252
},
5353
{

0 commit comments

Comments
 (0)