Transfer-Encoding
Request & response Connection

Overview

Transfer-Encoding is a hop-by-hop header specifying the encoding applied to safely transfer the message body over the network. Its main value, `chunked`, splits the body into size-prefixed pieces and enables streaming when the total size isn't known in advance.

Details

`chunked` breaks the body into chunks, each prefixed with a hexadecimal size, ending with a zero-size chunk. This lets a server start streaming before the whole response is ready and express message boundaries without Content-Length for dynamic content whose size can't be precomputed. So when you use chunked you don't use Content-Length (they are mutually exclusive).

This is fundamentally different from the end-to-end Content-Encoding. Transfer-Encoding is merely the transfer format between two adjacent nodes, so a proxy may reassemble chunks and forward with a different framing to the next hop. Consequently caches and ETags are unaffected by Transfer-Encoding.

In HTTP/1.1, when Content-Length and Transfer-Encoding both appear in one message, servers and proxies may disagree on which delimits the body — the classic HTTP request smuggling vulnerability. HTTP/2 and HTTP/3 use a different framing and forbid chunked Transfer-Encoding entirely.

Syntax

Transfer-Encoding: <coding>[, <coding>]* (chunked | gzip | ...)

e.g. Transfer-Encoding: chunked

Directives / values

chunkedSends the body as size-prefixed chunks; for streaming or unknown length. The final chunk has size 0.
gzipgzip-compress the body for transfer (hop-by-hop).
compressLegacy LZW compression (rarely used).

Notes

Related headers

Related status codes

Specification