输入一个url发生了什么

  1. DNS解析
  2. TCP链接
  3. 发送http请求
  4. 服务器处理请求
  5. 浏览器解析渲染页面
  6. 链接结束

DNS解析

什么是DNS?css

DNS是一种组织成域层次结构的计算机和网络服务命名系统,他用于TCP/IP网络,它所提供的服务是用来将主机名和域名转换成IP地址的工做。DNS就是这样的一位"翻译官",它的基本工做原理能够用下图来表示。css3

根域名服务器(root Name server) 是互联网域名解析系统(DNS)中最高级别的域名服务器,负责返回顶级域的权威域名服务器地址。它们是互联网基础设施中的重要部分,由于全部域名解析操做均离不开它们。因为DNS和某些协议(未分片的用户数据协议(UDP)数据包在IPv4内的最大有效大小为512字节)的共同限制,根域名服务器地址的数量呗限制为13个。web

顶级域名(TLD),就是最高层级的域名。简单说,就是网址的最后一个部分。好比,网址www.baidu.com的顶级域名就是.com。
他们能够分红两类。一类是通常性顶级域名(gTLD)也能够叫通用顶级域名,好比.com、net、.edu、.org等等,共有700多个。另外一类是国别顶级域名(ccTLD),表明不一样的国家和地区,好比.cn(中国)、.io(英属印度洋领地)等,共有300多个。后端

名称服务器(Name Server)在互联网中是指提供域名服务协议的程序或服务器。它能够将"人类可识别"的标识符,映射为系统内部一般为数字形式的标识码。域名系统(DNS)服务器是最著名的名称服务器:域名是互联网两大主要名字空间之一。浏览器

DNS解析过程缓存

  1. 检查浏览器缓存中是否缓存过该域名对应的ip地址
  2. 若是在浏览器缓存中没有找到ip,那么将继续查找本机系统是否缓存过ip
  3. 向本地域名解析服务发起域名解析的请求
  4. 向根域名解析服务器发起域名解析请求
  5. 根域名服务器返回gTLD(通用顶级域)域名解析服务器地址
  6. 向gTLD服务器发起解析请求
  7. gTLD服务器接收请求病返回Name Server服务器
  8. Name Server 服务器返回ip地址给本地服务器
  9. 本地域名服务器缓存解析结果
  10. 返回解析结果给用户

DNS负载均衡服务器

DNS负载均衡技术的实现原理是在DNS服务器中为同一个主机名配置多个IP地址,在应答NDS查询时,DNS服务器对每一个查询将以DNS文件中主机记录的IP地址按顺序返回不一样的解析结果,将客户端的访问引导到不一样的机器上去,使得不一样的客户端访问不一样的服务器,从而达到负载均衡的目的。网络

TCP链接

三次握手的目的并发

目的是为了防止已经失效的链接请求报文段忽然有传送到了服务端,于是产生错误负载均衡

三次握手的过程

  1. 客户端发送一个带SYN=1,Seq=X 的数据包到服务器端(第一次握手,由浏览器发起,告诉服务器我要发送请求了)
  2. 服务器发挥一个带SUN=1,ACK=Y的响应包以示传达确认信息(第二次握手,由服务器发起,告诉浏览器我准备接收了,能够发送了)
  3. 客户端再传回一个带ACK=Y+1,Seq=Z的数据报,表明握手结束(第三次握手,由浏览器发送,告诉服务器,我准备发送了)

报文格式:

  1. 序号:Seq序号(Sequence number顺序号码),占32位,用来标识从TCP源端向目的端发送的字节流,发起方发送数据时对此进行标记。
  2. 确认序号:Ack序号(Acknowledge number确认号码),占32位,只有ACK标志位为1时,确认序号字段才有效,Ack=Seq+1。
  3. 标志位(位码):共6个,即URG、ACK、PSH、RST、SYN、FIN,具体含义以下:
    • URG:urgent,紧急。紧急指针(urgent pointer)有效。
    • ACK:acknowledgement,确认。确认序号有效。
    • PSH:push,传送。接收方应该尽快将这个报文交给应用层。
    • RST:reset,重置。重置链接。
    • SYN:synchronous,创建联机。发起一个新链接。
    • FIN:finish,结束。释放一个链接。

须要注意的是:

  1. 不要将确认序号Ack与标志位中的ACK搞混了
  2. 确认方Ack=发起方Seq+1,两端配对。

(°ー°〃)咱们用大白话解释下三次握手

快递小哥:你好,你的快递到了,你在家没?
小明:在家呢,送过来吧。
快递小哥:好的,立刻送到。

发送HTTP请求

请求报文由请求行,请求头,空行,请求体四个部分组成。

请求行包含请求方法,URL,协议版本

  • 请求方法包括:GET、POST、PUT、DELETE、PATCH、HEAD、OPTIONS、TRACE。
  • URL即请求地址
  • 协议版本即http版本号
GET /js/count.js HTTP/1.1

上面代码中GET表明请求方法,/js/count.js表示URL,HTTP/1.1表明http版本

请求行包含请求的附加信息,由关键字/值对组成,每行一堆,关键字和值用英文冒号":"分隔。

请求头部通知服务器关于客户端请求的信息。它包含许多有关的客户端环境和请求正文的有用信息。好比:

  • Host:主机名,虚拟主机
  • Connection:HTTP/1.1增长的,使用keeoalive,即持久链接,一个链接能够发多个请求
  • User-Agent:客户端程序的信息,就是我发送请求的浏览器信息
  • Accept:浏览器能够接收的媒体数据类型
  • Accept-Encoding:是浏览器用来告知服务器它可以支持的内容编码及内容编码的优先级顺序,可一次性指定多种内容编码
  • Accept-Language:高hi服务器浏览器可以处理的天然语言集
  • Cookie:浏览器记录的用户相关信息

请求体:能够承载多个请求参数的数据,包含回车符、换行符和请求数据,并非全部请求都具备请求数据。

服务器处理请求返回HTTP报文

响应报文由相响应行、响应头、响应主体三个部分组成,以下图

响应行包含协议版本、状态码、状态码描述

HTTP/1.1 200 OK
  • 协议版本:HTTP/1.1
  • 状态码:200
    • 200:请求成功
    • 201:以建立,成功请求并建立了新的资源
    • 203:非受权信息。请求成功,但返回的meta信息不在原始的服务器,而是一个副本
    • 204:无内容。服务器处理成功,但未返回内容。在未更新网页的状况下,可确保浏览器继续显示当前文档
    • 301:永久重定向
    • 302:临时重定向
    • 307:临时重定向。与302相似。使用GET请求重定向
    • 400:客户端请求的语法错误,服务器没法理解(给服务端传的参数和服务端指定接受的字段不一样)
    • 404:服务器没法根据客户端的请求找到资源
    • 405:客户端请求中的方法被禁止(请求方法不对,好比服务端设置GET请求,客户端使用POST请求)
    • 500:服务端内部错误
  • 状态码描述:ok

响应头

响应头为客户端提供了额外的信息,使得客户端能够作出更好的响应。

  • Server:服务器告诉客户端当前服务器上安装得HTTP服务应用程序的信息,可能包含服务器上的软件应用名称,版本号
  • Content-Type:代表了服务器返回给浏览器的实体内容的类型
  • Transfer-Encoding: chunked 表示输出的长度不能肯定,普通的静态页面、图片之类的基本上都用不到这个。动态页面可能会用到。
  • Cache-Control:缓存控制,默认值为private,表示内容只缓存到私有缓存中(仅客户端能够缓存,代理服务器不可缓存)
  • Expires:告知客户端资源失效日期

响应主体

服务端给客户端返回的文本信息

浏览器解析渲染页面

关键渲染路径

关键渲染路径是指浏览器从最初接收请求来的HTML、CSS、JS等资源,而后解析,构建树、渲染布局、绘制,最后呈现给客户能看到的界面的整个过程

主要包括如下几步

  1. 解析HTML生成DOM树
  2. 解析CSS生成CSSOM规则树
  3. 将DOM树与CSSOM规则树合并在一块儿生成渲染树
  4. 遍历渲染树开始布局,计算每一个节点的位置大小信息
  5. 将渲染树每一个节点绘制到屏幕

构建DOM树

当浏览器接收到服务器响应来的HTML文档后,会遍历文档节点,生成DOM树。须要注意的是,DOM树生成过程当中可能会被CSS和JS的加载执行阻塞。

构建CSSOM规则书

浏览器解析CSS文件并生成CSS规则树,每一个CSS文件都被解析成一个StyleSheet对象,每一个对象都包含CSS规则。CSS规则对象包含对应于CSS语法的选择器和声明对象以及其余对象

渲染阻塞

当浏览器遇到一个script标记时,DOM构建将暂停,直至脚本完成执行,而后继续构建DOM。每次去执行Js脚本都会严重阻塞DOM树的构建,若是js脚本还操做的CSSOM,而正好这个CSSOM尚未下载和构建,浏览器甚至会延迟脚本执行和构建DOM,直至完成其CSSOM的下载和构建。

因此script标签的位置很重要。实际使用时,能够遵循下面两个原则:

  1. CSS优先:引入顺序上,CSS资源先于JS资源。
  2. JS置后:一般咱们把JS代码放到页面底部,且JS应尽可能少影响DOM构建

构建渲染树

经过DOM树和CSS规则树咱们即可以构建渲染树。浏览器会先从DOM树的根节点开始遍历每一个可见节点。对每一个可见节点,找到其适配的CSS样式规则并应用。

渲染树构建完成后,每一个节点都是可见节点而且都含有其内容和对应的规则的样式。这也是渲染树与DOM树最大的区别。渲染树是用于显示,那些不可见的元素固然就不会在这棵树中出现了,除此以外,display等于none的也不会被显示在这棵树里头,可是visibility等于hidden的元素是会显示在这棵树里头的。

渲染树布局

布局阶段会从渲染树的根节点开始遍历,而后肯定每一个接待你对象在页面上的确切大小与位置,布局阶段的输出是一个盒子模型,他会精确的捕获每一个元素在屏幕内的确切位置与大小。

渲染树绘制

在绘制阶段,遍历渲染树,调用渲染器的paint()方法在屏幕上显示其内容。渲染树的绘制工做是由浏览器的UI后端组件完成

回流与重绘

根据选安然树布局,计算CSS样式,即每一个节点在页面中的带线啊哦和位置等几何信息。HTML默认是流式布局的,CSS和JS会打破这种布局,改变DOM的外观样式以及大小和位置。这时就会触发回流和重绘

重绘

屏幕的一部分重绘,不影响总体布局,好比某个CSS的背景色变了,但元素的几何尺寸和位置不变。

常见引发重回的属性

  • color
  • border-style
  • box-shadow
  • background
  • background-size
  • border-radius
  • background-position

回流

当元素的大小位置改变,须要从新验证并计算渲染树。是渲染树的一部分或所有发生了变化。

常见引发回流的属性和方法

  • 添加或者删除可见的DOM元素
  • 元素尺寸改变--边距、填充、边框、宽度和高度
  • 内容变化,好比用户在input中输入文字
  • 浏览器窗口尺寸改变
  • 计算offsetWidth和offsetHeight

从上面能够看出:回流必将引发重绘,而重绘不必定会引发回流。

浏览器的渲染队列

思考下面代码会触发几回渲染?

div.style.left = '10px';
div.style.top = '10px';
div.style.width = '20px';
div.style.height = '20px';

这段代码理论上会触发4次重绘和回流,由于每次都改变了元素的集合属性,实际上最后支出法了一次回流,这都得益于

浏览器的渲染队列机制

当浏览器发现某一行代码是改变元素样式时,浏览器不会当即进行渲染,而是缓那么一哆嗦,看你下一行代码是否是在改样式,若是下一行仍是改样式,在缓一哆嗦,若是连续发现几行代码都是在改样式,浏览器会等待这几行代码所有执行完,才会进行渲染,这就是浏览器的渲染队列机制

动画效果应用position属性为absolutefixed元素上(脱离文档流)

这种方法也会引起回流,可是会对其余元素没有影响,能够提高性能

css3硬件加速(GPU加速)

硬件加速会自动规避回流和重绘
css中又一下几个属性能触发硬件加速

  1. transform
  2. opacity
  3. filter
  4. will-change

若是有一些元素不须要用到上述属性,可是须要触发硬件加速效果,可使用一些小技巧来诱导浏览器开启硬件加速。

-webkit-transform: translateZ(0);
    -moz-transform: translateZ(0);
    -ms-transform: translateZ(0);
    -o-transform: translateZ(0);
    transform: translateZ(0); 
    /**或者**/
    transform: rotateZ(360deg);
    transform: translate3d(0, 0, 0);

要注意的问题

  • 过多的开启硬件加速可能会耗费较多的内存。
  • GPU 渲染会影响字体的抗锯齿效果。这是由于 GPU 和 CPU 具备不一样的渲染机制,即便最终硬件加速中止了,文本仍是会在动画期间显示得很模糊。

断开链接

如今的页面为了优化请求的耗时,默认都会开启持久链接(keep-alive),那么一个TCP链接确切关闭的时机,是这个tab标签页关闭的时候。这个关闭的过程就是四次挥手.因为TCP链接时全双工的,所以,每一个方向都必需要单独进行关闭,这一原则是当一方完成数据发送任务后,发送一个FIN来终止这一方向的链接,收到一个FIN只是意味着这一方向上没有数据流动了,即不会再收到数据了,可是在这个TCP链接上仍然可以发送数据,直到这一方向也发送了FIN。首先进行关闭的一方将执行主动关闭,而另外一方则执行被动关闭

  1. client发送一个FIN,用来关闭client到server的数据传送,cliient进入FIN_WAIT_1状态
  2. server收到FIN后,发送一个ack给client,确认序列号为收到序列号+1(与SYN相同,一个FIN占用一个序号),server进入CLOSE_WAIT状态
  3. server发送一个FIN,用来关闭server到client的数据传送,server进入LAST_ACK状态
  4. client收到FIN后,client进入TIME_WAIT状态,接着发送一个ack给server,确认序列号为收到序列号+1,server进入CLOSED状态,完成四次挥手

状态详解:   CLOSED:表示初始状态。   LISTEN:表示服务器端的某个SOCKET处于监听状态,能够接受链接了。   SYN_RCVD:这个状态表示接受到了SYN报文,在正常状况下,这个状态是服务器端的SOCKET在创建TCP链接时的三次握手会话过程当中的一个中间状态,很短暂,基本上用netstat你是很难看到这种状态的,除非你特地写了一个客户端测试程序,故意将三次TCP握手过程当中最后一个ACK报文不予发送。所以这种状态时,当收到客户端的ACK报文后,它会进入到ESTABLISHED状态。   SYN_SENT:这个状态与SYN_RCVD遥想呼应,当客户端SOCKET执行CONNECT链接时,它首先发送SYN报文,所以也随即它会进入到了SYN_SENT状态,并等待服务端的发送三次握手中的第2个报文。SYN_SENT状态表示客户端已发送SYN报文。   ESTABLISHED:表示链接已经创建了。   FIN_WAIT_1:这个状态要好好解释一下,其实FIN_WAIT_1和FIN_WAIT_2状态的真正含义都是表示等待对方的FIN报文。而这两种状态的区别是:FIN_WAIT_1状态其实是当SOCKET在ESTABLISHED状态时,它想主动关闭链接,向对方发送了FIN报文,此时该SOCKET即进入到FIN_WAIT_1状态。而当对方回应ACK报文后,则进入到FIN_WAIT_2状态,固然在实际的正常状况下,不管对方何种状况下,都应该立刻回应ACK报文,因此FIN_WAIT_1状态通常是比较难见到的,而FIN_WAIT_2状态还有时经常能够用netstat看到。   FIN_WAIT_2:上面已经详细解释了这种状态,实际上FIN_WAIT_2状态下的SOCKET,表示半链接,也即有一方要求close链接,但另外还告诉对方,我暂时还有点数据须要传送给你,稍后再关闭链接。   TIME_WAIT:表示收到了对方的FIN报文,并发送出了ACK报文,就等2MSL(Max Segment Lifetime)后便可回到CLOSED可用状态了。若是FIN_WAIT_1状态下,收到了对方同时带FIN标志和ACK标志的报文时,能够直接进入到TIME_WAIT状态,而无须通过FIN_WAIT_2状态。   CLOSING:这种状态比较特殊,实际状况中应该是不多见,属于一种比较罕见的例外状态。正常状况下,当你发送FIN报文后,按理来讲是应该先收到(或同时收到)对方的ACK报文,再收到对方的FIN报文。可是CLOSING状态表示你发送FIN报文后,并无收到对方的ACK报文,反而却也收到了对方的FIN报文。什么状况下会出现此种状况呢?其实细想一下,也不可贵出结论:那就是若是双方几乎在同时close一个SOCKET的话,那么就出现了双方同时发送FIN报文的状况,也即会出现CLOSING状态,表示双方都正在关闭SOCKET链接。   CLOSE_WAIT:这种状态的含义实际上是表示在等待关闭。怎么理解呢?当对方close一个SOCKET后发送FIN报文给本身,你系统毫无疑问地会回应一个ACK报文给对方,此时则进入到CLOSE_WAIT状态。接下来呢,实际上你真正须要考虑的事情是察看你是否还有数据发送给对方,若是没有的话,那么你也就能够close这个SOCKET,发送FIN报文给对方,也即关闭链接。因此你在CLOSE_WAIT状态下,须要完成的事情是等待你去关闭链接。   LAST_ACK:它是被动关闭一方在发送FIN报文后,最后等待对方的ACK报文。当收到ACK报文后,也便可以进入到CLOSED可用状态了。

相关文章
相关标签/搜索