1. TCP 的“三次握手”
三次握手即TCP连接的建立。这个连接必须是一方主动打开,另一方被动打开的。
三次握手的过程:
- 客户端向服务器端发送一段TCP报文,其中:
- 标记位为
SYN
,表示请求建立新连接 - 序号为
Seq=x(x一般为1)
随后客户端进入 SYN-SENT 阶段。
- 标记位为
- 服务器端接收到来自客户端的TCP报文之后,结束
LISTEN
阶段。并返回一段TCP报文,其中:- 标志位为
SYN
和ACK
,表示确认客户端的报文Seq序号有效,服务器能正常接收客户端发送的数据,并同意创建新连接 - 序号为
Seq=y
- 确认号为
Ack=x+1
,表示收到客户端的序号Seq
并将其值加1作为自己确认号Ack
的值
随后服务器端进入 SYN-RECEIVED 阶段。
- 标志位为
- 客户端接收到来自服务器端的确认收到数据的TCP报文之后,明确了从客户端到服务器的数据传输是正常的,结束SYN-SENT阶段。并返回最后一段TCP报文。其中:
- 标志位为ACK,表示确认收到服务器端同意连接的信号
- 序号为
Seq=x+1
,表示收到服务器端的确认号Ack
,并将其值作为自己的序号值 - 确认号为
Ack=y+1
,表示收到服务器端序号Seq
,并将其值加1作为自己的确认号Ack的值;
随后客户端进入ESTABLISHED阶段。
- 服务器收到来自客户端的确认收到服务器的TCP报文之后,明确了从服务器到客户端的数据传输是正常的,结束SYN-RECEIVED阶段,进入ESTABLISHED阶段。
为什么是三次? 三次是保证双方互相明确对方能收能发的最低值。
2. TCP 的“四次挥手”
四次挥手即TCP连接的释放(解除)。连接的释放必须是一方主动释放,另一方被动释放。
四次挥手的过程:
- 客户端向服务器端发送一段TCP报文,其中:
- 标记位为
FIN
,表示请求释放连接 - 序号为
Seq=U
随后客户端进入FIN-WAIT-1 阶段,即半关闭阶段。并且停止在客户端到服务器端方向上发送数据,但是客户端仍然能接收从服务器端传输过来的数据。
- 服务器端接收到从客户端发出的TCP报文之后,确认了客户端想要释放连接,随后服务器端结束 ESTABLISHED 阶段,进入 CLOSE-WAIT 阶段(半关闭状态)并返回一段TCP报文,其中:
- 标记位为
ACK
,表示接收到客户端发送的释放连接的请求 - 序号为
Seq=V
- 确认号为
Ack=U+1
,表示是在收到客户端报文的基础上,将其序号Seq
值加1作为本段报文确认号Ack
的值
随后服务器端开始准备释放服务器端到客户端方向上的连接。
客户端收到从服务器端发出的TCP报文之后,确认了服务器收到了客户端发出的释放连接请求,随后客户端结束 FIN-WAIT-1 阶段,进入FIN-WAIT-2阶段。
- 服务器端自从发出ACK确认报文之后,经过 CLOSE-WAIT 阶段,做好了释放服务器端到客户端方向上的连接准备,再次向客户端发出一段TCP报文,其中:
- 标记位为
FIN
、ACK
,表示已经准备好释放连接 - 序号为
Seq=W
- 确认号为
Ack=U+1
,表示是在收到客户端报文的基础上,将其序号Seq值加1作为本段报文确认号Ack的值。
随后服务器端结束 CLOSE-WAIT 阶段,进入 LAST-ACK 阶段。并且停止在服务器端到客户端的方向上发送数据,但是服务器端仍然能够接收从客户端传输过来的数据。
- 客户端收到从服务器端发出的TCP报文,确认了服务器端已做好释放连接的准备,结束 FIN-WAIT-2 阶段,进入 TIME-WAIT 阶段,并向服务器端发送一段报文,其中:
- 标记位为
ACK
,表示接收到服务器准备好释放连接的信号 - 序号为
Seq=U+1
,表示是在收到了服务器端报文的基础上,将其确认号Ack值作为本段报文序号的值。 - 确认号为
Ack=W+1
,表示是在收到了服务器端报文的基础上,将其序号Seq值作为本段报文确认号的值。
随后客户端开始在 TIME-WAIT 阶段等待2MSL(MSL:最大生存时Maximum Segment Lifetime)。
服务器端收到从客户端发出的TCP报文之后结束LAST-ACK 阶段,进入 CLOSED 阶段。由此正式确认关闭服务器端到客户端方向上的连接。
客户端等待完2MSL之后,结束 TIME-WAIT 阶段,进入CLOSED 阶段。
为什么要等待2MSL? 客户端发送的最后一个ACK报文到达服务端最多需要一个MSL,该报文有可能丢失,服务端没有收到ACK
报文,重发FIN
报文到达客户端最多也需要一个MSL,等待2MSL是为了保证客户端发送的最后一个ACK报文段能够到达服务端。
3. GET 和 POST 的区别
- GET在浏览器回退时是无害的,而POST会再次提交请求。
- GET产生的URL地址可以被保存为书签,而POST不可以。
- GET请求会被浏览器主动cache,而POST不会,除非手动设置。
- GET请求只能进行url编码,而POST支持多种编码方式。
- GET请求参数会被完整保留在浏览器历史记录里,而POST中的参数不会被保留。
- GET请求在URL中传送的参数是有长度限制的,而POST没有。
- GET求只能传递 ASCII 数据,遇到非 ASCII 数据需要进行编码,POST 请求没有限制。
- GET比POST更不安全,因为参数直接暴露在URL上,所以不能用来传递敏感信息。
- GET参数通过URL传递,POST放在Request body中。
💡补充:
- 更多的区别是语义上的区别:
GET
用于获取指定的资源,POST
用于创建/更新某个资源 - POST产生两个TCP数据包,浏览器先发送header,服务器响应
100 continue
,浏览器再发送data,服务器响应200 ok(返回数据)
注:并不是所有的浏览器都发送两个TCP数据包。
4. 常见的HTTP请求头和响应头
请求头
Accept
: 浏览器能够接受的内容类型Accept-Charset
: 浏览器能够接受的字符编码集Accept-Encoding
:浏览器能够处理的内容压缩编码类型Accept-Language
:浏览器可接受的语言Connection
:是否建立长连接(keep-alive/close)Cookie
:当前页面设置的任何CookieHost
:请求的服务器的域名和端口号Referer
:发出请求的页面的URLUser-Agent
:浏览器的用户代理字符串
响应头
Date
:表示消息发送的时间,时间的描述格式由rfc822定义server
: 服务器名称Connection
:浏览器与服务器之间连接的类型Cache-Control
:控制HTTP缓存content-type
: 表示后面的文档属于什么MIME类型application/x-www-form-urlencoded
:浏览器的原生 form 表单multipart/form-data
:该种方式也是一个常见的 POST 提交方式,通常表单上传文件时使用该种方式。application/json
:服务器消息主体是序列化后的 JSON 字符串。text/xml
:该种方式主要用来提交 XML 格式的数据。
5. HTTP请求报文和响应报文
请求报文
- 请求行
- 请求方法
- 请求地址
- 协议版本
- 请求头(header)
- 空行(用于分隔请求头和请求数据,即使没有请求数据,空行也不能省略)
- 请求体
响应报文
- 响应行
- 协议版本
- 状态码
- 200:请求成功
- 301:资源(网页等)被永久转移到其他URL
- 404:请求的资源(网页等)不存在
- 500:内部服务器错误
- …
- 状态文字
- 响应头
- 键值对
- content-length: 响应主体长度
- 空行
- 响应体
6. Http1.0、Http1.1、Http2.0协议的区别
Http 1.0
- 无状态:服务器不跟踪不记录请求过的状态
- 可以借助cookie/session机制来做身份认证和状态记录
- 无连接:浏览器每次请求都需要建立tcp连接
- 无法复用连接:每次发送请求,都需要进行一次tcp连接( 即3次握手4次挥手),使得网络的利用率非常低
- 队头阻塞:在前一个请求响应到达之后下一个请求才能发送,如果前一个阻塞,后面的请求也会阻塞的
Http 1.1
- 长连接(keep-alive):新增
Connection
字段,可以设置keep-alive
值保持连接不断开 - 管道化:基于上面长连接的基础,管道化可以不等第一个请求响应继续发送后面的请求,但响应的顺序还是按照请求的顺序返回
- 缓存处理:新增字段
cache-control
- 文件断点续传
Http 2.0
- 二进制分帧:将所有传输的信息分割为更小的消息和帧,并对它们采用二进制格式的编码
- header头部压缩:使用HAPCK算法对header数据进行压缩,使数据体积变小,传输更快
- 服务器推送:服务器可以额外的向客户端推送资源,而无需客户端明确的请求
- 多路复用:在共享TCP连接的基础上,客户端和服务器可以同时发送多个请求或响应,而且不用按照顺序一一发送,避免了 “队头堵塞”
7. HTTP 和HTTPS 协议的区别
- 证书:
HTTPS
协议需要CA
证书;而HTTP
协议不需要; - 传输:
HTTP
信息是明文传输的;HTTPS
则是SSL加密的,更加安全; - 端口:
HTTP
协议端口是80
,HTTPS
协议端口是443
; - 协议:
HTTP
基于TCP/IP,HTTPS
是基于HTTP
的,额外增加了SSL/TSL
连接加密
8. 浏览器网页访问流程
- DNS解析:获取该域名的 IP 地址
- 获取MAC地址:目标IP和本机IP分别与子网掩码相与的结果相同,那么它们在一个子网,通过ARP协议可以查到目标主机的MAC地址,否则的话,需要通过网关转发,也就是目标MAC是网关的MAC。
- 建立 TCP 连接:TCP三次握手
- 发送GET请求:浏览器发送GET请求获取页面html
- 返回数据:服务器收到请求返回一个 html 文件作为响应
- 页面渲染:浏览器对该html文件进行解析,渲染显示。
- 断开TCP连接:如果没有再使用这个 TCP 连接,那么浏览器就会断开这个TCP连接(TCP四次挥手);如果浏览器或者服务器在其头部加入了
Connection:Keep-Alive
,那么这个TCP连接发送完仍然保持着连接状态,一般保持2小时。 - 浏览器渲染:解析html,生成DOM树;解析CSS,生成CSS规则树;生成渲染树;绘制页面。
- js代码解析执行
9. URI和URL
URI:统一资源标识符(Uniform Resource Identifiers, URI),是用来标识一个具体的资源的,我们可以通过 URI 知道一个资源是什么。URI是抽象的定义,不用什么方法表示,只要能定位一个资源,就叫URI,常用的使用两种定位方法:
- URL,用地址定位;
- URN,用名称定位。
URL:统一资源定位符(Uniform Resource Locator,URL),是用来定位具体的资源的,标示了一个具体的资源位置。URL是URI的一个子集,具体来说就是浏览器地址栏中的网址。
10. URL的组成
- 协议:代表网页使用的是协议类型。常见的有如
http
、https
、ftp
、file
、mailto
等,本例中的协议为HTTPS
协议。 - 主机:本例中的主机名为
www.example.com
。注:主机名可以为域名或IP地址。 - 端口:域名
:
后面的数字为端口。端口不是一个URL必须的部分,如果省略端口,将采用默认端口(HTTP协议默认端口是80
,HTTPS协议默认端口是443
)。本例中的端口为8080
。 - 路径:从域名后的第一个
/
开始到?
为止,(如果没有?
,则到#
为止,如果?
和#
都没有,则到URL最后),是URL路径部分,一般用来表示主机上的一个目录或者文件地址。本例中的路径部分为/test/index
。 - 参数:从
?
开始到#
为止之间的部分为参数部分,又称搜索部分
、查询部分
。本例中的参数部分为id=1&cate=2
。参数可以允许有多个参数,参数与参数之间用&
分隔。 - 锚:从
#
开始到最后部分,前端用来做页面定位。本例中的锚部分是#header
。
11. HTTP缓存
HTTP缓存主要分为协商缓存
与强缓存
,它们的基本原理如下:
- 浏览器在加载资源时,根据响应头的
Expires
和Cache-Control
判断是否命中强缓存,是则直接从缓存读取资源,不会发请求到服务器。 - 如果没有命中强缓存,浏览器一定会发送一个请求到服务器,通过
Last-Modified
和Etag
验证资源是否命中协商缓存,如果命中,服务器会将这个请求返回,但是不会返回这个资源的数据,依然是从缓存中读取资源 - 如果前面两者都没有命中,直接从服务器加载资源
12. HTTP 常用的请求方式,区别和用途?
请求方式 | 用途 |
---|---|
GET | 对服务器资源获取的简单请求 |
POST | 用于发送包含用户提交数据的请求 |
PUT | 向服务器提交数据,以修改数据 |
HEAD | 请求页面的首部,获取资源的元信息 |
DELETE | 删除服务器上的某些资源 |
CONNECT | 用于ssl隧道的基于代理的请求 |
OPTIONS | 返回所有可用的方法,常用于跨域 |
TRACE | 追踪请求-响应的传输路径 |
参考文档
1. 「2021」高频前端面试题汇总之计算机网络篇.CUGGZ
2. 一个TCP连接可以发送几个HTTP请求
3. HTTP缓存
4. 一文读懂http缓存
5.2W字!梳理50道经典计算机网络面试题(收藏版)