HTTP 概要
HTTP 1.0
Feature
短连接
每次发送请求都要重新建立 TCP 请求(三次握手协议), 性能较差
无 host 头域
HTTP 请求头里面不包含 Host 域
不允许断点续传
不能传输对象的一部分, 要求传输整个对象
HTTP 1.1
Feature
缓存处理
HTTP1.0中使用header里的If-Modified-Since,Expires 作为缓存判断的标准,而HTTP1.1则引入了更多的缓存控制策略例如Entity tag,If-Unmodified-Since, If-Match, If-None-Match等更多可供选择的缓存头来控制缓存策略。
Host 头域处理
HTTP1.0中, 认为每台服务器都应绑定一个唯一 IP 地址, 所以请求消息中的URL并没有传递主机名 (hostname)。但随着虚拟主机技术的发展,在一台物理服务器上可以存在多个虚拟主机 (Multi-homed Web Servers) ,并且它们共享一个IP地址。
此外, HTTP1.1的请求消息和响应消息都支持Host头域,且请求消息中如果没有Host头域会报告一个错误 (400 Bad Request)。
长连接
HTTP 1.1支持长连接 (PersistentConnection) 和请求的流水线 (Pipelining) 处理,在一个TCP连接上可以传送多个HTTP请求和响应,减少了建立和关闭连接的消耗和延迟,在HTTP1.1中默认开启Connection: keep-alive,一定程度上弥补了HTTP1.0每次请求都要创建连接的缺点。
请求头引入 Range 头域
在HTTP1.0中,存在一些带宽资源浪费现象, 例如客户端只是需要某个对象的一部分,而服务器却不得不将整个对象送过来,并且不支持断点续传功能,HTTP1.1则在请求头引入了 Range头域,它允许只请求资源的某个部分,状态返回码是 206 (Partial Content),方便工程师自由选择, 便于充分利用带宽和连接。
HTTP 2.0
Faeture
新的二进制格式 (Binary Format)
HTTP1.x的解析是基于文本, 基于文本协议的格式解析存在天然缺陷,文本的表现形式有多样性,要做到健壮性考虑的场景很多,二进制则不同,只考虑0和1的组合。因此, HTTP2.0的协议解析决定采用二进制格式,实现方便且健壮。
多路复用 (MultiPlexing)
连接共享, 一个连接上可以有多个 request (一个 request 对应一个id), 每个连接的request可以随机的混合在一起, 而接收方可以根据 request 的 id 将request再归属到各自不同的服务端请求里面。
Header压缩
HTTP1.x的 Header 带有大量信息, 且每次都需要重复发送,而HTTP2.0使用encoder来减少需要传输的header大小,通讯双方各自缓存一份header fields表。一方面避免重复 Header 的传输,同时又减小需要传输对象的大小。
服务端推送 (server push)
HTTP2.0具有server push功能。
HTTP 3.0
Feature
HTTP Over QUIC
HTTP 3.0 基于 Google 的 QUIC 协议, 而 QUIC 是运用 UDP 做的实现. 减少 TCP 三次握手建立时间和 TLS 安全传输协议握手时间。
解决TCP的队头阻塞
解决HTTP 2.0 中存在的前一个 stream 丢包后导致后一个stream阻塞的问题。
优化重传策略
以往版本的 HTTP 协议中, TCP丢包重传策略是: 在发送端为每一个封包标记一个编号(sequence number),接收端在收到封包时,就会回传一个带有对应编号的ACK封包给发送端,告知发送端封包已经确实收到。当发送端在超过一定时间之后还没有收到回传的ACK,就会认为封包已经丢失,启动重新传送的机制,复用与原来相同的编号重新发送一次封包,确保在接收端这边没有任何封包漏接。
这样的机制就会带来一些问题,假设发送端总共对同一个封包发送了两次(初始+重传),使用的都是同一个sequence number: 编号N。之后发送端在拿到编号N封包的回传ACK时,将无法判断这个带有编号N的ACK,是接收端在收到初始封包后回传的ACK。这就会加大后续的重传计算的耗时。
QUIC为了避免这个问题,发送端在传送封包时,初始与重传的每一个封包都改用一个新的编号,unique packet number,每一个编号都唯一而且严格递增,这样每次在收到ACK时,就可以依据编号明确的判断这个ACK是来自初始封包或者是重传封包。
连接迁移
不在采用 TCP 元组形式确定一个连接, 而是采用一个 64 位随机数来确定这个连接
流量控制
通过流量控制可以限制客户端传输资料量的大小,接收端可以只保留相对应大小的接收 buffer , 优化记忆体被占用的空间。但是如果存在一个流量极慢的stream ,光一个stream就有可能估用掉接收端所有的资源。
QUIC为了避免这个潜在的HOL Blocking,采用了连线层(connection flow control)和Stream层的(streamflow control)流量控制,限制单一Stream可以占用的最大buffer size。
Reference
|