HTTP/2技术调研

HTTP/2简介

2015年,HTTP/2发布。HTTP/2是现行HTTP协议(HTTP/1.x)的替代,但它不是重写,HTTP方法/状态码/语义都与HTTP/1.x一样。HTTP/2基于SPDY3,专注于性能,最大的一个目标是在用户和网站间只用一个连接(connection)。

HTTP/2没有改动HTTP的应用语义。 HTTP方法、状态代码、URI和标头字段等核心概念一如往常。 不过相较于HTTP/1.1来说,HTTP/2提供有如下新特性:

(1)多路复用

HTTP/2使用多路复用技术,同一个TCP连接可以并发处理多个请求。

(2)首部压缩

HTTP/1.1的首部带有大量信息,而且每次都要重复发送。HTTP/2.0要求通讯双方各自缓存一份首部字段表,从而避免了重复传输。

(3)服务端推送

HTTP/2在客户端请求一个资源时,会把相关的资源一起发送给客户端,客户端就不需要再次发起请求了。例如客户端请求index.html页面,服务端就把index.js一起发给客户端。

(4)二进制分帧

HTTP/1.1的解析是基于文本的,而HTTP/2采用二进制格式。

HTTP/2二进制分帧层

在不改动HTTP/1.x的语义、方法、状态码、URI以及首部字段等情况下, HTTP/2是如何做到「突破HTTP1.1的性能限制,改进传输性能,实现低延迟和高吞吐量」的?关键之一就是在应用层(HTTP/2)和传输层(TCP/UDP)之间增加一个二进制分帧层。

在二进制分帧层中, HTTP/2会将所有传输的信息分割为更小的消息和帧(frame),并对它们采用二进制格式的编码 ,其中HTTP1.x的首部信息会被封装到HEADER frame,而相应的Request Body则封装到DATA frame里面。

HTTP/2通信都在一个连接上完成,这个连接可以承载任意数量的双向数据流。

在过去, HTTP性能优化的关键并不在于高带宽,而是低延迟。TCP连接会随着时间进行自我「调谐」,起初会限制连接的最大速度,如果数据成功传输,会随着时间的推移提高传输的速度。这种调谐则被称为TCP慢启动。由于这种原因,让原本就具有突发性和短时性的HTTP连接变的十分低效。HTTP/2通过让所有数据流共用同一个连接,可以更有效地使用TCP连接,让高带宽也能真正的服务于HTTP的性能提升。

总结,单连接多资源的方式,减少服务端的链接压力,内存占用更少,连接吞吐量更大;由于TCP连接的减少而使网络拥塞状况得以改善,同时慢启动时间的减少,使拥塞和丢包恢复速度更快。

备注:Stream Identifier编号,表示了不同的HTTP请求/响应交互。

帧的种类有如下几种:

多路复用

多路复用,代替原来的序列和阻塞机制。所有的请求都是通过一个TCP连接并发完成。 HTTP 1.x中,如果想并发多个请求,必须使用多个TCP链接,且浏览器为了控制资源,还会对单个域名有6-8个的TCP链接请求限制。比如Chrome有个机制,对于同一个域名,默认允许同时建立6个TCP持久连接。使用持久连接时,虽然能共用一个TCP管道,但是在一个管道中同一时刻只能处理一个请求,在当前的请求没有结束之前,其他的请求只能处于阻塞状态,如果在同一个域名下同时有10个请求发生,那么其中4个请求会进入排队等待状态,直至进行中的请求完成。

HTTP/2可以很容易的去实现多流并行而不用依赖建立多个TCP连接。如下图,红色圈出来的请求就因域名链接数已超过限制,而被挂起等待了一段时间:

服务端推送

服务端可以在发送页面HTML时主动推送其它资源,而不用等到浏览器解析到相应位置,发起请求再响应。例如客户端向服务端请求index.html页面,html页面中嵌有JS和CSS文件,服务端可以主动把JS和CSS文件推送给客户端,而不需要客户端解析HTML时再发送这些请求。

服务端可以主动推送,客户端也有权利选择是否接收。如果服务端推送的资源已经被浏览器缓存过,浏览器可以通过发送RST_STREAM帧来拒收。主动推送也遵守同源策略,服务器不会随便推送第三方资源给客户端。

首部压缩

HTTP/1.1请求的大小变得越来越大,有时甚至会大于TCP窗口的初始大小,因为它们需要等待带着ACK的响应回来以后才能继续被发送。HTTP/2对消息头采用HPACK(专为HTTP/2头部设计的压缩格式)进行压缩传输,能够节省消息头占用的网络的流量。而HTTP/1.x每次请求,都会携带大量冗余头信息,浪费了很多带宽资源。

HTTP/2开启方法

(1)服务端开启HTTP/2

在Nginx的配置文件nginx.conf增加如下内容:

listen [::]:443 ssl http2 ipv6only=on; 
listen 443 ssl http2;

(2)客户端开启HTTP/2

主流浏览器都支持了HTTP/2啦。是否使用HTTP/2通信,还需要浏览器和服务端进行协商才可以啦。

学习资料参考于:
https://www.infoq.cn/article/kU4OkqR8vH123a8dLCCJ
https://blog.fundebug.com/2019/03/07/understand-http2-and-http3/