HTTP/2 前端应该了解的知识点

基础概念

帧: 消息通信的最小单位,一个请求或者响应由一个或多个帧组成。

流: 链接中的一个虚拟通道,每个流有一个唯一的整数ID。

HTTP/2采用二进制格式传输数据(HTTP/1采用的文本格式),二进制协议解析起来更高效。

HTTP/2中,同域名下的所有通信都是再单个链接上完成的,该链接可以承载任意数量的双向数据流。多个帧可以乱序发送,根据帧首部流标识重新组装。

多路复用

所有请求都是通过一个TCP连接并发完成。

HTTP/1中如果想并发多个请求,必须使用多个TCP链接,且浏览器为了控制资源,会对单个域名有6-8个TCP链接请求的限制,超过限制会被挂起等待。

HTTP/2使用二进制分帧之后,不在依赖TCP链接去实现多流并行了。再HTTP/2中:

  • 同域名下所有通信都在单个链接上完成

  • 单个链接可以承载任意数量的双向数据流

  • 数据流以消息的形式发送,一个消息由一个或者多个帧组成,多个帧之间可以乱序发送,根据帧首部流标识重新组装。

这一特性使性能有极大提升:

  • 同个域名只需要一个TCP链接,消除了因多个TCP链接而带来的延时和内存消耗/

  • 单个连接上并行交错的请求和响应,互不影响

  • HTTP/2中每个请求都可以携带优先级标识,采取不同策略发送流消息和帧。

服务器推送

HTTP/1 中,同一个TCP链接里,上一个回应response发送完了,服务器才能发送下一个,但在HTTP/2中可以多个response一起发送。

举个例子:一个简单的HTML页面

<html>
    <head>
        <link rel="stylesheet" href="style.css">
    </head>
    <body>
        <img src="example.png">
    </body>
</html>

这里面有三个文件需要处理:1. HTML页面 2. css文件style.css 3. 图片example.png。在HTTP/1 中client需要发送三个请求给Server

GET /index.html HTTP/1.1
GET /style.css HTTP/1.1
GET /example.png HTTP/1.1

平时为了解决这种问题,一般采用:

  • png转base64 嵌入css文件或这html文件

  • preload预加载,加载上一个页面的时候以前下载相关资源,但是这种方式没有减少http请求次数。 <link rel="preload" href="/style.css" as="style">

但是HTTP/2的server push可以实现,当client只请求index.html的时候,server把index.htmlstyle.cssexample.png全部发送给client,只需要一轮HTTP通信,Client就得到了全部资源。

头部压缩

HTTP/2对消息头进行压缩,节省消息头占用的网络流量。

在client与服务器之间:

  • 维护一份相同的静态表,包含常见的头部名称,以及特别常见的头部名称与值的组合

  • 维护一份相同的动态表,可以动态添加内容;

  • 基于静态哈夫曼码表的哈夫曼编码;

在HTTP头里,有些key:value是固定的,eg:

:method: GET
:scheme: http

在编码时,它们直接用一个index编号代替,例如:method:GET是2,这些在一个静态表定义。对于静态表里的字段,原来需要N个字符表示的现在只需要一个索引即可

如何判断是否支持HTTP/2

Chrome控制台中,打开network tab,看到请求的protocol为h2的就是HTTP/2的请求。

如何开启HTTP/2

需要后端支持 linux。也可以在nodejs中启用HTTP/2,nodejs官网示例:

// 服务器端示例
const http2 = require('http2');
const fs = require('fs');
​
const server = http2.createSecureServer({
  key: fs.readFileSync('localhost-privkey.pem'),
  cert: fs.readFileSync('localhost-cert.pem')
});
server.on('error', (err) => console.error(err));
​
server.on('stream', (stream, headers) => {
  // 流是双工的
  stream.respond({
    'content-type': 'text/html; charset=utf-8',
    ':status': 200
  });
  stream.end('<h1>Hello World</h1>');
});
​
server.listen(8443);

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值