1. HTTP (Hypertext Transfer Protocol)

  1. HTTP Headers

  1. Range
    1. Usage in requests
      1. Writing requests (clients)
      2. Reading requests (servers)
    2. Overview table
    3. Syntax
      1. "other-content-range"
    4. History

Range

The "Range" header field requests only one or more subranges of the selected representation data, rather than the entire selected representation. It is only meaningful in a GET request. Requests that include a Range header are called "Range requests."

Range requests are analogous to a seek operation on the filesystem; they are typically issued when skipping to certain time in a video or audio file; or when resuming a download.

Usage in requests

Writing requests (clients)

Clients may issue Range requests for a variety of reasons. They may need to seek to a specific offset in a file, for example when streaming media, or accessing a large database file.

The Accept-Ranges response header can indicate if the server supports Range requests or not; this can be used to avoid making a Range request in cases where the client is uninterested in downloading the entire document if the server does not support Range requests, which is indicated with Accept-Ranges: none. Range requests are frequently supported even in its absence, and clients may still optimistically try a Range request (the header will be ignored if Range requests are not supported).

The Range header is only meaningful for GET. Servers may ignore the Range header, and are supposed to ignore it for methods besides GET.

A server has honored the Range header if it sends back a 206 (Partial Content) response. If the response is any other status code, then the request for a Range was ignored.

If the client asked for a single range, or if server is only willing to fill one of the ranges, the response will include a Content-Range response header that indicates the offset of the enclosed body from the entire representation.

If the client asked for multiple ranges, the server will send back a multipart/byteranges response. You must parse the Content-Range response header in each part, since the ordering of the parts is allowed to mismatch and recombine the requested order, or not include every requested part.

Servers will typically respond to most Range requests in the same order. However, servers that generate a response as a stream may reorder Range parts in sequential order, so they do not have to buffer an entire response in memory or on disk.

Reading requests (servers)

If the request is not GET, ignore the header.

If the request has an If-Range header, then evaluation of this header becomes conditional on the outcome of processing If-Range. If the condition evaluates false, then ignore this header and prepare a full response normally. See that page for more information.

Servers are not required to implement Range headers, especially for dynamic content where the entire response would have to be buffered in memory. In this case, simply ignore the header and continue processing normally.

If the request does not contain an If-Range header, or if the If-Range condition evaluates true, then the server may respond with a Partial Content response. See the HTTP Range Request specification for details.

Overview table

Name
Range
Description
Specifies a subset of the representation to return in the response, instead of the entire document.
Direction
Request
Specification
RFC 9110: HTTP Semantics §14.2. Range

Syntax

Range = byte-ranges-specifier / other-ranges-specifier
other-ranges-specifier = other-range-unit "=" other-range-set
other-range-set = 1*VCHAR

Both the lower and upper indexes are inclusive; so there is no way to specify a zero-length range.

"other-content-range"

The ABNF suggests that it is possible to use units besides bytes. This is intended for future support of systems that might not natively use bytes, or perhaps documents with fixed-size multibyte characters (e.g. UTF-32). Some people have pointed out it is feasible to use this with other invented bytes, for example to do pagination.

In all cases, clients must be able to reconstruct the exact same document, byte-for-byte. This makes it difficult to use for pagination, depending on the syntax.

For example in JSON, array items must be joined with a comma, but cannot end with a comma. A hypothetical Range request for the first item of a JSON array (e.g. Range: item 0-0) would have to include the array-opening bracket, and a trailing comma (if the next item does not include a leading comma); which is invalid JSON. Such a solution would only make sense with streaming JSON parser that doesn't need the entire document to produce useful results.

History

  1. 1999-06: RFC 2616 §14.35. Range
  2. 2014-06: RFC 7233 §3.1. Range
  3. 2022-06: RFC 9110 §14.2. Range