WebSocket传输二进制音频流需用ArrayBuffer发送PCM数据,服务端设binaryType='arraybuffer',客户端用Web Audio API解码播放,并通过分帧、心跳、缓冲队列保障低延迟与稳定性。

WebSocket 传输二进制音频流是实时语音通信、远程会议、IoT 音频采集等场景的常见需求。关键不在于“能不能传”,而在于“怎么传得稳、低延迟、不丢帧、易解码”。核心要点:用 ArrayBuffer 或 Uint8Array 发送原始音频数据,服务端需保持二进制帧(binaryType = 'arraybuffer'),客户端接收后按采样格式(如 PCM)交由 Web Audio API 处理。
音频数据准备:明确格式与封装边界
浏览器不直接采集“裸 PCM 流”,需通过 MediaRecorder 或 AudioContext 获取。推荐使用 AudioContext + ScriptProcessorNode(已废弃)或更现代的 AudioWorklet / OfflineAudioContext 方式提取 PCM 数据。重点注意:
- 采样率(如 16kHz / 44.1kHz)、位深(16-bit signed integer 最常用)、声道数(mono/stereo)必须前后端一致,否则解码失真
- 避免直接发送未分帧的连续流;建议按固定时长(如 20ms)切片,每片对应
sampleRate × duration × bytesPerSample × channelCount字节 - 若需兼容性,可先将 PCM 转为 WAV 封装头 + 数据块(仅 header + data,无 ID3 等冗余),再作为二进制发送
WebSocket 配置:启用 binaryType 并处理帧类型
默认 WebSocket binaryType 是 'blob',但 blob 在高频小包场景下有额外解析开销。务必在连接建立后立即设置:
ws.binaryType = 'arraybuffer';
WebSocket 8.18.2 是该协议规范的一个重要迭代版本,主要优化了连接稳定性与数据传输效率。它通过全双工通信机制,允许客户端与服务器在单一长连接上实时交换数据,大幅降低传统 HTTP 轮询的开销。该版本增强了心跳保活、自动重连及二进制帧传输能力,适用于即时通讯、在线游戏及金融行情推送等低延迟场景,为开发者提供更可靠的实时网络交互基础。
发送时直接调用 ws.send(arrayBuffer);接收时判断 event.data instanceof ArrayBuffer 即可安全读取。注意:
- 服务端(如 Node.js 的
ws库)需显式支持 binary frame,避免自动转为 base64 字符串 - 不要混合发送 text 和 binary 帧到同一连接——除非你定义了自定义协议头来区分类型
- 高吞吐下考虑开启
ws.setNoDelay(true)(Node.js ws)减少 Nagle 算法延迟
客户端音频播放:用 Web Audio API 实时注入
收到 ArrayBuffer 后,不能直接给 <audio> 标签播放(它不支持裸 PCM)。正确路径是:
- 创建
AudioContext(推荐new AudioContext({ latencyHint: 'interactive' })) - 用
context.createBuffer()构建音频缓冲区,参数含声道数、采样点数、采样率 - 将 ArrayBuffer 解析为
Float32Array(如 PCM 16-bit → 归一化到 [-1,1])填入 buffer - 用
bufferSourceNode播放,并连接至destination;对连续流,应复用节点或使用AudioBufferSourceNode.start(when)控制时间戳防卡顿
稳定性增强:心跳、重连与缓冲策略
纯 WebSocket 不自带重传与拥塞控制,音频流极易受网络抖动影响。实用补救措施:
- 实现轻量心跳(如每 5s send
{ type: 'ping' }),超时未响应则主动 close + 重连 - 客户端维护一个
AudioBuffer队列(长度 ≈ 200–400ms),按时间戳排序播放,平滑网络抖动 - 服务端可做简单丢帧检测(如序列号跳变),客户端据此触发静音补偿或请求重发(仅适用于低延迟容忍场景)
- 首次连接后,建议先协商音频参数(采样率、通道数等),再开始流传输,避免硬编码导致不兼容

















