JavaScript WebSocket
外观
JavaScript WebSocket[编辑 | 编辑源代码]
WebSocket 是一种在单个 TCP 连接上进行全双工通信的协议,允许客户端和服务器之间实时交换数据。与传统的 HTTP 请求不同,WebSocket 提供持久的连接,使得数据可以双向流动,适用于实时应用如聊天、在线游戏和股票行情推送。
介绍[编辑 | 编辑源代码]
WebSocket 协议(RFC 6455)通过一次 HTTP 握手升级为 WebSocket 连接,之后客户端和服务器可以随时发送数据,无需重新建立连接。相比轮询或长轮询(Long Polling),WebSocket 减少了延迟和带宽消耗。
关键特性[编辑 | 编辑源代码]
- 全双工通信:客户端和服务器可以同时发送和接收数据。
- 低延迟:无需重复建立连接。
- 轻量级:数据帧头部较小,适合高频通信。
- 跨域支持:可通过 CORS 或代理服务器实现。
基本用法[编辑 | 编辑源代码]
以下是一个简单的 WebSocket 客户端示例:
// 创建 WebSocket 连接(ws:// 表示非加密,wss:// 表示加密)
const socket = new WebSocket('ws://example.com/socket');
// 连接打开时触发
socket.addEventListener('open', (event) => {
console.log('连接已建立');
socket.send('Hello Server!'); // 发送消息
});
// 接收服务器消息
socket.addEventListener('message', (event) => {
console.log('收到消息:', event.data);
});
// 连接关闭时触发
socket.addEventListener('close', (event) => {
console.log('连接已关闭');
});
// 错误处理
socket.addEventListener('error', (error) => {
console.error('WebSocket 错误:', error);
});
输出示例[编辑 | 编辑源代码]
假设服务器返回 "Welcome!",控制台输出如下:
连接已建立 收到消息: Welcome!
协议细节[编辑 | 编辑源代码]
WebSocket 握手阶段使用 HTTP 升级头:
GET /socket HTTP/1.1 Host: example.com Upgrade: websocket Connection: Upgrade Sec-WebSocket-Key: dGhlIHNhbXBsZSBub25jZQ== Sec-WebSocket-Version: 13
服务器响应:
HTTP/1.1 101 Switching Protocols Upgrade: websocket Connection: Upgrade Sec-WebSocket-Accept: s3pPLMBiTxaQ9kYGzzhZRbK+xOo=
实际案例[编辑 | 编辑源代码]
实时聊天应用[编辑 | 编辑源代码]
以下是一个简单的聊天室实现:
const chatSocket = new WebSocket('wss://chat.example.com');
// 发送消息
document.getElementById('send-button').addEventListener('click', () => {
const message = document.getElementById('message-input').value;
chatSocket.send(JSON.stringify({ type: 'message', text: message }));
});
// 接收消息
chatSocket.addEventListener('message', (event) => {
const data = JSON.parse(event.data);
if (data.type === 'message') {
const chatBox = document.getElementById('chat-box');
chatBox.innerHTML += `<div>${data.text}</div>`;
}
});
股票行情推送[编辑 | 编辑源代码]
使用 WebSocket 接收实时股价:
const stockSocket = new WebSocket('wss://stocks.example.com');
stockSocket.addEventListener('message', (event) => {
const stocks = JSON.parse(event.data);
stocks.forEach(stock => {
console.log(`${stock.symbol}: $${stock.price}`);
});
});
高级主题[编辑 | 编辑源代码]
二进制数据传输[编辑 | 编辑源代码]
WebSocket 支持发送二进制数据(如 ArrayBuffer 或 Blob):
socket.send(new Uint8Array([0x48, 0x65, 0x6c, 0x6c, 0x6f])); // 发送 "Hello" 的二进制形式
心跳机制[编辑 | 编辑源代码]
保持连接活跃的示例:
setInterval(() => {
if (socket.readyState === WebSocket.OPEN) {
socket.send('ping'); // 心跳包
}
}, 30000); // 每30秒发送一次
状态管理[编辑 | 编辑源代码]
WebSocket 对象有以下状态(通过 socket.readyState
获取):
CONNECTING (0)
:连接中OPEN (1)
:已连接CLOSING (2)
:关闭中CLOSED (3)
:已关闭
错误处理[编辑 | 编辑源代码]
常见错误及解决方案:
- 连接失败:检查服务器是否支持 WebSocket 或网络是否通畅。
- 协议不匹配:确保客户端和服务器的 WebSocket 版本一致。
- 数据格式错误:验证发送的数据是否为字符串或二进制类型。
性能优化[编辑 | 编辑源代码]
- 使用
wss://
(加密)避免中间人攻击。 - 压缩数据(如 JSON 或 Protocol Buffers)减少带宽。
- 实现重连逻辑应对网络波动。
与其他技术对比[编辑 | 编辑源代码]
技术 | 特点 | 适用场景 |
---|---|---|
频繁请求,高延迟 | 简单实时性要求低的应用 | ||
服务器保持连接直到有数据 | 中等实时性需求 | ||
服务器单向推送 | 实时通知(如新闻推送) | ||
全双工,低延迟 | 高频双向通信(如游戏、聊天) |
数学基础[编辑 | 编辑源代码]
WebSocket 的掩码计算(RFC 6455 要求客户端掩码数据): 其中 表示异或操作。
可视化连接流程[编辑 | 编辑源代码]
总结[编辑 | 编辑源代码]
WebSocket 是现代 Web 应用中实现实时通信的核心技术,适用于需要低延迟和高频数据交换的场景。通过本文的示例和解释,开发者可以快速掌握其基本用法和高级特性。