JavaWeb~在浏览器中输入网址到显示网页内容 中间经历了什么?

文章目录

1. 用户在地址栏中输入内容

判断用户输入的是搜索内容还是请求的URL
如果是搜索内容,地址栏会使用浏览器默认的搜索引擎合成带搜索关键字的URL
如果是URL,地址栏会根据规则,合成带有协议的完整URL

JavaWeb~在浏览器中输入网址到显示网页内容 中间经历了什么?

2. 查找本地浏览器缓存是否存有该资源

有,直接返回缓存资源给浏览器
无,进入下一步网络请求流程

3. 浏览器解析URL获取 协议、主机、端口、path

4. 浏览器组装一个HTTP(Get)请求报文

JavaWeb~在浏览器中输入网址到显示网页内容 中间经历了什么?

5. DNS解析,获取请求的IP地址 查找过程如下:

浏览器缓存
本机缓存
hosts主机文件
路由器缓存
ISP DNS缓存
DNS递归查询(可能存在负载均衡导致每次IP不一样)

6. 打开一个Socket与目标IP地址,端口建立TCP连接,三次握手如下

JavaWeb~在浏览器中输入网址到显示网页内容 中间经历了什么?

7. 浏览器端构建请求行(方法 URL 版本号)、请求头(Headers)信息,还要把把cookie数据附加到请求头中(如果浏览器此时保存了Cookie字段的话),接下来这个数据报就会被交给传输层

8. 传输层协议TCP就会把这个数据构造成一个TCP数据报 再交给网络层

9. 网络层会根据IP协议将这个TCP数据报构造成一个IP数据报 还有根据数据报的长度以及MTU的限制 考虑是否需要分包 再交给数据链路层

10. 数据链路层会根据以太网协议将其再构造成一个以太网数据帧 再将其交给物理层

构造以太网数据帧的时候需要填写源MAC地址(就是当前主机的MAC地址)和目的MAC地址(如果不知道目的MAC地址 就要根据ARP协议来进行 MAC学习) 最后根据上面IP地址来确认转发的端口号

11. 在物理层会将数据帧转换二进制bit流最后变成光信号或者电信号进行传输

JavaWeb~在浏览器中输入网址到显示网页内容 中间经历了什么?

12. 到达一台路由器的时候 路由器会对这个信号进行解析和分用 (解析到传输层就不再解析了)

路由器会解析到这个数据报的IP地址 然后将IP地址与其子网掩码进行 与 操作 得到其网络号 (NAT机制)
然后在当前路由表中查找 如果找到有匹配的网络号 对应的该网络端口号进行转发
如果没有找到匹配的就从默认的下一跳表项继续转发 他的生存时间也会减一(默认64)
在正常情况下 总会有路由器认识这个IP地址

  • 如果当前路由器不认识该IP地址 路由器会对这个数据报进行封装 和前述过程一样 最后还是变成光信号或者电信号传输

13. 中间经历若干路由器转发最终会到达目标服务器

14. 服务器的物理层将光信号转成二进制bit流 交给数据链路层

15. 数据链路层解析其中的IP数据报 再交给网络层

16. 网络层可能需要重新组包(因为前面可能由于IP数据报太打对其进行了拆包) 再交给传输层

17. 传输层对TCP数据报进行解析 将应用层的数据报交给应用程序 返回ACK应答(此处可能会涉及到确认序号 窗口大小 延迟应答 捎带应答)

ACK也会成为一个TCP数据报 也会涉及到一系列的上述封装和分用和路由选择的过程
JavaWeb~在浏览器中输入网址到显示网页内容 中间经历了什么?

18. 服务器的应用程序读取数据 然后请求计算响应 (计算过程由程序员敲代码决定) 结果会得到一个html页面 将这个页面构造成一个HTTP的响应报文 这个报文也同样会经过一系列的封装 解析分用 传输 直到到达客户端

JavaWeb~在浏览器中输入网址到显示网页内容 中间经历了什么?

19. 客户端的浏览器接收HTTP响应,然后根据情况选择关闭TCP连接或者保留重用,关闭TCP连接的四次挥手如下:

JavaWeb~在浏览器中输入网址到显示网页内容 中间经历了什么?

20. 浏览器接收到响应信息后进行解析

解析响应报文的时候会首先重点看其首行 (版本号 状态码 状态码描述)
响应行返回状态码200,请求成功,进入下一步
响应行返回状态码301或302,浏览器需要重定向到响应头Location字段的URL地址,重新开始发起请求
响应行返回状态码 40xx客户端错误
响应行返回状态码 5xx 服务器错误
接下来再解析Headers部分 解析body部分

21. 响应数据类型处理

响应头Content-Type返回值是application/octet-stream,表示返回的数据是字节流类型,浏览器会按下载类型来处理,将请求提交给浏览器的下载管理器,请求流程结束。
响应头Content-Type返回值是text/html,表返回的数据是HTML格式,进入下一步

22. 准备渲染进程

默认情况下,每打开一个新页面,创建一个新的渲染进程
从一个页面打开另一个页面,且两个页面在同一站点(同样的协议和根域名)下,共用一个渲染进程

23. 提交文档(响应体数据)

浏览器进程发出“提交文档”的消息
渲染进程接收到“提交文档”消息后和网络进程监理传输数据的通道
数据传输完成后,渲染进程返回“确认提交”的消息给浏览器进程
浏览器进程收到“确认提交”消息后更新浏览器的页面状态,包括安全状态、地址栏URL、前进后退的历史状态和web页面

24. 渲染阶段

页面解析和子资源加载
构建DOM树(DOM是保存在内存中浏览器可以理解的树状结构,可以通过JS进行增删改查)
样式计算
把css转换为浏览器能够理解的结构——styleSheets
转换样式表中的属性值,使其标准化,例如:
em、rem等单位解析成px
颜色设置解析为rgb格式
bold、lighter等单次解析成对应的数值

计算出DOM树中每个节点的具体样式,被保存到ComputedStyle结构内
样式继承
样式层叠
布局,计算DOM树中可见元素的几何位置
创建布局树(只包含可见元素)
布局计算(计算每个可见元素的坐标位置)
分层,生成图层树
布局树的节点不一定有对应的图层,若没有,则从属于父节点的图层
有明确定位属性、透明属性、css滤镜、剪裁等地方会被创建为图层
图层绘制
把图层的绘制拆分成很多绘制指令
按照顺序把绘制指令组成待绘制列表,提交到合成线程
分块(页面很长的时候,可视区域只能看到很小的一部分,合成线程将图层划分为图块,优先处理可视区域附近的图块,可以减小开销)
栅格化
将图块转换为位图的过程
使用GPU来加速生成,生成的位图保存在GPU内存中
合成
所有图块栅格化后,合成线程生成一个绘制图块的命令,提交给浏览器进程
浏览器接收到命令后将页面内容绘制到内存中,再将内存显示在屏幕上

25. 页面生成完成后,渲染进程会发送消息给浏览器进程

26. 浏览器进程收到消息后,停止标签图标的loading加载动画,一个完整的页面就生成了

JavaWeb~在浏览器中输入网址到显示网页内容 中间经历了什么?