HTTP缓存
类型
- 强缓存(本地缓存)
- 弱缓存(协商缓存)
流程
访问静态资源时的流程
- 强缓存阶段:先在本地查找是否有该资源,若有,且
Expires
和Cache-Control
都满足要求,则命中强缓存,返回200,直接返回强缓存中的数据,不会向服务器发出请求。 - 弱缓存阶段:在本地缓存找到该资源,发送http请求到服务器询问该资源是否有更新,若服务器判断没有更新,返回
304Not Modified
。则浏览器继续使用该资源。 - 缓存失败阶段:若在本地没有找到对应资源,或者资源已过期/更新,则服务器返回该资源。
强缓存VS弱缓存
- 状态码
强缓存返回200
弱缓存返回304 - 强缓存不需要发出http请求,而弱缓存需要。
强缓存
使用Expires
和cache-control
来控制。优先级:pragma
>cache-control
>Expires
Expires
服务器为资源设置一个
Expire
日期,在这Expire
日期之前可以将资源视作最新。此字段是为了兼容旧版本HTTP才保留的,在http1.0时配合pragma使用,pragma:no-cache
表示不缓存,pragma
的优先级大于Expires
Cache-Control
Cache-Control
是http1.1
为了弥补Expires
的缺陷而加入的(http1.0时,使用pragma
),当Expires
和Cache-Control
同时存在时,Cache-Control
的优先级高于Expires
。
Cache-Control取值 | 描述 |
---|---|
public | 服务器端和浏览器端都可以缓存 |
private | 只有浏览器可以缓存 |
no-cache | 强制浏览器在使用cache拷贝之前先提交一个http请求到原服务器进行确认,类似于弱缓存 |
only-if-cached | 表明客户端只接受已缓存的响应,并且不需要向服务器检查是否有更新的拷贝 |
max-age=60 | 单位:秒,缓存的有效期,超过这个时间后将被认为过期。此选项会覆盖Expires字段的过期日期 |
no-store | 不缓存,使用协商缓存 |
must-revalidate | 缓存必须在使用之前验证旧资源的状态,并且不可使用过期资源 |
弱缓存
有关字段 Last-Modified
/If-Modified-Since
(HTTP1.0)、Etag
/If-None-Match
(HTTP1.1)
Last-Modified
和Etag
为响应头部字段,分别对应请求头部字段中的if-Modifed-Since
/If-None-Match
。
Last-Modified
/If-Modified-Since
存在缺陷,当资源的实际内容没有改变而仅仅只是时间变化了(比如只是打开了文件,并保存了一下,尽管内容没有变化但还是修改过),还是需要重新请求资源。因此为了解决这个缺陷,http1.1提出了Etag
/If-None-Match
,Etag
类似于文件的hash,为文件提供了一个指纹,只检查文件内容是否一致。
流程:
- 当没有命中强缓存时,进入弱缓存阶段
- 浏览器首次访问网站时,服务器会在响应头部中附上
Last-Modified
/Etag
- 弱缓存阶段,浏览器再次访问时,会发送
If-Modified-Since
/If-None-Match
去询问是否有改变,有则重新获取,否则使用本地缓存。
缓存与浏览器刷新
- F5刷新,会使强缓存失效,浏览器进行协商缓存。
- Ctrl+F5刷新,为强制刷新,强缓存与弱缓存均失效,浏览器总会发送HTTP请求向服务器获取最新数据。