1、轮询(Polling)

客户端(通常指浏览器)定时向服务端发送请求。不论服务端返回的数据是否更新,是否有值,客户端都会进行处理,然后再下一时间点再继续发送请求。常用方法定时器定时去请求。



function sendRequest() {
$(function() {
$.ajax({
type: 'GET',
url: "user/list",
dataType: 'json',
success: function(data) {
console.log(data);
}
});
});
}
// 定时请求 5s 轮询一次
var timer = setInterval(function() {
sendRequest();
}, 5000)


2、长轮询(Long-Polling)

客户端在向服务端发起一次请求之后立刻挂起,一直到服务端数据有更新,服务端才主动推送信息到客户端。此周期内,客户端不会发送多余的请求,服务端也不做处理,只保留基本连接信息,待服务器有更新推送给客户端之后,客户端处理之后,重新发起下一轮请求。



function sendRequest() {
$(function() {
$.ajax({
type: 'GET',
url: "user/list",
dataType: 'json',
success: function(data) {
console.log(data);
sendRequest(); // 再进行下一次请求
},
complete: function(XMLHttpRequest, textStatus) {
if (textStatus == 'timeout') { // 超时处理
sendRequest(); // 超时之后,重新请求
}
}
});
});
}


3、WebSocket

WebSocket是HTML5出的协议,基于HTTP协议的一个持久化的协议。只需要建立一次HTTP连接,服务端会一直知道客户端的信息,主动推送信息给客户端。




// 服务端
const WebSocket = require('ws');
const WebSocketServer = WebSocket.Server;
const wss = new WebSocketServer({
port: 3000
});
wss.on('connnection', function(ws) {
console.log(`[Server] connection()`);
ws.on('message', function(message) {
console.log(`[Server] Received: ${message}` );
ws.send(`Echo: ${message}`, (err) => {
if (err) {
console.log(`[Server] error: ${err}`);
}
})
})
})
// 客户端
var ws;
function webSockectTest() {
if ('WebSocket' in window) {
alert('该浏览器支持WebSocket');
ws = new WebSocket('ws://localhost:3000/test');
// 已连接,发送数据
ws.onopen = function() {
ws.send('发送数据');
alert('数据发送中');
};

ws.onmessage = function(evt) {
var receivedMsg = evt.data;
alert('数据已接收' + receivedMsg);
}

ws.onerror = function(evt) {
alert('Error:' + JSON.stringify(evt));
}

ws.onclose = function() {
alert('连接已关闭');
}

} else {
alert('该浏览器不支持WebSocket');
}
}
webSockectTest();


方法

浏览器支持

服务器负载

客户端负载

延迟

实现复杂度

优点

缺点

例子

轮询

几乎所有浏览器

较少CPU资源;

较多内存资源和带宽资源;

占用较多的内存资源

非实时

实现简单

后端程序容易编写

浪费带宽和服务器资源

小型应用

长轮询

几乎所有浏览器

与传统相似

与传统轮询相似

同传统轮询

需要服务端配合,客户端实现简单。

在无消息的情况下不会频繁请求

服务器保持连接消耗资源

WebQQ

WebSocket

IE10+

Firefox4+

Chrome4+

Safari5+

Opera11.5+

无需循环等待,CPU和内存资源不以客户端数量衡量,而是以客户端事件数量衡量

同Server-Sent Event

实时

需要Socket程序实现和额外端口,客户端实现简单

建立一次连接之后,客户端不要频繁发请求,服务端主动推送信息

需要有浏览器支持限制

需要实时性高的应用