为什么需要缓存 ?
1、缓存可以减少用户等待时间,提升用户体验
2、减少网络带宽消耗
3、降低服务器压力
缓存的类型
浏览器缓存分为强缓存和协商缓存,两者都是通过HTTP响应头来控制缓存的模式。
1. 强缓存
当某个资源被强制缓存了,你再次请求相同的资源,不会向服务器发送请求。
与强缓存相关的Response Header有:
Expires 是GMT 格式的时间字符串,代表缓存资源的过期时间
Expires 也是需要在服务端配置(具体配置也根据服务器而定),Expires 添加的是该资源过期的日期。浏览器会根据该过期日期与客户端时间对比,如果过期时间还没到,则会去缓存中读取该资源,如果已经到期了,则浏览器判断为该资源已经不新鲜要重新从服务端获取。
通过这种方式,可以实现直接从浏览器缓存中读取,而不需要去服务端判断是否已经缓存,避免了这次 HTTP 请求。值得注意的是 Expires 时间可能存在 客户端时间跟服务端时间不一致的问题。所以Expires通常结合 Cache-Control一起使用
Cache-Control 具有强大的缓存控制能力
常用的有
Cache-Control:no-cache 表示每次请求需要校验服务器资源的新鲜度
Cache-Control:max-age 强缓存利用其 max-age 值来判断缓存资源的最大生命周期,它的值单位为秒。
2. 协商缓存
当一个资源进行协商缓存的时候,再次请求这个资源的时候,需要向服务器校验新鲜度,如果资源是新鲜的,返回 304状态码,从浏览器获取资源。
与协商缓存有关的Request/Response Headers 有以下几个:
Last-Modified/If-Modified-SinceEtag/If-None-Match
Last-Modified:值为资源最后更新时间,随服务器 Response 返回;
If-Modified-Since:通过比较两个时间来判断资源在两次请求期间是否有过修改,如果没有修改,则命中协商缓存。
ETag:表示资源内容的唯一标识,随服务器 Response 返回。Web 服务器响应请求时,告诉浏览器当前资源在服务器的唯一标识;
If-None-Match:服务器通过比较请求头部的 If-None-Match 与当前资源的 ETag 是否一致来判断资源是否在两次请求之间有过修改,如果没有修改,则命中协商缓存。
浏览器缓存流程
- 浏览器会先检测强缓存类型(Cache-Control 或者 Expires)是否有效;
- 如果命中了强缓存,则直接从本地获取缓存资源;
- 当强缓存没有命中时,客户端会发送请求到服务器,服务器通过另一些 Request Header 验证这个资源是否命中协商缓存,称为 HTTP 再验证,如果命中,服务器将请求返回,但不返回资源,而是告诉客户端直接从缓存中获取,客户端收到返回后就会从缓存中获取资源;
- 强缓存不会发送请求到服务器,但协商缓存会发送服务器请求;
- 当协商缓存也没命中时,服务器就会将资源发送回客户端。
一些不会被缓存的情况:
1.HTTP 信息头中包含 Cache-Control:no-cache ,pragma:no-cache(HTTP1.0),或 Cache-Control: max-age=0 等告诉浏览器不用缓存的请求;
2. 需要根据 Cookie,认证信息等决定输入内容的动态请求是不能被缓存的;
3. 经过 HTTPS 安全加密的请求;
4.POST 请求无法被缓存;
5.HTTP 响应头中不包含 Last-Modified/Etag,也不包含 Cache-Control/Expires 的请求无法被缓存;
关于强缓存的意外情况:
在刷新页面时,有的浏览器会重新验证缓存资源的新鲜度,有的不会。
假设第一次请求资源的 Response Heades 包含下列强制缓存信息
Date: Tue, 19 Jan 2021 08:37:05 GMT
Expires: Tue, 26 Jan 2021 08:37:05 GMT
在有效期内,按照强制缓存的概念解释,再次请求资源时,不会发送请求,直接返回 200。 但是在 firefox 中(使用版本:84.0.2),Request Headers 中包含If-Modified-Since头部,所以仍然会发送请求,返回 304。 在 chrome 中(使用版本:87.0.4280.141),不会发送请求,会直接使用缓存的资源,返回 200。
参考链接:
blog.csdn.net/wyouwd1/art…
q.shanyue.tech/base/http/8…