fix(agents): use fatal UTF-8 decoding for provider JSON responses (#108849)

* fix(agents): use fatal UTF-8 decoding in provider response readers

* fix(agents): use fatal UTF-8 decoding only for JSON responses, preserve compatibility for text
This commit is contained in:
zengLingbiao
2026-07-18 16:08:30 -07:00
committed by GitHub
parent 66aa22e4e8
commit b1c49677ec
2 changed files with 14 additions and 1 deletions
+13
View File
@@ -360,6 +360,19 @@ describe("provider error utils", () => {
expect(streamed.getReadCount()).toBeLessThan(20);
});
it("rejects provider JSON responses with invalid UTF-8 bytes instead of silently replacing them", async () => {
const invalidUtf8Bytes = new Uint8Array([0x7b, 0x22, 0x6b, 0x65, 0x79, 0x22, 0x3a, 0xff, 0x7d]);
const response = new Response(invalidUtf8Bytes.buffer, {
status: 200,
headers: { "Content-Type": "application/json" },
});
await expect(readProviderJsonResponse(response, "Provider JSON failed")).rejects.toMatchObject({
message: "Provider JSON failed: malformed JSON response",
cause: expect.any(TypeError) as unknown,
});
});
it("caps successful text responses instead of buffering oversized bodies", async () => {
const streamed = createStreamingTextResponse({
chunkCount: 20,
+1 -1
View File
@@ -341,7 +341,7 @@ export async function readProviderJsonResponse<T>(
new Error(`${label}: JSON response exceeds ${maxBytesLocal} bytes`),
});
try {
return JSON.parse(new TextDecoder().decode(bytes)) as T;
return JSON.parse(new TextDecoder("utf-8", { fatal: true }).decode(bytes)) as T;
} catch (cause) {
throw new Error(`${label}: malformed JSON response`, { cause });
}