为什么使用WebSockets构建:
- Full-duplex异步消息传递。换句话说,客户端和服务器都可以独立的向彼此传输消息。
- WebSockets无需重新配置即可通过大多数防火墙。
- 良好的安全模型(基于原始的安全模型)。
WebSockets开源解决方案
WebSockets库有两个主要类:其一实现协议并将剩余部分留给开发人员,另外一个构建在协议之上,具有实时消息传递应用程序通常所需的各种附加功能,例如恢复丢失连接,pub/subm和通道,验证,授权等等。
后一种类型通常要求客户端使用自己的库,而不是仅使用浏览器提供的原始WebSocket API.因此,确保您对他们的工作方式和所提供的产品感到满意至关重要。一旦将所有解决方案集成到您的架构中,您可能会发现自己被锁定在所选择的方案中,并且可靠性,性能,和扩展性方面的任何问题都可能使你困惑。
让我们从列入两个类别中的第一个类别的列表开始。
注意:以下所有内容都是开源库。
Ws
Ws是一个简单易用,快速且经过全面测试的WebSocket客户端和node.js的服务器。它绝对是一个准系统实现,旨在完成协议的所有艰苦工作,但是连接恢复,发布/订阅,等附加功能是您必须自己管理的问题。
客户端(浏览器,捆绑前):
const WebSocket = require('ws'); const ws = new WebSocket('ws://www.host.com/path'); ws.on('open', function open() { ws.send('something'); }); ws.on('message', function incoming(data) { console.log(data); });
Server (Node.js):
const WebSocket = require('ws'); const wss = new WebSocket.Server({ port: 8080 }); wss.on('connection', function connection(ws) { ws.on('message', function incoming(message) { console.log('received: %s', message); }); ws.send('something'); });
uWebSockets
uWs是ws的直接替代品,特别注重性能和稳定性。据我所知,它是一英里内最快的WebSocket服务器实现。
由于作者试图从哲学原因将其从NPM中拉出来,最近围绕uWS引起了一些争议,但是最新的工作版本仍然在NPM上,并且可以在从NPM安装时明确指定该版本。也就是说,作者正在开发一个新版本,并且还在开发中附带了node.js绑定。
var WebSocketServer = require('uws').Server; var wss = new WebSocketServer({ port: 3000 }); function onMessage(message) { console.log('received: ' + message); } wss.on('connection', function(ws) { ws.on('message', onMessage); ws.send('something'); });
客户端-在浏览器中使用WebSockets
WebSocket API在WHATWG HTML Living Standard中定义,实际上非常简单易用。构造WebSocket需要一行代码。
JS
const ws = new WebSocket('ws://example.org');
注意你通常使用http方案的地方ws的使用。还有另外一种选择,使用wss,这里你通常会使用https.这些协议与WebSocket规范一起引入,旨在表示HTTP连接,其中包括升级连接以使用WebSockets的请求。
创建WebSocket对象本身并没有做很多事情。连接时异步建立的,因此您需要在发送任何消息之前侦听握手的完成,并且还包括从服务器接收的消息的侦听器。
ws.addEventListener('open', () => { // Send a message to the WebSocket server ws.send('Hello!'); }); ws.addEventListener('message', event => { // The `event` object is a typical DOM event object, and the message data sent // by the server is stored in the `data` property console.log('Received:', event.data); });
还有错误和关闭事件。连接终止时WebSockets不会自动恢复-这是您需要自己实现的,并且是存在许多客户端库的原因之一。虽然WebSocket类很简单易用,但它实际上只是一个基本的构建块。必须单独实现对不同子协议或消息传递通道等附加功能的支持。
- Go: golongpoll
- PHP: php-long-polling
- Node.js: Pollymer
- Python: A simple COMET server
Ably, WebSockets, 和长轮询
Ably的大多数客户端库SDK使用WebSocket建立与Ably的实时连接,然后对包括身份验证在内的所有其他REST操作使用简单的HTTP请求。
但是客户端库SDK(例如我们的JS浏览器库)旨在根据浏览器和可用连接选择最佳可用传输。通过支持能够回退到最低公分母的额外传输,Ably确保现在几乎所有浏览器都能够建立与Ably的实时连接。我们的JS浏览器库目前支持以下传输,以实现最佳性能:
- WebSockets(supported by 94% of browsers globally as of Dec 2017)
- XHR streaming
- XHR polling
- JSONP polling
实施WebSockets支持并且长轮询作为后备时,需要考虑很多-不仅在客户端和服务器实现细节方面,还包括支持其他传输以确保对不同客户端环境的强大支持,以及更广泛的关注,例如身份验证和授权,确保消息传递,可靠的消息排序,历史信息保留,还有更多。