node icon indicating copy to clipboard operation
node copied to clipboard

The `http.Server` adds a `Transfer-Encoding: chunked` header when the response has no body

Open ijisol opened this issue 3 months ago • 5 comments

Version

22 (but maybe every version)

Platform

Microsoft Windows NT 10.0.22631.0 x64 (but maybe not platform-specific)

Subsystem

node:http

What steps will reproduce the bug?

The Transfer-Encoding: chunked header is always added when there is no response body. There seems to be no way to remove it.

However, since this header is not added when the request method is HEAD, the response headers are different when the request method is GET and HEAD, which is against the HTTP specification.

Example server code:

import { createServer } from 'node:http';
import { finished } from 'node:stream/promises';

createServer(function (req, res) {
  finished(req.resume()).then(() => {
    res.writeHead(200, { 'Cache-Control': 'no-store' });
    res.end(); // No body
  }).catch((err) => {
    this.emit('error', err);
  })
}).listen(8000, '0.0.0.0');

GET:

$ curl -i http://localhost:8000/
HTTP/1.1 200 OK
Cache-Control: no-store
Date: Sat, 23 Nov 2024 09:01:22 GMT
Connection: keep-alive
Keep-Alive: timeout=5
Transfer-Encoding: chunked

HEAD:

$ curl --head -i http://localhost:8000/
HTTP/1.1 200 OK
Cache-Control: no-store
Date: Sat, 23 Nov 2024 09:01:17 GMT
Connection: keep-alive
Keep-Alive: timeout=5

A monkey patching solution I found is to always add the Content-Length: 0 header.

However, I'm not sure if this is really the intended behavior. I think it should be possible to send a response without adding a Content-Length: 0 header when there is no body.

Or, if it's intended behavior, it should be documented.

How often does it reproduce? Is there a required condition?

Always.

What is the expected behavior? Why is that the expected behavior?

I would guess that the generally expected behavior is that the Transfer-Encoding: chunked header is NOT added when there is no response body.

What do you see instead?

.

Additional information

Perhaps this issue https://github.com/denoland/deno/issues/20063 may be related.

ijisol avatar Nov 23 '24 09:11 ijisol