HTML5 WebSocket 通信API
WebSocket 是 HTML5 引入的重要通信协议,它在浏览器与服务器之间建立了全双工通信通道,实现了实时、双向的数据传输。
简介
传统的 HTTP 通信采用请求-响应模式,客户端发起请求,服务器返回响应后连接关闭。这种模式对于实时应用来说效率很低,因为客户端需要不断轮询服务器来获取最新数据。WebSocket 解决了这个问题,它在客户端与服务器之间建立了持久的 TCP 连接,双方可以随时发送数据,无需重复建立连接。
WebSocket 协议使用 ws:// 或 wss://(加密)作为 URL 前缀,与 HTTP 共享默认端口 80 和 443,这使得它能够与现有网络基础设施良好兼容。
基本用法
创建 WebSocket 连接非常简单,只需实例化一个 WebSocket 对象并指定服务器地址:
创建 WebSocket 连接
// 普通连接(非加密)
var ws = new WebSocket("ws://example.com/ws");
// 安全连接(加密,推荐)
var wss = new WebSocket("wss://example.com/ws");
// 使用 SockJS(支持更多浏览器)
var sock = new SockJS("/ws");
事件处理
WebSocket 对象提供了四个核心事件,用于处理连接的不同状态:
WebSocket 事件示例
var ws = new SockJS("/ws");
// 连接建立时触发
ws.onopen = function() {
console.log("连接已打开");
ws.send("Hello Server!");
};
// 收到消息时触发
ws.onmessage = function(event) {
console.log("收到消息: ", event.data);
};
// 发生错误时触发
ws.onerror = function(error) {
console.error("错误: ", error);
};
// 连接关闭时触发
ws.onclose = function(event) {
console.log("连接已关闭, 代码: " + event.code);
};
方法
WebSocket 对象提供以下常用方法:
- send(data) - 向服务器发送数据,支持发送字符串、JSON、ArrayBuffer
- close([code], [reason]) - 关闭 WebSocket 连接
发送消息示例
// 发送字符串消息
ws.send("Hello World");
// 发送 JSON 数据
ws.send(JSON.stringify({
type: "message",
username: "张三",
content: "你好"
}));
// 关闭连接
ws.close(1000, "正常关闭");
连接状态
通过 readyState 属性可以获取 WebSocket 的当前状态:
连接状态常量
WebSocket.CONNECTING = 0; // 连接中
WebSocket.OPEN = 1; // 已打开
WebSocket.CLOSING = 2; // 关闭中
WebSocket.CLOSED = 3; // 已关闭
检查连接状态
function sendMessage(data) {
if (ws && ws.readyState === WebSocket.OPEN) {
ws.send(data);
} else {
console.log("连接未就绪,当前状态: " + ws.readyState);
}
}
SSE vs WebSocket
选择 SSE 还是 WebSocket 取决于具体需求:
| 特性 | SSE | WebSocket |
|---|---|---|
| 通信方向 | 单向(服务器→客户端) | 全双工(双向) |
| 协议 | HTTP/HTTPS | WebSocket (ws/wss) |
| 兼容性 | 除IE外都支持 | 所有现代浏览器 |
| 自动重连 | 支持 | 需要手动实现 |
| 适用场景 | 股票、新闻、通知 | 聊天、游戏、协作 |
注意事项
开发提示
- 生产环境应使用 wss://(加密连接)而非 ws://
- WebSocket 连接是持久的,需要在页面卸载时正确关闭
- 服务器可能意外断开,需要实现自动重连机制
- 发送大量数据时考虑使用二进制格式提高性能