HTTP Library Handles Missing Content Length Incorrectly
Zig Version
0.11.0
Steps to Reproduce and Observed Behavior
Create and send an http request to a server which doesn't always send a content-length (this is technically permissible by the spec, it's only a SHOULD https://datatracker.ietf.org/doc/html/rfc2616#section-4.4, https://datatracker.ietf.org/doc/html/rfc2616#section-14.13 and a server can legally just close the connection.) thttpd is one such server when you get any error. The following code will reproduce it with a thttpd's website:
const std = @import("std");
pub fn main() !void {
var gpa = std.heap.GeneralPurposeAllocator(.{}){};
var alloc = gpa.allocator();
var client = std.http.Client{ .allocator = alloc };
var uri = try std.Uri.parse("http://acme.com/fakepage");
var request = try client.request(.GET, uri, std.http.Headers{ .allocator = alloc }, .{});
try request.start();
try request.finish();
try request.wait();
var resp_body = try request.reader().readAllAlloc(alloc, 1 << 20);
std.debug.print("{s}\n", .{resp_body});
}
Zig things the body is empty, but curl/netcat/etc will confirm that there is one.
Expected Behavior
The full response body is given to the user (reading until the server has closed the connection.)
I fully understand if this is closed as wontfix since it's an obscure case which is only technically in-spec, but I'm hoping that the page existing will at least prevent someone else from spending a couple hours debugging what the heck is going on and why their body is getting eaten.
FWIW, the latest RFC 9112 for HTTP/1.1 specifies that [1], in the case of a response message without Content-Length and Transfer-Encoding, the message body length is determined by the number of octets received prior to the server closing the connection, except when the message is a 2xx response to a CONNECT request, or when the status code is 1xx, 204, or 304.
[1] https://www.rfc-editor.org/rfc/rfc9112.html#name-message-body-length