Backend change during retry in varnish 4

I would like to be able to change the backend to repeat in Varnish 4. We have work on another (older) application using Varnish 3, but I could not figure it out v4, and also did not find a lot of documentation. We want us to have 2 sets of directors - one for the initial request, trying a local server in the same data center as the varnish, because it is much faster, and only when that fails, randomly select from another Directors for servers in other data centers.

In v3, this was easy:

sub vcl_recv { if (req.restarts == 0) { set req.backend = defaultdirector; } else { set req.backend = backupdirector; } } #Then in vcl_fetch and/or vcl_error something like: if (beresp.status >= 500 && req.restarts < some_max) { return(restart); } 

But now, in version v4, the restart was supposedly replaced by repetition, with all the documentation:

In 3.0, you could return (restart) after you noticed that the response to the backend was incorrect in order to switch to another backend.

Now this is called return (retry) and returns to vcl_backend_fetch.

This only affects the flow of the original sample; processing on the client side does not.

However, I still see a sample code with several people containing return (restart), not return (retry), and not just one example of how it works with the retry command.

I understand that the varnish should not do all the work in vcl_recv again (for example, deleting cookies), since it was only connected with the message from the backend, so it makes sense to go back to the backend selection and not redo all the processing of the interface, but I get compilation error if I try to change the backend in vcl_backend_fetch. How to do it?

+6
source share
1 answer

official documentation - misleading. In fact, a reboot still exists: you can catch the error in vcl_deliver and set the backend in vcl_recv accordingly using req.backend_hint

 sub vcl_recv { if (req.restarts == 0) { set req.backend_hint = defaultdirector.backend(); } else { set req.backend_hint = backupdirector.backend(); } } sub vcl_deliver { if (resp.status >= 500 && req.restarts < some_max) { return(restart); } } 

Or, if it is more adequate, you can use repeat between vcl_backend_response and vcl_backend_fetch :

 sub vcl_backend_fetch { if (bereq.retries > 0) { set bereq.backend = backupdirector.backend(); } } sub vcl_backend_response { if (beresp.status >= 500 && bereq.retries < some_max) { return(retry); } } 
+7
source

Source: https://habr.com/ru/post/1243277/


All Articles