基于Varnish 3.0.4的网站静态加速(2)

2、后端WEB服务健康检测

# vim /usr/local/varnish/etc/health_check.vcl

probe backend_healthcheck {

.interval = 5s;

.timeout = 3s;

.window = 10;

.threshold = 8;

.request =

"GET /index.html HTTP/1.1"

"Host: mycheckweb.mytest.com"

"Connection: close"

"Accept-Encoding: foo/bar";

}


-----------------------------------------------------------------------------------------------------------------------------------------------


3、后端WEB服务定义

# vim /usr/local/varnish/etc/hosts/10.160.22.88_8080.conf

backend WEBSRV_10_160_22_88_8080 {

.host = "10.160.22.88";

.port = "8080";

.connect_timeout = 50s;

.between_bytes_timeout = 30s;

.first_byte_timeout = 30s;

.probe = backend_healthcheck;

}


# vim /usr/local/varnish/etc/hosts/10.173.146.35_8080.conf


backend WEBSRV_10_173_146_35_8080 {

.host = "10.173.146.35";

.port = "8080";

.connect_timeout = 50s;

.between_bytes_timeout = 30s;

.first_byte_timeout = 30s;

.probe = backend_healthcheck;

}


-----------------------------------------------------------------------------------------------------------------------------------------------


4、集群定义

# vim /usr/local/varnish/etc/cluster.vcl

include "/usr/local/varnish/etc/health_check.vcl";

include "/usr/local/varnish/etc/hosts/10.160.22.88_8080.conf";

include "/usr/local/varnish/etc/hosts/10.173.146.35_8080.conf";

director CLUSTER_BACKEND_SERVER round-robin {

{ .backend = WEBSRV_10_160_22_88_8080; }

{ .backend = WEBSRV_10_173_146_35_8080; }

}


-----------------------------------------------------------------------------------------------------------------------------------------------


5、Varnish主配置文件

# vim /usr/local/varnish/etc/varnish.vcl


include "/usr/local/varnish/etc/cluster.vcl";

acl allow_purge_cache {

"127.0.0.1";

"10.0.0.0"/8;

"172.0.0.0"/8;

}

sub vcl_recv {

if (req.request == "PURGE") {

if (!client.ip ~ allow_purge_cache) {

error 405 "Not Allowed.";

}

return (lookup);

}

if (req.http.host ~ "^(.*).mytest.com") {

set req.backend = CLUSTER_BACKEND_SERVER;

}

## 动态资源直接抛到后端服务器

if (req.url ~ "\.(php|asp|aspx|jsp|do|ashx|shtml)($|\?)") {

return (pass);

}

## 静态资源需要去除cookie信息

if (req.request == "GET" && req.url ~ "\.(css|js|bmp|png|gif|jpg|jpeg|ico|gz|tgz|bz2|tbz|zip|rar|mp3|mp4|ogg|swf|flv)($|\?)") {

unset req.http.cookie;

return (lookup);

}

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.http.Cache-Control ~ "no-cache") {

return (pass);

}

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 != "GET" && req.request != "HEAD") {

return (pass);

}

if (req.http.Authorization || req.http.Cookie) {

return (pass);

}

## 静态资源压缩

if (req.http.Accept-Encoding) {

if (req.url ~ "\.(bmp|png|gif|jpg|jpeg|ico|gz|tgz|bz2|tbz|zip|rar|mp3|mp4|ogg|swf|flv)$") {

remove req.http.Accept-Encoding;

} elseif (req.http.Accept-Encoding ~ "gzip") {

set req.http.Accept-Encoding = "gzip";

} elseif (req.http.Accept-Encoding ~ "deflate") {

set req.http.Accept-Encoding = "deflate";

} else {

remove req.http.Accept-Encoding;

}

}

## 防盗链设置

if (req.http.referer ~ "http://.*") {

if (!(req.http.referer ~ "http://.*\.qq\.com" ||

req.http.referer ~ "http://.*\.baidu\.com" ||

req.http.referer ~ "http://.*\.google\.com.*" ||

req.http.referer ~ "http://.*\.sogou\.com" ||

req.http.referer ~ "http://.*\.soso\.com" ||

req.http.referer ~ "http://.*\.so\.com")) {

set req.http.host = "www.mytest.com";

set req.url = "/";

}

}

if (!req.backend.healthy) {

unset req.http.Cookie;

}

## 跳过缓存大文件

if (req.http.x-pipe && req.restarts > 0) {

unset req.http.x-pipe;

return (pipe);

}

## 若backend是健康的,则仅grace 5s,如果backend不健康,则grace 1m,主要用于提高并发时的吞吐率

if (req.backend.healthy) {

set req.grace = 5s;

} else {

set req.grace = 1m;

}

}

sub vcl_pipe {

return (pipe);

}

sub vcl_pass {

if (req.request == "PURGE") {

error 502 "PURGE on a passed object";

}

}

sub vcl_hash {

hash_data(req.url);

if (req.http.host) {

hash_data(req.http.host);

} else {

hash_data(server.ip);

}

if (req.http.Accept-Encoding ~ "gzip") {

hash_data("gzip");

} elseif (req.http.Accept-Encoding ~ "deflate") {

hash_data("deflate");

}

return (hash);

}

sub vcl_hit {

if (req.request == "PURGE") {

purge;

error 200 "Purged.";

}

}

sub vcl_miss {

if (req.request == "PURGE") {

purge;

error 404 "Purged.";

}

}

sub vcl_fetch {

## 确保所有Cache中的内容在TTL过期后5分钟内不被删除,以应对高并发的场合

set beresp.grace = 5m;

if (beresp.http.Set-Cookie) {

return (hit_for_pass);

}

## 如果返回头有Cache-Control,则删除Set-Cookie头

if (beresp.http.Cache-Control && beresp.ttl > 0s) {

set beresp.grace = 1m;

unset beresp.http.Set-Cookie;

}

## 不缓存大于10MB的资源文件

if (beresp.http.Content-Length ~ "[0-9]{8,}") {

set req.http.x-pipe = "1";

return (restart);

}

if (req.url ~ "\.(php|asp|aspx|jsp|do|ashx|shtml)($|\?)") {

return (hit_for_pass);

}

if (req.request == "GET" && req.url ~ "\.(css|js|bmp|png|gif|jpg|jpeg|ico|gz|tgz|bz2|tbz|zip|rar|mp3|mp4|ogg|swf|flv)($|\?)") {

unset beresp.http.set-cookie;

}

## 如果返回头没有Cache-Control,则标记为hit_for_pass,强制后续请求回源

if ((!beresp.http.Cache-Control && !beresp.http.Expires) ||

beresp.http.Pragma ~ "no-cache" ||

beresp.http.Cache-Control ~ "(no-cache|no-store|private)") {

set beresp.ttl = 120s;

return (hit_for_pass);

}

if (beresp.ttl <= 0s || beresp.http.Set-Cookie || beresp.http.Vary == "*") {

set beresp.ttl = 120s;

return (hit_for_pass);

}

## 对不同类型静态资源进行缓存时间设置

if (req.request == "GET" && req.url ~ "\.(css|js|bmp|png|gif|jpg|jpeg|ico)($|\?)") {

set beresp.ttl = 15m;

} elseif (req.request == "GET" && req.url ~ "\.(gz|tgz|bz2|tbz|zip|rar|mp3|mp4|ogg|swf|flv)($|\?)") {

set beresp.ttl = 30m;

} else {

set beresp.ttl = 10m;

}

return (deliver);

}

sub vcl_deliver {

if (obj.hits > 0) {

set resp.http.X-Cache = "HIT from " + req.http.host;

set resp.http.X-Cache-Hits = obj.hits;

} else {

set resp.http.X-Cache = "MISS from " + req.http.host;

}

## 去掉不必要的头信息

unset resp.http.X-Powered-By;

unset resp.http.Server;

unset resp.http.Via;

unset resp.http.X-Varnish;

unset resp.http.Age;

}

sub vcl_error {

if (obj.status == 503 && req.restarts < 5) {

set obj.http.X-Restarts = req.restarts;

return (restart);

}

}

sub vcl_init {

return (ok);

}

sub vcl_fini {

return (ok);

}


-----------------------------------------------------------------------------------------------------------------------------------------------


6、Varnish启动参数配置文件

# vim /usr/local/varnish/etc/varnish.conf

# Configuration file for varnish

#

# /etc/init.d/varnishd expects the variable $DAEMON_OPTS to be set from this

# shell script fragment.

#

# Maximum number of open files (for ulimit -n)

NFILES=131072

# Locked shared memory (for ulimit -l)

# Default log size is 82MB + header

MEMLOCK=82000

# Maximum number of threads (for ulimit -u)

NPROCS="unlimited"

# Set this to 1 to make init script reload try to switch vcl without restart.

# To make this work, you need to set the following variables

# explicit: VARNISH_VCL_CONF, VARNISH_ADMIN_LISTEN_ADDRESS,

# VARNISH_ADMIN_LISTEN_PORT, VARNISH_SECRET_FILE, or in short,

# use Alternative 3, Advanced configuration, below

RELOAD_VCL=1

#

# # Main configuration file. You probably want to change it :)

VARNISH_VCL_CONF=/usr/local/varnish/etc/varnish.vcl

#

# # Default address and port to bind to

# # Blank address means all IPv4 and IPv6 interfaces, otherwise specify

# # a host name, an IPv4 dotted quad, or an IPv6 address in brackets.

VARNISH_LISTEN_ADDRESS=0.0.0.0

VARNISH_LISTEN_PORT=80

#

# # Telnet admin interface listen address and port

VARNISH_ADMIN_LISTEN_ADDRESS=127.0.0.1

VARNISH_ADMIN_LISTEN_PORT=8080

#

# # Shared secret file for admin interface

#VARNISH_SECRET_FILE=/etc/varnish/secret

#

# # The minimum number of worker threads to start

VARNISH_MIN_THREADS=10

#

# # The Maximum number of worker threads to start

VARNISH_MAX_THREADS=5000

#

# # Idle timeout for worker threads

VARNISH_THREAD_TIMEOUT=120

#

# # Cache file location

VARNISH_STORAGE_FILE=/data/varnish/varnish_storage.bin

#

# # Cache file size: in bytes, optionally using k / M / G / T suffix,

# # or in percentage of available disk space using the % suffix.

VARNISH_STORAGE_SIZE=3G

#

# # Backend storage specification

#VARNISH_STORAGE="file,${VARNISH_STORAGE_FILE},${VARNISH_STORAGE_SIZE}"

VARNISH_STORAGE="malloc,${VARNISH_STORAGE_SIZE}"

#

# # Default TTL used when the backend does not specify one

VARNISH_TTL=120

#

# # Other optimization parameter

HTTP_RESP_HDR_LEN="http_resp_hdr_len=8192"

HTTP_MAX_HDR="http_max_hdr=256"

HTTP_REQ_HDR_LEN="http_req_hdr_len=8192"

THREAD_POOLS="thread_pools=8"

THREAD_POOL_MIN="thread_pool_min=50"

THREAD_POOL_MAX="thread_pool_max=5120"

THREAD_POOL_TIMEOUT="thread_pool_timeout=10"

LRU_INTERVAL="lru_interval=20"

LISTEN_DEPTH="listen_depth=1024"

#

# # DAEMON_OPTS is used by the init script.  If you add or remove options, make

# # sure you update this section, too.

DAEMON_OPTS="-a ${VARNISH_LISTEN_ADDRESS}:${VARNISH_LISTEN_PORT} \

-f ${VARNISH_VCL_CONF} \

-T ${VARNISH_ADMIN_LISTEN_ADDRESS}:${VARNISH_ADMIN_LISTEN_PORT} \

-t ${VARNISH_TTL} \

-w ${VARNISH_MIN_THREADS},${VARNISH_MAX_THREADS},${VARNISH_THREAD_TIMEOUT} \

-u nobody -g nogroup \

-s ${VARNISH_STORAGE} \

-p ${HTTP_RESP_HDR_LEN} \

-p ${HTTP_MAX_HDR} \

-p ${HTTP_REQ_HDR_LEN} \

-p ${THREAD_POOLS} \

-p ${THREAD_POOL_MIN} \

-p ${THREAD_POOL_MAX} \

-p ${THREAD_POOL_TIMEOUT} \

-p ${LRU_INTERVAL} \

-p ${LISTEN_DEPTH}"

内容版权声明:除非注明,否则皆为本站原创文章。

转载注明出处:https://www.heiqu.com/77c1658830e101f236ca1ac80968031e.html