小测试对 HTTP/2 的了解

1. 字如其名

HTTP 协议名称为超文本传输协议,字面意思可以看出 HTTP 诞生之初其实是为了传输超文本,也就是 HTML(超文本标记语言)。但是随着各种技术的发展,网络世界中需要传输的内部不再局限于超文本,于是就迎来了 HTTP1.1,也就是现在主要使用的 HTTP 协议。

  • 截屏来自百度首页
     
    HTTP1.1 是以 REST 理论(1998 年 RoyT. Fielding 博士提出)为指导设计出来的。在 HTTP1.1 中引入 “资源” 这个极为重要的抽象概念,将 HTTP 从一种面向文档的协议彻底转换为一种面向资源的协议。“资源” 是一种很强大的抽象工具,Web 之上不再只有大量具体,静态的 “文档”,而是包括了无数抽象,动态的 “资源”。 难以想象的事 HTTP/1.1 从 1998 年发布之后,已经二十几年没有更新了,很多方面难以跟上时代发展的要求。例如:一个网页包含了几百个请求的应用场景。 于是,经过各方参与者几年的不懈努力,HTTP/2 在 2015 年正式发布。 HTTP/2,简称 h2,目的是提升加载 Web 内容时的感知性能。

2. HTTP/2 概述

2.1 HTTP/1.1 缺点

  • 队头阻塞
    • 一个页面所有的图片资源都在 OSS 服务商。如果仅仅使用一个连接,需要发送请求,等待,响应之后才能发送下一个请求。
    • 在请求应答过程中,如果出现任何状况,剩下所有的工作都会阻塞在那次请求应答之后。
    • 假如我们今天要在外卖平台 10 份外卖的时候:第一笔下单,付款是一个正常的流程。然后第二单:下单,付款,“余额不足”,然后未付款,那么接下来的 8 份外卖会因为这一份外卖而导致无法正常工作。
  • 低效的 TCP 利用
    • TCP 是可靠的传输协议,除了三次握手,每次报文都需要 ACK 确认之外,还有一个专门针对于最差的网络状况的设计:拥塞控制。
    • 拥塞控制是指在接收方确认数据包之前,发送方可以发出的 TCP 包的数量。
    • 例如:如果拥塞窗口指定为 1,那么发送方发出 1 个数据包之后,只有接收方确认了那个包,才能发送下一个。
    • TCP 慢启动,慢启动指的是探索当前连接对应拥塞窗口的合适大小。目的是为了让新连接搞清楚当前网络状况,避免给已经拥堵的网络添乱。
    • 于是,问题就来了,在现在一个网页是 10 个请求,20 个请求的时候,甚至更多的请求连接的时候,这几次慢启动的数据往返,每个连接都避免不了拥塞窗口的调节。
  • 臃肿的消息首部
    • 虽然 HTTP/1.1 提供了压缩请求内容的机制,但是报文头部是无法压缩的,尽管它比响应资源少,但是可能占请求的绝大部分。
    • 例如:get 请求,option 请求,算上 cookie 的话几千字节就很正常了。
    • 上面说的拥塞窗口的往返确定,再加上稍大消息首部,在一些网络延迟中的损耗就会被迅速放大。
    • 例如:“体育馆效应”,成千上万人在同一时间出现在同一地点,会迅速消耗带宽,这时候,如果能压缩请求头部,把请求变的更小,就能缓解带宽压力,降低负载。

2.1 前身 SPDY

详情可以参考这篇博客:https://www.cnblogs.com/keva/p/spdy-protocol.html

HTTP2/2 诞生之前,Google 提出了一种 HTTP 的替代方案:SPDY。
在 SPDY 之前,人们认为在商业应用中没有必要对 HTTP/1.1 做出突破性的,不兼容的改变。要兼容浏览器,服务器,网络代理和其他各种各样的中间件,代价极其昂贵(比如我们这一代人讲了 20 多年的中国话,突然有一天要把日常用语转换为其他的语言,这个转换成本是要经过一代人的努力的)。
SPDY 协议在性能上对 HTTP 做了优化,核心是尽量减少连接个数。于是 SPDY 奠定了 HTTP/2 的基础,例如多路复用,帧和首部压缩等。

2.2 HTTP/2 期望

由于【2.1 HTTP/1.1 缺点】内标注的一些问题,HTTP 工作组在启动下一个 HTTP 版本的工作的时候,纲领的关键部分阐述了工作组对新协议的期望(也就是我们日常项目中的需求文档):

  • 相比于使用 TCP 的最终用户可感知的多数延迟都有能够量化的显著改改善
  • 解决 HTTP 中的队头阻塞问题
  • 并行的实现机制不依赖与服务器建立多个连接,从而提升 TCP 连接的利用率,特别是在拥塞控制方面
  • 保留 HTTP/1.1 的语义,可以利用已有的文档资源 (如上所述),包括 (但不限于

方法、状态码、∪RI 和首部字段

  • 明确定义 HTTP1.x 和 HTTP/2.0 交互的方法,特别是通过中介时的方法 (双向)
  • 明确指出它们可以被合理使用的新的扩展点和策略

2.3 报文展示

报文文件:https://gitee.com/wangyix/book/tree/master/%E6%8A%80%E6%9C%AF%E5%B0%9D%E9%B2%9C/HTTP2/%E6%8A%A5%E6%96%87

从我的经验来看,想快速了解协议的话,直接看协议的报文结构是最快的。因为协议的一些特性都在报文上体现,而代码/调试工具只是来模拟报文进行发送/响应。

  • HTTP/1.1 报文

     

     

  • HTTP/2 报文

报文具体内容可以搜下:HTTP/2 帧结构/-

 

 

 

3. HTTP/2 特性

https://halfrost.com/http2-http-frames-definitions/

3.1 帧结构

HTTP/2 的报文被称为:分帧层。更改了数据传输类型,放弃了庞大的数据包,改用数据帧来传输数据。因此,HTTP/2 是一个二进制协议,方便了机器解析,但是肉眼看起来比较困难
分帧层大致可以分为两部分:headers 和 data。不管怎么设计,目的都是传输 HTTP,而不是其他内容。
报文结构如下所示:

 

 

3.2 流(多路复用)

3.2.1 流定义

HTTP/2 规范对流的定义是:HTTP/2 连接上独立的,双向的帧序列和交换。

 

 

 

 

流,是连接上的一系列帧的统称,或者可以叫做会话流。
如果客户端想要发出请求,就会开启一个新的流(发送 headers 帧。

 

 

然后,服务器将在这个流上回复。和 HTTP/1.1 的请求/响应流程区别在于有分帧,所以多个请求和响应可以交错,而不会互相阻塞。流 ID 用来表示帧所属的流。

 

 

3.2.2 流程控制

HTTP/2 中,一切几乎都是对称的。

服务端和客户端都可以调整传输的速度。而在 HTTP/1.1 中,只要客户端可以处理,服务器就会尽可能快的发送数据。
当一端接收并消费被发送数据时,它将发出一个 WINDOW_UPDATE 帧来指示更新后的处理字节的能力。

 

 

3.2.3 其他特性

  • 优先级
  • 服务端推送

3.3 首部压缩

首部压缩(HPACK)是 HTTP/2 的关键因素。HPACK 是一种表查找压缩方案,利用霍夫曼编码获得接近 GZIP 的压缩率。
大概指的是:
请求端和响应端各维护了两张表格。其中之一是动态表,一张是静态表,由最常见首部的键值组合而成。

 

 

服务器会查找对应的表格,并把这些数字还原成索引对应的完整首部。

 

 

4. 测试须知

从【3.1】的帧结构可知 HTTP/2 是一个二进制协议,所以需要了解一个对二进制友好的数据结构:protobuf。
目前基于 HTTP/2 的服务的话,主流的是 Grpc 框架,对应延伸出来的就是 grpc 调试工具。

 

 

posted @ 2021-08-24 16:02  杭州铁锤  阅读(165)  评论(0编辑  收藏  举报