Friends of OpenJDK Today

The Vary HTTP Header

May 15, 2024

Author(s)

  • Avatar photo
    Nicolas Frankel

    Nicolas is a developer advocate with 15+ years experience consulting for many different customers, in a wide range of contexts (such as telecoms, banking, insurances, large retail and public sector). ... Learn more

I try to constantly to deepen my knowledge of HTTP and REST. Recently, I stumbled upon the list of all registered HTTP Headers. This post is dedicated to the Vary HTTP Header.

The problem

Two years ago, I wrote about web resource caching server-side. The idea is to set up a component between the client and the upstream to cache previously computed results to avoid overloading the latter. Depending on your infrastructure and requirements, this component can be a reverse proxy or an API Gateway. HTTP offers the Cache-Control header to customize the different aspects of caching, e.g., the time the server holds the resource in cache before it considers it stale. I used plugin configuration in the above post, but you can also delegate to Cache-Control.

Now, imagine the following scenario. You request a resource, _e.g., GET /book/1 and get the result:

HTTP/1.1 200 OK
Content-Type: application/json

{
  "id": 1,
  "title": "Notre-Dame de Paris"
}

The request succeeds; the result is cached. Now, I request the same resource, but because my code works around XML, I set the Accept header to application/xml. Unfortunately, the server returns the cached JSON resource, which differs from what I asked and probably utterly breaks my code.

The problem is that the cache key has a single dimension, the URL, by default.

The solution

We need a configurable multi-dimension cache key. As you can probably guess by now, that's the role of the Vary header: it explicitly lists all dimensions of the cache key. In the example above, the upstream would communicate the additional cache key with the following:

HTTP/1.1 200 OK
Content-Type: application/json
Content-Language: en
Vary: Accept


{
  "id": 1,
  "title": "Notre-Dame de Paris"
}

Instead of a single cache entry per URL, we now have one per MIME type/URL combination. Note that it's up to the caching component to use this information.

Another common request header is Accept-Encoding, which usually specifies which compression algorithms the client can accept. Encoding is another possible cache key. The specification allows specifying multiple cache keys:

HTTP/1.1 200 OK
Content-Type: application/json
Content-Language: en
Vary: Accept, Accept-Encoding


{
  "id": 1,
  "title": "Notre-Dame de Paris"
}

Conclusion

I've described the Varyresponse header in this post. As soon as you configure caching, you must consider possible cache keys and use the Vary header accordingly.

To go further:


Originally published at A Java Geek on May 5th, 2024

Topics:

Related Articles

View All

Author(s)

  • Avatar photo
    Nicolas Frankel

    Nicolas is a developer advocate with 15+ years experience consulting for many different customers, in a wide range of contexts (such as telecoms, banking, insurances, large retail and public sector). ... Learn more

Comments (0)

Your email address will not be published. Required fields are marked *

Highlight your code snippets using [code lang="language name"] shortcode. Just insert your code between opening and closing tag: [code lang="java"] code [/code]. Or specify another language.

Save my name, email, and website in this browser for the next time I comment.

Subscribe to foojay updates:

https://foojay.io/feed/
Copied to the clipboard