Skip to main content

9. Extensions to HTTP/3 (HTTP/3扩展)

HTTP/3允许通过扩展协议来增强功能。扩展是可选的,可以由实现决定是否支持。本节描述如何定义和使用HTTP/3扩展。

9.1 扩展机制

HTTP/3使用与HTTP/2相同的扩展机制。扩展可以使用:

  1. 新的帧类型(第7.2节)
  2. 新的SETTINGS参数(第7.2.4节)
  3. 新的错误代码(第8节)
  4. 新的单向流类型(第6.2节)

9.2 扩展发现

HTTP/3支持贪婪扩展发现 (greedy extension discovery),通过保留特定值的空间:

  • 保留的帧类型0x1f * N + 0x21
  • 保留的SETTINGS标识符0x1f * N + 0x21
  • 保留的错误代码0x1f * N + 0x21
  • 保留的流类型0x1f * N + 0x21

其中N是非负整数(0, 1, 2, ...)

贪婪发现的目的

保留这些值允许实现:

  • 测试对未知扩展的处理
  • 防止实现对特定值产生依赖
  • 确保协议的可扩展性

处理保留值

实现必须 (MUST):

  • 不明确发送这些保留值(除非用于测试)
  • 将接收到的这些值视为未知值并忽略
  • 不将这些值视为错误

9.3 扩展协商

扩展可以通过以下方式协商:

SETTINGS帧协商

客户端 → 服务器: SETTINGS { EXTENSION_FOO = 1 }
服务器 → 客户端: SETTINGS { EXTENSION_FOO = 1 }

结果: 扩展FOO已启用

ALPN协商

某些扩展可能需要在TLS握手期间通过ALPN协商:

ClientHello: ALPN = ["h3-foo", "h3"]
ServerHello: ALPN = "h3-foo"

结果: 使用带扩展FOO的HTTP/3

9.4 扩展设计指南

定义HTTP/3扩展时应考虑:

1. 向后兼容性

  • 扩展应该 (SHOULD) 设计为可选
  • 不支持扩展的端点应该 (SHOULD) 能够正常运行

2. 协商机制

  • 明确定义扩展如何协商
  • 使用SETTINGS或ALPN

3. 影响范围

  • 明确扩展影响流、连接还是两者
  • 定义扩展如何与其他扩展交互

4. 安全考虑

  • 分析扩展的安全影响
  • 考虑隐私影响

9.5 已知的HTTP/3扩展

虽然本文档不定义特定扩展,但以下是已知的HTTP/3扩展示例:

Extended CONNECT

  • 参考:[RFC 8441]
  • 目的:允许CONNECT方法用于非TCP协议(如WebSocket over HTTP/3)
  • 协商:SETTINGS_ENABLE_CONNECT_PROTOCOL

WebTransport

  • 目的:在HTTP/3上提供双向数据流
  • 使用:游戏、实时应用

QPACK Dynamic Table

  • 参考:[RFC 9204]
  • 目的:HTTP/3的头部压缩
  • 集成:QPACK编码器和解码器流

扩展示例:自定义流类型

假设我们想定义一个新的单向流类型用于日志传输:

// 定义新的流类型
STREAM_TYPE_LOGGING = 0x54

// 流格式
Logging Stream {
Stream Type (i) = 0x54,
Log Entry (..) ...,
}

Log Entry {
Timestamp (i),
Level (i),
Message Length (i),
Message (..),
}

// SETTINGS协商
SETTINGS_ENABLE_LOGGING = 0x1000

协商过程

  1. 客户端发送:SETTINGS { SETTINGS_ENABLE_LOGGING = 1 }
  2. 服务器响应:SETTINGS { SETTINGS_ENABLE_LOGGING = 1 }
  3. 双方现在可以创建类型为 0x54 的流

关键要点

  • HTTP/3具有强大的扩展机制
  • 使用SETTINGS、帧类型、流类型和错误代码进行扩展
  • 保留值支持贪婪扩展发现
  • 扩展应该向后兼容和可选
  • 扩展通过SETTINGS或ALPN协商