前端必知的 HTTP

83 阅读8分钟

http 0.9

只有 GET 请求, 响应只有文件内容本身

http 1.0

特点:

  1. 引入了请求头和响应头。可以根据 Header 的不同来处理不同的资源。

  2. 引入了状态码。

  3. 引入了服务端缓存机制,减轻服务器压力。

  4. 支持长链接,默认是短连接。

缺点:

  1. 队头阻塞:等上一个请求响应后,才可以下一次请求。上一个请求迟迟没有响应,就会阻塞下一次请求。

  2. 默认是短连接,每个 TCP 连接只能发送一个 http 请求。也就是说每个 http 请求都要使用 TCP 的三次握手与四次挥手。

http 1.1

特点:

  1. 默认开启 keep-alive, 长连接。

  2. http 请求可以复用 TCP 连接。

  3. 管线化。同一个域名,默认允许同时建立 6 个 TCP 长连接。也就是说同一时间最多可以有 6 个 http 请求。

  4. 引入了 Cookie。

缺点:

  1. 队头阻塞:6 个 TCP 长连接能够,但是依然存在队头阻塞的问题。

  2. http 头部内容较多,增加了传输成本

  3. 明文传输,不安全

http 2

特点:

  1. 头部压缩,减少请求数据的大小。

  2. 多路复用,并行请求。一个域名建立一个 TCP 连接。单个 TCP 连接可以承载任意数量的 http 请求。

  3. 服务器可以推送数据给客户端。

  4. 使用 TLS 来加密通信,更安全。

缺点:

  1. 增加了连接延时。TLS 握手也需要一定时间。

  2. 依然存在队头阻塞。由于只有一个 TCP 连接,一旦丢包,整个 TCP 都要等待重传,这会阻塞该 TCP 连接中的所有请求。

  3. 多路复用导致服务器压力增大

  4. 多路复用导致带宽、服务器等资源稀释,容易造成超时

http 3

采用 UDP。解决了 TCP 的队头阻塞问题。在 UDP 上加了一个 QUIC(快速 UDP 互联网连接)协议。

quic.png

http3 中的 QUIC 协议集合了以下几点功能:

  1. 实现了类似 TCP 的流量控制、传输可靠性的功能。

虽然 UDP 不提供可靠性的传输,但 QUIC 在 UDP 的基础之上增加了一层来保证数据可靠性传输。它提供了数据包重传、拥塞控制以及其他一些 TCP 中存在的特性。

  1. 集成了 TLS 加密功能。

目前 QUIC 使用的是 TLS1.3,相较于早期版本 TLS1.3 有更多的优点,其中最重要的一点是减少了握手所花费的 RTT 个数。

  1. 实现了多路复用的功能。

和 TCP 不同,QUIC 实现了在同一物理连接上可以有多个独立的逻辑数据流。实现了数据流的单独传输,就解决了 TCP 中队头阻塞的问题。

  1. 实现了快速握手功能。

由于 QUIC 是基于 UDP 的,所以 QUIC 可以实现使用 0-RTT 或者 1-RTT 来建立连接,这意味着 QUIC 可以用最快的速度来发送和接收数据,这样可以大大提升首次打开页面的速度。

https

http 与 https 区别

二者的主要区别在于安全性。

  1. http 是明文传输,https 使用 TLS/SSL 协议进行加密。

  2. https 要求使用数字证书。一定程度上避免了中间人攻击。

  3. http 端口是 80,https 端口是 443

https 工作流程

TCP 三次握手

在建立 HTTPS 连接之前,客户端和服务器之间进行三次握手,以建立 TCP 连接。

TLS 握手

在 TCP 连接建立后,客户端和服务器之间开始进行 TLS 握手,以建立安全连接。具体步骤如下:

  1. 客户端向服务器发送一个 ClientHello 消息, 其中包含以下信息:
  • 支持的 TLS 版本列表:客户端支持的 TLS 版本。
  • 支持的加密套件列表:客户端支持的加密算法套件(例如 RSA、AES、ECDHE 等)。
  • 随机数:一个随机生成的数值,用于后续的密钥协商。
  • 可选的会话 ID:如果客户端之前与该服务器建立过会话,则会携带该会话 ID。
  1. 服务器向客户的发送 ServerHello 消息,其中包含以下信息:
  • 所选的 TLS 版本:服务器选择的 TLS 版本。
  • 所选的加密套件:服务器选择的加密算法套件。
  • 随机数:服务器生成的随机数。
  • 可选的会话 ID:如果服务器之前与该客户端建立过会话,则会携带该会话 ID。
  1. 服务器发送证书

服务器将证书发送给客户端,该证书包括服务器的公钥,由受信任的第三方证书颁发机构(CA)签名。客户端将使用该证书来验证服务器的身份。

  1. 客户的验证证书

客户端会验证证书的有效性,包括检查证书是否由受信任的 CA 签名,并检查证书中的域名是否与服务器的域名匹配。如果验证失败或客户端没有提供所需的信任根证书,连接将终止。

  1. 客户端发送 ClientKeyExchange 消息

客户端使用服务器的公钥加密生成的预主密钥 Pre-Master Secret,然后发送给服务器。这个步骤确保只有服务器能够解密预主密钥。

  1. 服务器解密预主密钥

服务器通过私钥解密客户端发送的预主密钥, 从而获得主密钥 Master Secret

  1. 握手完成

客户端发送一个 ChangeCipherSpec 消息,通知服务器从现在开始使用协商好的会话密钥进行加密通信。然后,客户端发送一个 Finished 消息,服务器收到后也发送自己的 Finished 消息,用于验证握手过程是否成功。

数据传输阶段

在 TLS 握手成功完成后,客户端和服务器之间的通过主密钥 Master Secret 加密和解密后续的数据传输。

https 是如何保证安全的

1. 加密

https 在握手阶段中使用了非对称加密来协商生成主密钥,在数据传输阶段是通过 (主密钥)对称秘钥进行加密的。

对称加密:

  • 加密和解密使用相同的密钥。
  • 加密速度快,适合用于大量数据的加密传输。
  • 密钥的管理相对简单,但需要确保安全传输密钥。

非对称加密:

  • 加密和解密使用不同的密钥(公钥和私钥)。
  • 加密速度较慢,适合用于小量数据的加密。
  • 公钥可以公开分享,私钥必须保密。
  • 可用于密钥交换和数字签名等安全场景。

https 同时使用了对称加密和非对称加密是出于 兼顾安全性(非对称加密)和效率(对称加密) 的考虑。

2. 证书

数字证书用于验证服务器的身份。

在 TLS 握手的时候,服务器会发送其数字证书给客户端。客户端会验证证书的有效性,包括检查证书是否由受信任的第三方证书颁发机构(CA)签名,证书中的域名是否与实际连接的服务器域名匹配等。这样客户端可以确认连接到的是正确的服务器,而不是恶意仿冒或中间人攻击

TLS 与 SSL

可以简单理解为 TLS 是 SSL 的现代版本,比 SSL 更安全和强大。在实际应用中应尽可能使用 TLS,尽量避免使用较旧的 SSL 版本。

http 缓存

强缓存

强缓存是指浏览器在第一次请求资源时,将资源缓存到本地。并在下一次请求时直接从缓存中获取,而不是向服务器发送请求。

强缓存会返回状态码 200 OK(from memory cache) 或者 200 OK(from disk cache)

from-disk-cache.jpg

强缓存可以通过设置 http 响应头中的 Cache-ControlExpires 字段来实现。

  • Cache-Control: 用来设置缓存的最大时间。

  • Expires: 用来设置缓存的过期时间。

当二者同时设置时候,Cache-Control 优先级更高。

协商缓存

协商缓存是浏览器在第一次请求资源时,服务器会返回一个包含资源信息的响应头 (ETag 和 Last-Modified),浏览器会将信息保存在缓存中。下一次请求时,浏览器会将这些信息 (If-Modified-Since 和 If-None-Match) 发送给服务器,服务器会根据这些信息判断资源是否更新。如果没有更新,则返回一个 304 的响应,告诉浏览器可以直接从缓存中获取资源。

也就是说,浏览器会根据服务器返回的信息来决定是否使用缓存。

304.jpg

协商缓存可以通过设置 http 响应头中的 ETagLast-Modified 字段来实现。

  • ETag: URL 的 tag,用来标识 URL 对应的资源是否改变。

  • Last-Modified: 用来设置资源最后修改时间。

下次请求时, 会在请求头加上 If-Modified-SinceIf-None-Match 来确认是否使用缓存(其实就是跟设置的 ETagLast-Modified 作比较)。

参考文档

解读 HTTP1/HTTP2/HTTP3

Web 开发中的强缓存和协商缓存策略