WebSocket 协议细节:帧格式与握手过程

一、握手过程

WebSocket 握手基于 HTTP 升级机制,分为客户端请求和服务器响应两个阶段:

  1. 客户端握手请求
    客户端发送 HTTP GET 请求,关键头部如下:

    GET /chat HTTP/1.1
    Host: example.com
    Upgrade: websocket
    Connection: Upgrade
    Sec-WebSocket-Key: dGhlIHNhbXBsZSBub25jZQ==
    Sec-WebSocket-Version: 13
    

    • UpgradeConnection 声明协议升级意图
    • Sec-WebSocket-Key:16字节随机值的 Base64 编码
    • Sec-WebSocket-Version:协议版本(通常为13)
  2. 服务器握手响应
    服务器返回 HTTP 101 状态码:

    HTTP/1.1 101 Switching Protocols
    Upgrade: websocket
    Connection: Upgrade
    Sec-WebSocket-Accept: s3pPLMBiTxaQ9kYGzzhZRbK+xOo=
    

    • Sec-WebSocket-Accept 生成过程:
      1. 拼接客户端密钥与固定 GUID:
        Sec-WebSocket-Key + "258EAFA5-E914-47DA-95CA-C5AB0DC85B11"
      2. 计算 SHA-1 哈希
      3. 对哈希结果进行 Base64 编码

    握手成功后,TCP 连接升级为 WebSocket 全双工通道。


二、帧格式

WebSocket 数据传输单位是帧(Frame),二进制格式如下:

 0                   1                   2                   3
 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
+-+-+-+-+-------+-+-------------+-------------------------------+
|F|R|R|R| opcode|M| Payload len |    Extended payload length    |
|I|S|S|S|  (4)  |A|     (7)     |             (16/64)           |
|N|V|V|V|       |S|             |                               |
| |1|2|3|       |K|             |                               |
+-+-+-+-+-------+-+-------------+-------------------------------+
|     Extended payload length (continued)       | Masking-key   |
+-------------------------------+-------------------------------+
| Masking-key (continued)       |          Payload Data         |
+-------------------------------- - - - - - - - - - - - - - - - +
:                     Payload Data continued ...                :
+---------------------------------------------------------------+

关键字段说明:
  1. 基础头(2字节)

    • FIN (1 bit):是否为消息的最后一帧
    • RSV1-3 (各1 bit):保留位(通常为0)
    • Opcode (4 bits):帧类型标识
      • $0x1$:文本帧(UTF-8)
      • $0x2$:二进制帧
      • $0x8$:连接关闭
      • $0x9$:Ping
      • $0xA$:Pong
    • MASK (1 bit):是否使用掩码(客户端→服务端必须为1
    • Payload len (7 bits):负载长度标识
      • $0 \leq \text{len} \leq 125$:直接表示长度
      • $\text{len} = 126$:后续2字节存储长度
      • $\text{len} = 127$:后续8字节存储长度
  2. 扩展长度(0/2/8字节)
    Payload len 为126或127时,存储实际长度(大端序)。

  3. 掩码键(4字节)
    MASK=1 时存在,用于解码负载数据。

  4. 负载数据(变长)
    实际传输内容,若启用掩码需按以下规则解码:
    对于第 $i$ 字节数据:
    $$ \text{decoded}[i] = \text{encoded}[i] \oplus \text{mask}[i \bmod 4] $$


三、关键特性
  1. 数据分片:大消息可拆分为多帧(FIN=0 表示未完,Opcode=0 为续帧)
  2. 控制帧
    • Ping/Pong 用于保活检测(最大负载长度 125 字节)
    • Close 帧含 2 字节状态码(如 $1000$=正常关闭)
  3. 掩码机制:防止代理服务器缓存污染(仅客户端发送时启用)

:WebSocket 默认端口与 HTTP 一致(80/443),但可运行于任意 TCP 端口。

Logo

中国智能体开发者社区,聚焦智能体与大模型开发,提供前沿资讯、实用工具链、开源项目及行业案例。通过技术沙龙、开发者大赛等活动,促进经验交流与协作,助力开发者快速构建创新智能应用。

更多推荐