VCL有多个状态引擎,状态之间存在相关性,但状态引擎彼此间互相隔离;每个状态引擎可使用return(x)指明关联至哪个下一级引擎;每个状态引擎对应于vcl文件中的一个配置段,即为subroutine
变量类型:
内建变量:
req.*:request,表示由客户端发来的请求报文相关;
bereq.*:由varnish发往BE主机的httpd请求相关;
resp.*:由varnish响应给client相关;
obj.*:存储在缓存空间中的缓存对象的属性;只读;
常用变量:
bereq.*, req.*:
bereq.http.HEADERS
bereq.request:请求方法;
bereq.url:请求的url;
bereq.proto:请求的协议版本;
bereq.backend:指明要调用的后端主机;
req.http.Cookie:客户端的请求报文中Cookie首部的值;
req.http.User-Agent ~ “chrome”
beresp.*, resp.*:
beresp.http.HEADERS
beresp.status:响应的状态码;
reresp.proto:协议版本;
beresp.backend.name:BE主机的主机名;
beresp.ttl:BE主机响应的内容的余下的可缓存时长;
obj.*
obj.hits:此对象从缓存中命中的次数 >1 表示命中;
obj.ttl:对象的ttl值
server.*
server.ip
server.hostname
client.*
client.ip
介绍几个VCL配置的实例:
(1)添加报文首部:vim default.vcl
obj.hits是内建变量,用于保存某缓存项的从缓存中命中的次数;
在sub vcl_deliver中添加
if (obj.hits>0) {
set resp.http.X-Cache = “HIT via ” + server.ip;
} else {
set resp.http.X-Cache = “MISS via ” + server.ip;
}
在交互式命令行下手动装载配置,并使用:
vcl.load test default.vcl
vcl_use test
测试:
刷新网页,再次访问,会出现“ HIT via... .”字样
(2)强制对某类资源的请求不检查缓存,在请求报文中包含以/login|admin 为首的不查缓存,直接送到backend(后端服务器) :
sub vcl_recv {
if (req.url ~ “(?i)^/(login|admin)”) {
return(pass);
}
}
禁止以curl方式访问:
sub vcl_recv {
if (req.http.User-Agent ~ “(?i)^/curl”) {
return(synth(403));
}
}
测试:
(3)对于特定类型的资源,例如公开的图片等,取消其私有标识(cookie),并强行设定其可以由varnish缓存的时长;
sub vcl_backend_response {
if (beresp.http.cache-control !~ “s-maxage”) {
if (bereq.url ~ “(?i)\.(jpg|jpeg|png|gif|css|js)$”) {
unset beresp.http.Set-Cookie;
set beresp.ttl = 3600s;
}
}
}
(4)设置后端服务器日志中记录真实的客户端地址:
sub vcl_recv {
if (req.restarts == 0) {
if (req.http.X-Fowarded-For) {
set req.http.X-Forwarded-For = req.http.X-Forwarded-For + “,” + client.ip;
} else {
set req.http.X-Forwarded-For = client.ip;
}
}
}
并在后端服务器中设置日志格式:
vim /etc/httpd/conf/httpd.conf
将格式修改为:LogFormat “%{X-Forwarded-For}i %l %u %t \”%r\“ %>s %b \” %{Referer}i\” \”%{User-Agent}i\”” combined
测试:
(5)访问控制
缓存对象的修剪:purge, ban
测试:缓存后,用curl查看网页信息
裁剪,将缓存删除:curl -X PURGE http://172.16.252.187/index.html
Banning 在交互式模式 用于临时按需要清理缓存
示例:
在配置文件中,使用ban()函数,相当于purge的用法;示例:
if (req.method == “BAN”) {
ban(“req.http.host == ” + req.http.host + ” && req.url == ” + req.url);
return(synth(200, “Ban added”));
}
清空一个域的缓存:
ban req.url == / && req.http.host ~ “ilinux.io”(慎用)
(6)负载均衡,Director:
使用前需要导入:import directors
示例:
动静分离配置示例:
import director s
…..
backend imgsrv1 {
.host = “192.168.251.11”;
.port = “80”;
}
backend imgsrv2 {
.host = “192.168.251.12”;
.port = “80”;
}
backend appsrv1 {
.host = “192.168.251.13”;
.port = “80”;
}
backend appsrv2 {
.host = “192.168.251.14”;
.port = “80”;
}
sub vcl_init {
new imgsrvs = directors.random();
imgsrvs.add_backend(imgsrv1,10);
imgsrvs.add_backend(imgsrv2,20);
new staticsrvs = directors.round_robin();
appsrvs.add_backend(appsrv1);
appsrvs.add_backend(appsrv2);
new appsrvs = directors.hash();
appsrvs.add_backend(appsrv1,1);
appsrvs.add_backend(appsrv2,1);
}
sub vcl_recv {
if (req.url ~ “(?i)\.(css|js)$” {
set req.backend_hint = staticsrvs.backend();
}
if (req.url ~ “(?i)\.(jpg|jpeg|png|gif)$” {
set req.backend_hint = imgsrvs.backend();
} else {
set req.backend_hint = appsrvs.backend(req.http.cookie);
}
}
(7)基于cookie的session sticky:
sub vcl_init {
new h = directors.hash();
h.add_backend(one, 1); // backend ‘one’ with weight ‘1’
h.add_backend(two, 1); // backend ‘two’ with weight ‘1’
}
sub vcl_recv {
set req.backend_hint = h.backend(req.http.cookie);
}
(8)健康状态检测:
.probe:定义健康状态检测方法;
.url:检测时要请求的URL,默认为”/”;
.request:发出的具体请求;
.request =
“GET /.healthtest.html HTTP/1.1”
“Host: www.magedu.com”
“Connection: close”
.window:基于最近的多少次检查来判断其健康状态;
.threshold:最近.window中定义的这么次检查中至有.threshhold定义的次数是成功的;
.interval:检测频度;
.timeout:超时时长;
.expected_response:期望的响应码,默认为200;
配置示例:
显示健康状态信息,在交互式界面中:
4、性能调整:vim /etc/varnish/varnish.params
根据对网页的测试来适当调整数值
5、varnish日志
1>、varnishstat – Varnish Cache statistics 各种计数器
-1 批次显示,只显示1次
-1 -f FILED_NAME
-l:可用于-f选项指定的字段名称列表;
# varnishstat -1 -f MAIN.cache_hit -f MAIN.cache_miss
# varnishstat -l -f MAIN -f MEMPOOL
2>、varnishtop – Varnish log entry ranking 将日志文件中相关数据逆序排序
-1 Instead of a continously updated display, print the statistics once and exit.
-i taglist,可以同时使用多个-i选项,也可以一个选项跟上多个标签;筛选
-I <[taglist:]regex>
-x taglist:排除列表
-X <[taglist:]regex>
varnishtop -i RespStatus 查看响应码
3>、varnishlog – Display Varnish logs 查看实时日志
4>、 varnishncsa – Display Varnish logs in Apache / NCSA combined log format 标准日志格式