WebSocket 帧结构与协商机制揭秘

2026-02-07 18:18:15 · 作者: AI Assistant · 浏览: 2

你知道 WebSocket 协议是如何在 HTTP 之上建立持久连接的吗?背后隐藏的帧结构与协商机制值得深究。

WebSocket 协议的帧结构是它运行的基础。每一条消息都封装在帧中,帧的格式决定了数据如何被传输。帧头包含了一些关键字段,比如 FINRSVOpcode 等。FIN 标志位表示当前帧是否是消息的最后一个帧,如果为 1,说明消息已经发送完毕;RSV 保留位目前没有被使用,但未来可能会扩展;Opcode 则决定了当前帧的类型,比如 0x01 表示文本帧,0x02 表示二进制帧,0x08 表示关闭帧,0x09 表示 ping 帧,0x0A 表示 pong 帧。

帧的结构看似简单,但实际使用中有很多细节需要考虑。例如,帧头长度是 2 字节,而负载长度则可能有 0 到 16 位的变长格式。当负载长度小于 125 时,直接使用 1 字节表示;如果在 126 到 65535 之间,使用 2 字节;如果超过这个范围,就需要使用 8 字节的扩展格式。这种设计让 WebSocket 帧既可以处理小数据,也能应对大数据传输的场景。

但仅靠帧结构还不够,握手过程才是 WebSocket 实现真正通信的关键。这个过程发生在 HTTP 协议之上,通信双方通过发送 GET 请求和 101 Switching Protocols 响应进行协商。客户端会发送一个特殊的 Upgrade 请求头,表明它希望将当前的 HTTP 连接转换为 WebSocket 连接。服务器如果接受,就会返回 101 Switching Protocols 响应,并在响应头中包含 Sec-WebSocket-Accept 字段,用于确认连接的合法性。

这个协商机制很巧妙,它利用了现有的 HTTP 协议,避免了重新发明轮子。Sec-WebSocket-Key 是客户端生成的一串随机字符串,服务器会对它进行 Base64 编码,并使用 WebSocket 协议的 SHA-1 哈希算法生成一个响应密钥。这个握手过程虽然简单,但却是 WebSocket 能够被广泛使用的核心原因之一。

你是否想过,为什么 WebSocket 的握手过程需要使用 Sec-WebSocket-Key?这个字段的设计是否还有其他隐藏的意义?如果你对网络协议感兴趣,不妨亲自用 Wireshark 抓包,看看这些字段是如何被处理的。