Http1.0~2演变与实践
AI摘要: 本文介绍了HTTP协议的演变,从HTTP1.0到HTTP2.0,并探讨了其优缺点。文章还讨论了如何在Nginx配置中启用HTTP2.0以提升浏览速度。
Http协议作为互联网时代的基石协议,至今已经演变了近30年。从当初简单的文本传输,到现在支持音频、视频、文本等各种信息,为了满足需求,Http从1.0演变到2.0。这里简单介绍下各个版本的Http优缺点。
HTTP协议的分层设计
| OSI七层网络模型 | TCP/IP四层概念模型 | 对应的网络协议 |
| --------------- | ------------------ | --------------- |
| 应用层 | 应用层 | HTTP,SMTP,FTP |
| 表示层 | 应用层 | Telnet |
| 会话层 | 应用层 | SMTP,DNS |
| 传输层 | 传输层 | TCP、UDP |
| 网络层 | 网络层 | IP、ICMP、ARP |
| 数据链路层 | 数据链路层 | Ethernet |
| 物理层 | 数据链路层 | IEEE 802.1A |
以一次实际的网络传输案例讲解:
由于表示层和会话层已经很少提及,所以客户端和服务端的用户空间数据传输统称为应用层
,比如我们浏览器中的HTTP请求;
HTTP请求需要基于传输层
的TCP连接传输,其他协议的请求可能通过UDP连接请求;
TCP连接需要通过IP地址来确定传输目的地,这就是网络层
;
IP地址需要转化为物理硬件的MAC地址来找到目标网卡,这就是数据链路层
;
网卡的信息需要通过各种网络硬件设计(交换机、光纤)等传输,这就是物理层
;
Http1.0
这是初代Http协议,无状态也无连接。
-
无状态:请求并不会保存客户端的状态,(虽然可以通过Cookie和Session等方式另辟蹊径);
-
无连接:这里指的是无长连接,每一次Http请求都需要建立一条TCP连接,多次挥手和握手注定了它的效率低下;
Http1.1
随着请求的日益增多,频繁的挥手和握手成了了性能瓶颈。
Http1.1的重要优化思路就是多次http请求复用同一个TCP连接。具体而言,通过Keep-alive
来告诉服务端保留TCP连接不关闭,当客户端发送两次Http请求,比如一个请求js文件,另外一个请求css文件,那么两次请求就会按照顺序复用同一个TCP连接, 这就是大名鼎鼎的长连接;
不过,两次请求是按照顺序来实现的。当第一次Http请求向服务端索要js文件的时候,第二个索要css文件的Http请求是无法执行的,必须要等第一次Http请求完全完成才能继续。一般来说,一个网站的js文件的体积大于css文件,对于客户端而言,优先获取到css文件渲染部门页面的用户留存率效果要远远好于先获取js文件再慢慢加载css文件。但是很可惜,Http请求并无法知道需要获取的数据包的大小,因此这里又埋下优化的伏笔。
除此之外,Http1.1还引入了其他的改进:
-
更多的请求方法:delete、put、option;
-
管道机制:在同一个TCP中,不用等待请求结束就可以发送下一个请求,看样子正好可以解决上述Http1.1的问题,但是实际上因为设计问题,无法实现,并不推荐使用;
-
引入了Host:同一个IP可以部署多个网站,每个网站拥有不同的Host;
总而言之,这一代Http协议最大亮点便是同一个TCP上可以跑多个Http请求,但是同一时刻只能有一个Http请求处理。
Http2.0
这一代的Http协议发生了很多重大更新,不仅仅压缩了传输体积,而且提供了多路复用的能力,提高了传输效率。
从上图可以看出,Http2.0在同一个TCP连接可以跑多个Http请求的基础上,在同一时刻也能跑多个Http请求,真正实现了同一连接、多个同时处理Http请求。主要的实现方式是通过二进制分帧,将请求和响应数据拆分成多个小的帧,每个帧都有一个唯一的标识符(Stream ID),这些帧可以在同一个连接中并行传输。这样一来,客户端和服务器就能够更高效地利用带宽,减少了延迟。
举个具体的例子,一个网站如果有很多图片,在HTTP1.0中,图片的请求都是在同一个TCP连接中,但是图片是一张一张显示的,后面的图片只会转圈圈等待,只有前一张图片请求完全之后才能轮到后一张图片;在HTTP2中,图片可以几乎瞬间同时显示,不存在先后等待关系。
多路复用并没有解决头部阻塞问题。从上图可以看出,数据包(stream
)在TCP层面依然是串行的,如果stream1
发生丢包,肯定会激活TCP的重传机制导致阻塞,stream2
和stream3
老老实实地等着, 这个问题在HTTP3(QUIC)中才有解决之道。
最后,简单总结一下,HTTP2中的几个特点:
-
多路复用:多个请求和响应可以在同一个连接中并行处理,无需为每个请求建立新的连接,从而减少了连接建立和关闭的开销,这也是HTTP2最重要的特性!;
-
头部压缩:通过HPACK算法,Http2.0对HTTP头部进行压缩,显著减少了冗余数据的传输,提高了性能;
-
服务器推送:服务器可以主动向客户端推送资源,而无需客户端明确请求。这种机制可以加快页面加载速度,特别是在需要多个资源的情况下;
-
二进制协议:Http2.0使用二进制格式而非文本格式,这不仅提高了解析速度,还减少了出错的可能性。二进制格式使得协议更为简洁和高效;
优缺点对比
-
HTTP1
-
队头阻塞
-
传输效率低
-
明文传输不安全
-
-
HTTP2
-
多路复用:多个HTTP请求复用同一个TCP连接
-
头部压缩
-
二进制协议
-
nginx配置Http2.0
server{
listen 443 ssl http2;
server_name we1.top www.we1.top;
ssl_certificate /etc/letsencrypt/live/we1.top/fullchain.pem;
ssl_certificate_key /etc/letsencrypt/live/we1.top/privkey.pem;
location / {
proxy_pass http://blog;
proxy_http_version 1.1;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_read_timeout 90;
}
}
通过开启Http2.0,本博客系统的浏览速度相比于之前得到了明显的提升。