设为首页 收藏本站
查看: 929|回复: 0

[经验分享] Squid中的时间和过期

[复制链接]

尚未签到

发表于 2018-12-26 08:15:27 | 显示全部楼层 |阅读模式
  Squid作为一个缓存工具,其核心的功能就是缓存。那么判断一个obj是否缓存以及缓存多久就是极为重要的工作。事实上目前我们SQUID开发的很多内容都是和这个问题有关。Squid在过期时间处理上有其独有的细致一面:不可避免的就会引入复杂的一面。理解squid就必须理解过期时间处理。这也是用好squid的一个前提。
1. squid过期相关的基础知识
1.1 概述
  谈论squid就不得不谈论HTTP,谈论HTTP则必须提及RFC2616.
  RFC2616文档(http1.1协议)定义了一系列的规则,我们需要就这些规则来指导我们的行为(也许跟据需求做相反的事情)。
  HTTP缓存被定义为:除去许多情况下的对发送请求的需求,和除去在其他许多情况下发送完整响应的需求。前者需要控制不必要的网络奔波去下载不需要的东西,而后者是控制对不需要的东西仅请求不下载。这就牵扯到过期机制的两个组成方式:截止机制和验证机制。
  截止机制:通俗说就是过期时间。HTTP缓存效率最大值的表现。如果一个资源(URI)仅仅从本地缓存目录中提取而产生响应无疑是最省力的。换句话说,缓存能够不必首先联系服务器而返回响应。
  验证机制:和截止机制相关的。即在截止机制中设置了一个过期时间。当超过这个时间时,会收到一个带有验证请求的访问发往缓存而不是一个正常请求。如果缓存中的副本未有变化,则采用304Not Modified来说明此问题。否则必须回复完整响应(包含实体body)。
1.2 Date与 Expires
  Date和Expires都是表示绝对时间的概念,其不同点在于:
  Date给出的是响应发出的绝对时间。
  格式为:
“Date:” HTTP-date  Expires给出响应的内容过期的绝对时间。
  格式为:
“Expires:” HTTP-date  例如,今天是3月25日,apache源站设置了
ExpiresActive on  ExpiresDefault “access plus 1 month”
  那么请求该源站返回的header中就应该包括
Expires: Fri, 24 Apr 2009 08:00:57 GMT  注意:
  a. Date与Expires都是绝对时间。
  b. Date与Expires通常是格林尼治标准时间(如果后面带有GMT),也就是比北京时间早8个小时。
1.3 Age与max-age
  这两个概念是比较容易搞混的。其相同点是:
  a. 都是响应头的一部分
  b. 都是一个时间长度,以秒为单位
  但主要是不同点:
  其中age是指:自从这个响应在源站服务器上生成以来(而不是源站内容修改以来!!),到现在所经历的秒数。
  Age通常只对cache才有意义。
  其格式为:
“Age:”age-value  max-age是指:一个响应被源站发出后,在cache当中存活的时间,换句话说,一个响应的Age值如果超过了max-age,就认为这个响应是过期的。
  当然,max-age也是对于cache才有意义。
  其格式为:
“Cache-control: max-age=” max-age-value  再次重申:max-age比Expires更加优先!
1.4 If-Modified-Since与Last-Modified
  如果一个内容真的过期了,怎么办?从源站重新下载吗?
  当然不。http协议对于过期的内容的处理,是先到源站验证一下,这个内容有没有发生改变,如果没有改变过,当然就不用重新下载了。这种验证是通过 If-Modified-Since等一系列http头实现的。
  If-Modified-Since是http请求头的一部分,它表示客户端向源站询问“这个内容自从x年x月x日x时起,是否变过?”
  其格式为:
“If-Modified-Since:” HTTP-date  如果源站发现该内容变过,则会返回一个200OK的响应,并把新的内容发回来给客户端。
  如果源站发现内容没有变过,则会返回一个304的响应,告诉客户端“没有改变过,你的内容还是可以用的”,这种情况下就不用发送内容了,可以大大节省传输带宽。
  注意:
  a)如果客户端发的If-Modified-Since后面的日期是非法的日期,源站将直接返回200OK+新内容。
  b) If-Modified-Since后面跟的日期是客户端上一次接到的响应中,Last-Modified的值。
  Last-Modified是响应头的一部分,是源站给出的,一个内容在源站上最终更新的时间。
  对于静态内容,Last-Modified是文件的更新时间,对于动态内容,取决于源站的具体实现。
  其格式为:
“Last-Modified:” HTTP-date1.5 Etag与If-None-Match
  有的时候,Last-Modified 与 If-Modified-Since不能够可靠地标示内容的改变,这就需要Etag等更加可靠的打标签的机制。
  Etag是响应头的一部分,是源站对内容所打的一个标签,用来标示这个文件,这个标签当且仅当内容变化才会变化,就像md5码一样。
  与md5码不同的是,打Etag不需要读取整个文件的内容,比md5消耗的资源要少得多。
  Etag起到的作用跟Last-Modified差不多,都是标示内容的变化,只是比Last-Modified更可靠。
  If-None-Match是请求头的一部分,它表示客户端向源站询问“这个内容的标签还是不是xxxxxx?
  如果源站发现该内容变过,则会返回一个200OK的响应,并把新的内容发回来给客户端。
  如果源站发现内容没有变过,则会返回一个304的响应,告诉客户端“没有改变过,你的内容还是可以用的”,这种情况下就不用发送内容了,可以大大节省传输带宽。
2. 目前过期时间部分我们的squid是如何实现(修改)的
2.1 squid碰到了什么困境
  如上的squid描述我们可以看出squid在处理过期时间方面的支持是很强大也很全面的。但我们仍然发现一些因源站给出错误header导致我们缓存过期的问题(通常出现此问题即出现连续过期)。很多客户囿于技术/策略问题,将控制权交给我们。此时,我们就需要squid理顺过期关系进行自维护的处理。
2.2 mod_use_server_date做了什么
  mod_use_server_date做的最重要的一件事情,就是确定一个obj的“起始”时间。知道一个obj从什么时候“出生”,然后知道其生存时间,即可完全决定其在squid的生存时间。第二件重要的事情就是“推定”经过其他squid设备的obj的“起始”时间。下面画图说明此问题:
  如上图所示,在菱形时间点发生了请求,下层去获取OBJ进入squid群组和过期时间。
  从上图我们可以发现其中核心功能实现是max-age(或者由expire和date计算得到)。而多层squid之间的交流主要靠AGE。也就是说:
Max-age(或者由expires-date计算得到)决定OBJ生存时长  Age决定OBJ的出生时间点
2.3 expires和refresh_pattern哪个在生效
  如上(2.2节)是use_server_date的设计大意。那么在复杂的网络条件下,如何知道“expires功能生效呢,还是refresh_pattern策略生效呢?
  要回答这个问题,首先要确认的是:
配置的refresh_pattern, URL对应行是否配置override-expire:  1)如果配置了,refresh_pattern生效,忽略过期时间
  2)如果没有,先检查过期时间,再检查refresh_pattern
  目前我们的默认配置都是
  ignore-reload 和override-lastmod(稍后讲解refresh_pattern时解释)所以可以不用注意如上问题。
  如果确认如上refresh_pattern没有配置override-expire,则遵循如下规则:
如果源站给的信息可以计算出OBJ生存时间,则OBJ不走refresh_pattern  源站给的header可能:
  1)有max_age
  2)有expires和date
  3)仅有expires
  上述3者关系是顺序优先匹配,如果1符合就不需要2、3,同理2符合就不需要3.
  满足此3项的为可计算生存时间的OBJ.
  有如上3个条件符合所得出的过期时间也不尽相同。
  squid的处理策略,
  如果源站给的Header符合:
  1)有max_age
  2)有expires和date
  则结果相同,过期时间是squid最初服务时间+max-age或者是squid最初服务时间+源站expire-源站date。
  如果源站给的Header符合:
  3)仅有expires
  则以此header数据为准,绝对时间设置过期。
3. 目前的refresh_pattern使用情况和存在问题
3.1 refresh_pattern概述
  refresh_pattern是squid.conf中关于过期的一种配置项。
  通常如下格式:
refresh_pattern -i  ^http    1440   0%  1440   ignore-reload override-lastmod  我们可以分解一行配置行为:
  l  功能节名:refresh_pattern
  l  URL正则匹配区:-i  ^http (-I含义为是否区分大小写)
  l  Age&lm-factore区:1440   0%  1440
  l  Options区:ignore-reload override-lastmod等
  前二区目前没有疑问,下面就后二区详细介绍。
3.2 Age&lm-factore区
  本区有3个配置节 分别为 min percentage max。
  Min:是指一个object在缺少明确的Expires的情况下,能够确定的在cache中被认为新鲜分钟数(小于此值肯定是新鲜的)。这个参数推荐设为0,否则会造成动态应用中的内容被不正确地缓存住。
  Max:是指一个object在缺少明确的Expires的情况下,在 cache中可能被认为新鲜的分钟数的最大值(大于此值肯定是过期的)
  percentage是指,一个object在缺少明确的Expires的情况下,它的LM-factor的最大值(LM-factor超过此值则认为过期,否则新鲜)
LM-factor= (当前时间-到达cache的时间) / (到达cache的时间 – Last-Modified) * 100%  关于LM-factor,在《Squid: The Definitive Guide》一书中,有一个更加形象的图来说明这个概念。
  LM-factor是HTTP协议中关于Last-Modifed时间参与过期计算的一个模糊处理过期时间的方式(如果不指明某URL过期时间)。显然在我们目前的应用下,是不该使用此项模糊策略的。我们目前线上机器配置percentage为0%,已经省略此功能节。
3.2 Options区
  我们squid使用squid2.7,其options区目前可以有:

  • override-expire: 强制min在expires前生效。
  • override-lastmod: 强制min在lm-factor之前生效(在expire之后)。
  • reload-into-ims:将no-cache或者reload请求转化为IMS请求给源站。
  • ignore-reload:将no-cache或者reload请求头忽略。
  • ignore-no-cache:强制忽略从源站而来的“Pragma: no-cache”和“Cache-control: no-cache”
  • ignore-private:强制忽略从源站而来的“Cache-control: private”
  • ignore-auth:强制将一个请求认为是源站发送的带有“Cache-control: public”
  • stale-while-revalidate=NN:强制在过期时间生效后的NN秒内非过期
  • ignore-stale-while-revalidate:强制忽略源站带有的“Cache-Control: stale-while-revalidate=NN”header
  • max-stale=NN:强制将一个超过NN秒的OBJ设置为未缓存,即使其在cache,或者更新失败。
  • negative-ttl=NN:强制此行refresh_pattern的negative_ttl时间,即使全局已经有过期时间设置。
3. SQUID 304的修改
  Squid如果缓存了一个OBJ,且其未过期时,如果碰到客户端来请求更新此obj,则squid向下发送的304/Not Modified中的header不能进行更新(特别是Date和Expires),还是给源站给的。此时会导致客户的IE中的date和expires 显示为很早之前的(上层一直缓存的)。 在这种情况下源站不发送过期时间靠我们refresh_pattern进行判断的话,则不能刷新客户端的缓存记录时间。
  此问题虽然可以使用update_headers来规避,但是显然其开销是非常大的。SQUID 304修改可以在无损状态下修复此问题。对于关闭update_headers导致304较多或者源站未给明确过期时间的请求,修改后都可以看到很明显


运维网声明 1、欢迎大家加入本站运维交流群:群②:261659950 群⑤:202807635 群⑦870801961 群⑧679858003
2、本站所有主题由该帖子作者发表,该帖子作者与运维网享有帖子相关版权
3、所有作品的著作权均归原作者享有,请您和我们一样尊重他人的著作权等合法权益。如果您对作品感到满意,请购买正版
4、禁止制作、复制、发布和传播具有反动、淫秽、色情、暴力、凶杀等内容的信息,一经发现立即删除。若您因此触犯法律,一切后果自负,我们对此不承担任何责任
5、所有资源均系网友上传或者通过网络收集,我们仅提供一个展示、介绍、观摩学习的平台,我们不对其内容的准确性、可靠性、正当性、安全性、合法性等负责,亦不承担任何法律责任
6、所有作品仅供您个人学习、研究或欣赏,不得用于商业或者其他用途,否则,一切后果均由您自己承担,我们对此不承担任何法律责任
7、如涉及侵犯版权等问题,请您及时通知我们,我们将立即采取措施予以解决
8、联系人Email:admin@iyunv.com 网址:www.yunweiku.com

所有资源均系网友上传或者通过网络收集,我们仅提供一个展示、介绍、观摩学习的平台,我们不对其承担任何法律责任,如涉及侵犯版权等问题,请您及时通知我们,我们将立即处理,联系人Email:kefu@iyunv.com,QQ:1061981298 本贴地址:https://www.yunweiku.com/thread-655885-1-1.html 上篇帖子: squid流量限制 下篇帖子: Linux Squid安装配置指南
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

扫码加入运维网微信交流群X

扫码加入运维网微信交流群

扫描二维码加入运维网微信交流群,最新一手资源尽在官方微信交流群!快快加入我们吧...

扫描微信二维码查看详情

客服E-mail:kefu@iyunv.com 客服QQ:1061981298


QQ群⑦:运维网交流群⑦ QQ群⑧:运维网交流群⑧ k8s群:运维网kubernetes交流群


提醒:禁止发布任何违反国家法律、法规的言论与图片等内容;本站内容均来自个人观点与网络等信息,非本站认同之观点.


本站大部分资源是网友从网上搜集分享而来,其版权均归原作者及其网站所有,我们尊重他人的合法权益,如有内容侵犯您的合法权益,请及时与我们联系进行核实删除!



合作伙伴: 青云cloud

快速回复 返回顶部 返回列表