diff --git a/CHANGES.rst b/CHANGES.rst index 75dbc2439..f0b0ce63f 100644 --- a/CHANGES.rst +++ b/CHANGES.rst @@ -11,6 +11,9 @@ Unreleased ```` and ````. :issue:`2390` - Fix ability to set some ``cache_control`` attributes to ``False``. :issue:`2379` +- Disable ``keep-alive`` connections in the development server, which + are not supported sufficiently by Python's ``http.server``. + :issue:`2397` Version 2.1.1 diff --git a/src/werkzeug/serving.py b/src/werkzeug/serving.py index 1e5088089..712307606 100644 --- a/src/werkzeug/serving.py +++ b/src/werkzeug/serving.py @@ -271,18 +271,23 @@ def write(data: bytes) -> None: # is the more conservative behavior and matches other # parts of the code. # https://httpwg.org/specs/rfc7230.html#rfc.section.3.3.1 - if not ( - "content-length" in header_keys - or environ["REQUEST_METHOD"] == "HEAD" - or (100 <= code < 200) - or code in {204, 304} + if ( + not ( + "content-length" in header_keys + or environ["REQUEST_METHOD"] == "HEAD" + or (100 <= code < 200) + or code in {204, 304} + ) + and self.protocol_version >= "HTTP/1.1" ): - if self.protocol_version >= "HTTP/1.1": - chunk_response = True - self.send_header("Transfer-Encoding", "chunked") - else: - self.send_header("Connection", "close") - + chunk_response = True + self.send_header("Transfer-Encoding", "chunked") + + # Always close the connection. This disables HTTP/1.1 + # keep-alive connections. They aren't handled well by + # Python's http.server because it doesn't know how to + # drain the stream before the next request line. + self.send_header("Connection", "close") self.end_headers() assert isinstance(data, bytes), "applications must write bytes"