memcached+varnish

memcached

緩存服務器:

1.緩存:cache,無持久存儲功能

2.行掛失緩存bypass,而不是代理式緩存

3.僅提供緩存功能,存什麼,怎麼存全有客戶端決定

4.k/v cache,只能存儲可序列化數據

5.存儲項是非常簡單的:key,value,flag,expire time(過期時間)單數上限:1M

6.功能的實現一把依賴於memcached,一半是client

7.不能高可用,掛了緩存就丟失了

8.O(1)的執行效率

9.分佈式緩存互不通信的分佈式集羣

分佈式系統請求路由方法:取膜法,一致性哈希算法

10.緩存耗盡時基於LRU(最近最少使用)清理

緩存過期項:惰性清理機制,新的直接覆蓋舊的

memcached協議

客戶端要擁有連接memcached的適配器php-memcached


yum安裝就好


配置文件/etc/sysconfig/memcached

默認監聽11211/tcp,11211/udp


主程序 /usr/bin/memcached


協議格式:

文本格式

二進制格式


telnet文本交互:


常用命令

統計類:stats items | slabs |sizes


存儲類:set,add,replace,append,perpend


獲取數據類:get,delete,incr/decr


清空:flesh_all



add mykey 0 30 5  添加mykey

hello  內容hello

set mykey 0 30 5  設置mykey的值

hello

get mykey  獲取mykey值


 0:標誌位

   30:緩存ttl值時長,30秒後無法獲得

      5:整個數據的長度


append mykey 0 300 11   追加內容,注意長度的修改,是指添加了多少個字符而不是添加到


prepend mkkey 0 300 3  同上,只不過是在前邊添加,想要兩個值之間帶空格就在字符數多幾個字符



incr key_name #  將key的值+1  key值要是數字

decr          #           -1


(常用於微博微信之類的贊轉發之類的計數)


flush all  清空緩存




程序常用選項


-m #:緩存空間大小,單位mb默認64

-c #:併發連接數,默認1024

-u username:程序運行者身份,一般要用普通用戶

-p Port:監聽的tcp端口

-u Port:監聽的udp端口

-l ip_addr:監聽的IP地址,默認本機所有IP地址

-M :一旦緩存空間耗盡的時候,想請求存儲緩存項換回錯誤信息,而非使用默認的lru算法

-f factor :用來指明chunk的增長因子,默認是1.25

-vv:詳細內容

-t #:線程數量,默認爲4,最好<cpu數



啓動服務一般選項


memcached -u    -p    -m   -c   $options


在環境文件中配置後,直接memcached就行

/etc/sysconfig/memcached

options項寫-a xxx之類的就行













memcached的認證功能

默認沒有認證機制,可以藉助SASL進行認證


SASL:簡單安全認證層



API:C++:libmemcached(c語言)

php:memcached:php-pecl-memcached

 memcache :php-pecl-memcache















Varnish:web cache (page cache)


中小型web應用架構 圖



線程限制是針對域名來說的,單域名雙線程,所以,多個域名也可以提升性能



程序運行具有局部性特徵

空間局部性:

某一個數據被訪問過,離他較近的數據也有可能被訪問到

時間局部性:

某一個數據被訪問到,隨後有可能很快會被再次訪問到


熱區:一段時間內會有一個特別流行的數據,80%的訪問量被20%的數據承載(尤其是電商,流行商品,淘寶爆款),這些就叫熱區,其實就是局部性的表現,體現出緩存的價值,因爲緩存主要存放的及時熱區數據


時效性:緩存是會過期的,所以要具備過期處理邏輯

緩存清理:

過期清理

緩存溢出清理:LRU最近最少使用




緩存就是利用空間換取時間,在較短的時間內快速獲得結果


緩存命中率:命中次數/未命中次數+命中次數

(0,1)


頁面命中率:基於頁面數量進行衡量

字節命中率:基於頁面的大小,體積進行衡量

以上要有一個是收益OK的,那麼緩存就是有效的



緩存與否:

私有數據:private,例如郵箱等:只能放在私有緩存中

公共數據:public,例如電商的商品頁面:放在私有緩存和公有緩存


緩存種類:

私有緩存:瀏覽器緩存

公有緩存:reverse proxy,cache


如何分辨私有公有:

帶有某個標籤或者是存在cookie的都是私有的,沒有的就被認定是公有的


緩存處理的步驟


接受請求--->解析請求(提取請求首部中的URL及其他首部)---->查詢緩存--->新鮮度檢測(是不是在有效期)--->檢查元數據是不是改變,如果沒改變--->構建響應報文-->發送響應--->記錄日誌(類似於httpd的combined)



過期檢查機制:

每個緩存都是會有服務器加一個過期時間.在這個時間內都是有緩存返回的,如果過期了或者沒有緩存,就反代到後端服務器,後端服務器發送數據和過期時間給緩存和請求


首部:HTTP/1.0

Expire:絕對時間:xxx-xxx

HTTP/1.1

Cache-Control:maxage=相對時長,過多長時間過期

Cache-Control:s-maxage=公共緩存時長


條件檢查機制:validation

(1)LASTMODIFIED:最近修改時間


  IF MOFIFIED SINCE:從上次開始是不是修改過時間


  請求數據到緩存服務器上,如果超出有效時間,緩存服務器向後端服務器發送一個請求報文,詢問是不是修改了,如果是,就由後端服務器來發送數據,沒有的話就是有緩存發送


(2)Etag:資源標籤

  if-none-match:標籤有沒變換 


  基本上和上邊相同,只是尋問的是標籤有沒有變化



兩者結合:超時有效時長的,向後端服務器發送條件檢查




開源解決方案:

squid:

varnish:在非常大的併發連接數下,varnish不是很穩定



varnish:絕大多數站點都是varnish www.varnish-cache.org 最新穩定版本4.1.3 (分支5.0|4.1|4.0) 




Architecture        圖









組織架構

management進程

child/cache進程:包含多種類型的線程

accept worker expiry

shared memeory log:

統計數據的計數器

日誌區域


配置接口:VCL

VCL complier--->c complier------->shared object


上午第二節課



環境文件

配置文件

/etc/varnish/default.vcl配置緩存工作(child/cache)

/etc/varnish/varnish.params配置varnish自身(端口之類的)

主程序

CLI interface

varnishadm


shared log

/usr/bin/varnishhist

/usr/bin/varnishlog

/usr/bin/varnishncsa

/usr/bin/varnishstat

/usr/bin/varnishtest

/usr/bin/varnishtop



varnishtest:模擬varnish的客戶端,測試varnish的工作是不是正常


systemd unitfile

varnish.service


varnishlog

varnishncsa:日誌持久化服務,每個多長時間讀取次日誌



varnish的緩存存儲機制

(1)malloc[,size]

內存存儲

(2)file[path[,size[,granularity]]]

文件存儲,黑盒,重啓後緩存失效

(3)persistent,path,size

文件存儲,黑盒,重啓不失效,但是還在測試




varnish程序的選項

(1)程序選項 /etc/varnish/varnish.params

-a IP地址:port

服務接口,不能是127,默認6081

-T IP地址:port

管理接口,默認6082

-s [name]=type[,options]

定義緩存存儲機制

-u user

-g group

定義運行身份

-f config

VCL配置文件

-F 

前臺運行

(2)運行時參數(運行時可以更改的)

-p param=value

-r param[,param..]運行時不可以更改,只讀


大多數運行參數都有默認值不用設定,必要設定時候要在varnish.params定義,在程勳運行前定義

在底下的DEMON_OPTS

例如:

#DAEMON_OPTS="-p thread_pool_min=5 -p thread_pool_max=500 -p thread_pool_timeout=300"



具體配置


6081可以改

6082是管理接口,也可以改


#DAEMON_OPTS="-p thread_pool_min=5 -p thread_pool_max=500 -p thread_pool_timeout=300"

最小/最大線程池數量,超時時間



VARNISH_STORAGE="file,/var/lib/varnish/varnish_storage.bin,1G"

文件存儲


VARNISH_STORAGE="malloc,1G"

內存存儲



事實上大多時候都不需要更改直接使用,主要還是VCL



varnish_reload_vcl:vcl配置文件重載程序




varnishadm -S /etc/varnish/sercet -T address:port


help獲取命令列表


配置文件相關

vcl.list:列出vcl文件有哪些

load:裝載,加載並編譯


vcl.load testconfig1 default.vcl


use:激活


vcl.use testconfig1  激活了,生效了


discard:刪除,最好先激活另一個後在刪除上一個

運行時參數

param.show:顯示參數列表

 show<param>顯示某個參數配置

 set<PARAM><VALUE>設定


緩存存儲

storage.list


後端服務器:

backend.list



VCL:域專有類型的配置語言

state engine:狀態引擎


VCL有多個狀態引擎.且之間存在相關性,但是彼此間互相隔離,每個狀態引擎可使用return指明關聯至那個下一級引擎













vcl_recv--->vcl_pipe

收到後不知道做什麼直接送到後端

vcl_recv--->vcl_error

收到後不允許給他數據或者直接請求就是錯的



vcl_pass:多加的處理邏輯,可以額外做一些處理的設定


vcl_purge:緩存的修剪



varnish 4:

vcl_recv ---->vcl_hash

(1)hit:vcl_hit--->vcl_deliver

(2)pass,hit for pass:vcl_pass--->vcl_backend_fetch-->_response-->vcl_deliver

(3)miss:vcl_miss--->[vcl_pass--->]vcl_backend_fetch-->_response-->vcl_deliver

(4)purge:vcl_purge--->vcl_synth

(5)pipe:vcl_pipe

(6)busy:vcl_waiting




vcl語法格式

(1)支持註釋符

//:單行註釋

/*...*/:多行註釋

#:註釋

(2)sub $name:定義子例程;sub vcl_recv{..}只對vcl_recv有效

(3)不支持循環,但是支持條件判斷

(4)有大量的內建變量,生效位置有特定要求

(5)使用終止語句return決定下一個狀態引擎;但是沒有返回值

(6)操作符

=:賦值

==:等值判斷

!:取反

~:匹配

&&:邏輯與

||:邏輯或

>,<,>=,<=

(7)語句使用;結尾




變量類型

內建變量:

req.*:request,由客戶端發來的請求報文相關的衆多數據

req.http.*

req.http.User-Agent:客戶端瀏覽器類型

.Referer:從哪裏引用過來的

.method:get等

各引擎都可用,都是隻讀只寫

bereq.*:backend 由varnish發給後端的請求

berep.http.*

beresp.*:有後端響應給varnish的

beresp.http.*

obj.*:發送給緩存服務器的

resp.*:響應給前端請求的



常用變量

bereq.*:

bereq.http.HEADERS

bereq.request:請求方法

.url:請求的url

.proto:請求的協議版本

.backend:指明要調用的後端主機

beresp.*:

bereq.http.HEADERS

 .status:響應的狀態碼

 .proto:協議版本

 .backend.name:BE主機的主機名

 .ttl:BE主機響應內容的餘下的可緩存時長

obj.*:

obj.hits:當前正在訪問的緩存的命中次數(這一次)

.ttl:對象的ttl值,緩存時長


server.*

server.ip

 .hostname

client.*

.ip


下午第一節課

set:設置一個變量

unset:取消一個變量



用戶自定義:

事例1:強制對某類資源的請求不檢查緩存

vcl_recv{

if (req.url ~ "(?i)^/(login|admin)") {

return(pass);

}

}

                    


事例2:對於特定類型的資源,例如公開的圖片等,取消其私有標誌,並強行設定器可以由varnish緩存的時長


vcl_backend_response{

if (beresp.http.caceh-control !~ "s-maxage") {

if (bereq.url ~ "(?i)\.(jpg|jpeg|png|gif|css|js)$") {

unset beresp.http.Set-Cppkie;

set beresp.ttl=3600s;

}

}


}

                



緩存對象的修剪:purge ban


purge:


(1)sub vcl_purge {

return(synth(200,"purged自己定義"));

}


(2)要在recv中定義那些請求到purge中

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

return(purge);

}


(3)定義訪問控制列表

acl purgers {

"127.0.0.0"/8;

"172.16.0.0"/16;

}


sub vcl_recv {

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

if(!dlient.ip ~ purgers){

return(405,"Purging not allowed for" = + client.ip));

}

}

}




如何設定使用多個後端主機:

backend name {

.host = " ";

.port = " ";

}


sub vcl_recv {

if (req.url ~ "(?i)\.php$") {

set req.backend_hint = appsrv;

} else {

set req.backend_hint = default;

}


}

}




後端多個主機不做分離式做負載均衡


varnish做director

varnish module

使用前要先導入

import directors



sub vcl_init:處理任何請求之前要執行的vcl代碼,主要用於初始化VMODs

   vcl_fini:所有的請求都退出後,在vcl配置被丟棄的時候處理調用,主要用於清理VMODs


   調度方法:random,hash,round_robin()


   import directors;


   sub vcl_init{

   newbar = director.round_robin();

   自定義組名          .調度算法

   bar.add_backend(server1);

   bar.add_backend(server2);

   }



   sub vcl_recv {

    set req.backend_hint = newbar.backend();

   }




BE健康狀態檢查


backend BE_NAME{

.host

.port

.probe={

.url:檢測要請求的url,默認爲主頁

.request:指明打出請求報文怎麼發

.timeout:檢測的超時時長

.inteval:檢查頻度,多長時間檢查一次

.window = #:基於最近的多少次檢查判斷健康狀態

.threshold = #:至少幾次是成功才認定是健康的

.expected_response:期望的響應碼,默認是200

}

}


也可以

probe NAME {

.url:檢測要請求的url,默認爲主頁

.request:指明打出請求報文怎麼發

.timeout:檢測的超時時長

.inteval:檢查頻度,多長時間檢查一次

.window = #:基於最近的多少次檢查判斷健康狀態

.threshold = #:至少幾次是成功才認定是健康的

.expected_response:期望的響應碼,默認是200

}


然後在.host下邊

.probe = NAME;






varnish的運行時參數:查看參數 param.show -l

線程模型:

cache-worker

cache-main

ban lurker

acceptor

epoll/kqueue* 

...



線程相關的參數

在線程池內部,其每一個請求有一個線程處理;其worker線程的最大數決定了varnish的併發響應能力


thread_pools :線程池個數,小於等於cpu核心數

thread_pool_max:調整每個線程池的最大工作線程數量,默認5000個

最大併發數上邊兩個相乘


thread_pool_min:......


param.set thread_poll_max 1000(但是重啓不保存,編輯配置文件)



#DAEMON_OPTS="-p thread_pool_min=5 -p thread_pool_max=500 -p thread_pool_timeout=300"


記住要用-p指定,每一個都要,不可以一個-p指多個參數


thread_poll_timeout:默認10秒


  _add_delay:創建線程之間要不要有間隔,默認0


  _destroy_delay:多長時間清理一個線程,默認10毫秒






客戶端命令的使用

/usr/bin/varnishhist

/usr/bin/varnishlog

/usr/bin/varnishncsa

/usr/bin/varnishstat

/usr/bin/varnishtest

/usr/bin/varnishtop

日誌區域

計數器


日誌信息




/usr/bin/varnishstat查看統計數據

varnishstat -1:持續刷新類似watch -n

-f:指向顯示那些字段,-1出來的都是字段

-1 -f xxxx

-l:那些字段可以跟-f使用


MAIN.cache_miss

MAIN.cache_hit  重點關注的兩項,可以計算命中率







/usr/bin/varnishtop顯示日誌,對日誌做排序

varnishtop -1:持續性顯示

  -i:查看指定標籤信息,標籤名去-1信息裏邊找,多個","隔開

  -I:同-i,但是支持正表

  -x:排除列表,不顯示某個標籤

  -X:支持正表的-x



/usr/bin/varnishlog正兒八經的顯示日誌本身的

varnishlog


/usr/bin/varnishncsa將日誌以combined的格式顯示,就是httpd的日誌格式


varnishncsa -f:指定日誌記錄什麼,就是httpd的那些%的東西


想保存起來就執行/usr/lib/systemd/system/varnishncsa.service


systemctl start varnishncsa.service




vcl可以做url重寫,使用一個內建函數




一個客戶端有多個域名,使用hash算法來命中

hash_data():指明hash計算的數據,減少差異以提升命中率

regsub(str,regex,sub):正則表達式的模式替換,吧str中第一次被regex匹配到的替換爲sub

regsuball():全部替換,主要用於url重寫


return()

ban(expression):清理緩存,後跟普通表達式

ban_url(regex):清理緩存,後跟正表


最後一節課最後的hash_data


synth(status,"string"):purge,一次只清理一個url緩存對象






實踐作業

前段nginx將用戶請求調度到兩個varnish,並保證命中率,hash他的url,map和consistent的hash算法,varnish要方向代理用戶請求到後端主機,後端主機上部署以個wordpress,並且把請求分發到三個主機上的時候有什麼不同








生成靜態頁面,當服務器掛了,就定到靜態頁面服務器上,降級xx的概念



博客作業,以上所有內容




haproxy和tomcat





































發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章