深入探讨Varnish缓存命中率也许你还在为刚才动态内容获得7336.76 reqs/s的吞吐率感到振奋,等等,理想和现实是有差距的,你要忍受现实的残酷,别忘了,我们压力测试中的动态内容都处于全缓存情况下,也就是每次请求都命中缓存,这在现实中往往是不可能的。 首先,缓存区空间大小是有限的,而我们的站点可能有大量的内容需要被缓存,而不像前边压力测试时只有一个内容。一旦缓存区被装满,那么缓存管理器便会淘汰一些它认为不再需要的缓存内容,比如通过LRU(最近最少使用算法)将使用频率较低的缓存内容淘汰出去,但是,这里判断“不常使用”的标准是不严格的,也许被淘汰的内容就是你将要访问的下一个内容,这便影响了它的命中率。 其次,缓存的过期时间也影响到它的命中率,假如有效期很短,为10秒,那么最少10秒便会有一次无法命中。 还有,有些内容可能根本没有被代理服务器缓存,比如这些内容包含了set-cookie等不可缓存的HTTP头信息,导致反向代理不会缓存它们,并且在浏览器请求它们的时候也不会去缓存区查找。这是影响命中率的一个重要因素,但往往被我们所忽略。 幸运的是,这些问题我们都可以轻松的解决,前提是,我们需要了解反向代理缓存的实时工作状态,比如Varnish便提供了一个命令行的状态监控程序varnishstat,我们打开它,便看到了当前时刻的状态,如下: client_conn 9908723 94.05 Client connections accepted client_drop 0 0.00 Connection dropped, no sess/wrk client_req 16433490 155.99 Client requests received cache_hit 8751732 83.07 Cache hits cache_hitpass 42592 0.40 Cache hits for pass cache_miss 7573389 71.89 Cache misses backend_conn 3889845 36.92 Backend conn. success backend_unhealthy 220 0.00 Backend conn. not attempted backend_busy 0 0.00 Backend conn. too many backend_fail 4536 0.04 Backend conn. failures backend_reuse 3780212 35.88 Backend conn. reuses backend_toolate 3866687 36.70 Backend conn. was closed backend_recycle 7646677 72.58 Backend conn. recycles backend_unused 0 0.00 Backend conn. unused fetch_head 57 0.00 Fetch head fetch_length 155097 1.47 Fetch with Length fetch_chunked 7508522 71.27 Fetch chunked fetch_eof 0 0.00 Fetch EOF fetch_bad 0 0.00 Fetch had bad headers fetch_close 3982 0.04 Fetch wanted close fetch_oldhttp 0 0.00 Fetch pre HTTP/1.1 closed fetch_zero 0 0.00 Fetch zero len fetch_failed 0 0.00 Fetch failed n_sess_mem 1033 . N struct sess_mem n_sess 633 . N struct sess n_object 1016443 . N struct object n_vampireobject 0 . N unresurrected objects n_objectcore 1017564 . N struct objectcore n_objecthead 982903 . N struct objecthead n_smf 2647421 . N struct smf n_smf_frag 622470 . N small free smf n_smf_large 3 . N large free smf n_vbe_conn 12 . N struct vbe_conn n_wrk 8000 . N worker threads n_wrk_create 8000 0.08 N worker threads created n_wrk_failed 0 0.00 N worker threads not created n_wrk_max 11021 0.10 N worker threads limited n_wrk_queue 0 0.00 N queued work requests n_wrk_overflow 2441 0.02 N overflowed work requests n_wrk_drop 0 0.00 N dropped work requests n_backend 4 . N backends n_expired 6344546 . N expired objects n_lru_nuked 183957 . N LRU nuked objects n_lru_saved 0 . N LRU saved objects n_lru_moved 3692170 . N LRU moved objects n_deathrow 0 . N objects on deathrow losthdr 84 0.00 HTTP header overflows n_objsendfile 0 0.00 Objects sent with sendfile n_objwrite 15466812 146.81 Objects sent with write n_objoverflow 0 0.00 Objects overflowing workspace s_sess 9906155 94.03 Total Sessions s_req 16433490 155.99 Total Requests s_pipe 37 0.00 Total pipe s_pass 108252 1.03 Total pass s_fetch 7667658 72.78 Total fetch s_hdrbytes 7187255662 68221.35 Total header bytes s_bodybytes 111592032839 1059230.32 Total body bytes sess_closed 1905544 18.09 Session Closed sess_pipeline 0 0.00 Session Pipeline sess_readahead 0 0.00 Session Read Ahead sess_linger 15277717 145.02 Session Linger sess_herd 13547370 128.59 Session herd shm_records 1028855796 9765.89 SHM records shm_writes 77957008 739.97 SHM writes shm_flushes 131005 1.24 SHM flushes due to overflow shm_cont 144281 1.37 SHM MTX contention shm_cycles 427 0.00 SHM cycles through buffer sm_nreq 15306717 145.29 allocator requests sm_nobj 2024948 . outstanding allocations sm_balloc 13595295744 . bytes allocated sm_bfree 40091795456 . bytes free sma_nreq 0 0.00 SMA allocator requests sma_nobj 0 . SMA outstanding allocations sma_nbytes 0 . SMA outstanding bytes sma_balloc 0 . SMA bytes allocated sma_bfree 0 . SMA bytes free sms_nreq 14062 0.13 SMS allocator requests sms_nobj 0 . SMS outstanding allocations sms_nbytes 487 . SMS outstanding bytes sms_balloc 6844837 . SMS bytes allocated sms_bfree 6846298 . SMS bytes freed backend_req 7668789 72.79 Backend requests made n_vcl 1 0.00 N vcl total n_vcl_avail 1 0.00 N vcl available n_vcl_discard 0 0.00 N vcl discarded n_purge 740577 . N total active purges n_purge_add 905392 8.59 N new purges added n_purge_retire 164815 1.56 N old purges deleted n_purge_obj_test 13397373 127.17 N objects tested n_purge_re_test 131875330367 1251759.15 N regexps tested against n_purge_dups 240655 2.28 N duplicate purges removed hcb_nolock 0 0.00 HCB Lookups without lock hcb_lock 0 0.00 HCB Lookups with lock hcb_insert 0 0.00 HCB Inserts esi_parse 0 0.00 Objects ESI parsed (unlock) esi_errors 0 0.00 ESI parse errors (unlock) accept_fail 2553 0.02 Accept failures client_drop_late 0 0.00 Connection dropped late uptime 105352 1.00 Client uptime
N struct object 当前被cache的条目 Client requests received 代表到目前为止,浏览器向反向代理服务器发送的HTTP请求累积次数,由于可能使用长连接,所以它可能会大于上边的Client connections accepted。 Cache hits 代表在这些请求中,反向代理服务器在缓存区中查找并且命中缓存的次数。 Cache misses 代表在这些请求中,反向代理服务器在缓存区中查找但是没有命中缓存的次数。 N expired objects 代表过期的缓存内容个数 N LRU nuked objects 由于cache空间满而不得不扔掉的cache条目,如果这个数字是0,就没必要增加cache的大小了。 N LRU moved objects 代表被淘汰的缓存内容个数 Total header bytes 代表缓存区中所有缓存内容的HTTP头信息长度 Total body bytes 代表缓存区中所有缓存内容的正文长度 4+10:37:44 my.server.com Hitrate ratio: 1 1 1 Hitrate avg: 0.0364 0.0364 0.0364 2324 0.00 0.01 Client connections accepted 6191 0.00 0.02 Client requests received 12 0.00 0.00 Cache hits 7 0.00 0.00 Cache hits for pass 318 0.00 0.00 Cache misses 6179 0.00 0.02 Backend connections success 0 0.00 0.00 Backend connections not attempted 0 0.00 0.00 Backend connections too many 0 0.00 0.00 Backend connections failures 4057 0.00 0.01 Backend connections reuses 6151 0.00 0.02 Backend connections recycles ... 我们看到,Varnish一共处理了来自浏览器的6191个请求,其中命中缓存的有12个,真是太少了,而没有命中缓存的有318个,奇怪,剩下的那么多请求根本就没有去缓存区检查,也就是说,Varnish认为那些内容不能被缓存。不能被缓存总是有原因的,你需要根据反向代理缓存的规则,来进一步的检查。而我们这个例子中,都是cookies惹得祸,因为在wordpress中由于我们会安装一些各种各样的插件,有些插件会使得wordpress的每个页面都带有写入cookies的set-cookie标记,而我们前边在vcl_fetch函数中禁止了这类内容的缓存,问题就在这里了,我们希望将这些多余的cookie关闭掉,但是,wordpress自身的登录和管理页面是需要cookies才可以正常工作的,所以我们还需要让反向代理不缓存这些页面,我们使用以下VCL配置: sub vcl_recv { if (!(req.url ~ "wp-(login|admin)")) { unset req.http.cookie; } } sub vcl_fetch { if (!(req.url ~ "wp-(login|admin)")) { unset obj.http.set-cookie; } } 可以看到,除了wordpress自身的登录和管理页面以外,我们将其它内容的HTTP头信息中有关cookie的标记全部都清除掉,这使得Varnish可以将大部分内容缓存起来,提高缓存命中率,同时不影响我们登录和管理wordpress。 |
|