老生常谈 输入url到页面加载显示完成

老生常谈 输入url到页面加载显示完成,中间都经历了什么 && 浏览器缓存解析

来自:https://www.dazhuanlan.com/2019/12/18/5df9c4cb4e563/

基本过程

  1. 输入url -Enter
  2. 浏览器先查看 浏览器缓存-系统缓存-路由器缓存,如果缓存中有,会直接在屏幕中显示内容。若没有则跳到第三步操作
  3. DNS解析,获取相应的IP地址(先查缓存是否有域名对应ip,然后查询本地hosts文件,都没得,才查询dns服务器)
  4. 浏览器向服务器发起TCP连接,与浏览器建立TCP三次握手。
  5. 握手成功后,浏览器向服务器发送http请求,请求数据
  6. 服务器收到请求,将数据发送至浏览器
  7. 浏览器接受响应
  8. 读取页面内容,浏览器渲染,解析html源码
  9. 生成dom树,css树,js解析
  10. 客户端和服务器交互
  11. ajax请求

过程2解析(彻底理解浏览器缓存机制)

image

两个概念

  • 强缓存

用户发送的请求,直接从客户端缓存中获取,不发送请求到服务器,不与服务器发生交互行为。

  • 协商缓存

用户发送的请求,发送到服务器后,由浏览器判断是否从缓存中获取资源。

图中四个过程浅析

(a)浏览器判定是否有缓存

所谓“客户端缓存”就是指用户本地资源。不同浏览器缓存文件的地址也不尽相同。

进入chrome://cache页面,里面的每一项都是缓存

随便点一个资源,可以看到:
image

回到问题,浏览器怎么判定是否有缓存,就可以转化为浏览器去读取本地放缓存的地方(注:不同浏览器不同系统都会不同)是否有该对应的请求啦。

总结来说就是个查找文件是否存在的问题。

(b)缓存是否过期

image

我们再以这张图为例,这张图中表明,客户端保留了一个服务器端的response header。
里面的Date字段表明此次缓存时服务器的时间。
里面有两个字段:expires 、Cache-Control

  • expires

Http1.0 中的标准,表明过期时间,注意此处的时间都是指的是服务器的时间。
可以看到过期时间被设定为了:Thu, 28 Sep 2017 06:38:37 GMT

存在的问题:服务器时间与客户端时间的不一致,就会导致缓存跟期待效果出现偏差。

  • Cache-Control

Http1.1 中的标准,可以看成是 expires 的补充。使用的是相对时间的概念。
简单介绍下Cache-Control的属性设置。

  1. max-age: 设置缓存的最大的有效时间,单位为秒(s)。max-age会覆盖掉Expires

  2. s-maxage: 只用于共享缓存,比如CDN缓存(s -> share)。与max-age的区别是:max-age用于普通缓存,而s-maxage用于代理缓存。如果存在s-maxage,则会覆盖max-age 和 Expires.

  3. public:响应会被缓存,并且在多用户间共享。默认是public。

  4. private: 响应只作为私有的缓存,不能在用户间共享。如果要求HTTP认证,响应会自动设置为private。
  5. no-cache: 指定不缓存响应,表明资源不进行缓存。但是设置了no-cache之后并不代表浏览器不缓存,而是在缓存前要向服务器确认资源是否被更改。因此有的时候只设置no-cache防止缓存还是不够保险,还可以加上private指令,将过期时间设为过去的时间。
  6. no-store: 绝对禁止缓存。
  7. must-revalidate: 如果页面过期,则去服务器进行获取。

所以判断缓存是否过期步骤是:

  1. 查看是否有cache-control 的max-age / s-maxage , 如果有,则用服务器时间date值 + max-age/s-maxage的秒数计算出新的过期时间,将当前时间与过期时间进行比较,判断是否过期

  2. 查看是否有cache-control 的max-age / s-maxage,则用expires 作为过期时间比较

总结:(b)过程执行完后,如果判定为未过期,则使用客户端缓存。那么就是属于“强缓存”。

(c)跟服务器协商是否使用缓存

image

到这一步的时候,浏览器会向服务器发送请求,同时如果上一次的缓存中有Last-modified 和 Etag 字段,
浏览器将在request header 中加入If-Modified-Since(对应于Last-modified), 和If-None-Match(对应于Etag)。

  • Last-modified: 表明请求的资源上次的修改时间。
  • If-Modified-Since:客户端保留的资源上次的修改时间。
  • Etag:资源的内容标识。(不唯一,通常为文件的md5或者一段hash值,只要保证写入和验证时的方法一致即可)
  • If-None-Match: 客户端保留的资源内容标识。

通常情况下,如果同时发送 If-None-Match 、If-Modified-Since字段,服务器只要比较etag 的内容即可,当然具体处理方式,看服务器的约定规则。

(d)协商缓存

在这个阶段,服务器一般会将Cache-control、expires 、last-modified、date、etag 等字段在response header 中返回,便于下次缓存。当然具体的场景,也是看服务器的约定规则设定。

用户行为

最后附上一张,用户行为影响浏览器的缓存行为。

猜你喜欢

转载自blog.csdn.net/Handsome2013/article/details/115025544