httphttp-headerscontent-negotiationhttp-range

HTTP Content Negotiation and the Range header


How does the Range header work with Content Negotiation? Let me explain, but first let's all agree to the following: HTTP is a stateless protocol.

When an HTTP Server is able to send multiple representation of a single resource, content negotiation is used to figure which representation to send: The client might indicate its preference (i.e. English and GIFs) then the server would comply or -- in a scenario where it can't -- the server would choose, through some heuristic evaluation, which representation to send the client.

So far so good... but what happens when you throw Range into the mix?

Imagine the following scenario:

John is in an airport in Paris and his browser sends an HTTP request. For some reason, his browser doesn't indicates any preferences in content type, language nor compression.

GET /uri HTTP/1.1
Host: example.com

Since it has very little to go by, the server, through some heuristics, decides to send the french representation of the URI (the IP is recognized as being from France.)

200 Okay
Accept-Ranges: bytes
Content: text/html
Content-Language: fr
....data...

Mid-transfer, John stops the download to catch his flight. John resumes his download once he arrives in New York.

 GET /uri HTTP/1.1
 Host: example.com
 Range: 2000-3000

Again, with little information on the client's preference, the server this time decides to send the english representation of the URI (the IP is recognized as being from New York.)

By this point, the file is corrupt since part of it is in French and the other part is in English.

Conjecture:

Notes:


TL;DR

GET /uri HTTP/1.1
Host: example.com
Accept: text/html; q=1.0, text/plain; q=0.8, */*; q=0.1
Accept-Language: en; q=1.0, */*; q=0.1
Range: 100-200

In the above, the range applies to which representation of the requested resource?!


Solution

  • Short answer: don't use Range request without If-Match: etag request header field.