mirror of
https://github.com/denoland/deno.git
synced 2025-03-03 09:31:22 -05:00
fix(std/http): avoid directly modifying the headers object (#5024)
This commit is contained in:
parent
be65f6692f
commit
e57f0749e7
3 changed files with 23 additions and 25 deletions
|
@ -11,7 +11,6 @@ import { posix, extname } from "../path/mod.ts";
|
|||
import { listenAndServe, ServerRequest, Response } from "./server.ts";
|
||||
import { parse } from "../flags/mod.ts";
|
||||
import { assert } from "../testing/asserts.ts";
|
||||
import { setContentLength } from "./io.ts";
|
||||
|
||||
interface EntryInfo {
|
||||
mode: string;
|
||||
|
@ -173,7 +172,6 @@ async function serveDir(
|
|||
body: page,
|
||||
headers,
|
||||
};
|
||||
setContentLength(res);
|
||||
return res;
|
||||
}
|
||||
|
||||
|
|
|
@ -214,24 +214,6 @@ export async function writeTrailers(
|
|||
await writer.flush();
|
||||
}
|
||||
|
||||
export function setContentLength(r: Response): void {
|
||||
if (!r.headers) {
|
||||
r.headers = new Headers();
|
||||
}
|
||||
|
||||
if (r.body) {
|
||||
if (!r.headers.has("content-length")) {
|
||||
// typeof r.body === "string" handled in writeResponse.
|
||||
if (r.body instanceof Uint8Array) {
|
||||
const bodyLength = r.body.byteLength;
|
||||
r.headers.set("content-length", bodyLength.toString());
|
||||
} else {
|
||||
r.headers.set("transfer-encoding", "chunked");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
export async function writeResponse(
|
||||
w: Deno.Writer,
|
||||
r: Response
|
||||
|
@ -253,14 +235,21 @@ export async function writeResponse(
|
|||
|
||||
let out = `HTTP/${protoMajor}.${protoMinor} ${statusCode} ${statusText}\r\n`;
|
||||
|
||||
setContentLength(r);
|
||||
assert(r.headers != null);
|
||||
const headers = r.headers;
|
||||
const headers = r.headers ?? new Headers();
|
||||
|
||||
if (r.body && !headers.get("content-length")) {
|
||||
if (r.body instanceof Uint8Array) {
|
||||
out += `content-length: ${r.body.byteLength}\r\n`;
|
||||
} else if (!headers.get("transfer-encoding")) {
|
||||
out += "transfer-encoding: chunked\r\n";
|
||||
}
|
||||
}
|
||||
|
||||
for (const [key, value] of headers) {
|
||||
out += `${key}: ${value}\r\n`;
|
||||
}
|
||||
out += "\r\n";
|
||||
|
||||
out += `\r\n`;
|
||||
|
||||
const header = encoder.encode(out);
|
||||
const n = await writer.write(header);
|
||||
|
|
|
@ -19,7 +19,7 @@ import { chunkedBodyReader } from "./io.ts";
|
|||
import { ServerRequest, Response } from "./server.ts";
|
||||
import { StringReader } from "../io/readers.ts";
|
||||
import { mockConn } from "./mock.ts";
|
||||
const { Buffer, test } = Deno;
|
||||
const { Buffer, test, readAll } = Deno;
|
||||
|
||||
test("bodyReader", async () => {
|
||||
const text = "Hello, Deno";
|
||||
|
@ -357,6 +357,17 @@ test("writeResponse with trailer", async () => {
|
|||
assertEquals(ret, exp);
|
||||
});
|
||||
|
||||
test("writeResponseShouldNotModifyOriginHeaders", async () => {
|
||||
const headers = new Headers();
|
||||
const buf = new Deno.Buffer();
|
||||
|
||||
await writeResponse(buf, { body: "foo", headers });
|
||||
assert(decode(await readAll(buf)).includes("content-length: 3"));
|
||||
|
||||
await writeResponse(buf, { body: "hello", headers });
|
||||
assert(decode(await readAll(buf)).includes("content-length: 5"));
|
||||
});
|
||||
|
||||
test("readRequestError", async function (): Promise<void> {
|
||||
const input = `GET / HTTP/1.1
|
||||
malformedHeader
|
||||
|
|
Loading…
Add table
Reference in a new issue