写在前面的话
缓存是前端面试中的必问题目html
缓存对于web开发有重要做用,尤为是大负荷web系统开发中前端
想了解更多关于性能优化的知识,请移步[三分钟小文]前端性能优化-HTML、CSS、JS部分、[三分钟小文]前端性能优化-页面加载速度优化、[三分钟小文]前端性能优化-网络传输层优化git
文章建议阅读时间:5分钟github
本篇文章同时收录【前端知识点】中,连接直达web
阅读本文您将收获
- 缓存的相关概念
- 缓存的做用
- 缓存机制
- 缓存策略详解
缓存的概念知识
- 缓存的分类:服务器缓存(代理服务器缓存、CDN 缓存),第三方缓存,浏览器缓存等。
- 缓存的相关术语:
- 缓存命中率:从缓存中获得数据的请求数与全部请求数的比率。理想状态是越高越好。
- 过时内容:超过设置的有效时间,被标记为 '陈旧' 的内容。一般过时内容不能用于回复客户端的请求,必须从新向源服务器请求新的内容或者验证缓存的内容是否仍然可用。
- 验证:验证缓存中的过时内容是否仍然有效,验证经过的话刷新过时时间或策略。
- 失效:失效就是把内容从缓存中移除。当内容发生改变时就必须移除失效的内容。
- 另: 浏览器缓存是代价最小的,由于浏览器缓存依赖的是客户端,而几乎不耗费服务器端的资源(极端状况下至关于纯静态页面)。
缓存的做用
- 减小网络带宽消耗
- 下降服务器压力
- 减小网络延迟,加快页面打开速度
缓存机制
- 强缓存优先于协商缓存,强缓存生效则使用强缓存,若强缓存失败,则进行协商缓存
- 协商缓存由服务器决定是否使用缓存,若协商缓存失效,那么表明该请求的缓存失效,从新获取请求结果,再存入浏览器缓存中;生效则返回304,继续使用缓存

缓存策略 图片来源:IMWeb前端
Expires(过时时间)(强缓存机制)
- 值:是一个GMT时间格式的绝对时间,
Expires
的日期时间必须是格林威治时间(GMT),而不是本地时间。举例:Expires: Fri, 30 Oct 1998 14:19:41
- 做用:告诉缓存器相关副本在多长时间内是新鲜的。过了这个时间,缓存器就会向源服务器发送请求,检查文档是否被修改。
- 兼容性:几乎全部的缓存服务器都支持Expires(过时时间)属性
- 规则:基于客户最后查看副本的时间(最后访问时间)或者根据服务器上文档最后被修改的时间
- 应用:
- 对于设置静态图片文件(例如导航栏和图片按钮)缓存特别有用;由于这些图片修改不多,你能够给它们设置一个特别长的过时时间,这会使你的网站对用户变得相应很是快
- 对于控制有规律改变的网页也颇有用,例如:你天天早上6点更新新闻页,你能够设置副本的过时时间也是这个时间,这样缓存服务器就知道何时去取一个更新版本,而没必要让用户去按浏览器的"刷新"按钮。
- 过时时间头信息属性值只能是HTTP格式的日期时间,其余的都会被解析成当前时间"以前",副本会过时
- 局限性:虽然过时时间属性很是有用,可是它仍是有些局限,
- 首先:是牵扯到了日期,这样Web服务器的时间和缓存服务器的时间必须是同步的,若是有些不一样步,要么是应该缓存的内容提早过时了,要么是过时结果没及时更新。
- 若是你设置的过时时间是一个固定的时间,若是你返回内容的时候又没有连带更新下次过时的时间,那么以后全部访问请求都会被发送给源Web服务器,反而增长了负载和响应时间
Cache-Control(缓存控制)(强缓存机制)
- 值:
max-age=[秒]
— 执行缓存被认为是最新的最长时间。
- 相对时间,不是绝对时间
- 单位是秒:从请求时间 开始到过时时间之间的秒数。
- 做用:让网站的发布者能够更全面的控制他们的内容,并定位过时时间的限制。是http 1.1中为了弥补
Expires
缺陷新加入的。
- 相关控制字段:
s-maxage=[秒]
— 相似于max-age属性,除了他应用于共享(如:代理服务器)缓存
public
— 标记认证内容也能够被缓存,通常来讲: 通过HTTP认证才能访问的内容,输出是自动不能够缓存的;
no-cache
— 强制每次请求直接发送给源服务器,而不通过本地缓存版本的校验。这对于须要确认认证应用颇有用(能够和public结合使用),或者严格要求使用最新数据 的应用(不惜牺牲使用缓存的全部好处);
no-store
— 强制缓存在任何状况下都不要保留任何副本
must-revalidate
— 告诉缓存必须遵循全部你给予副本的新鲜度的
proxy-revalidate
— 和 must-revalidate
相似,除了他只对缓存代理服务器起做用
Last-Modified/If-Modified-Since (协商缓存机制)
- 一般服务器知道你所请求的数据的最后修改时间,而且 HTTP 为服务器提供了一种将最近修改数据连同你请求的数据一同发送的方法。
- 若是你第二次 (或第三次,或第四次) 请求相同的数据,告诉服务器上一次得到的最后修改日期:在请求中发送一个
If-Modified-Since
头信息,它包含了上一次从服务器连同数据所得到的日期。
- 若是数据从那时起没有改变,服务器将返回一个特殊的 HTTP 状态代码 304,这意味着 “从上一次请求后这个数据没有改变”。
- 当服务器发送状态编码 304 时,再也不从新发送数据。因此当数据没有更新时,你不须要一次又一次地下载相同的数据
- 兼容性 :全部现代的浏览器都支持 (
last-modified
) 的数据检查。
ETag/If-None-Match (协商缓存机制)
- 做用: 没有变化时不从新下载数据
- 工做方式 :
Etag
是上一次加载资源时,服务器返回的 response header
,是对该资源的一种惟一标识,只要资源有变化,Etag
就会从新生成
- 浏览器在下一次加载资源向服务器发送请求时,会将上一次返回的
Etag
值放到 request header
里的 If-None-Match
里,服务器比较客户端传来的 If-None-Match
跟本身服务器上该资源的 ETag
是否一致
- 若是服务器发现
ETag
匹配不上,那么直接以常规 GET 200
回包形式将新的资源(固然也包括了新的 ETag
)发给客户端;若是 ETag
是一致的,则直接返回304知会客户端直接使用本地缓存便可。
几种缓存策略的对比
两种强缓存机制对比 Expires
VS Cache-Control
- 差异不大,区别就是
Expires
是 HTTP1.0
的产物,而 Cache-Control
是 HTTP1.1
的产物
- 优先级上,二者同时存在的话,
Cache-Control
优先级高于 Expires
,Expires
更像是一种备选方案,在某些不支持 Cache-Control
的环境中发挥做用
- 两者共同的弊端 就是这种强缓存的机制仅仅关心缓存是否超出或者超过某个过时时间,并不关心服务器端的资源是否已经更新,因此单纯使用这两种缓存策略会致使客户端拿到的资源不是最新的
两种协商缓存机制对比 Last-Modified/If-Modified-Since
VS ETag/If-None-Match
- 精度上,
ETag
要明显优于前者,Last-Modified/If-Modified-Since
策略的时间单位为秒,这就意味着在秒级的请求上,作不到真正的及时更新,可是 ETag
每次请求都会对其进行改变从而确保精度,而且在使用负载均衡的服务器上,各个服务器生成的 Last-Modified
也有可能不相同
- 性能上,
ETag
要逊于 Last-Modified/If-Modified-Since
策略,毕竟 Last-Modified/If-Modified-Since
策略只是记录时间,而 ETag
须要进行一步hash运算
- 优先级上,服务器会优先考虑
ETag
用户行为对缓存策略的影响
并非全部的操做都会启用正常的缓存机制,在某些用户行为下,缓存机制是能够正常跳过的面试
- 地址栏访问,连接跳转是正经常使用户行为,将会触发浏览器缓存机制
- F5刷新,浏览器会设置
max-age=0
,跳过强缓存判断,会进行协商缓存判断
- ctrl+F5刷新,跳过强缓存和协商缓存,直接从服务器拉取资源
写在最后
- 若是你以为这篇文章对你有益,烦请点赞以及分享给更多须要的人!
快到碗里来!百度校招还有HC!甩简从来!
极速直接内推【字节跳动】&【百度】&【猿辅导】&【京东】
欢迎关注微信公众号【全栈道路】,获取更多科技相关知识及免费书籍。


更多好文
Vue3.0 响应式数据原理:ES6 Proxy浏览器
几行代码教你解决微信生成海报及二维码缓存
冷门的HTML - tabindex 的做用性能优化
[万字长文]百度和好将来面试经含答案服务器
[前端面试]前端缓存问题看这篇,让面试官爱上你
记一次惨痛的Vue-cli + VueX + SSR经历
[三分钟小文]前端性能优化-HTML、CSS、JS部分
[三分钟小文]前端性能优化-页面加载速度优化
[三分钟小文]前端性能优化-网络传输层优化