LOGO 首页 OA教程 ERP教程 模切知识交流 PMS教程 CRM教程 技术文档 其他文档  
 
网站管理员

[点晴模切ERP]抛弃TCP改用UDP,HTTP3疯了吗?

zhenglin
2026年6月4日 10:15 本文热度 67

导读

HTTP协议用过这么多年,但HTTP/1.1、HTTP/2、HTTP/3到底有什么区别?各自解决了什么问题,又各自留下了什么遗憾?这篇把三个版本放在同一张桌子上,逐项对比

先说结论

维度HTTP/1.1HTTP/2HTTP/3 (QUIC)
传输层协议TCPTCPUDP
多路复用❌ 不支持✅ 支持(流级别)✅ 支持(流级别)
头部压缩❌ 纯文本重复发送✅ HPACK(静态字典+动态字典+Huffman)✅ QPACK(改进版HPACK)
服务端推送❌ 不支持✅ 支持❌ 已移除(几乎没人用)
队头阻塞TCP层级阻塞 + 请求级阻塞TCP层级仍阻塞彻底解决
连接建立1-RTT(TCP握手)1-RTT(TCP握手) + TLS0-RTT(恢复连接时)
连接迁移❌ IP变了就断❌ IP变了就断✅ 网络切换不断连

一句话总结:HTTP/2解决了应用层的队头阻塞,HTTP/3解决了传输层的队头阻塞




HTTP/1.1到底慢在哪?

问题一:连接级队头阻塞(Connection-level Head-of-Line Blocking)

HTTP/1.1的队头阻塞发生在TCP连接层面——浏览器对同一域名有连接数限制,Chrome限制6个TCP连接。这意味着同时最多只能发6个请求,第7个必须等前面某个完成才能发。

浏览器想加载一个页面,需要请求10个资源:

  CSS、JS、图片1、图片2、图片3、字体、API数据...


但只有6个通道:

  [通道1: CSS ████████████ 完成]

  [通道2: JS  ███████████████████████ 还在传...]

  [通道3: 图片1 ██████ 完成]

  [通道4: 图片2 ████████████████ 还在传...]

  [通道5: 字体 ██████████████████████████████████ 还在传...]

  [通道6: API  ████████████ 完成]


图片3、图片4... 全在排队等!

因为通道2的JS文件特别大,堵住了后面的所有请求。

这就是连接级队头阻塞:一个慢请求占满通道,导致后面的所有请求排队。

问题二:头部冗余

HTTP头部是纯文本,每次请求都完整携带:

GET /api/user HTTP/1.1

Host: api.example.com

Accept: application/json

Content-Type: application/json

Authorization: Bearer eyJhbGciOiJIUzI1NiIs...

User-Agent: Mozilla/5.0 ...

Accept-Language: zh-CN,zh;q=0.9

Cookie: session=abc123; theme=dark; ...


--- 第二次请求,同样的头部再发一遍 ---


GET /api/order HTTP/1.1

Host: api.example.com       ← 一样

Accept: application/json    ← 一样

Content-Type: application/json ← 一样

Authorization: Bearer eyJhbGciOiJIUzI1NiIs... ← 一样

User-Agent: Mozilla/5.0 ... ← 一样

Accept-Language: zh-CN,zh;q=0.9 ← 一样

Cookie: session=abc123; ... ← 差不多

一次页面加载可能发出几十个请求,每个请求重复携带500-2000字节的头部。大部分字段完全相同,纯浪费带宽。

问题三:无法主动推送

用户请求了HTML,服务器知道HTML里引用了CSS和JS。但按照HTTP/1.1的规则,服务器必须等浏览器解析完HTML、发现需要CSS和JS、再发起请求——白白多等了一个往返时间(RTT)。




HTTP/2怎么解决这些问题?

核心变化:二进制分帧层(Binary Framing)

这是HTTP/2最根本的改变。HTTP/1.1是基于文本的,HTTP/2把所有数据拆成更小的单元——帧(Frame)

HTTP/1.1:一条完整的请求/响应 = 一大块文本


HTTP/2:一条消息 → 拆成多个帧

         ┌─────────────────────────────┐

         │  帧类型  │  帧标识  │   负载   │

         ├─────────┼─────────┼─────────┤

         │ HEADERS │ Stream3 │ 请求头   │

         │ DATA    │ Stream3 │ 请求体   │

         │ HEADERS │ Stream5 │ 请求头   │

         │ DATA    │ Stream5 │ 请求体   │

         │ HEADERS │ Stream7 │ 请求头   │

         │ DATA    │ Stream7 │ 请求体   │

         └─────────┴─────────┴─────────┘

                    ↓

           在同一个TCP连接上交错发送

帧的类型:

帧类型作用
HEADERS携带HTTP头部信息
DATA携带HTTP body
SETTINGS协商连接参数
PING心跳检测
WINDOW_UPDATE流量控制
RST_STREAM终止某个流(不影响其他)
PUSH_PROMISE服务端推送承诺

多路复用:一个连接搞定一切

有了二进制分帧,HTTP/2可以在同一个TCP连接上同时发送多个请求/响应,互不干扰:

HTTP/1.1(6个连接):

  TCP连接1 ──→ 请求A ──→ 响应A

  TCP连接2 ──→ 请求B ──→ 响应B

  TCP连接3 ──→ 请求C ──→ 响应C

  ...


HTTP/2(1个连接):

  TCP连接1 ─┬─→ Stream1: 请求A ←→ 响应A(交错传输)

            ├─→ Stream3: 请求B ←→ 响应B(交错传输)

            ├─→ Stream5: 请求C ←→ 响应C(交错传输)

            └─→ Stream7: 请求D ←→ 响应D(交错传输)

好处很明显:

  • 浏览器不再受6连接数限制


  • 一个慢请求不会阻塞其他请求


  • 减少TCP连接建立的开销(每次握手都要1-RTT)


HPACK头部压缩

HTTP/2用HPACK算法压缩头部,三层机制配合:

第一层:静态字典

常用头部组合预定义好,编号0-61,直接用编号代替:

编号2 : method: GET

编号4 : path: /

编号6 : scheme: http

编号20: content-type: application/json

...

第二层:动态字典

连接期间出现过的头部存下来,后续直接用编号引用。假设第1个请求完整发送了:

:method: GET

:path: /api/user

:scheme: https

authorization: Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...


这些被加入动态字典,编号依次为 61、62、63、64...

第2个请求要发完全相同的 authorization,只需要发一个字节 0x3E(二进制 00111110,对应编号62)——连"authorization"这个词都不用发,解码器查字典就知道是哪个头部。实际传输量从几十字节压缩到1-2字节。


第三层:Huffman编码

对还没被字典收录的字段,用Huffman算法进一步压缩。HTTP头部中大量ASCII字符,Huffman编码后体积能减少20-30%。

实际效果: 头部大小从平均800字节降到约200字节,压缩率约75%。

服务端推送(Server Push)

服务器可以在客户端请求之前主动推送资源:

浏览器请求:GET /index.html


服务器返回HTML的同时,顺便推:

  PUSH_PROMISE: /style.css

  PUSH_PROMISE: /main.js


浏览器收到HTML时,CSS和JS已经在路上了

省了一次RTT


但这个功能在实际中几乎没人用。 原因不少:

  • 推送的资源浏览器可能已经有了(缓存命中),白推了


  • 推送占用带宽,可能挤掉真正需要的资源


  • 很难精确判断该推什么、什么时候推


  • 开发调试困难


所以HTTP/3直接把这个特性移除了。Google的数据显示,Server Push的实际使用率不到0.1%。


HTTP/2还有问题吗?

有。而且是个致命问题。

TCP级队头阻塞(Transport-layer Head-of-Line Blocking)

HTTP/2用多路复用解决了HTTP层面的队头阻塞——多个请求可以交错发送互不干扰。但它跑在TCP之上,TCP有自己的问题:

TCP保证有序交付:包1、包2、包3 必须按顺序到达


如果包2丢了:

  包1 到达 ✓ → 交给应用层

  包2 丢失 ✗ → 等待重传...

  包3 到达 ✗ → 不能交给应用层!必须等包2先到!


结果:包3明明已经到了,却因为包2丢了而被阻塞

这就是 **TCP级队头阻塞**:传输层丢一个包,应用层所有流都被卡住。


在网络状况不好的场景下(移动网络、跨运营商),丢包率升高,TCP重传频繁,整个连接的所有流都会受影响——哪怕只有其中一个流的包丢了。

具体影响有多大? Google测试数据显示:在1%丢包率的网络环境下,HTTP/2的吞吐量下降比HTTP/1.1还严重。因为HTTP/1.1可以开多个TCP连接,一个连接丢包不影响其他;而HTTP/2只有一个连接,一损俱损。


HTTP/3(QUIC):彻底换底座

既然问题出在TCP上,那就不走TCP了。HTTP/3底层换成QUIC协议,而QUIC跑在UDP之上。

为什么选UDP而不是继续改TCP?

TCP的问题不是小修小补能解决的——它的有序交付机制是协议层面写死的,改不了。要彻底解决队头阻塞,只能换协议。

但重新设计一个传输层协议推广难度极大(操作系统内核、中间设备全要支持)。所以QUIC选择在用户空间实现,跑在UDP之上——UDP足够简单,几乎所有网络设备都能放行。

QUIC的核心改进

1. 无队头阻塞

QUIC的每个Stream独立有序,但Stream之间无序

TCP(HTTP/2):

  Connection ──→ [Stream1][Stream2][Stream3]  包2丢了 → 全阻塞


QUIC(HTTP/3):

  Connection ──┬→ Stream1: [包1][包2][包3]  独立有序

              ├→ Stream2: [包1][包2][包3]  独立有序,互不影响

              └→ Stream3: [包1][包2][包3]  Stream2丢包只阻塞Stream2

Stream2的包丢了,只影响Stream2本身。Stream1和Stream3照常交付。

2. 0-RTT连接建立

传统TLS握手需要2-RTT(ECDHE密钥交换场景):

首次连接(HTTP/1.1 或 HTTP/2):

  Client          Server

    │               │

    │──ClientHello──>│          RTT 1: 发起握手

    │<─ServerHello───│          RTT 2: 服务器响应 + 证书

    │──KeyExchange──>│          RTT 3: 密钥交换

    │<─Finished──────│          RTT 4: 握手完成

    │               │

    │════ 数据传输 (已加密) ════│    终于可以发数据了

    │               │


首次连接(QUIC/HTTP/3):

  Client          Server

    │               │

    │──ClientHello──>│          RTT 1: 握手 + 第一个请求一起发

    │<─ServerHello───│          RTT 2: 响应 + 确认

    │               │

    │════ 数据传输 (已加密) ════│    少了一个RTT


恢复连接(QUIC/HTTP/3):

  Client          Server

    │               │

    │──请求数据 + 恢复凭证 ─>│   RTT 0: 直接带数据

    │<──────── 数据 ─────────│    第一次往返就能拿到响应

对于移动端用户来说,0-RTT 意味着打开 App 的首屏时间显著缩短。

代价也要说清楚: 0-RTT 存在"重放攻击"风险——攻击者截获历史请求和密钥材料,重新发送相同请求到服务器。解决方案是请求加上"anti-replay"机制,服务端对相同请求只执行一次。所以0-RTT适合读请求,不适合写请求(下单、转账等)。

3. 连接迁移

换个WiFi或者从4G切到5G,IP地址会变。TCP用四元组(源IP、源端口、目的IP、目的端口)标识连接,IP一变连接就断了,得重新握手。

QUIC用Connection ID标识连接,跟IP无关:


手机从WiFi切到4G:

  TCP:IP变了 → 连接断开 → 重新三次握手 → 重新TLS握手 → 恢复数据传输(卡顿明显)


  QUIC:IP变了 → Connection ID没变 → 连接保持 → 继续传输(用户无感知)

这对移动端体验提升很大——地铁里进出站、电梯上下,网络频繁切换,QUIC不断连。

4. 内置TLS 1.3

QUIC强制使用TLS 1.3加密,不像TCP+TLS是两层拼起来的。加密是协议原生的一部分,不存在"明文握手阶段"这种漏洞窗口。

QPACK:改进的头部压缩

HTTP/3用 QPACK 替代 HPACK,解决的是HPACK在多路复用场景下的队头阻塞问题。

HPACK为什么会阻塞?

HPACK的动态字典是"按顺序积累"的——第1个请求的头部加入字典,第2个请求复用第1个的字典状态。如果第1个请求的HEADERS帧丢了,第2个请求的帧就解不出来了(字典状态对不上)。

这跟TCP的队头阻塞是一个道理,只是堵的是头部解码器,不是传输层。

QPACK怎么解决的?

QPACK引入单向流(Uni-directional Stream)机制——字典同步和数据传输彻底分开:


QPACK 两条独立流:


  编码器 ──单向流──> 解码器

  (只发送字典变化,不携带数据)


  编码器 ──单向流──> 解码器

  (携带数据帧,但引用字典编号,不包含完整头部)

字典同步走专门的流,跟数据流完全隔离。即使数据流丢包,字典同步流不受影响,解码器仍然可以处理其他帧。

效果:即使某个流的HEADERS帧丢失,不会影响其他流的头部解码,真正实现了"一Stream堵了,其他Stream照常工作"。



三代HTTP对比全景图

应用层:

特性HTTP/1.1HTTP/2HTTP/3
协议格式文本协议二进制分帧二进制分帧
头部压缩无,每次重复发送HPACK(静态+动态字典+Huffman)QPACK(单向流隔离)
多路复用无(连接数限制6个)支持(流级别)支持(流级别)
服务端推送不支持支持已废弃

安全层:

特性HTTP/1.1HTTP/2HTTP/3
加密TLS可选TLS必须TLS 1.3内置(原生)
握手独立层独立层集成在QUIC内部

传输层:

特性HTTP/1.1HTTP/2HTTP/3
传输协议TCPTCPUDP
可靠性TCP保证有序可靠TCP保证有序可靠QUIC在用户空间实现可靠+有序
队头阻塞TCP级阻塞(丢包堵所有连接)TCP级阻塞(丢包堵所有流)无队头阻塞(Stream独立)


实际性能差多少?

理论 vs 现实

理论上HTTP/3应该全面碾压HTTP/2,但实际效果取决于场景:

场景HTTP/2表现HTTP/3表现说明
理想网络(低延迟低丢包)已经很快略快差距不大,瓶颈不在协议
高延迟网络(跨国)较慢明显更快0-RTT和减少握手轮次优势大
高丢包网络(移动弱网)性能下降严重表现稳定无队头阻塞的优势体现
大文件下载差不多单流场景差异不大
小文件密集请求一般更好多路复用+头部压缩叠加


什么时候该升级?

  • 网站主要面向国内用户:HTTP/2已经够用,国内网络质量好,HTTP/3提升有限


  • 有海外用户或移动端为主:HTTP/3值得上,弱网和跨境场景收益明显


  • 实时性要求高(直播、在线协作):HTTP/3的低延迟优势重要


  • 还在用HTTP/1.1:优先升HTTP/2,改动小收益大;然后再考虑HTTP/3



浏览器和服务端支持情况

浏览器支持:

浏览器HTTP/2HTTP/3
Chrome✅ 默认启用✅ 默认启用(2019年起)
Firefox✅ 默认启用✅ 默认启用
Safari✅ 默认启用✅ 默认启用(14.1+)
Edge✅ 默认启用✅ 默认启用

主流浏览器全部支持HTTP/3,不需要做兼容处理。

服务端支持:

服务/软件HTTP/2HTTP/3
Nginx⚠️ 需要编译QUIC模块(官方尚未默认内置)
Apache⚠️ 需要mod_quic
Caddy默认支持(最简单的HTTP/3开启方式)
Cloudflare全网支持(CDN场景免配置)
阿里云CDN✅ 支持开启

如果你用的是Nginx,目前最省事的方式是在前面套一层Cloudflare CDN,自动获得HTTP/3能力。自建的话Caddy是最友好的选择——一行配置搞定。




总结

三代HTTP的演进主线很清晰:

HTTP/1.1 — 能用,但问题一堆:队头阻塞、头部冗余、连接数受限。就像一条单车道公路,车多了就堵。

HTTP/2 — 解决了应用层的大部分问题:二进制分帧实现多路复用、HPACK压缩头部、单连接搞定所有请求。但底层还是TCP,丢包时全军覆没。像拓宽到了多车道高速,但只要有一辆车抛锚,整条路都得停。

HTTP/3 — 彻底换了运输工具:放弃TCP改用QUIC(基于UDP),从根子上消灭了队头阻塞,加上0-RTT连接和连接迁移,移动端弱网体验大幅提升。像升级成了高铁加飞机,不仅快,还不怕堵。

不过技术选型永远要看场景。如果你的用户在国内、网络条件好,HTTP/2已经能给到90分的体验,HTTP/3那额外的10分不一定值得投入。但如果你的产品面向全球或有大量移动端用户,HTTP/3就是那个值得投入的升级点。


阅读原文


点晴模切ERP更多信息:https://moqie.clicksun.cn,联系电话:4001861886

该文章在 2026/6/4 10:15:40 编辑过
关键字查询
相关文章
正在查询...
点晴ERP是一款针对中小制造业的专业生产管理软件系统,系统成熟度和易用性得到了国内大量中小企业的青睐。
点晴PMS码头管理系统主要针对港口码头集装箱与散货日常运作、调度、堆场、车队、财务费用、相关报表等业务管理,结合码头的业务特点,围绕调度、堆场作业而开发的。集技术的先进性、管理的有效性于一体,是物流码头及其他港口类企业的高效ERP管理信息系统。
点晴WMS仓储管理系统提供了货物产品管理,销售管理,采购管理,仓储管理,仓库管理,保质期管理,货位管理,库位管理,生产管理,WMS管理系统,标签打印,条形码,二维码管理,批号管理软件。
点晴免费OA是一款软件和通用服务都免费,不限功能、不限时间、不限用户的免费OA协同办公管理系统。
Copyright 2010-2026 ClickSun All Rights Reserved  粤ICP备13012886号-2  粤公网安备44030602007207号