Developer
Developer

Reputation: 2895

varnish not cacheable symfony

i test on page http://www.okw-rutex.pl/ this site include js file varnish cache for file - http://miejsce.eu/shared,4980,101.js

here is headers for this file

Request URL:http://miejsce.eu/shared,4980,101.js
Request Method:GET
Status Code:200 OK
Remote Address:188.165.215.9:80
Response Headers
view source
Accept-Ranges:bytes
Age:0
Cache-Control:max-age=86400, public
Connection:keep-alive
Content-Encoding:gzip
Content-Length:3673
Content-Type:text/html; charset=UTF-8
Date:Thu, 14 Jan 2016 13:35:56 GMT
Expires:Fri, 15 Jan 2016 13:35:57 GMT
Server:Apache/2.4.7 (Ubuntu)
Vary:Accept-Encoding
X-Cache:MISS
X-Cacheable:NO:Not Cacheable
X-Powered-By:PHP/5.5.9-1ubuntu4.14
XH:0
Request Headers
view source
Accept:*/*
Accept-Encoding:gzip, deflate, sdch
Accept-Language:pl-PL,pl;q=0.8,en-US;q=0.6,en;q=0.4,pt;q=0.2,de;q=0.2,sk;q=0.2
Cache-Control:max-age=0
Connection:keep-alive
Host:miejsce.eu
Referer:http://www.okw-rutex.pl/
User-Agent:Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Ubuntu Chromium/47.0.2526.106 Chrome/47.0.2526.106 Safari/537.36

in symfony controller i use cache annotations -

@Cache(expires="1 day",public=true, maxage="86400")

in varnish config part return not cacheable is

} elsif (beresp.ttl <= 0s) {
        # Varnish determined the object was not cacheable
        set beresp.http.X-Cacheable = "NO:Not Cacheable";

how i can turn varnish cache on ?

if i refresh page with F5 (without sending Cache-Control:max-age=0) still have

X-Cache:MISS
X-Cacheable:NO:Not Cacheable

here if full varnish config

more /etc/varnish/default.vcl
#
# This is an example VCL file for Varnish.
#
# It does not do anything by default, delegating control to the
# builtin VCL. The builtin VCL is called when there is no explicit
# return statement.
#
# See the VCL chapters in the Users Guide at https://www.varnish-cache.org/docs/
# and https://www.varnish-cache.org/trac/wiki/VCLExamples for more examples.

# Marker to tell the VCL compiler that this VCL has been adapted to the
# new 4.0 format.
vcl 4.0;

# Default backend definition. Set this to point to your content server.
backend default {
    .host = "127.0.0.1";
    .port = "8080";
}

sub vcl_recv {

 # Only cache GET or HEAD requests. This makes sure the POST requests are always passed.
#  if (req.method != "GET" && req.method != "HEAD") {
#    return (pass);
#  }

 # Strip hash, server doesn't need it.
  if (req.url ~ "\#") {
    set req.url = regsub(req.url, "\#.*$", "");
  }


# removes all cookies named _ and google analistics, tracking, utma, utmb...)
set req.http.Cookie = regsuball(req.http.Cookie, "(^|(?<=; )) *_.=[^;]+;? *", "\1");
set req.http.Cookie = regsuball(req.http.Cookie, "utmctr=[^;]+(; )?", "");
  set req.http.Cookie = regsuball(req.http.Cookie, "utmcmd.=[^;]+(; )?", "");
  set req.http.Cookie = regsuball(req.http.Cookie, "utmccn.=[^;]+(; )?", "");

  # Are there cookies left with only spaces or that are empty?
  if (req.http.cookie ~ "^\s*$") {
    unset req.http.cookie;
  }

if (req.http.Cache-Control ~ "(?i)no-cache") {
 if (! (req.http.Via || req.http.User-Agent ~ "(?i)bot" || req.http.X-Purge)) {
# return(purge); # Couple this with restart in vcl_purge and X-Purge header to avoid loops
unset req.http.Cache-Control;
}
}


 # Large static files are delivered directly to the end-user without
  # waiting for Varnish to fully read the file first. Varnish 4 fully supports Streaming, so set do_stream in vcl_backend_response()
  if (req.url ~ "^[^?]*\.(mp[34]|rar|tar|tgz|gz|wav|zip|bz2|xz|7z|avi|mov|ogm|mpe?g|mk[av]|webm)(\?.*)?$") {
    unset req.http.Cookie;
    return (hash);
  }

# Remove all cookies for static files

if (req.url ~ "^[^?]*\.(bmp|mov|mp4|webm|avi|bz2|css|doc|eot|flv|gif|gz|ico|jpeg|jpg|js|less|pdf|png|rtf|swf|txt|woff|xml)(\?.*)?$") {
    unset req.http.Cookie;
    return (hash);
  }


    # Happens before we check if we have this in cache already.
    #
    # Typically you clean up the request here, removing cookies you don't need,
    # rewriting the request, etc.

 set req.http.Surrogate-Capability = "abc=ESI/1.0";

if (req.http.X-Forwarded-Proto == "https" ) {
        set req.http.X-Forwarded-Port = "443";
    } else {
        set req.http.X-Forwarded-Port = "80";
    }

}

sub vcl_backend_response {
    # Happens after we have read the response headers from the backend.
    #
    # Here you clean the response headers, removing silly Set-Cookie headers
    # and other mistakes your backend does.

if (beresp.http.Surrogate-Control ~ "ESI/1.0") {
        unset beresp.http.Surrogate-Control;
        set beresp.do_esi = true;
    }

# Enable cache for all static files
if (bereq.url ~ "^[^?]*\.(bmp|bz2|css|doc|eot|flv|gif|gz|ico|jpeg|jpg|js|less|mp[34]|pdf|png|rar|rtf|swf|tar|tgz|txt|wav|woff|xml|zip|webm)(\?.*)?$") {
    unset beresp.http.set-cookie;
  }

# Large static files are delivered directly to the end-user without
if (bereq.url ~ "^[^?]*\.(mp[34]|rar|tar|tgz|gz|wav|zip|bz2|xz|7z|avi|mov|ogm|mpe?g|mk[av]|webm)(\?.*)?$") {
    unset beresp.http.set-cookie;
    set beresp.do_stream = true; # Check memory usage it'll grow in fetch_chunksize blocks (128k by default) if the backend doesn't send a Content-Length header, s
o only enable it for big objects
    set beresp.do_gzip = false; # Don't try to compress it for storage
  }

if (bereq.http.Cookie ~ "(UserID|_session)") {
        set beresp.http.X-Cacheable = "NO:Got Session";
        set beresp.uncacheable = true;
        return (deliver);

} elsif (beresp.ttl <= 0s) {
        # Varnish determined the object was not cacheable
        set beresp.http.X-Cacheable = "NO:Not Cacheable";

} elsif (beresp.http.set-cookie) {
        # You don't wish to cache content for logged in users
        set beresp.http.X-Cacheable = "NO:Set-Cookie";
        set beresp.uncacheable = true; return (deliver);
        return (deliver);

} elsif (beresp.http.Cache-Control ~ "private") {
        # You are respecting the Cache-Control=private header from the backend
        set beresp.http.X-Cacheable = "NO:Cache-Control=private";
        set beresp.uncacheable = true;

} else {
        # Varnish determined the object was cacheable
        set beresp.http.X-Cacheable = "YES";
    }
        return (deliver);
}

sub vcl_deliver {
    # Happens when we have all the pieces we need, and are about to send the
    # response to the client.
    #
    # You can do accounting or modifying the final object here.

if (obj.hits > 0) { # Add debug header to see if it's a HIT/MISS and the number of hits, disable when not needed
    set resp.http.X-Cache = "HIT";
  } else {
    set resp.http.X-Cache = "MISS";
  }

set resp.http.XH = obj.hits;

unset resp.http.X-Varnish;
unset resp.http.Via;

}

i change varnish config like here

#
# This is an example VCL file for Varnish.
#
# It does not do anything by default, delegating control to the
# builtin VCL. The builtin VCL is called when there is no explicit
# return statement.
#
# See the VCL chapters in the Users Guide at https://www.varnish-cache.org/docs/
# and https://www.varnish-cache.org/trac/wiki/VCLExamples for more examples.

# Marker to tell the VCL compiler that this VCL has been adapted to the
# new 4.0 format.
vcl 4.0;

# Default backend definition. Set this to point to your content server.
backend default {
    .host = "127.0.0.1";
    .port = "8080";
}

sub vcl_recv {

 # Only cache GET or HEAD requests. This makes sure the POST requests are always passed.
#  if (req.method != "GET" && req.method != "HEAD") {
#    return (pass);
#  }

 # Strip hash, server doesn't need it.
  if (req.url ~ "\#") {
    set req.url = regsub(req.url, "\#.*$", "");
  }


# removes all cookies named _ and google analistics, tracking, utma, utmb...)
set req.http.Cookie = regsuball(req.http.Cookie, "(^|(?<=; )) *_.=[^;]+;? *", "\1");
set req.http.Cookie = regsuball(req.http.Cookie, "utmctr=[^;]+(; )?", "");
  set req.http.Cookie = regsuball(req.http.Cookie, "utmcmd.=[^;]+(; )?", "");
  set req.http.Cookie = regsuball(req.http.Cookie, "utmccn.=[^;]+(; )?", "");

  # Are there cookies left with only spaces or that are empty?
  if (req.http.cookie ~ "^\s*$") {
    unset req.http.cookie;
  }

if (req.http.Cache-Control ~ "(?i)no-cache") {
 if (! (req.http.Via || req.http.User-Agent ~ "(?i)bot" || req.http.X-Purge)) {
# return(purge); # Couple this with restart in vcl_purge and X-Purge header to avoid loops
unset req.http.Cache-Control;
}
}


 # Large static files are delivered directly to the end-user without
  # waiting for Varnish to fully read the file first. Varnish 4 fully supports Streaming, so set do_stream in vcl_backend_response()
  if (req.url ~ "^[^?]*\.(mp[34]|rar|tar|tgz|gz|wav|zip|bz2|xz|7z|avi|mov|ogm|mpe?g|mk[av]|webm)(\?.*)?$") {
    unset req.http.Cookie;
    return (hash);
  }

# Remove all cookies for static files

if (req.url ~ "^[^?]*\.(bmp|mov|mp4|webm|avi|bz2|css|doc|eot|flv|gif|gz|ico|jpeg|jpg|js|less|pdf|png|rtf|swf|txt|woff|xml)(\?.*)?$") {
    unset req.http.Cookie;
    return (hash);
  }


    # Happens before we check if we have this in cache already.
    #
    # Typically you clean up the request here, removing cookies you don't need,
    # rewriting the request, etc.

 set req.http.Surrogate-Capability = "abc=ESI/1.0";

if (req.http.X-Forwarded-Proto == "https" ) {
        set req.http.X-Forwarded-Port = "443";
    } else {
        set req.http.X-Forwarded-Port = "80";
    }

}

sub vcl_backend_response {
    # Happens after we have read the response headers from the backend.
    #
    # Here you clean the response headers, removing silly Set-Cookie headers
    # and other mistakes your backend does.

if (beresp.http.Surrogate-Control ~ "ESI/1.0") {
        unset beresp.http.Surrogate-Control;
        set beresp.do_esi = true;
    }

# Enable cache for all static files
if (bereq.url ~ "^[^?]*\.(bmp|bz2|css|doc|eot|flv|gif|gz|ico|jpeg|jpg|js|less|mp[34]|pdf|png|rar|rtf|swf|tar|tgz|txt|wav|woff|xml|zip|webm)(\?.*)?$") {
    unset beresp.http.set-cookie;
  }

# Large static files are delivered directly to the end-user without
if (bereq.url ~ "^[^?]*\.(mp[34]|rar|tar|tgz|gz|wav|zip|bz2|xz|7z|avi|mov|ogm|mpe?g|mk[av]|webm)(\?.*)?$") {
    unset beresp.http.set-cookie;
    set beresp.do_stream = true; # Check memory usage it'll grow in fetch_chunksize blocks (128k by default) if the backend doesn't send a Content-Length header, so only enable it for big objects
    set beresp.do_gzip = false; # Don't try to compress it for storage
  }





        return (deliver);
}

sub vcl_deliver {

    # Happens when we have all the pieces we need, and are about to send the
    # response to the client.
    #
    # You can do accounting or modifying the final object here.

if (bereq.http.Cookie ~ "(UserID|_session)") {
        set beresp.http.X-Cacheable = "NO:Got Session";
        set beresp.uncacheable = true;


} elsif (beresp.ttl <= 0s) {
        # Varnish determined the object was not cacheable
        set beresp.http.X-Cacheable = "NO:Not Cacheable";

} elsif (beresp.http.set-cookie) {
        # You don't wish to cache content for logged in users
        set beresp.http.X-Cacheable = "NO:Set-Cookie";
        set beresp.uncacheable = true; 

} elsif (beresp.http.Cache-Control ~ "private") {
        # You are respecting the Cache-Control=private header from the backend
        set beresp.http.X-Cacheable = "NO:Cache-Control=private";
        set beresp.uncacheable = true;

} else {
        # Varnish determined the object was cacheable
        set beresp.http.X-Cacheable = "YES";
    }

if (obj.hits > 0) { # Add debug header to see if it's a HIT/MISS and the number of hits, disable when not needed
    set resp.http.X-Cache = "HIT";
  } else {
    set resp.http.X-Cache = "MISS";
  }

set resp.http.XH = obj.hits;

unset resp.http.X-Varnish;
unset resp.http.Via;

}

this throw error

sudo service varnish restart
open files                      (-n) 1024
open files                      (-n) 1024
Error:
Message from VCC-compiler:
'bereq.http.Cookie': Not available in method 'vcl_deliver'.
At: ('input' Line 120 Pos 5)
if (bereq.http.Cookie ~ "(UserID|_session)") {
----#################-------------------------

Running VCC-compiler failed, exited with 2
VCL compilation failed
 * Syntax check failed, not restarting

but removing log part from config allow to varnish cache HIT. How should look sub vcl_deliver with no cache info ?

Upvotes: 0

Views: 834

Answers (1)

Peter
Peter

Reputation: 31751

vcl_backend_response is called before objects are written to the cache, so you are modifying the response before it enters the cache. That means that you are not seeing stale response headers. Move your diagnostics to vcl_deliver instead.

Upvotes: 1

Related Questions