Configure Varnish 4 multiple domains different ports - varnish

I got this to load both the websites, however I am unable to log into both wordpress websites.
backend websiteone {
.host = "127.0.0.1";
.port = "7070";
}
backend websitetwo {
.host = "127.0.0.1";
.port = "2082";
}
sub vcl_recv {
if (req.http.host ~ "^(.*\.)?websiteone\.com$") {
set req.backend_hint = websiteone;
return (hash);
}
if (req.http.host ~ "^(.*\.)?websitetwo\.com$") {
set req.backend_hint = websitetwo;
return (hash);
}
}

Here is what I did to resolve this issue:
mkdir /etc/varnish/sites-enabled
cd /etc/varnish/sites-enabled
nano siteone.com.vcl
sub vcl_recv {
if (req.http.host == "siteone.com") {
if (req.url ~ "/(cart|my-account|checkout|addons|/?add-to-cart=)") {
return (pass);
}
}
}
nano sitetwo.com.vcl
backend sitetwo {
.host = "127.0.0.1";
.port = "2082";
}
sub vcl_recv {
if (req.http.host == "sitetwo.com") {
set req.backend_hint = sitetwo;
}
}
Then I had to edit /etc/varnish/default.vcl
cd /etc/varnish/
nano default.vcl
The backend is configured for sitetwo as you can see above, but the backend for siteone is configured in default.vcl so I changed
backend default {
.host = "127.0.0.1";
.port = "7070";
}
And added these two lines to the bottom of default.vcl
include "sites-enabled/siteone.com.vcl";
include "sites-enabled/sitetwo.com.vcl";
Everything seems to be working correctly now! And if I have to add any more sites all I have to do is create sitetree.com.vcl in /sites-enabled folder and paste
backend sitethree {
.host = "127.0.0.1";
.port = "port number";
}
sub vcl_recv {
if (req.http.host == "sitethree.com") {
set req.backend_hint = sitethree;
}
}
Note: Siteone is running an ecommerce site so if you are not running a store then you should just be able to use the following in siteone.com.vcl
sub vcl_recv {
if (req.http.host == "siteone.com") {
set req.backend_hint = siteone;
}
}

Related

How do I merge these two varnish backends?

I am using thumbor and s3.
I want to use varnish infront of them.
I know how to do place varnish in each of them but I can't combine the two
varnish setup for thumbor
vcl 4.0;
import directors;
backend thumbor1 { .host ="127.0.0.1"; .port="8888"; .max_connections = 200; .connect_timeout = 5s; .between_bytes_timeout = 5s; }
# backend thumbor2 { .host ="127.0.0.1"; .port="9002"; .max_connections = 200; .connect_timeout = 5s; .between_bytes_timeout = 5s; }
acl internal {
"localhost";
"127.0.0.1";
}
sub vcl_init {
new vdir = directors.round_robin();
vdir.add_backend(thumbor1);
# vdir.add_backend(thumbor2);
}
sub vcl_recv {
set req.backend_hint = vdir.backend();
if (req.method == "PURGE") {
if (!client.ip ~ internal) {
return (synth(405, "This IP is not allowed to send PURGE requests."));
}
return (purge);
}
if (req.url ~ "\?$") {
set req.url = regsub(req.url, "\?$", "");
}
return (hash);
}
varnish setup for s3
vcl 4.0;
backend default
{
.host = "my.bucket.s3.amazonaws.com";
.port = "80";
}
sub vcl_backend_fetch
{
set bereq.http.Host = "my.bucket.s3.amazonaws.com";
set bereq.http.Date = now;
}
I'd like the final result would be something like
client => varnish => thumbor => s3 (thumbnail image)
client => varnish => s3 (normal image)
You should put 2 backend blocks in the one file. Then in the vcl_recv you should set which backend do you want by some header, url path etc.
To set which backend to use, you could use:
set req.backend_hint = thumbor1;
# Or
set req.backend_hint = default;
There you could find how I've applied it to use 2 backends - localhost:3000 & localhost:8080: https://github.com/new-fantastic/vsf-cache-varnish/blob/master/docker/varnish/shared.vcl

Varnish returns incorrect backend content from User-Agent rule

I have a simple rule to redirect traffic to special backend if the User-Agent == GlobalSign or if the request url is /globalsign. I have noticed on a rare occasion varnish will return content from the special backend incorrectly. It seems happens randomly and does not repeat.
if (req.http.User-Agent ~ "(?i)GlobalSign" || req.url ~ "^/globalsign" ) {
set req.url = "/";
set req.backend = dgs1;
return(pipe);
}
Backend rules
backend b1 {
//Backend 1
.host = "10.8.8.16";
.port = "80";
.probe = {
.url = "/service_up";
.timeout = 1s;
.interval = 5s;
.window = 10;
.threshold = 8;
}
}
backend gs1 {
// Set host: Globalsign
.host = "10.8.8.15";
.port = "80";
.probe = {
.url = "/service_up";
.timeout = 5s;
.interval = 5s;
.window = 10;
.threshold = 8;
}
}
director dgs1 random {
{
.backend = gs1;
.weight = 1;
}
}
director d01 random {
{
.backend = b1;
.weight = 1;
}
}
Full VCL
include "backends.vcl";
include "bans.vcl";
include "acl.vcl";
sub vcl_recv {
// Use the director we set up above to answer the request if it's not cached.
set req.backend = d01;
if( req.url ~ "^/service_up" ) {
return(lookup);
}
if(client.ip ~ evil_networks){
error 403 "Forbidden";
}
if (req.http.User-Agent ~ "(?i)GlobalSign" || req.url ~ "^/globalsign" ) {
set req.url = "/";
set req.backend = dgs1;
return(pipe);
}
return(pass)
}
sub vcl_fetch {
set beresp.grace = 24h;
if (beresp.status >= 400) {
return (hit_for_pass);
}
// New Set Longer Cache
if (req.http.user-agent ~ "(Googlebot|msnbot|Yandex|Slurp|Bot|Crawl|bot|Baid|Mediapartners-Google)") {
unset beresp.http.set-cookie;
set beresp.ttl = 5d;
return (deliver);
}
if (req.request == "GET" && req.url ~ "\.(css|xml|txt)$") {
set beresp.ttl = 5d;
unset beresp.http.set-cookie;
return (deliver);
}
// multimedia
if (req.request == "GET" && req.url ~ "\.(gif|jpg|jpeg|bmp|png|tiff|tif|ico|img|tga|woff|eot|ttf|svg|wmf|js|swf|ico)$") {
unset beresp.http.set-cookie;
set beresp.ttl = 5d;
return (deliver);
}
set beresp.ttl = 5d;
return (deliver);
}
include "errors.vcl";
sub vcl_deliver {
return(deliver);
}
I guess return(pipe); is the suspect one.
If you have keep-alive HTTP client making just one request with GlobalSign user agent or to /globalsign url, all subsequent requests will be piped to dgs1, even if they do not meet the criteria.
Try to avoid piping if possible, it's common source of a lot of hard to track issues. And possibly security hole too.

Running a varnish redirect to a node js server with socket.io

So I'm running a website, on the front it's a simple Apache home page nothing important. But I want to run a sync client on a sub domain
backend apache {
.host = "127.0.0.1";
.port = "8051";
.connect_timeout = 1s;
}
backend node {
.host = "127.0.0.1";
.port = "8081";
.connect_timeout = 1s;
}
backend bot {
.host = "127.0.0.1";
.port = "8080";
.connect_timeout = 1s;
}
sub vcl_recv {
if(req.http.host == "Base-domain.com") {
set req.backend = apache;
}
if(req.http.host == "bot.base-domain.com") {
set req.backend = bot;
}
if(req.http.host == "sync.base-domain.com") {
set req.backend = node;
}
if (req.http.Upgrade ~ "(?i)websocket") {
set req.backend = node;
return (pipe);
}
if (req.http.host == "sync.based-domain.moe") {
if (req.url ~ "^/socket.io/") {
set req.backend = node;
return (pipe);
}
return (pass);
}
}
sub vcl_pipe {
if (req.http.upgrade) {
set bereq.http.upgrade = req.http.upgrade;
}
}
Searching all over for information on how to run the node JS as the one with a socket is turning up no help. Due to a connection issue the websocket is on 1338 rather than 1337. Pretty new to this so not sure what to do.
Should I be changing my varnish or modification the node's config further? Thanks in advance.

using varnish for load balancing

i write a varnish vcl rules for my server and i don't know this is sufficient for my intent. i want run my project on 2 ports of server and on another server such that if one server gone down ,requests forward to other server. moreover i want to serve static files such that don't working apache web server and request for them directly sent to tornado. this is my vcl rules , can u help me ?
import directors;
probe healthcheck {
.url = "/";
.interval = 30s;
.timeout = 1 s;
.window = 5;
.threshold = 2;
.initial = 2;
.expected_response = 200;
}
backend server1{
.host="127.0.0.1"
.port = 8004
.probe = healtcheck;
}
backend server1-2{
.host="127.0.0.1"
.port = 8005
.probe = healtcheck;
}
backend server2{
.host="192.168.1.1"
.port = 8004
.probe = healtcheck;
}
sub vcl_init {
new vdir = directors.round_robin();
vdir.add_backend(server1);
vdir.add_backend(server1-2);
vdir.add_backend(server2);
}
sub vcl_recv{
set req.grace = 600s;
### always cache these items:
if (req.request == "GET" && req.url ~ "\.(js)") {
lookup;
}
## images
if (req.request == "GET" && req.url ~ "\.(gif|jpg|jpeg|bmp|png|tiff|tif|ico|img|tga|wmf)$") {
lookup;
}
## various other content pages
if (req.request == "GET" && req.url ~ "\.(css|html)$") {
lookup;
}
## multimedia
if (req.request == "GET" && req.url ~ "\.(svg|swf|ico|mp3|mp4|m4a|ogg|mov|avi|wmv)$") {
lookup;
}
## xml
if (req.request == "GET" && req.url ~ "\.(xml)$") {
lookup;
}
### do not cache these rules:
if (req.request != "GET" && req.request != "HEAD") {
pipe;
}
### if it passes all these tests, do a lookup anyway;
lookup;
}
sub vcl_fetch {
if (req.url ~ "\.(gif|jpg|jpeg|swf|css|js|flv|mp3|mp4|pdf|ico|png)(\?.*|)$") {
set beresp.ttl = 365d;
}
}
Depending on if you require sessions to work for users you should switch from round_robin to hash. This will ensure the same users will be directed to the same backend.

How to log the selected director>backend in varnishncsa

I have multiple backend servers and I "round-robin" between them using a director.
Is there a way and - if there is - how to log which backend gets used (either the backend name or the backend host name)?
The above refers to using std.log("key:value") and %{VCL_Log:*key*}x with varnishncsa.
My vcl config:
backend aws_frontend1 {
.host = "aws1.domain.mobi";
.port = "80";
}
backend aws_frontend2 {
.host = "aws2.domain.mobi";
.port = "80";
}
director lb_aws_frontend round-robin {
{
.backend = aws_frontend1;
}
{
.backend = aws_frontend2;
}
}
sub vcl_recv {
set req.backend = lb_aws_frontend;
unset req.http.Cookie;
}
sub vcl_fetch {
if (beresp.http.cache-control ~ "(no-cache|private)" || beresp.http.pragma ~ "no-cache") {
set beresp.ttl = 0s;
} else {
set beresp.ttl = 168h;
}
}
sub vcl_error {
if (obj.status == 750) {
set obj.status = 403;
return(deliver);
}
}
Edit:
Below is the updated code thanks to NITEMAN...
This code prints out the backend name when a miss and "varnish cache" is a hit:
import std;
backend aws_frontend1 {
.host = "aws1.domain.mobi";
.port = "80";
}
backend aws_frontend2 {
.host = "aws2.domain.mobi";
.port = "80";
}
director lb_aws_frontend round-robin {
{
.backend = aws_frontend1;
}
{
.backend = aws_frontend2;
}
}
sub vcl_recv {
set req.backend = lb_aws_frontend;
unset req.http.Cookie;
}
sub vcl_fetch {
if (beresp.http.cache-control ~ "(no-cache|private)" || beresp.http.pragma ~ "no-cache") {
set beresp.ttl = 0s;
} else {
set beresp.ttl = 168h;
}
std.log("backend_used:" + beresp.backend.name);
}
sub vcl_hit {
std.log("backend_used:varnish cache");
}
sub vcl_error {
if (obj.status == 750) {
set obj.status = 403;
return(deliver);
}
}
Backend's name (even when a director is used) is available on vcl_fetch, for debugging purposes I usually use:
sub vcl_fetch {
# ...
set beresp.http.X-Backend = beresp.backend.name;
# ...
}

Resources