1

I have a server which returns a different response based on the Accept header e.g. if Accept header includes "image/webp", a webp image is served, otherwise a jpg is served.

We run Varnish at server-level and it does this correctly, as per example below:

Request (with image/webp in Accept header):

curl -s -D - -o /dev/null "https://REDACTED/media/tokinoha_bowl-4.jpg?sh=2&fmt=webp,jpg" -H "Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*/*;q=0.8"

Response (webp image served):

HTTP/2 200 
date: Wed, 06 Feb 2019 08:25:05 GMT
content-type: image/webp
access-control-allow-origin: *
cache-control: public, s-maxage=31536000, max-age=31536000
x-frame-options: SAMEORIGIN
x-xss-protection: 1; mode=block
x-content-type-options: nosniff
strict-transport-security: max-age=31536000; includeSubDomains
vary: Accept-Encoding, Accept-Encoding,Origin
referrer-policy: strict-origin-when-cross-origin
accept-ranges: bytes
content-length: 60028

Request (no webp in Accept header, jpg served):

curl -s -D - -o /dev/null "https://REDACTED/media/tokinoha_bowl-4.jpg?sh=2&fmt=webp,jpg" -H "Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/apng,*/*;q=0.8"

Response:

HTTP/2 200 
date: Wed, 06 Feb 2019 08:25:18 GMT
content-type: image/jpeg
access-control-allow-origin: *
cache-control: public, s-maxage=31536000, max-age=31536000
x-frame-options: SAMEORIGIN
x-xss-protection: 1; mode=block
x-content-type-options: nosniff
strict-transport-security: max-age=31536000; includeSubDomains
vary: Accept-Encoding, Accept-Encoding,Origin
referrer-policy: strict-origin-when-cross-origin
accept-ranges: bytes
content-length: 166991

We have the below options in the Rules Engine set up, however whichever content-type is cached first is served on all subsequent requests irrespective of request header.

Rules Engine settings

enter image description here

Does anyone know of a way to achieve this?

Thanks in advance!

Alain Merigot
  • 10,667
  • 3
  • 18
  • 31
Tristan
  • 21
  • 3

1 Answers1

2

We had the same problem with Verizon/Edgecast: One URL delivered two different image types (JPEG and WebP) depending on Accept header. The origin (imgix) sent correctly Vary: Accept, but Edgecast ignored that and cached what it get and so browsers without WebP support got sometimes the wrong format.

We solved it with a rule in Edgecast: WebP rule

The query parameter auto is always part of the URL and can therefore always be removed from the cache key. With the second query parameter varyWebP we recognize the URLs definitely and prevent a collision with URLs without query parameter auto.

In this case the URL

https://[HOST]/[PATH]?a=1&b=2&c=3&auto=compress,format

creates the same cache key as:

https://[HOST]/[PATH]?a=1&b=2&c=3

That's why the query parameter varyWebP protects us.

Shahbaz A.
  • 4,047
  • 4
  • 34
  • 55