I'm new to Varnish and to reverse proxies in general. I'm testing Varnish in an application that works like a blog where I have a page with an "updated_at" that changes once the page is updated. As a consequence, I decided that my cache strategy should be based on the last-modified header. The reason for that is the user wants to see the change immediately once the page is modified in the backoffice.
In addition to that, I understood that I could add a s-maxage with must-revalidate to cache-control so if the last-modified didn't change Varnish would not even try to make a new request.
I also added an expire for the browser so there will be a client cache. As a result, the browser will not even ask varnish to do a request to Apache again.
However, I noticed that the cache-control s-maxage has priority over the last-modified even with must-revalidate. Moreover, even if I don't add a cache-control, 'last-modified' doesn't work. Varnish use its default ttl and nothing happens. What am I doing wrong?
I'm using Symfony and these are the headers:
$response = new Response();
$response->setPublic();
// expiration model for the browser cache (EXPIRE)
// the browser will only make a new request to Varnish again after ten minutes (600 seconds)
$date = new \DateTime();
$date->modify('+600 seconds');
$response->setExpires($date);
// expiration model for Varnish (CACHE-CONTROL)
// Varnish will only make a new request to Apache again after one hour (3600 seconds)
// The must-revalidate tells Varnish to do this request before serving the files after one hour (it's already de default behaviour)
// cache-control has priority over expire
//$response->setSharedMaxAge(3600);
$response->headers->addCacheControlDirective('must-revalidate', true);
// validation model for varnish (LAST-MODIFIED)
// Varnish will only make a new request to Apache again if the updated_at of the page changed even if the expiration time is ended
$response->setLastModified($page->getUpdatedAt());
// if the response didn't change, stop here
if ($response->isNotModified($request)) {
return $response;
}
Here are my headers the first time when I have a MISS and the second time when I have a HIT. Then, it doesn't matter if the last-modified changes the headers are always the same as this second one. (My browser cacher is disabled so I have 200 instead of 304)