IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> 网络协议 -> HTTP2牛逼在哪儿? -> 正文阅读

[网络协议]HTTP2牛逼在哪儿?

一、HTTP1.1的高延迟性能问题

  • HTTP头部巨大且重复
  • 对头阻塞问题
  • 不支持服务器推送消息
  • 并发连接有限

二、HTTP2的针对HTTP1.1的优化

兼容老版本

  • HTTP没有在URI里引入新的协议名,仍然用http://表示明文协议,用https://表示加密协议, 于是只需要浏览器和服务器在背后自动升级协议,这样可以让用户意识不到协议的升级,很好的实现了协议的平滑升级。
  • 只在应用层做了改变,还是基于 TCP 协议传输,应用层方面为了保持功能上的兼容,HTTP2把HTTP分解成了语义和语法两个部分,语义层不做改动,与 HTTP1.1 完全?致,比如请求方法、状态码、头字段等规则保留不变。 但是,HTTP/2 在语法层面做了很多改造,基本改变了 HTTP 报文的传输格式。

头部压缩

HTTP1.1存在的问题

  • 存在很多固定字段,比如Cookie、Accept等,加起来占的字节高达几百到几千,有必要进行压缩。
  • 大量的请求和报文里很多字段都是重复的,有必要避免重复性。
  • 字段是ASCII编码的,虽然易于观察,但不适合传输,有必要改成二进制编码。

HTTP2没有使用常见的gzip,而是开发了HPACK算法

  • 静态字典
  • 动态字典
  • Huffman编码(压缩算法)

客户端和服务器两端都会建立和维护字典,用长度较小的索引号表示重复的字符串,再用Huffman 编码压缩数据,可达到 50%~90% 的高压缩率。

静态表编码

概述

HTTP2为高频出现在头部的字符串和字段建?了?张静态表,它是写入到 HTTP2框架里的,不会变化的,静态表里共有61组。

过程

例如,server头部字段的Index为 54,?进制为110110,再加上固定01,头部格式第1个字节就是 01110110,第二个字节的首个比特位表示Value是否经过 Huffman编码,剩余的 7 位表示Value的长度,10000110,首位为1,表示 Value字符串是经过Huffman编码的,经过Huffman编码的Value长度为6。

动态表编码

概述

静态表只包含了 61 种?频出现在头部的字符串,不在静态表范围内的头部字符串就要自行构建动态表,它的Index从62起步,会在编码解码的时候随时更新。

过程

例如,第?次发送时头部中的user-agent字段数据有上百个字节,经过 Huffman 编码发送出去后,客户端和服务器双方都会更新自己的动态表,添加?个新的Index号62。那么在下?次发送的时候,就不用重复发这个字段的数据了,只用发 1 个字节的 Index号就好了,因为双方都可以根据自己的动态表获取到字段的数据。

使用前提

使用动态表的前提是:必须同?个连接上,重复传输完全相同的 HTTP 头部。如果消息字段在 1 个连接上只发送了1次,或者重复传输时,字段总是略有变化,动态表就无法被充分利用了。

不足

动态表越大,占用的内存也就越大,如果占用了太多内存,是会影响服务器性能的,因此Web服务器都会提供类似 http2_max_requests 的配置,用于限制?个连接上能够传输的请求数量,避免动态表无限增大,请求数量到达上限后,就会关闭 HTTP/2 连接来释放内存。

二进制帧

HTTP/2 把响应报文划分成了两个帧(首部,消息负载)传输,并采用二进制来编码。
首部

  • 前3个字节:代表数据帧的长度
  • 第4个字节:表示帧的类型(共有10种,一般分为数据帧和控制帧)
  • 第5个字节:标志位,用于携带简单的控制信息
    • END_HEADERS 表示头数据结束标志
    • END_STREAM 表示单方向数据发送结束,后续不会再有数据帧
    • PRIORITY 表示流的优先级
  • 最后4个字节:流标识符(StreamID),但最高位被保留不用,只有 31 位可以使用,它的作用是用来标识该 Fream 属于哪个Stream,接收方可以根据这个信息从乱序的帧里找到相同StreamID的帧,从而有序组装信息。

消息负载

  • HPACK算法压缩过的HTTP头部
  • HPACK算法压缩过的 HTTP包体
    HTTP2二进制帧结构
    在这里插入图片描述

并发传输

Steam、Message、Frame之间的关系

  • 1个TCP连接包含?个或者多个Stream
  • Stream里可以包含1个或多个Message,Message对应 HTTP1中的请求或响应,由HTTP 头部和包体构成
  • Message里包含?条或者多个Frame,Frame 是 HTTP/2最小单位,以?进制压缩格式存放HTTP/1中的内容(头部和包体)
  • HTTP消息可以由多个Frame构成,以及1个Frame可以由多个TCP报文构成

StreamID

  • 不同 Stream的帧是可以乱序发送的(因此可以并发不同的 Stream ),因为每个帧的头部会携带Stream ID信息,所以接收端可以通过Stream ID有序组装成HTTP消息,而同一Stream内部的帧必须是严格有序的。
  • 客户端建立的 Stream ID必须是奇数号,而服务器建立的Stream必须是偶数号。
  • 同?个连接中的 Stream ID是不能复?的,只能顺序递增,所以当 Stream ID 耗尽时,需要发?个控制帧 GOAWAY ,用来关闭 TCP 连接。 在 Nginx 中,可以通过http2_max_concurrent_streams 配置来设置 Stream 的上限,默认是 128 个

Stream优先级

HTTP/2还可以对每个Stream 设置不同优先级,帧头中的标志位可以设置优先级。
在这里插入图片描述

服务器主动推送资源

客户端发起的请求,必须使?的是奇数号Stream,服务器主动的推送,使用的是偶数号 Stream。服务器在推送资源时,会通过PUSH_PROMISE帧传输 HTTP 头部,并通过帧中的Promised Stream ID字段告知客户端,接下来会在哪个偶数号Stream 中发送包体。
在Stream 1中通知客户端CSS 资源即将到来,然后在Stream2中发送 CSS 资源,注意 Stream1和2是可以并发的。

  网络协议 最新文章
使用Easyswoole 搭建简单的Websoket服务
常见的数据通信方式有哪些?
Openssl 1024bit RSA算法---公私钥获取和处
HTTPS协议的密钥交换流程
《小白WEB安全入门》03. 漏洞篇
HttpRunner4.x 安装与使用
2021-07-04
手写RPC学习笔记
K8S高可用版本部署
mySQL计算IP地址范围
上一篇文章      下一篇文章      查看所有文章
加:2021-10-11 17:52:51  更:2021-10-11 17:54:33 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 -2024/11/26 3:45:20-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码