实时通信技术能够让客户端和服务端在不刷新页面的情况下实现双向或单向的数据实时传输,在JavaScript网络编程中,开发者可以根据业务场景选择不同的实现方案,每种方案都有对应的适用场景和实现逻辑。

常见的实时通信实现方案
1. 长轮询
长轮询是早期实现实时通信的常用方案,原理是客户端向服务端发送请求后,服务端不会立即返回响应,而是等待有数据更新或者超时后再返回,客户端收到响应后立刻再次发起新的请求,以此模拟实时通信的效果。
这种方案的优点是实现简单,兼容性好,不需要特殊的服务端支持;缺点是会频繁创建连接,服务端压力大,实时性相对较弱。
下面是长轮询的客户端实现代码示例:
// 长轮询客户端实现
function longPolling() {
fetch('/api/long-polling')
.then(response => response.json())
.then(data => {
// 处理接收到的数据
console.log('接收到新数据:', data);
// 立刻发起下一次请求
longPolling();
})
.catch(error => {
console.error('长轮询请求出错:', error);
// 出错后延迟一段时间再重试
setTimeout(longPolling, 3000);
});
}
// 启动长轮询
longPolling();
2. Server Sent Events(SSE)
Server Sent Events是HTML5规范中定义的单向实时通信技术,服务端可以向客户端主动推送数据,客户端通过EventSource对象接收数据。这种方式基于HTTP协议,服务端返回的数据格式是text/event-stream,连接会保持打开状态,服务端可以多次推送数据。
优点是实现简单,基于标准HTTP协议,不需要额外的协议升级,适合服务端向客户端单向推送数据的场景;缺点是不支持客户端向服务端主动发送数据,只支持单向通信。
客户端使用EventSource的代码示例:
// 创建EventSource实例,连接服务端SSE接口
const eventSource = new EventSource('/api/sse');
// 监听服务端推送的消息
eventSource.onmessage = function(event) {
const data = JSON.parse(event.data);
console.log('接收到SSE推送数据:', data);
};
// 监听连接错误
eventSource.onerror = function(error) {
console.error('SSE连接出错:', error);
};
对应的Node.js服务端实现示例:
const http = require('http');
const server = http.createServer((req, res) => {
if (req.url === '/api/sse') {
// 设置响应头为event-stream类型
res.writeHead(200, {
'Content-Type': 'text/event-stream',
'Cache-Control': 'no-cache',
'Connection': 'keep-alive'
});
// 定时推送数据
let count = 0;
const timer = setInterval(() => {
count++;
// 推送的数据格式需要符合SSE规范
res.write(`data: ${JSON.stringify({ num: count })}nn`);
// 推送10次后结束连接
if (count >= 10) {
clearInterval(timer);
res.end();
}
}, 1000);
}
});
server.listen(3000, () => {
console.log('服务启动在3000端口');
});
3. WebSocket
WebSocket是HTML5提供的全双工通信协议,客户端和服务端只需要完成一次握手,就可以建立持久的连接,双方都可以主动向对方发送数据,实时性最强,是目前主流的实时通信方案。
优点是支持全双工通信,实时性高,连接建立后开销小;缺点是实现相对复杂,需要服务端支持WebSocket协议,部分老旧浏览器可能不兼容。
客户端WebSocket实现代码示例:
// 创建WebSocket连接
const socket = new WebSocket('ws://localhost:3000/ws');
// 连接建立成功回调
socket.onopen = function() {
console.log('WebSocket连接已建立');
// 向服务端发送数据
socket.send(JSON.stringify({ type: 'greeting', content: 'hello server' }));
};
// 接收服务端推送的数据
socket.onmessage = function(event) {
const data = JSON.parse(event.data);
console.log('接收到WebSocket数据:', data);
};
// 连接关闭回调
socket.onclose = function() {
console.log('WebSocket连接已关闭');
};
// 连接出错回调
socket.onerror = function(error) {
console.error('WebSocket连接出错:', error);
};
对应的Node.js服务端使用ws库的实现示例:
const WebSocket = require('ws');
const wss = new WebSocket.Server({ port: 3000 });
// 监听连接事件
wss.on('connection', function connection(ws) {
console.log('有新的WebSocket连接建立');
// 接收客户端发送的数据
ws.on('message', function message(data) {
const parsedData = JSON.parse(data);
console.log('接收到客户端数据:', parsedData);
// 向客户端返回数据
ws.send(JSON.stringify({ type: 'response', content: '收到你的消息了' }));
});
// 连接关闭事件
ws.on('close', function() {
console.log('WebSocket连接关闭');
});
});
三种方案对比
我们可以通过下面的表格直观对比三种方案的差异:
| 方案类型 | 通信方向 | 实时性 | 实现复杂度 | 适用场景 |
|---|---|---|---|---|
| 长轮询 | 单向(客户端请求,服务端响应) | 较弱 | 低 | 兼容性要求高、实时性要求不高的场景 |
| Server Sent Events | 单向(服务端推送到客户端) | 中等 | 中等 | 服务端单向推送数据的场景,如股票行情、新闻推送 |
| WebSocket | 全双工(双向通信) | 强 | 较高 | 即时聊天、协同编辑、实时游戏等双向实时通信场景 |
方案选择建议
在实际的JavaScript网络编程中,选择实时通信方案可以参考以下原则:
- 如果业务只需要服务端单向推送数据,且不需要太高的实时性,优先选择Server Sent Events,实现简单且兼容性好。
- 如果需要双向实时通信,比如即时聊天、实时协作功能,优先选择WebSocket,能够满足高实时性的需求。
- 如果需要兼容非常老旧的浏览器,且实时性要求不高,可以选择长轮询作为降级方案。
另外需要注意的是,WebSocket和SSE都需要服务端的对应支持,开发前需要确认服务端是否能够实现对应的接口逻辑,避免出现前后端协议不匹配的问题。
WebSocketServer_Sent_Events长轮询EventSource实时通信修改时间:2026-06-25 07:00:40