Varnish Cache empties cart in Magento - magento

We are running a Amazon Web Service EC2 Magento instance with RDS and Varnish Cache and nginx. We are currently facing the problem, that the cart is empty when a user tries to add a second item to the cart. The session is dropped because a new Cookie is set. Here you'll find our .vcl file
# default backend definition. Set this to point to your content server.
backend default {
.host = "127.0.0.1";
.port = "8080";
}
# admin backend with longer timeout values. Set this to the same IP & port as your default server.
backend admin {
.host = "127.0.0.1";
.port = "8080";
.first_byte_timeout = 18000s;
.between_bytes_timeout = 18000s;
}
# add your Magento server IP to allow purges from the backend
acl purge {
"localhost";
"127.0.0.1";
}
sub vcl_recv {
if (req.restarts == 0) {
if (req.http.x-forwarded-for) {
set req.http.X-Forwarded-For =
req.http.X-Forwarded-For + ", " + client.ip;
} else {
set req.http.X-Forwarded-For = client.ip;
}
}
if (req.request != "GET" &&
req.request != "HEAD" &&
req.request != "PUT" &&
req.request != "POST" &&
req.request != "TRACE" &&
req.request != "OPTIONS" &&
req.request != "DELETE" &&
req.request != "PURGE") {
/* Non-RFC2616 or CONNECT which is weird. */
return (pipe);
}
# purge request
if (req.request == "PURGE") {
if (!client.ip ~ purge) {
error 405 "Not allowed.";
}
ban("obj.http.X-Purge-Host ~ " + req.http.X-Purge-Host + " && obj.http.X-Purge-URL ~ " + req.http.X-Purge-Regex + " && obj.http.Content-Type ~ " + req.http.X-Purge-Content-Type);
error 200 "Purged.";
}
# switch to admin backend configuration
if (req.http.cookie ~ "adminhtml=") {
set req.backend = admin;
}
# we only deal with GET and HEAD by default
if (req.request != "GET" && req.request != "HEAD") {
return (pass);
}
# normalize url in case of leading HTTP scheme and domain
set req.url = regsub(req.url, "^http[s]?://[^/]+", "");
# static files are always cacheable. remove SSL flag and cookie
if (req.url ~ "^/(media|js|skin)/.*\.(png|jpg|jpeg|gif|css|js|swf|ico)$") {
unset req.http.Https;
unset req.http.Cookie;
}
# not cacheable by default
if (req.http.Authorization || req.http.Https) {
return (pass);
}
# do not cache any page from
# - index files
# - ...
if (req.url ~ "^/(index)") {
return (pass);
}
# checkout should not be cached by varnish
if (req.url ~ "/(checkout|customer|catalog/product_compare|wishlist)/") {
return(pass);
}
# if (req.url ~ "^/(index.php/)?(checkout|onepagecheckout)")
# {
# return(pipe);
# }
# as soon as we have a NO_CACHE cookie pass request
if (req.http.cookie ~ "NO_CACHE=") {
return (pass);
}
# normalize Aceept-Encoding header
# http://varnish.projects.linpro.no/wiki/FAQ/Compression
if (req.http.Accept-Encoding) {
if (req.url ~ "\.(jpg|png|gif|gz|tgz|bz2|tbz|mp3|ogg|swf|flv)$") {
# No point in compressing these
remove req.http.Accept-Encoding;
} elsif (req.http.Accept-Encoding ~ "gzip") {
set req.http.Accept-Encoding = "gzip";
} elsif (req.http.Accept-Encoding ~ "deflate" && req.http.user-agent !~ "MSIE") {
set req.http.Accept-Encoding = "deflate";
} else {
# unkown algorithm
remove req.http.Accept-Encoding;
}
}
# remove Google gclid parameters
set req.url = regsuball(req.url,"\?gclid=[^&]+$",""); # strips when QS = "?gclid=AAA"
set req.url = regsuball(req.url,"\?gclid=[^&]+&","?"); # strips when QS = "?gclid=AAA&foo=bar"
set req.url = regsuball(req.url,"&gclid=[^&]+",""); # strips when QS = "?foo=bar&gclid=AAA" or QS = "?foo=bar&gclid=AAA&bar=baz"
return (lookup);
}
# sub vcl_pipe {
# # Note that only the first request to the backend will have
# # X-Forwarded-For set. If you use X-Forwarded-For and want to
# # have it set for all requests, make sure to have:
# # set bereq.http.connection = "close";
# # here. It is not set by default as it might break some broken web
# # applications, like IIS with NTLM authentication.
# return (pipe);
# }
#
# sub vcl_pass {
# return (pass);
# }
#
sub vcl_hash {
hash_data(req.url);
if (req.http.host) {
hash_data(req.http.host);
} else {
hash_data(server.ip);
}
if (!(req.url ~ "^/(media|js|skin)/.*\.(png|jpg|jpeg|gif|css|js|swf|ico)$")) {
call design_exception;
}
return (hash);
}
#
# sub vcl_hit {
# return (deliver);
# }
#
# sub vcl_miss {
# return (fetch);
# }
sub vcl_fetch {
if (beresp.status == 500) {
set beresp.saintmode = 10s;
return (restart);
}
set beresp.grace = 5m;
# add ban-lurker tags to object
set beresp.http.X-Purge-URL = req.url;
set beresp.http.X-Purge-Host = req.http.host;
if (beresp.status == 200 || beresp.status == 301 || beresp.status == 404) {
if (beresp.http.Content-Type ~ "text/html" || beresp.http.Content-Type ~ "text/xml") {
if ((beresp.http.Set-Cookie ~ "NO_CACHE=") || (beresp.ttl < 1s)) {
set beresp.ttl = 0s;
return (hit_for_pass);
}
# marker for vcl_deliver to reset Age:
set beresp.http.magicmarker = "1";
# Don't cache cookies
unset beresp.http.set-cookie;
} else {
# set default TTL value for static content
set beresp.ttl = 30d;
}
return (deliver);
}
return (hit_for_pass);
}
sub vcl_deliver {
# debug info
if (resp.http.X-Cache-Debug) {
if (obj.hits > 0) {
set resp.http.X-Cache = "HIT";
set resp.http.X-Cache-Hits = obj.hits;
} else {
set resp.http.X-Cache = "MISS";
}
set resp.http.X-Cache-Expires = resp.http.Expires;
} else {
# remove Varnish/proxy header
remove resp.http.X-Varnish;
remove resp.http.Via;
remove resp.http.Age;
remove resp.http.X-Purge-URL;
remove resp.http.X-Purge-Host;
}
if (resp.http.magicmarker) {
# Remove the magic marker
unset resp.http.magicmarker;
set resp.http.Cache-Control = "no-store, no-cache, must-revalidate, post-check=0, pre-check=0";
set resp.http.Pragma = "no-cache";
set resp.http.Expires = "Mon, 31 Mar 2008 10:00:00 GMT";
set resp.http.Age = "0";
}
}
# sub vcl_error {
# set obj.http.Content-Type = "text/html; charset=utf-8";
# set obj.http.Retry-After = "5";
# synthetic {"
# <?xml version="1.0" encoding="utf-8"?>
# <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN"
# "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
# <html>
# <head>
# <title>"} + obj.status + " " + obj.response + {"</title>
# </head>
# <body>
# <h1>Error "} + obj.status + " " + obj.response + {"</h1>
# <p>"} + obj.response + {"</p>
# <h3>Guru Meditation:</h3>
# <p>XID: "} + req.xid + {"</p>
# <hr>
# <p>Varnish cache server</p>
# </body>
# </html>
# "};
# return (deliver);
# }
#
# sub vcl_init {
# return (ok);
# }
#
# sub vcl_fini {
# return (ok);
# }
sub design_exception {
}
Are we doing something basically wrong? or are we searching the wrong spot?
Many thanks for your help.
cheers,
Wolfgang

Your posted .vcl looks fine but however:
1) Make sure you have the official Pagecache powered by Varnish Magento module installed.
2) In the backend, under System => Configuration => System there is a whole tab dedicated to Varnish, make sure all settings are filled in correctly.
3) Verify that after adding a product to the cart there is a "NO_CACHE" or "EXTERNAL_NO_CACHE" cookie set
4) Everything should work?

Related

I can't configure Varnish with Prestashop

i am setting varnish
from this url https://github.com/nexylan/varnish-prestashop/blob/master/vcl/varnish4.vcl
and the error I'm having is I can't enter the prestashop admin and the other problem is that when I add products to the cart it doesn't save them
Thank You.
# disable cookies for static files
if (req.url ~ "\.(js|css|jpg|jpeg|png|gif|gz|tgz|bz2|tbz|mp3|ogg|swf|pdf)$" && ! (req.url ~ "\.(php)") ) {
unset req.http.Cookie;
return (hash);
}
# pipe on weird http methods
if (req.method !~ "^GET|HEAD|PUT|PATCH|POST|TRACE|OPTIONS|DELETE$") {
return(pipe);
}
if (req.method == "GET" && (req.url ~ "^/?mylogout=")) {
unset req.http.Cookie;
return (pass);
}
#we should not cache any page for Prestashop backend
if (req.method == "GET" && (req.url ~ "^/admin")) {
return (pass);
}
#we should not cache any custom directory
if (req.method == "GET" && (req.url ~ "^/custom")) {
return (pass);
}
#we should not cache any page for customers
if (req.method == "GET" && (req.url ~ "^/authentification" || req.url ~ "^/mon-compte")) {
return (pass);
}
#we should not cache any page for customers
if (req.method == "GET" && (req.url ~ "^/informations" || req.url ~ "^/unt.php")) {
return (pass);
}
#we should not cache any page for sales
if (req.method == "GET" && (req.url ~ "^/commande" || req.url ~ "^/historique")) {
return (pass);
}
#we should not cache any page for sales
if (req.method == "GET" && (req.url ~ "^/adresse" || req.url ~ "^/order-detail.php")) {
return (pass);
}
#we should not cache any page for sales
if (req.method == "GET" && (req.url ~ "^/order-confirmation.php" || req.url ~ "^/order-return.php")) {
return (pass);
}
#we should not cache any module
if (req.method == "GET" && req.url ~ "^/module") {
return (pass);
}
if (req.method != "GET" && req.method != "HEAD") {
return (pass);
}

Helm not Importing file correctly

I am creating an Helm Chart and I am having problems when it comes to importing files:
apiVersion: v1
kind: ConfigMap
metadata:
name: vcl-template
namespace: {{.Release.Namespace}}
data:
{{- (.Files.Glob "config/varnish/default.vcl.tmpl").AsConfig | nindent 2 }}
{{- (.Files.Glob "config/varnish/nginx.conf").AsConfig | nindent 2 }}
This imports the file config/varnish/nginx.conf just fine but the file config/varnish/default.vcl.tmpl is imported with \n instead of newlines, so the data on the ConfigMap gets all buggy:
apiVersion: v1
kind: ConfigMap
metadata:
name: vcl-template
namespace: default
data:
default.vcl.tmpl: "vcl 4.0;\n\nimport std;\nimport directors;\n\n{{ range .Frontends
}}\nbackend {{ .Name }} {\n .host = \"{{ .Host }}\";\n .port = \"{{ .Port
}}\";\n}\n{{- end }}\n\n{{ range .Backends }}\nbackend be-{{ .Name }} {\n .host
= \"{{ .Host }}\";\n .port = \"{{ .Port }}\";\n}\n{{- end }}\n\nacl purge {\n
\ \"127.0.0.1\";\n \"localhost\";\n \"::1\";\n {{- range .Frontends }}\n
\ \"{{ .Host }}\";\n {{- end }}\n {{- range .Backends }}\n \"{{ .Host
}}\";\n {{- end }}\n}\n\nsub vcl_init {\n new cluster = directors.hash();\n\n
\ {{ range .Frontends -}}\n cluster.add_backend({{ .Name }}, 1);\n {{ end
}}\n\n new lb = directors.round_robin();\n\n {{ range .Backends -}}\n lb.add_backend(be-{{
.Name }});\n {{ end }}\n}\n\nsub vcl_recv {\n\n unset req.http.x-cache;\n
\ set req.backend_hint = cluster.backend(req.url);\n set req.http.x-shard =
req.backend_hint;\n if (req.http.x-shard != server.identity) {\n return(pass);\n
\ }\n set req.backend_hint = lb.backend();\n\n if (req.method == \"PURGE\")
{\n if (client.ip !~ purge) {\n return (synth(405, \"Method not
allowed\"));\n }\n # To use the X-Pool header for purging varnish
during automated deployments, make sure the X-Pool header\n # has been added
to the response in your backend server config. This is used, for example, by the\n
\ # capistrano-magento2 gem for purging old content from varnish during it's
deploy routine.\n if (!req.http.X-Magento-Tags-Pattern && !req.http.X-Pool)
{\n return (synth(400, \"X-Magento-Tags-Pattern or X-Pool header required\"));\n
\ }\n if (req.http.X-Magento-Tags-Pattern) {\n ban(\"obj.http.X-Magento-Tags
~ \" + req.http.X-Magento-Tags-Pattern);\n }\n if (req.http.X-Pool)
{\n ban(\"obj.http.X-Pool ~ \" + req.http.X-Pool);\n }\n return
(synth(200, \"Purged\"));\n }\n\n if (req.method != \"GET\" &&\n req.method
!= \"HEAD\" &&\n req.method != \"PUT\" &&\n req.method != \"POST\"
&&\n req.method != \"TRACE\" &&\n req.method != \"OPTIONS\" &&\n req.method
!= \"DELETE\") {\n /* Non-RFC2616 or CONNECT which is weird. */\n return
(pipe);\n }\n\n # We only deal with GET and HEAD by default\n if (req.method
!= \"GET\" && req.method != \"HEAD\") {\n return (pass);\n }\n\n #
Bypass shopping cart, checkout and search requests\n if (req.url ~ \"/checkout\"
|| req.url ~ \"/catalogsearch\") {\n return (pass);\n }\n\n # Bypass
admin\n if (req.url ~ \"^/admin($|/.*)\") {\n return (pass);\n }\n\n
\ # Bypass health check requests\n if (req.url ~ \"/pub/health_check.php\")
{\n return (pass);\n }\n\n # Set initial grace period usage status\n
\ set req.http.grace = \"none\";\n\n # normalize url in case of leading HTTP
scheme and domain\n set req.url = regsub(req.url, \"^http[s]?://\", \"\");\n\n
\ # collect all cookies\n std.collect(req.http.Cookie);\n\n # Compression
filter. See https://www.varnish-cache.org/trac/wiki/FAQ/Compression\n if (req.http.Accept-Encoding)
{\n if (req.url ~ \"\\.(jpg|jpeg|png|gif|gz|tgz|bz2|tbz|mp3|ogg|swf|flv)$\")
{\n # No point in compressing these\n unset req.http.Accept-Encoding;\n
\ } elsif (req.http.Accept-Encoding ~ \"gzip\") {\n set req.http.Accept-Encoding
= \"gzip\";\n } elsif (req.http.Accept-Encoding ~ \"deflate\" && req.http.user-agent
!~ \"MSIE\") {\n set req.http.Accept-Encoding = \"deflate\";\n }
else {\n # unknown algorithm\n unset req.http.Accept-Encoding;\n
\ }\n }\n\n # Remove all marketing get parameters to minimize the cache
objects\n if (req.url ~ \"(\\?|&)(gclid|cx|ie|cof|siteurl|zanpid|origin|fbclid|mc_[a-z]+|utm_[a-z]+|_bta_[a-z]+)=\")
{\n set req.url = regsuball(req.url, \"(gclid|cx|ie|cof|siteurl|zanpid|origin|fbclid|mc_[a-z]+|utm_[a-z]+|_bta_[a-z]+)=[-_A-z0-9+()%.]+&?\",
\"\");\n set req.url = regsub(req.url, \"[?|&]+$\", \"\");\n }\n\n #
Static files caching\n if (req.url ~ \"^/(pub/)?(media|static)/\") {\n return
(pass);\n }\n\n return (hash);\n}\n\nsub vcl_hash {\n if (req.http.cookie
~ \"X-Magento-Vary=\") {\n hash_data(regsub(req.http.cookie, \"^.*?X-Magento-Vary=([^;]+);*.*$\",
\"\\1\"));\n }\n\n # For multi site configurations to not cache each other's
content\n if (req.http.host) {\n hash_data(req.http.host);\n } else
{\n hash_data(server.ip);\n }\n\n if (req.url ~ \"/graphql\") {\n call
process_graphql_headers;\n }\n\n # To make sure http users don't see ssl warning\n
\ if (req.http.X-Forwarded-Proto) {\n hash_data(req.http.X-Forwarded-Proto);\n
\ }\n \n}\n\nsub process_graphql_headers {\n if (req.http.Store) {\n hash_data(req.http.Store);\n
\ }\n if (req.http.Content-Currency) {\n hash_data(req.http.Content-Currency);\n
\ }\n}\n\nsub vcl_backend_response {\n\n set beresp.grace = 3d;\n\n if (beresp.http.content-type
~ \"text\") {\n set beresp.do_esi = true;\n }\n\n if (bereq.url ~ \"\\.js$\"
|| beresp.http.content-type ~ \"text\") {\n set beresp.do_gzip = true;\n
\ }\n\n if (beresp.http.X-Magento-Debug) {\n set beresp.http.X-Magento-Cache-Control
= beresp.http.Cache-Control;\n }\n\n # cache only successfully responses and
404s\n if (beresp.status != 200 && beresp.status != 404) {\n set beresp.ttl
= 0s;\n set beresp.uncacheable = true;\n return (deliver);\n }
elsif (beresp.http.Cache-Control ~ \"private\") {\n set beresp.uncacheable
= true;\n set beresp.ttl = 86400s;\n return (deliver);\n }\n\n
\ # validate if we need to cache it and prevent from setting cookie\n if (beresp.ttl
> 0s && (bereq.method == \"GET\" || bereq.method == \"HEAD\")) {\n unset
beresp.http.set-cookie;\n }\n\n # If page is not cacheable then bypass varnish
for 2 minutes as Hit-For-Pass\n if (beresp.ttl <= 0s ||\n beresp.http.Surrogate-control
~ \"no-store\" ||\n (!beresp.http.Surrogate-Control &&\n beresp.http.Cache-Control
~ \"no-cache|no-store\") ||\n beresp.http.Vary == \"*\") {\n # Mark
as Hit-For-Pass for the next 2 minutes\n set beresp.ttl = 120s;\n set
beresp.uncacheable = true;\n }\n\n return (deliver);\n}\n\nsub vcl_deliver
{\n if (resp.http.X-Magento-Debug) {\n if (resp.http.x-varnish ~ \" \")
{\n set resp.http.X-Magento-Cache-Debug = \"HIT\";\n set resp.http.Grace
= req.http.grace;\n } else {\n set resp.http.X-Magento-Cache-Debug
= \"MISS\";\n }\n } else {\n unset resp.http.Age;\n }\n\n #
Not letting browser to cache non-static files.\n if (resp.http.Cache-Control
!~ \"private\" && req.url !~ \"^/(pub/)?(media|static)/\") {\n set resp.http.Pragma
= \"no-cache\";\n set resp.http.Expires = \"-1\";\n set resp.http.Cache-Control
= \"no-store, no-cache, must-revalidate, max-age=0\";\n }\n\n unset resp.http.X-Magento-Debug;\n
\ unset resp.http.X-Magento-Tags;\n unset resp.http.X-Powered-By;\n unset
resp.http.Server;\n unset resp.http.X-Varnish;\n unset resp.http.Via;\n unset
resp.http.Link;\n}\n\nsub vcl_hit {\n if (obj.ttl >= 0s) {\n # Hit within
TTL period\n return (deliver);\n }\n if (std.healthy(req.backend_hint))
{\n if (obj.ttl + 300s > 0s) {\n # Hit after TTL expiration, but
within grace period\n set req.http.grace = \"normal (healthy server)\";\n
\ return (deliver);\n } else {\n # Hit after TTL and
grace expiration\n return (miss);\n }\n } else {\n #
server is not healthy, retrieve from cache\n set req.http.grace = \"unlimited
(unhealthy server)\";\n return (deliver);\n }\n}\n"
nginx.conf: |
worker_processes auto;
events {
worker_connections 1024;
}
pcre_jit on;
error_log /var/log/nginx/error.log warn;
include /etc/nginx/modules/*.conf;
http {
include /etc/nginx/mime.types;
default_type application/octet-stream;
server_tokens off;
client_max_body_size 15m;
keepalive_timeout 30;
sendfile on;
tcp_nodelay on;
gzip_vary on;
log_format main '$remote_addr - $remote_user [$time_local] "$request" '
'$status $body_bytes_sent "$http_referer" '
'"$http_user_agent" "$http_x_forwarded_for"';
access_log /var/log/nginx/access.log main;
include /etc/nginx/conf.d/*.conf;
}
nginx.conf:
worker_processes auto;
events {
worker_connections 1024;
}
pcre_jit on;
error_log /var/log/nginx/error.log warn;
include /etc/nginx/modules/*.conf;
http {
include /etc/nginx/mime.types;
default_type application/octet-stream;
server_tokens off;
client_max_body_size 15m;
keepalive_timeout 30;
sendfile on;
tcp_nodelay on;
gzip_vary on;
log_format main '$remote_addr - $remote_user [$time_local] "$request" '
'$status $body_bytes_sent "$http_referer" '
'"$http_user_agent" "$http_x_forwarded_for"';
access_log /var/log/nginx/access.log main;
include /etc/nginx/conf.d/*.conf;
}
default.vcl.tmpl:
vcl 4.0;
import std;
import directors;
{{ range .Frontends }}
backend {{ .Name }} {
.host = "{{ .Host }}";
.port = "{{ .Port }}";
}
{{- end }}
{{ range .Backends }}
backend be-{{ .Name }} {
.host = "{{ .Host }}";
.port = "{{ .Port }}";
}
{{- end }}
acl purge {
"127.0.0.1";
"localhost";
"::1";
{{- range .Frontends }}
"{{ .Host }}";
{{- end }}
{{- range .Backends }}
"{{ .Host }}";
{{- end }}
}
sub vcl_init {
new cluster = directors.hash();
{{ range .Frontends -}}
cluster.add_backend({{ .Name }}, 1);
{{ end }}
new lb = directors.round_robin();
{{ range .Backends -}}
lb.add_backend(be-{{ .Name }});
{{ end }}
}
sub vcl_recv {
unset req.http.x-cache;
set req.backend_hint = cluster.backend(req.url);
set req.http.x-shard = req.backend_hint;
if (req.http.x-shard != server.identity) {
return(pass);
}
set req.backend_hint = lb.backend();
if (req.method == "PURGE") {
if (client.ip !~ purge) {
return (synth(405, "Method not allowed"));
}
# To use the X-Pool header for purging varnish during automated deployments, make sure the X-Pool header
# has been added to the response in your backend server config. This is used, for example, by the
# capistrano-magento2 gem for purging old content from varnish during it's deploy routine.
if (!req.http.X-Magento-Tags-Pattern && !req.http.X-Pool) {
return (synth(400, "X-Magento-Tags-Pattern or X-Pool header required"));
}
if (req.http.X-Magento-Tags-Pattern) {
ban("obj.http.X-Magento-Tags ~ " + req.http.X-Magento-Tags-Pattern);
}
if (req.http.X-Pool) {
ban("obj.http.X-Pool ~ " + req.http.X-Pool);
}
return (synth(200, "Purged"));
}
if (req.method != "GET" &&
req.method != "HEAD" &&
req.method != "PUT" &&
req.method != "POST" &&
req.method != "TRACE" &&
req.method != "OPTIONS" &&
req.method != "DELETE") {
/* Non-RFC2616 or CONNECT which is weird. */
return (pipe);
}
# We only deal with GET and HEAD by default
if (req.method != "GET" && req.method != "HEAD") {
return (pass);
}
# Bypass shopping cart, checkout and search requests
if (req.url ~ "/checkout" || req.url ~ "/catalogsearch") {
return (pass);
}
# Bypass admin
if (req.url ~ "^/admin($|/.*)") {
return (pass);
}
# Bypass health check requests
if (req.url ~ "/pub/health_check.php") {
return (pass);
}
# Set initial grace period usage status
set req.http.grace = "none";
# normalize url in case of leading HTTP scheme and domain
set req.url = regsub(req.url, "^http[s]?://", "");
# collect all cookies
std.collect(req.http.Cookie);
# Compression filter. See https://www.varnish-cache.org/trac/wiki/FAQ/Compression
if (req.http.Accept-Encoding) {
if (req.url ~ "\.(jpg|jpeg|png|gif|gz|tgz|bz2|tbz|mp3|ogg|swf|flv)$") {
# No point in compressing these
unset req.http.Accept-Encoding;
} elsif (req.http.Accept-Encoding ~ "gzip") {
set req.http.Accept-Encoding = "gzip";
} elsif (req.http.Accept-Encoding ~ "deflate" && req.http.user-agent !~ "MSIE") {
set req.http.Accept-Encoding = "deflate";
} else {
# unknown algorithm
unset req.http.Accept-Encoding;
}
}
# Remove all marketing get parameters to minimize the cache objects
if (req.url ~ "(\?|&)(gclid|cx|ie|cof|siteurl|zanpid|origin|fbclid|mc_[a-z]+|utm_[a-z]+|_bta_[a-z]+)=") {
set req.url = regsuball(req.url, "(gclid|cx|ie|cof|siteurl|zanpid|origin|fbclid|mc_[a-z]+|utm_[a-z]+|_bta_[a-z]+)=[-_A-z0-9+()%.]+&?", "");
set req.url = regsub(req.url, "[?|&]+$", "");
}
# Static files caching
if (req.url ~ "^/(pub/)?(media|static)/") {
return (pass);
}
return (hash);
}
sub vcl_hash {
if (req.http.cookie ~ "X-Magento-Vary=") {
hash_data(regsub(req.http.cookie, "^.*?X-Magento-Vary=([^;]+);*.*$", "\1"));
}
# For multi site configurations to not cache each other's content
if (req.http.host) {
hash_data(req.http.host);
} else {
hash_data(server.ip);
}
if (req.url ~ "/graphql") {
call process_graphql_headers;
}
# To make sure http users don't see ssl warning
if (req.http.X-Forwarded-Proto) {
hash_data(req.http.X-Forwarded-Proto);
}
}
sub process_graphql_headers {
if (req.http.Store) {
hash_data(req.http.Store);
}
if (req.http.Content-Currency) {
hash_data(req.http.Content-Currency);
}
}
sub vcl_backend_response {
set beresp.grace = 3d;
if (beresp.http.content-type ~ "text") {
set beresp.do_esi = true;
}
if (bereq.url ~ "\.js$" || beresp.http.content-type ~ "text") {
set beresp.do_gzip = true;
}
if (beresp.http.X-Magento-Debug) {
set beresp.http.X-Magento-Cache-Control = beresp.http.Cache-Control;
}
# cache only successfully responses and 404s
if (beresp.status != 200 && beresp.status != 404) {
set beresp.ttl = 0s;
set beresp.uncacheable = true;
return (deliver);
} elsif (beresp.http.Cache-Control ~ "private") {
set beresp.uncacheable = true;
set beresp.ttl = 86400s;
return (deliver);
}
# validate if we need to cache it and prevent from setting cookie
if (beresp.ttl > 0s && (bereq.method == "GET" || bereq.method == "HEAD")) {
unset beresp.http.set-cookie;
}
# If page is not cacheable then bypass varnish for 2 minutes as Hit-For-Pass
if (beresp.ttl <= 0s ||
beresp.http.Surrogate-control ~ "no-store" ||
(!beresp.http.Surrogate-Control &&
beresp.http.Cache-Control ~ "no-cache|no-store") ||
beresp.http.Vary == "*") {
# Mark as Hit-For-Pass for the next 2 minutes
set beresp.ttl = 120s;
set beresp.uncacheable = true;
}
return (deliver);
}
sub vcl_deliver {
if (resp.http.X-Magento-Debug) {
if (resp.http.x-varnish ~ " ") {
set resp.http.X-Magento-Cache-Debug = "HIT";
set resp.http.Grace = req.http.grace;
} else {
set resp.http.X-Magento-Cache-Debug = "MISS";
}
} else {
unset resp.http.Age;
}
# Not letting browser to cache non-static files.
if (resp.http.Cache-Control !~ "private" && req.url !~ "^/(pub/)?(media|static)/") {
set resp.http.Pragma = "no-cache";
set resp.http.Expires = "-1";
set resp.http.Cache-Control = "no-store, no-cache, must-revalidate, max-age=0";
}
unset resp.http.X-Magento-Debug;
unset resp.http.X-Magento-Tags;
unset resp.http.X-Powered-By;
unset resp.http.Server;
unset resp.http.X-Varnish;
unset resp.http.Via;
unset resp.http.Link;
}
sub vcl_hit {
if (obj.ttl >= 0s) {
# Hit within TTL period
return (deliver);
}
if (std.healthy(req.backend_hint)) {
if (obj.ttl + 300s > 0s) {
# Hit after TTL expiration, but within grace period
set req.http.grace = "normal (healthy server)";
return (deliver);
} else {
# Hit after TTL and grace expiration
return (miss);
}
} else {
# server is not healthy, retrieve from cache
set req.http.grace = "unlimited (unhealthy server)";
return (deliver);
}
}
How come that the second file is not imported correctly? Latest Helm version and latest Go version.
Anyone has any ideas? The encoding of both files on VSCode shows as UTF8.
They're actually equivalent from YAML's PoV, just not as pretty, but most important for your specific case it's because yaml cannot represent trailing whitespace without quoting it, which is what it did due to line 164 of your .tmpl file, as seen by the \n \n in:
\ }\n \n}\n\nsub process_graphql_headers {\n if (req.http.Store) {\n hash_data(req.http.Store);\n
$ sed -ne 164p default.vcl.tmpl | xxd
00000000: 2020 2020 0a .
turning on "strip trailing whitespace" in your editor will help that, or for this specific case you can just fix line 164

Codeigniter switch language with multi-segment

I have no problem with using i18n in mydomain.com/en/controller
My problem begin if I used something like mydomain/foldername/en/controller
when I switch language it's coming like mydomain/foldername/en/ar/controller
as ar is the other language
my base_url is mydomain/foldername/
I believe that it coming from one index and i tried to change it in MY_LANG:
// Originaly CodeIgniter i18n library by Jérome Jaglale
// http://maestric.com/en/doc/php/codeigniter_i18n
//modified by Tobin Thomas
class MY_Lang extends CI_Lang {
/**************************************************
configuration
***************************************************/
// Add your languages here
private $languages = array(
'en' => 'english',
'ar' => 'arabic'
);
// special URIs (not localized)
private $special = array (
'admin',
'assets',
'editor'
);
// where to redirect if no language in URI
private $uri;
private $default_uri;
private $lang_code;
/**************************************************/
function MY_Lang()
{
parent::__construct();
global $CFG;
global $URI;
global $RTR;
$this->uri = $URI->uri_string();
$this->default_uri = $RTR->default_controller;
$uri_segment = $this->get_uri_lang($this->uri);
$this->lang_code = $uri_segment['lang'] ;
$url_ok = false;
if ((!empty($this->lang_code)) && (array_key_exists($this->lang_code, $this->languages)))
{
$language = $this->languages[$this->lang_code];
$CFG->set_item('language', $language);
$url_ok = true;
}
if ((!$url_ok) && (!$this->is_special($uri_segment['parts'][0]))) // special URI -> no redirect
{
// set default language
$CFG->set_item('language', $this->languages[$this->default_lang()]);
$uri = (!empty($this->uri)) ? $this->uri: $this->default_uri;
$uri = ($uri[0] != '/') ? '/'.$uri : $uri;
$new_url = $CFG->config['base_url'].$this->default_lang().$uri;
header("Location: " . $new_url, TRUE, 302);
exit;
}
}
// get current language
// ex: return 'en' if language in CI config is 'english'
function lang()
{
global $CFG;
$language = $CFG->item('language');
$lang = array_search($language, $this->languages);
if ($lang)
{
return $lang;
}
return NULL; // this should not happen
}
function is_special($lang_code)
{
if ((!empty($lang_code)) && (in_array($lang_code, $this->special)))
return TRUE;
else
return FALSE;
}
function switch_uri($lang)
{
if ((!empty($this->uri)) && (array_key_exists($lang, $this->languages)))
{
if ($uri_segment = $this->get_uri_lang($this->uri))
{
$uri_segment['parts'][0] = $lang;
$uri = implode('/',$uri_segment['parts']);
}
else
{
$uri = $lang.'/'.$this->uri;
}
}
return $uri;
}
//check if the language exists
//when true returns an array with lang abbreviation + rest
function get_uri_lang($uri = '')
{
if (!empty($uri))
{
$uri = ($uri[0] == '/') ? substr($uri, 0): $uri;
$uri_expl = explode('/', $uri, 2);
$uri_segment['lang'] = NULL;
$uri_segment['parts'] = $uri_expl;
if (array_key_exists($uri_expl[0], $this->languages))
{
$uri_segment['lang'] = $uri_expl[0];
}
return $uri_segment;
}
else
return FALSE;
}
// default language: first element of $this->languages
function default_lang()
{
$browser_lang = !empty($_SERVER['HTTP_ACCEPT_LANGUAGE']) ? strtok(strip_tags($_SERVER['HTTP_ACCEPT_LANGUAGE']), ',') : '';
$browser_lang = substr($browser_lang, 0,2);
return (!empty($browser_lang) && array_key_exists($browser_lang, $this->languages)) ? $browser_lang: 'en';
}
// add language segment to $uri (if appropriate)
function localized($uri)
{
if (!empty($uri))
{
$uri_segment = $this->get_uri_lang($uri);
if (!$uri_segment['lang'])
{
if ((!$this->is_special($uri_segment['parts'][0])) && (!preg_match('/(.+)\.[a-zA-Z0-9]{2,4}$/', $uri)))
{
$uri = $this->lang() . '/' . $uri;
}
}
}
return $uri;
}
}
// END MY_Lang Class
/* End of file MY_Lang.php */
/* Location: ./application/core/MY_Lang.php */
ANY IDEA?
i was facing the same behavior. The problem was not in MY_Lang. It was the call of $this->lang->switch_uri('lang') in the view. I do not used codeigniter functions like anchor, site_url to generate the right link. I used plain html. Small mistake, minutes/hours of code review.
<a href="<?php echo $this->lang->switch_uri('en'); ?>"><img ...
won't work. It adds lang segment twice to uri, instead use anchor or site_url
<a href="<?php echo site_url($this->lang->switch_uri('en')); ?>"><img ...

Varnish with Magento 1.8.1 Community editon not getting cache results

I'm newbie to Varnish Cache. I've installed Varnish 4 ( latest version) on Cent OS server successfully and configured perfectly. I'm also getting X-Varnish, Via 1.1 varnish - v4 in Response header. I've found everything working perfectly. If I stop varnish, website stops which seems correct.
My question is, eventhough varnish is configured correctly I'm not having enough speed. I thought, I'm not getting varnish cache result, it looks server always called backend server to get results. Normally, without varnish it takes 3-4 seconds to get results. After installing varnish, It takes same amount of time.
Resonse header
Accept-Ranges bytes Age 0 Cache-Controlno-store, no-cache,
must-revalidate, post-check=0, pre-check=0 Connectionkeep-alive
Content-EncodinggzipContent-Typetext/html; charset=UTF-8DateFri, 01
Aug 2014 14:08:51 GMTExpiresThu, 19 Nov 1981 08:52:00
GMTPragmano-cacheServerApache/2.2.15
(CentOS)Set-Cookiefrontend=rfdi8hd6kq136puafk93lm0ra7; expires=Fri,
01-Aug-2014 15:08:51 GMT; path=/; domain=www.usapooldirect.com;
httponlyTransfer-EncodingchunkedVaryAccept-Encoding,User-Agent Via
1.1 varnish-v4 X-Powered-By PHP/5.3.3X-Varnish
Request Header
Accepttext/html, application/xhtml+xml, application/xml;q=0.9
,/;q=0.8Accept-Encodinggzip,
deflateAccept-Languageen-US,en;q=0.5Connectionkeep-aliveCookiefrontend=rfdi8hd6kq136puafk93lm0ra7;
external_no_cache=1;
adminhtml=pt3bt6t30m4vtqdsm1ldv716v7Hostwww.usapooldirect.com
Refererhttp://www.usapooldirect.com/User-Agent Mozilla/5.0 (X11;
Ubuntu; Linux x86_64; rv:31.0) Gecko/20100101 Firefox/31.0
Thank you,
Ankit
You should check Varnish hits with help of Varnishstat.
You can also put below code which you can check in browser if it got served from Varnish cache or backend.
sub vcl_deliver {
if (obj.hits > 0) {
set resp.http.X-Cache = "HIT ("+obj.hits+")";
} else {
set resp.http.X-Cache = "MISS";
# set resp.http.X-Cache-Hash = obj.http.hash;
}
return (deliver);
}
Whatever module you'll use to improve caching, as long as Magento is involved - even if it is only for determining what data to load from its cache - it will be slow. Varnish is always been a solution to speed up Magento.
But after Magento 1.8.1, Varnish cache is practically becomes useless. You can see here how you can configure Varnish Cache with Magento 1.8.1! and above.
You can use below sample Varnish file.
backend default {
.host = "localhost";
.port = "80";
}
sub vcl_recv {
if (req.http.x-forwarded-for) {
remove req.http.X-Forwarded-For;
set req.http.x-forwarded-for = req.http.X-Forwarded-For + ", " + client.ip;
} else {
set req.http.X-Forwarded-For = client.ip;
}
if (!req.backend.healthy) {
unset req.http.Cookie;
}
if (req.backend.healthy) {
set req.grace = 60s;
} else {
set req.grace = 24h;
}
if (req.request != "GET" &&
req.request != "HEAD" &&
req.request != "PUT" &&
req.request != "POST" &&
req.request != "TRACE" &&
req.request != "OPTIONS" &&
req.request != "DELETE") {
return (pipe);
}
if (req.request == "POST") {
return(pipe);
}
if (req.request != "GET" && req.request != "HEAD") {
return (pass);
}
if (req.http.Accept-Encoding) {
if (req.url ~ "\.(jpg|png|gif|gz|tgz|bz2|tbz|mp3|ogg)$") {
remove req.http.Accept-Encoding;
}
elsif (req.http.Accept-Encoding ~ "gzip") {
set req.http.Accept-Encoding = "gzip";
}
elsif (req.http.Accept-Encoding ~ "deflate" && req.http.user-agent !~ "MSIE") {
set req.http.Accept-Encoding = "deflate";
}
} else {
remove req.http.Accept-Encoding;
}
if (!req.backend.healthy) {
unset req.http.Cookie;
}
if (req.http.Cookie) {
return (pass);
}
return (lookup);
}
sub vcl_pipe {
return (pipe);
}
sub vcl_pass {
return (pass);
}
sub vcl_hash {
hash_data(req.url);
if (req.http.host) {
hash_data(req.http.host);
} else {
hash_data(server.ip);
}
return (hash);
}
sub vcl_hit {
return (deliver);
}
sub vcl_miss {
return (fetch);
}
sub vcl_fetch {
if (beresp.status == 404 || beresp.status == 503) {
set beresp.ttl = 0s;
return (hit_for_pass);
}
if (!req.backend.healthy) {
set beresp.ttl = 1h;
unset beresp.http.set-Cookie;
}
if (beresp.http.Set-Cookie) {
return (hit_for_pass);
}
set beresp.grace = 24h;
return (deliver);
}
sub vcl_deliver {
if (obj.hits > 0) {
set resp.http.X-Varnish-Cache = "HIT";
}
else {
set resp.http.X-Varnish-Cache = "MISS";
}
}
sub vcl_init {
return (ok);
}
sub vcl_fini {
return (ok);
}
sub vcl_error {
return(deliver);
}

Varnish not purging quickly/correctly

I'm setting up a Varnish server in front of a Joomla site via Apache/MySQL. I've gotten Varnish to work with Apache and here the Varnish config:
acl purge {
"localhost";
}
backend apache {
.host = "127.0.0.1";
.port = "8090";
}
sub vcl_recv {
if (req.url ~ "^/administrator" ||
req.url ~ "^/component/banners" ||
req.request == "POST") {
return (pass);
}
if (req.request == "PURGE") {
if (!client.ip ~ purge) {
error 405 "Not allowed.";
}
return (lookup);
}
if (req.http.Accept-Encoding) {
if (req.url ~ "\.(jpg|png|gif|gz|tgz|bz2|tbz|mp3|ogg)$") {
# No point in compressing these
remove req.http.Accept-Encoding;
} elsif (req.http.Accept-Encoding ~ "gzip") {
set req.http.Accept-Encoding = "gzip";
} elsif (req.http.Accept-Encoding ~ "deflate") {
set req.http.Accept-Encoding = "deflate";
} else {
# unkown algorithm
remove req.http.Accept-Encoding;
}
}
remove req.http.X_Forwarded-For;
set req.http.X-Forwareded-For = client.ip;
unset req.http.Cookie;
set req.grace = 1h;
return (lookup);
}
sub vcl_fetch {
set beresp.grace = 1h;
set beresp.ttl = 60s;
return (deliver);
}
sub vcl_hit {
if (req.request == "PURGE") {
purge;
error 200 "Purged.";
}
}
sub vcl_miss {
if (req.request == "PURGE") {
purge;
error 200 "Purged.";
}
}
So here is my problem: When I create a new article/update an article, and I purge the cache manual for the home page, it's not purging it and updating the cache with the new article/update.
Any suggestions?
Also, any suggestions/additions/subtractions from my current Varnish config?

Resources