* WGs marked with an * asterisk has had at least one new draft made available during the last 5 days

Ticket #37 (closed design: fixed)

Opened 7 years ago

Last modified 5 years ago

Vary and non-existant headers

Reported by: mnot@pobox.com Owned by:
Priority: normal Milestone: unassigned
Component: p6-cache Severity: Active WG Document
Keywords: Cc:
Origin: http://lists.w3.org/Archives/Public/ietf-http-wg/2004JanMar/0021.html

Description

When an origin server selects the response by looking at a request header, and the header does not exist, is it correct for the server to add the name of that header to Vary?

For example, suppose a server's logic is like this pseudo-code:

reponse_headers (Vary) = "Accept-Language"

IF request_headers (Accept-Language) contains "ja" THEN
serve the japanese page
ELSE 
serve the english page
ENDIF

What is the correct HTTP response when the request doesn't have an Accept-Language header?

I would guess that the correct response is to "include Vary: Accept-Language", but that begs the next question:

  • How should a cache treat missing requests headers which are mentioned in Vary, when deciding if a stored entity matches a request?

    • a. If the stored entity was requested _without_ the header mentioned in Vary, and the new request is also _without_ the header, does the stored entity match? (This would come from scenario 1 above).
    • b. If the stored entity was requested _without_ the header mentioned in Vary, and the new request is _with_ the header, does the stored entity match?
    • c. If the stored entity was requested _with_ the header mentioned in Vary, and the new request is _without_ the header, does the stored entity match?

    I would imagine that in case a, the entity matches, and in cases b and c, the entity doesn't match and must be revalidated.

    But the language of RFC 2616 is a unclear:

    When the cache receives a subsequent request whose Request-URI specifies one or more cache entries including a Vary header field, the cache MUST NOT use such a cache entry to construct a response to the new request unless all of the selecting request-headers present in the new request match the corresponding stored request-headers in the original request.

    Can the selecting request-headers "match" if they are absent? What about case a?

    The selecting request-headers from two requests are defined to match if and only if the selecting request-headers in the first request can be transformed to the selecting request-headers in the second request by adding or removing linear white space (LWS) at places where this is allowed by the corresponding BNF, and/or combining multiple message-header fields with the same field name following the rules about message headers in section 4.2.

    Is this supposed to mean that an absent header is equivalent to an empty header, or that an absent header is semantically a distinct value from an empty header, or that an absent header is not considered at all in the decision, or that an absent header cannot be matched even with an absent header in the original request for the cached entity?

  • Does this mean that server code which inspects a header value, and finds the header missing, should look like this instead?

    IF exists request_headers (Accept-Language) THEN
    reponse_headers (Vary) = "Accept-Language"
    ELSE
    response_headers (Vary) = "*"
    ENDIF
    
    IF request_headers (Accept-Language) contains "ja" THEN
    serve the japanese page
    ELSE 
    serve the english page
    ENDIF

    The conservative thing to do is to disable cacheing when an examined request-header is absent, but that seems excessively pessimistic.

  • Change History

    comment:1 Changed 7 years ago by mnot@pobox.com

    comment:2 Changed 7 years ago by mnot@pobox.com

    • Component set to payload
    • Milestone set to unassigned

    comment:3 Changed 7 years ago by mnot@pobox.com

    • version set to 00-draft

    comment:4 Changed 6 years ago by mnot@pobox.com

    • Component changed from p3-payload to p6-cache

    comment:5 Changed 5 years ago by julian.reschke@gmx.de

    This may be resolved with change [607].

    comment:6 Changed 5 years ago by mnot@pobox.com

    • Priority set to normal
    • Status changed from new to closed
    • Resolution set to fixed
    • Severity set to Active WG Document
    Note: See TracTickets for help on using tickets.