什么是浏览器缓存?
所谓的浏览器缓存指的是浏览器将用户请求过的静态资源,存储到本地内存和磁盘中,当浏览器再次访问时,就可以直接从本地加载,不用再次发起请求。
为什么需要浏览器缓存?
- 减少了服务器的负担,提高了网站的性能
- 加快了客户端网页的加载速度
- 减少了多余网络数据传输
浏览器缓存的机制
一、强缓存
如果缓存资源有效,则直接使用缓存资源,不必再向服务器发起请求。
设置方式:
Expires:服务器通过在响应头中添加 Expires 属性,来指定资源的过期时间。在过期时间以内,该资源可以被缓存使用,不必再向服务器发送请求,这个是HTTP 1.0的方式,因为用绝对时间可能存在误差导致缓存失败。
Cache-Control:因为Expires的一些缺点,在 HTTP 1.1 中提出了这个属性,它提供了对资源的缓存的更精确的控制。通过设置 max-age= XXX 来进行强缓存。
二、协商缓存
强缓存失效后,浏览器先向服务器发送一个请求,如果资源没有发生修改,则返回一个 304 状态,让浏览器使用本地的缓存副本。如果资源发生了修改,则返回修改后的资源。
协商缓存可以通过下面两种方式来设置:
(1)Last-Modified & If-Modified-Since:服务器通过在响应头中添加 Last-Modified 属性来指出资源最后一次修改的时间,当浏览器下一次发起请求时,会在请求头中添加一个 If-Modified-Since 的属性,属性值为上一次资源返回时的 Last-Modified 的值。当请求发送到服务器后服务器会通过这个属性来和资源的最后一次的修改时间来进行比较,以此来判断资源是否做了修改。如果资源没有修改,那么返回 304 状态,让客户端使用本地的缓存。如果资源已经被修改了,则返回修改后的资源。使用这种方法有一个缺点,就是 Last-Modified 标注的最后修改时间只能精确到秒级,如果某些文件在1秒钟以内,被修改多次的话,那么文件已将改变了但是 Last-Modified 却没有改变,这样会造成缓存命中的不准确。
(2)Etag & If-None-Match:因为 Last-Modified 的这种可能发生的不准确性,http 中提供了另外一种方式,那就是 Etag 属性。服务器在返回资源的时候,在头信息中添加了 Etag 属性,这个属性是资源生成的唯一标识符,当资源发生改变的时候,这个值也会发生改变。在下一次资源请求时,浏览器会在请求头中添加一个 If-None-Match 属性,这个属性的值就是上次返回的资源的 Etag 的值。服务接收到请求后会根据这个值来和资源当前的 Etag 的值来进行比较,以此来判断资源是否发生改变,是否需要返回资源。通过这种方式,比 Last-Modified 的方式更加精确。
Etag 的优先级高于 Last-Modified。