[CDN 技术] 读squid权威指南笔记:squid集群(sibling模式)

Apr 7th, 2008

转载本站文章请注明,转载自:扶凯[http://www.php-oa.com]

本文链接: http://www.php-oa.com/2008/04/07/squid-sibling.html

 

认真读了几次squid权威指南,其中的第10章 与其他Squid会话 就是指的squid集群(sibling模式)的工作.

做了一些小的总结.环境squid2.6

配置成sibling时的工作原理.

默认的,squid首先发送大多数的请求到邻居cache,然后再到原始服务器.当ICP查询进来时,squid通过检查内存索引,能告知它是否有更新的、缓存的响应.squid会计算URI的MD5 hash值,并且在索引里查找它.假如没有找到,squid返回ICP_MISS消息.假如找到了,squid检查超时时间.假如目标没有刷新,squid返回ICP_MISS.对刷新的目标,squid返回ICP_HIT.

cache选择的顺序
选择新鲜cache目标的优先级是:
local cache
parent
sibling
direct


对ICP的理解

因为ICP会更加快,所以这选择ICP.
ICP是轻量级的目标定位协议,它作为Harvest项目的一部分而被发明.ICP客户发送查询消息到一个或多个ICP服务器,询问它们是否缓存了某个 URI(ICP查询仅包含URI,没有另外的请求头部.这让它很难精确的指示cache命中).每个服务器响应一个ICP_HIT(ICP命中),ICP_MISS(ICP丢失),或其他类型的ICP消息.ICP客户使用ICP响应里的信息来做转发决定.
ICP也得承受某些设计不足带来的责难:安全性,伸缩性,假命中,和请求方式的缺乏.该协议不包括任何安全机制.通常squid不能确认某个ICP消息是可信的;它依赖于基于地址的访问控制来过滤掉不想要的ICP消息.
ICP的伸缩性也很差.ICP消息的数量(和带宽)增长,与邻居cache的数量成正比.除非使用某种隔离机制,这实际上限制了你能使用的邻居cache的数量.我不推荐拥有超过5或6个邻居cache.
netdb主要用于ICP查询.netdb是设计来测量到原始服务器的远近

有用的命令
log_icp_queries on #是否记录指令来阻止记录icp的日志从这些查询
icp_hit_stale on
注意.它是告诉squid对任何cache住的目标,即使它是陈旧的,都返回ICP_HIT.这在父子关系的cache中很安全,但对姐妹关系的cache有问题.假如必须转发所有的假命中,激活icp_hit_stale就会给姐妹关系cache带来麻烦.这时ICP客户端cache_peer的allow-miss选项就变得有用.当设置了allow-miss选项时,squid忽略它发送到姐妹cache的HTTP请求里的only-if- cached指令.
假如激活了icp_hit_stale,必须确保miss_access不会拒绝来自姐妹cache的cache(源squid)丢失请求.

Cache摘要(Cache Digest)
Cache摘要基于由Pei Cao首先发布的一项技术,叫做摘要缓存.基本思路是用一个Bloom filter来表现cache内容.邻居cache下载其他每个cache的Bloom filter(也即摘要).然后,通过查询摘要来决定某个URI是否在邻居的cache里.

相对于ICP,cache摘要以空间交换时间.ICP查询浪费时间(延时),cache摘要浪费空间(内存,磁盘).在squid中,邻居的摘要完全存放在内存里.在一个典型的摘要里,每百万目标需要大约625KB的内存.

digest_generation on #开启.本参数指令控制squid是否产生自己的cache摘要

squid堆叠会有三个问题要注意
1.经历错误的http头,如服务不可达的中squid中的html错误.
2.假命中.
3.转发循环

转发循环的控制方法有
1.使用cache_peer_access指令来阻止这类循环.例如,假如邻居cache的IP地址是192.168.1.1,下面的行让squid不会产生转发循环:

acl FromNeighbor src 192.168.1.1
           
cache_peer_access the.neighbor.name deny FromNeighbor

2.转发循环在HTTP拦截里也能发生,特别是当拦截设备位于squid和原始服务器之间的路径上时.

Squid 通过检查Via头部里的主机名,来检测转发循环.假如2个协作cache有相同的主机名,实际上就会得到假转发循环.在该情形下,unique_hostname指令很有用.注意,假如Via头部被过滤掉了(例如使用headers_access指令),squid就不能检测到转发循环.
 

下面转一个别人对这个的笔记

1) cache_peer邻居分为parent(父邻居),sibling(子邻居).parent和sibling的区别在于父邻居能为子cache转发丢失的Cache,而子邻居不可能.(是可以的,但要设置miss_access)

2) cache_peer通过cache_peer_access和cache_peer_domain来控制邻居的访问.二者的区别在于前者一般需要先定义一个ACL而后者都直接匹配相应的域名就可以了.
如:
cache_peer 192.168.0.1 parent 3128 3130
acl AllowDomain dst www.abc.com
cache_peer_access AllowDomain 192.168.0.1
cache_peer_domain 192.168.0.1 parent .xyc.com

3) cache_peer通过never_direct,always_direct,hierarchy_stoplist等限制对邻居的访问.

4) squid与邻居cache的通信一般为先为never_direct,always_direct确定怎么样转发(根据相应的标识driect, never_direct标识为direct_no,always_direct标识为direct_yes即直接转发到原始服务器等等 direct_maybe详情见Squid中文权威指南10.10.1),接着Squid根据Squid的设置查看邻居的摘要是否命中(根据ICP或 HCTP的请求所发现的),若命中则立即放入转发列表中.这一切也依靠cache_peer_access,cache_peer_domain的.同时 squid检查netdb侦测的RTT是否最优,决定是否选择此邻居转发.

5)子邻居不转发任何命中丢失的请求,而父邻居可以转发,若Squid发现父邻居到原始服务器的RTT(往返时间)小于自已到原始服务器的RTT,将此请求转发给此父邻居.(RTT时间需借助Netdb选项的检测,对于父邻居的选择还有另外一些定义选项如:Weigh=N设置父邻居的权重来给予他更高的优先级)

ICP/HCTP和Cache摘要以及CARP一样,都是判断请求的URI是否在邻居中被命中.ICP是发送URL请求,Squid等待着邻居的回应,网络的延迟也是很大的,而且在姐妹Cache中假命中又显得很突出.No-Query,禁用ICP协议! Cache摘要是在邻居中生成摘要信息,摘要往往把反应在Cache中的信息,邻居下载每个Cache中的摘要,发送URI请求时查看URL是否在某个摘要中.

Del.icio.us Google书签 Digg Live Bookmark Technorati Furl Yahoo书签 Facebook 百度搜藏 新浪 ViVi 365Key 网摘 天极网摘 和讯网摘 博拉网 POCO 网摘 饭否 QQ 书签 Digbuzz 我挖网 Mister Wong
  1. ydf
    Dec 24th, 2009 at 03:34
    Reply | Quote | #1

    楼主,在晚上看到了很多转载这篇文章的,总算找到原创出处了。
    不过我看了后有一些疑问,希望你能指点迷津:
    问题就是关于,sibling 和 parent 的请求顺序
    文章说
    选择新鲜cache目标的优先级是:
    local cache
    parent
    sibling
    direct
    这个好像是那个中译本手册的作者blog说的,但是,文章中之前说默认是先发送到邻居squid,这里的邻居是指parent还是sibling?
    是按照先parent再sibling的顺序吗?
    但是一般来说如果parent里没有它会去查realserver吧?那这不是把sibling和parent的定义搞混了吗?

    按我的理解是,首先查local,没有?群发icp到sibling,如果没有命中,再查parent,parent没有,parent会查realserver,然后得到了最终结果了。

    不知道真正的顺序是怎样的,望兄台指点~谢谢

  2. admin
    Dec 24th, 2009 at 13:28
    Reply | Quote | #2

    这个方面我不太记的了,不是很关注这个,这种模式对性能影响太大

  3. ydf
    Dec 25th, 2009 at 02:55
    Reply | Quote | #3

    呵呵,谢谢~ 是的这个模式是不太好
    我之前的想法是:sibling用大内存的内存盘作为一级cache,然后parent是二级的缓存,用disk坐缓存,sibling共用一两个parent squid,这样可以利用一级内存cache来提高效率。后来还是用比较通用的方法,在查询squid前用程序或者nginx 做url hash指定 squid,这样命中率会明显提高些,也省去了squid之间的耦合。