文章
关于HTTP/1.1、HTTP/2、HTTP/3、tus以及QUIC等常见概念
这五个词不在同一层级。
**业务层**:tus,负责文件如何创建、暂停、恢复、提交
**HTTP 层**:HTTP/1.1、HTTP/2、HTTP/3,负责请求和响应如何表达
**传输层**:TCP 或 QUIC,负责连接、丢包恢复、拥塞控制
**网络层**:IP
其中:
- HTTP/1.1、HTTP/2、HTTP/3 是 HTTP 的不同版本。
- QUIC 是传输协议,不是文件传输协议。
- tus 是基于 HTTP 的断点续传上传协议。
- HTTP/3 是“HTTP 语义运行在 QUIC 上”。RFC 9110、RFC 9114
一、What:它们分别是什么#
| 技术 | 本质 | 典型特征 |
|---|---|---|
| HTTP/1.1 | 基于 TCP 的 HTTP 应用协议 | 文本格式、长连接、并发通常依赖多个连接 |
| HTTP/2 | 基于 TCP 的 HTTP 应用协议 | 二进制帧、单连接多路复用、HPACK Header 压缩 |
| HTTP/3 | 基于 QUIC 的 HTTP 应用协议 | QUIC 流、多路复用、QPACK、UDP |
| QUIC | 基于 UDP 的安全可靠传输协议 | TLS 1.3、流、丢包恢复、连接迁移 |
| tus | 基于 HTTP 的可恢复上传协议 | POST 创建、HEAD 查询偏移、PATCH 继续上传 |
HTTP/1.1 使用文本起始行和 Header;HTTP/2 使用二进制帧和独立流。RFC 9112、RFC 9113
二、Why:为什么需要它们#
HTTP/1.1#
目标是简单、兼容、容易实现。它适合传统代理、老旧设备和请求数量不多的服务。 缺点是同一连接上的请求并发能力有限。客户端通常需要打开多个 TCP 连接,连接数量多时会增加握手、资源和拥塞控制开销。
HTTP/2#
目标是让多个请求共享一条 TCP 连接:
一条 TCP 连接
├── API 请求
├── CSS 请求
├── JavaScript 请求
└── 文件请求
它减少了连接数量,压缩了重复 Header,并允许多个请求交错传输。 但 HTTP/2 仍建立在 TCP 上。一个 TCP 数据包丢失时,连接中所有流都可能等待缺失字节,这叫 TCP 层队头阻塞。RFC 9113
HTTP/3#
目标是解决 HTTP/2 的 TCP 队头阻塞问题,同时改善移动网络和网络切换场景。 HTTP/3 的请求使用独立 QUIC 流。一个流丢包时,其他流通常仍能继续传输。RFC 9114
QUIC#
目标是提供比 TCP 更适合现代互联网的传输能力,包括:
- TLS 1.3 集成
- 可靠、有序的单流传输
- 多流并发
- 丢包检测和拥塞控制
- IP、端口或接入网络变化后的连接迁移 QUIC 不知道“文件”“上传任务”“文件名”或“提交完成”是什么。它只负责传输字节和流。RFC 9000
tus#
目标是解决“文件上传到一半断网,恢复后不要从头上传”的问题。典型流程是:
POST /files 创建上传
HEAD /files/{id} 查询当前 Upload-Offset
PATCH /files/{id} 从该偏移继续上传
tus 规范不绑定具体 HTTP 版本,因此理论上可以运行在 HTTP/1.1、HTTP/2 或 HTTP/3 之上。tus 协议规范
三、When:什么时候使用#
| 场景 | 推荐 |
|---|---|
| 老旧设备、工业网关、兼容性优先 | HTTP/1.1 |
| 普通 REST API、网站、内部服务 | HTTP/2 |
| gRPC | 通常 HTTP/2 |
| 移动端、公网、弱网、多网络切换 | HTTP/3,保留 HTTP/2 回退 |
| 单个稳定的大文件下载 | HTTP/1.1、HTTP/2、HTTP/3 都可以 |
| 大文件断点上传 | tus,底层使用 HTTP/1.1 或 HTTP/2 |
| 断网时间较长、客户端可能重启 | tus 或自定义持久化断点协议 |
| 自定义实时传输、完全控制两端 | QUIC 自定义协议 |
| 浏览器直接访问 | HTTP API、HTTP/2 或 HTTP/3,不能直接访问裸 QUIC |
需要注意:HTTP/3 不保证单个大文件一定比 HTTP/2 快。 单文件通常只占用一个流,此时主要受带宽、拥塞控制、磁盘和应用层断点策略影响。 同样,QUIC 也不会自动提供断点续传。如果连接彻底断开,应用仍然需要记录任务 ID、文件偏移、哈希和提交状态。
四、How:实际应该怎么组合#
浏览器侧通常不需要手动选择:
fetch("https://api.example.com/api/v1/me");
浏览器通过 TLS ALPN 与服务端协商:
优先 HTTP/3
失败则 HTTP/2
再失败则 HTTP/1.1
服务端可以使用边缘网关:
浏览器
|
| HTTP/3 或 HTTP/2
v
Nginx / Caddy / CDN
|
| HTTP/1.1 或 HTTP/2
v
应用服务
例如 Nginx 可以配置:
server {
listen 443 ssl;
http2 on;
ssl_certificate /etc/nginx/fullchain.pem;
ssl_certificate_key /etc/nginx/private.key;
location / {
proxy_pass http://127.0.0.1:8080;
proxy_http_version 1.1;
proxy_set_header Host $host;
# 大文件上传时避免代理先缓存完整请求
proxy_request_buffering off;
}
}
HTTP 版本是逐跳协商的,所以浏览器到 Nginx 可以是 HTTP/2,而 Nginx 到应用仍然是 HTTP/1.1。Nginx 官方的 HTTP/2 配置方式见 ngx_http_v2_module。
对于船岸业务,建议这样落地:
控制数据:
HTTPS API,HTTP/2 作为基线,HTTP/3 作为优化路径
文件上传:
tus + HTTP/2/TCP 作为基线
tus + HTTP/3/QUIC 作为弱网优化
HTTP/3 不可用时自动回退
文件下载:
文件清单 + Range + ETag + SHA-256/BLAKE3 校验
tusd 当前官方配置文档列出的原生监听模式主要是 HTTP/1.1 和 HTTP/2;如果希望浏览器使用 HTTP/3,可以让支持 HTTP/3 的网关在前面终止 QUIC,再转发给 tusd。tusd 配置文档