菜单

【金沙国际】辩驳联系实际:从零通晓WebSocket的通信原理、协议格式、安全性

2019年1月18日 - 金沙前端

WebSocket:5分钟从入门到了解

2018/01/08 · HTML5 · 1
评论 ·
websocket

原稿出处: 先后猿小卡   

一、内容概览

原稿出处: 先后猿小卡   

正文来源云栖社区主次猿小卡的技艺分享。

一、内容概览

WebSocket的出现,使得浏览器具备了实时双向通信的力量。本文由浅入深,介绍了WebSocket怎么样建立连接、交流数据的底细,以及数据帧的格式。其余,还简要介绍了针对性WebSocket的中卫攻击,以及协和是何等抵抗类似攻击的。

WebSocket的产出,使得浏览器具备了实时双向通信的力量。本文由浅入深,介绍了WebSocket咋样树立连接、交换数据的细节,以及数据帧的格式。此外,还简要介绍了针对WebSocket的平安攻击,以及协和是什么抵挡类似攻击的。

一、内容概览

WebSocket的产出,使得浏览器具备了实时双向通信的力量。本文由浅入深,介绍了WebSocket怎么着建立连接、互换数据的底细,以及数据帧的格式。此外,还简要介绍了针对WebSocket的自贡攻击,以及协和是如何抵抗类似攻击的。

1、前言

WebSocket的产出,使得浏览器具备了实时双向通信的能力。本文由浅入深,介绍了WebSocket怎么着树立连接、交流数据的细节,以及数据帧的格式。另外,还简要介绍了针对性WebSocket的黑河攻击,以及协和是如何抵抗类似攻击的。

(本文同步发布于:http://www.52im.net/thread-1341-1-1.html)

二、什么是WebSocket

HTML5上马提供的一种浏览器与服务器举行全双工通讯的网络技术,属于应用层协议。它遵照TCP传输协议,并复用HTTP的抓手通道。

对大多数web开发者来说,下边这段描述有点枯燥,其实假设记住几点:

  1. WebSocket可以在浏览器里采用
  2. 支撑双向通信
  3. 运用很简短

二、什么是WebSocket

二、什么是WebSocket

HTML5方始提供的一种浏览器与服务器举行全双工通讯的网络技术,属于应用层协议。它依据TCP传输协议,并复用HTTP的握手通道。

对绝大多数web开发者来说,下边这段描述有点枯燥,其实只要记住几点:

  1. WebSocket可以在浏览器里使用
  2. 协理双向通信
  3. 应用很粗略

2、参考文章

《WebSocket详解(一):开首认识WebSocket技术》

《WebSocket详解(二):技术原理、代码演示和选取案例》

《WebSocket详解(三):深切WebSocket通信协议细节》

《WebSocket详解(四):刨根问底HTTP与WebSocket的涉嫌(上篇)》

《WebSocket详解(五):刨根问底HTTP与WebSocket的关系(下篇)》

《WebSocket详解(六):刨根问底WebSocket与Socket的涉及》

1、有什么亮点

说到优点,这里的比较参照物是HTTP协议,概括地说就是:襄助双向通信,更灵活,更高效,可扩张性更好。

  1. 帮忙双向通信,实时性更强。
  2. 更好的二进制协理。
  3. 较少的控制支出。连接创造后,ws客户端、服务端举办数据交流时,协议决定的数目咸阳部较小。在不含有头部的场馆下,服务端到客户端的宿迁唯有2~10字节(取决于数量包长度),客户端到服务端的来说,需要加上额外的4字节的掩码。而HTTP协议每便通信都亟需带领完整的头部。
  4. 帮忙扩充。ws协商定义了扩充,用户可以扩展协议,或者实现自定义的子协议。(比如辅助自定义压缩算法等)

对此背后两点,没有研商过WebSocket协议正式的校友也许清楚起来不够直观,但不影响对WebSocket的就学和使用。

HTML5初叶提供的一种浏览器与服务器举行全双工通讯的网络技术,属于应用层协议。它依照TCP传输协议,并复用HTTP的握手通道。

1、有怎么样亮点

说到优点,这里的对照参照物是HTTP协议,概括地说就是:匡助双向通信,更灵敏,更迅捷,可扩展性更好。

  1. 支撑双向通信,实时性更强。
  2. 更好的二进制辅助。
  3. 较少的决定支出。连接成立后,ws客户端、服务端举办数据交流时,协议决定的数额秦皇岛部较小。在不包含头部的事态下,服务端到客户端的新乡唯有2~10字节(取决于数量包长度),客户端到服务端的来说,需要丰盛额外的4字节的掩码。而HTTP协议每趟通信都亟需带领完整的头部。
  4. 补助扩大。ws商事定义了扩展,用户可以扩充协议,或者实现自定义的子协议。(比如匡助自定义压缩算法等)

对此背后两点,没有研讨过WebSocket协议正式的同桌可能精通起来不够直观,但不影响对WebSocket的上学和应用。

3、更多材料

Web端即时通讯新手入门贴:

《新手入门贴:详解Web端即时通讯技术的法则》

Web端即时通讯技术盘点请参见:

《Web端即时通讯技术盘点:短轮询、Comet、Websocket、SSE》

关于Ajax短轮询:

找这下面的材料没什么意义,除非忽悠客户,否则请考虑其他3种方案即可。

有关Comet技术的详尽介绍请参见:

《Comet技术详解:基于HTTP长连接的Web端实时通信技术》

《WEB端即时通讯:HTTP长连接、长轮询(long
polling)详解》

《WEB端即时通讯:不用WebSocket也同样能搞定信息的即时性》

《开源Comet服务器iComet:帮助百万并发的Web端即时通讯方案》

关于WebSocket的详细介绍请参见:

《新手神速入门:WebSocket简明教程》

《WebSocket详解(一):开头认识WebSocket技术》

《WebSocket详解(二):技术原理、代码演示和利用案例》

《WebSocket详解(三):深远WebSocket通信协议细节》

《Socket.IO介绍:帮助WebSocket、用于WEB端的即时通讯的框架》

《socket.io和websocket
之间是何许关联?有咋样分别?》

关于SSE的详实介绍随笔请参见:

《SSE技术详解:一种崭新的HTML5服务器推送事件技术》

更多WEB端即时通讯作品请见:

http://www.52im.net/forum.php?mod=collection&action=view&ctid=15

2、需要学习如何东西

对网络应用层协议的读书来说,最要害的频繁就是总是建立过程数据交流教程。当然,数据的格式是逃不掉的,因为它直接决定了商事本身的能力。好的数据格式能让协议更连忙、扩展性更好。

下文首要围绕下边几点举行:

  1. 何以树立连接
  2. 哪些互换数据
  3. 数据帧格式
  4. 如何保持连接

对大多数web开发者来说,下面这段描述有点枯燥,其实假设记住几点:

2、需要上学怎样东西

对网络应用层协议的上学来说,最首要的一再就是一连建立过程数据互换教程。当然,数据的格式是逃不掉的,因为它直接决定了协和本身的力量。好的数量格式能让协议更迅速、增添性更好。

下文首要围绕下边几点开展:

  1. 什么树立连接
  2. 咋样互换数据
  3. 数码帧格式
  4. 哪些保持连接

4、什么是WebSocket

HTML5起初提供的一种浏览器与服务器举行全双工通讯的网络技术,属于应用层协议。它依据TCP传输协议,并复用HTTP的抓手通道。(更多WebSocket的连带介绍,可参见“参考著作”这一节)

对多数web开发者来说,下边这段描述有点枯燥,其实只要记住几点:

WebSocket可以在浏览器里应用;

支撑双向通信;

动用很简单。

三、入门例子

在正儿八经介绍协议细节前,先来看一个简短的例证,有个直观感受。例子包括了WebSocket服务端、WebSocket客户端(网页端)。完整代码可以在
这里
找到。

那边服务端用了ws本条库。相比我们熟练的socket.iows心想事成更轻量,更符合学习的目标。

WebSocket能够在浏览器里应用

三、入门例子

在正儿八经介绍协议细节前,先来看一个概括的事例,有个直观感受。例子包括了WebSocket服务端、WebSocket客户端(网页端)。完整代码可以在
这里
找到。

这里服务端用了ws其一库。相比较大家理解的socket.iows落实更轻量,更合乎学习的目的。

4.1 有咋样亮点

说到优点,这里的对待参照物是HTTP协议,概括地说就是:补助双向通信,更灵敏,更快捷,可扩大性更好。

切切实实优化如下:

1)补助双向通信,实时性更强;

2)更好的二进制扶助;

3)较少的支配支出:

连续创造后,ws客户端、服务端举行数据互换时,协议决定的数量湖州部较小。在不带有头部的情景下,服务端到客户端的扬州只有2~10字节(取决于数量包长度),客户端到服务端的来说,需要添加额外的4字节的掩码。而HTTP协议每趟通信都需要引导完整的头顶;

4)帮忙扩张:

ws合计定义了扩大,用户可以扩充协议,或者实现自定义的子协议(比如帮助自定义压缩算法等)。

对此背后两点,没有研商过WebSocket协议正式的校友也许清楚起来不够直观,但不影响对WebSocket的学习和应用。

1、服务端

代码如下,监听8080端口。当有新的总是请求到达时,打印日志,同时向客户端发送音讯。当接到到来自客户端的消息时,同样打印日志。

var app = require(‘express’)(); var server =
require(‘http’).Server(app); var WebSocket = require(‘ws’); var wss =
new WebSocket.Server({ port: 8080 }); wss.on(‘connection’, function
connection(ws) { console.log(‘server: receive connection.’);
ws.on(‘message’, function incoming(message) { console.log(‘server:
received: %s’, message); }); ws.send(‘world’); }); app.get(‘/’, function
(req, res) { res.sendfile(__dirname + ‘/index.html’); });
app.listen(3000);

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
var app = require(‘express’)();
var server = require(‘http’).Server(app);
var WebSocket = require(‘ws’);
 
var wss = new WebSocket.Server({ port: 8080 });
 
wss.on(‘connection’, function connection(ws) {
    console.log(‘server: receive connection.’);
    
    ws.on(‘message’, function incoming(message) {
        console.log(‘server: received: %s’, message);
    });
 
    ws.send(‘world’);
});
 
app.get(‘/’, function (req, res) {
  res.sendfile(__dirname + ‘/index.html’);
});
 
app.listen(3000);

支撑双向通信

1、服务端

代码如下,监听8080端口。当有新的连接请求到达时,打印日志,同时向客户端发送信息。当接过到来自客户端的消息时,同样打印日志。

var app = require(‘express’)(); var server =
require(‘http’).Server(app); var WebSocket = require(‘ws’); var wss =
new WebSocket.Server({ port: 8080 }); wss.on(‘connection’, function
connection(ws) { console.log(‘server: receive connection.’);
ws.on(‘message’, function incoming(message) { console.log(‘server:
received: %s’, message); }); ws.send(‘world’); }); app.get(‘/’, function
(req, res) { res.sendfile(__dirname + ‘/index.html’); });
app.listen(3000);

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
var app = require(‘express’)();
var server = require(‘http’).Server(app);
var WebSocket = require(‘ws’);
 
var wss = new WebSocket.Server({ port: 8080 });
 
wss.on(‘connection’, function connection(ws) {
    console.log(‘server: receive connection.’);
    
    ws.on(‘message’, function incoming(message) {
        console.log(‘server: received: %s’, message);
    });
 
    ws.send(‘world’);
});
 
app.get(‘/’, function (req, res) {
  res.sendfile(__dirname + ‘/index.html’);
});
 
app.listen(3000);

4.2 需要学习如何东西

对网络应用层协议的求学来说,最要害的频繁就是接连建立过程、数据交换教程。当然,数据的格式是逃不掉的,因为它直接决定了商事本身的力量。好的数据格式能让协议更高效、增添性更好。

下文首要围绕下边几点实行:

怎么树立连接;

怎么着交流数据;

数据帧格式;

怎么着保障连接。

2、客户端

代码如下,向8080端口发起WebSocket连接。连接建立后,打印日志,同时向服务端发送信息。接收到来自服务端的消息后,同样打印日志。

1
 

选拔很简短

2、客户端

代码如下,向8080端口发起WebSocket连接。连接建立后,打印日志,同时向服务端发送音讯。接收到来自服务端的音信后,同样打印日志。

1
 

5、入门例子

在正式介绍协议细节前,先来看一个大概的例证,有个直观感受。例子包括了WebSocket服务端、WebSocket客户端(网页端)。

本节完整例代码请下载本附件:

(请从链接:http://www.52im.net/thread-1341-1-1.html 处下载)

此间服务端用了ws这么些库。相相比我们耳熟能详的socket.io(详见《Socket.IO介绍:补助WebSocket、用于WEB端的即时通讯的框架》),ws实现更轻量,更契合学习的目的。

3、运行结果

可分别查看服务端、客户端的日记,这里不举办。

服务端输出:

server: receive connection. server: received hello

1
2
server: receive connection.
server: received hello

客户端输出:

client: ws connection is open client: received world

1
2
client: ws connection is open
client: received world

1、有什么样亮点

3、运行结果

可分别查看服务端、客户端的日志,这里不举办。

服务端输出:

server: receive connection. server: received hello

1
2
server: receive connection.
server: received hello

客户端输出:

client: ws connection is open client: received world

1
2
client: ws connection is open
client: received world

5.1 服务端

代码如下,监听8080端口。当有新的总是请求到达时,打印日志,同时向客户端发送信息。当收到到来自客户端的音信时,同样打印日志。

varapp = require(‘express’)();

varserver = require(‘http’).Server(app);

varWebSocket = require(‘ws’);

varwss = newWebSocket.Server({ port: 8080 });

wss.on(‘connection’, functionconnection(ws) {

    console.log(‘server: receive connection.’);

    ws.on(‘message’, functionincoming(message) {

        console.log(‘server: received: %s’, message);

    });

    ws.send(‘world’);

});

app.get(‘/’, function(req, res) {

  res.sendfile(__dirname + ‘/index.html’);

});

app.listen(3000);

四、怎样树立连接

前方提到,WebSocket复用了HTTP的拉手通道。具体指的是,客户端通过HTTP请求与WebSocket服务端协商升级协议。协议升级成功后,后续的数据沟通则遵照WebSocket的合计。

说到优点,这里的对待参照物是HTTP协议,概括地说就是:协理双向通信,更灵活,更快速,可增加性更好。

四、如何树立连接

眼前提到,WebSocket复用了HTTP的拉手通道。具体指的是,客户端通过HTTP请求与WebSocket服务端协商升级协议。协议升级成功后,后续的数据互换则遵照WebSocket的合计。

5.2 客户端

代码如下,向8080端口发起WebSocket连接。连接建立后,打印日志,同时向服务端发送音信。接收到来自服务端的信息后,同样打印日志。

  varws = newWebSocket(‘ws://localhost:8080’);

  ws.onopen = function() {

    console.log(‘ws onopen’);

    ws.send(‘from client: hello’);

  };

  ws.onmessage = function(e) {

    console.log(‘ws onmessage’);

    console.log(‘from server: ‘+ e.data);

  };

1、客户端:申请协议升级

先是,客户端发起协议升级请求。能够观察,选用的是正规的HTTP报文格式,且只辅助GET方法。

GET / HTTP/1.1 Host: localhost:8080 Origin:
Connection: Upgrade Upgrade: websocket Sec-WebSocket-Version: 13
Sec-WebSocket-Key: w4v7O6xFTi36lq3RNcgctw==

1
2
3
4
5
6
7
GET / HTTP/1.1
Host: localhost:8080
Origin: http://127.0.0.1:3000
Connection: Upgrade
Upgrade: websocket
Sec-WebSocket-Version: 13
Sec-WebSocket-Key: w4v7O6xFTi36lq3RNcgctw==

第一呼吁首部意义如下:

只顾,下面请求省略了一部分非重点请求首部。由于是正式的HTTP请求,类似Host、Origin、库克(Cook)ie等请求首部会照常发送。在握手阶段,可以透过有关请求首部举办安全范围、权限校验等。

支撑双向通信,实时性更强。

1、客户端:申请协议升级

率先,客户端发起协议升级请求。可以看出,采纳的是正统的HTTP报文格式,且只帮忙GET方法。

GET / HTTP/1.1 Host: localhost:8080 Origin:
Connection: Upgrade Upgrade: websocket Sec-WebSocket-Version: 13
Sec-WebSocket-Key: w4v7O6xFTi36lq3RNcgctw==

1
2
3
4
5
6
7
GET / HTTP/1.1
Host: localhost:8080
Origin: http://127.0.0.1:3000
Connection: Upgrade
Upgrade: websocket
Sec-WebSocket-Version: 13
Sec-WebSocket-Key: w4v7O6xFTi36lq3RNcgctw==

重大呼吁首部意义如下:

瞩目,下边请求省略了一部分非重点请求首部。由于是规范的HTTP请求,类似Host、Origin、Cookie等请求首部会照常发送。在握手阶段,可以经过有关请求首部举办安全范围、权限校验等。

5.3 运行结果

可各自查看服务端、客户端的日记,这里不举办。

服务端输出:

server: receive connection.

server: received hello

客户端输出:

client: ws connection is open

client: received world

2、服务端:响应协议升级

服务端重返内容如下,状态代码101代表协议切换。到此形成商事升级,后续的数额交互都遵照新的商谈来。

HTTP/1.1 101 Switching Protocols Connection:Upgrade Upgrade: websocket
Sec-WebSocket-Accept: Oy4NRAQ13jhfONC7bP8dTKb4PTU=

1
2
3
4
HTTP/1.1 101 Switching Protocols
Connection:Upgrade
Upgrade: websocket
Sec-WebSocket-Accept: Oy4NRAQ13jhfONC7bP8dTKb4PTU=

备注:每个header都以\r\n说到底,并且最后一行加上一个附加的空行\r\n。另外,服务端回应的HTTP状态码只好在拉手阶段接纳。过了拉手阶段后,就只好使用一定的错误码。

更好的二进制襄助。

2、服务端:响应协议升级

服务端重返内容如下,状态代码101表示协议切换。到此形成协商升级,后续的数码交互都依照新的商谈来。

HTTP/1.1 101 Switching Protocols Connection:Upgrade Upgrade: websocket
Sec-WebSocket-Accept: Oy4NRAQ13jhfONC7bP8dTKb4PTU=

1
2
3
4
HTTP/1.1 101 Switching Protocols
Connection:Upgrade
Upgrade: websocket
Sec-WebSocket-Accept: Oy4NRAQ13jhfONC7bP8dTKb4PTU=

备注:每个header都以\r\n末段,并且最终一行加上一个额外的空行\r\n。其余,服务端回应的HTTP状态码只好在拉手阶段选择。过了拉手阶段后,就只可以使用一定的错误码。

6、咋样建立连接

面前提到,WebSocket复用了HTTP的抓手通道。具体指的是,客户端通过HTTP请求与WebSocket服务端协商升级协议。协议升级成功后,后续的数据交换则遵照WebSocket的商议。

3、Sec-WebSocket-Accept的计算

Sec-WebSocket-Accept遵照客户端请求首部的Sec-WebSocket-Key总结出来。

总结公式为:

  1. Sec-WebSocket-Key258EAFA5-E914-47DA-95CA-C5AB0DC85B11拼接。
  2. 因而SHA1划算出摘要,并转成base64字符串。

伪代码如下:

>toBase64( sha1( Sec-WebSocket-Key +
258EAFA5-E914-47DA-95CA-C5AB0DC85B11 ) )

1
>toBase64( sha1( Sec-WebSocket-Key + 258EAFA5-E914-47DA-95CA-C5AB0DC85B11 )  )

注明下边前的归来结果:

const crypto = require(‘crypto’); const magic =
‘258EAFA5-E914-47DA-95CA-C5AB0DC85B11’; const secWebSocketKey =
‘w4v7O6xFTi36lq3RNcgctw==’; let secWebSocketAccept =
crypto.createHash(‘sha1’) .update(secWebSocketKey + magic)
.digest(‘base64’); console.log(secWebSocketAccept); //
Oy4NRAQ13jhfONC7bP8dTKb4PTU=

1
2
3
4
5
6
7
8
9
10
const crypto = require(‘crypto’);
const magic = ‘258EAFA5-E914-47DA-95CA-C5AB0DC85B11’;
const secWebSocketKey = ‘w4v7O6xFTi36lq3RNcgctw==’;
 
let secWebSocketAccept = crypto.createHash(‘sha1’)
    .update(secWebSocketKey + magic)
    .digest(‘base64’);
 
console.log(secWebSocketAccept);
// Oy4NRAQ13jhfONC7bP8dTKb4PTU=

较少的控制支出。连接创造后,ws客户端、服务端举办数据互换时,协议决定的数目连云港部较小。在不含有头部的情状下,服务端到客户端的廊坊只有2~10字节(取决于数量包长度),客户端到服务端的来说,需要添加额外的4字节的掩码。而HTTP协议每回通信都亟需指导完整的头部。

3、Sec-WebSocket-Accept的计算

Sec-WebSocket-Accept据悉客户端请求首部的Sec-WebSocket-Key总括出来。

统计公式为:

  1. Sec-WebSocket-Key258EAFA5-E914-47DA-95CA-C5AB0DC85B11拼接。
  2. 透过SHA1统计出摘要,并转成base64字符串。

伪代码如下:

>toBase64( sha1( Sec-WebSocket-Key +
258EAFA5-E914-47DA-95CA-C5AB0DC85B11 ) )

1
>toBase64( sha1( Sec-WebSocket-Key + 258EAFA5-E914-47DA-95CA-C5AB0DC85B11 )  )

申明下边前的归来结果:

const crypto = require(‘crypto’); const magic =
‘258EAFA5-E914-47DA-95CA-C5AB0DC85B11’; const secWebSocketKey =
‘w4v7O6xFTi36lq3RNcgctw==’; let secWebSocketAccept =
crypto.createHash(‘sha1’) .update(secWebSocketKey + magic)
.digest(‘base64’); console.log(secWebSocketAccept); //
Oy4NRAQ13jhfONC7bP8dTKb4PTU=

1
2
3
4
5
6
7
8
9
10
const crypto = require(‘crypto’);
const magic = ‘258EAFA5-E914-47DA-95CA-C5AB0DC85B11’;
const secWebSocketKey = ‘w4v7O6xFTi36lq3RNcgctw==’;
 
let secWebSocketAccept = crypto.createHash(‘sha1’)
    .update(secWebSocketKey + magic)
    .digest(‘base64’);
 
console.log(secWebSocketAccept);
// Oy4NRAQ13jhfONC7bP8dTKb4PTU=

6.1 客户端:申请协议升级

先是,客户端发起协议升级请求。可以见到,拔取的是标准的HTTP报文格式,且只帮助GET方法:

GET / HTTP/1.1

Host: localhost:8080

Origin: [url=]

Connection: Upgrade

Upgrade: websocket

Sec-WebSocket-Version: 13

Sec-WebSocket-Key: w4v7O6xFTi36lq3RNcgctw==

最首要呼吁首部意义如下:

Connection: Upgrade:表示要升级协议

Upgrade: websocket:表示要提升到websocket协和。

Sec-WebSocket-Version:
13:表示websocket的版本。假诺服务端不匡助该版本,需要重返一个Sec-WebSocket-Versionheader,里面含有服务端帮助的版本号。

Sec-WebSocket-Key:与背后服务端响应首部的Sec-WebSocket-Accept是配套的,提供基本的制止,比如恶意的接连,或者无意的连接。

注意:上边请求省略了部分非重点请求首部。由于是正统的HTTP请求,类似Host、Origin、库克ie等请求首部会照常发送。在握手阶段,可以经过有关请求首部进行安全限制、权限校验等。

五、数据帧格式

客户端、服务端数据的置换,离不开数据帧格式的概念。因而,在骨子里讲解数据交流在此以前,大家先来看下WebSocket的数额帧格式。

WebSocket客户端、服务端通信的微小单位是帧(frame),由1个或五个帧组成一条完整的信息(message)。

  1. 出殡端:将信息切割成多少个帧,并发送给服务端;
  2. 接收端:接收音讯帧,并将涉及的帧重新组装成完全的信息;

本节的根本,就是教课数据帧的格式。详细定义可参考 RFC6455
5.2节 。

支撑扩张。ws协商定义了扩张,用户可以增添协议,或者实现自定义的子协议。(比如援助自定义压缩算法等)

五、数据帧格式

客户端、服务端数据的交换,离不开数据帧格式的概念。因而,在事实上讲解数据交流此前,我们先来看下WebSocket的数据帧格式。

WebSocket客户端、服务端通信的细单反位是帧(frame),由1个或四个帧组成一条完整的音信(message)。

  1. 发送端:将音讯切割成六个帧,并发送给服务端;
  2. 接收端:接收音信帧,并将关乎的帧重新组装成完全的消息;

本节的关键,就是上课数据帧的格式。详细定义可参考 RFC6455
5.2节 。

6.2 服务端:响应协议升级

服务端再次回到内容如下,状态代码101表示协议切换:

HTTP/1.1 101 Switching Protocols

Connection:Upgrade

Upgrade: websocket

Sec-WebSocket-Accept: Oy4NRAQ13jhfONC7bP8dTKb4PTU=

到此形成商事升级,后续的数码交互都按照新的协议来。

备注:每个header都以\r\n结尾,并且最后一行加上一个附加的空行\r\n。此外,服务端回应的HTTP状态码只好在握手阶段采用。过了拉手阶段后,就只能动用一定的错误码。

1、数据帧格式概览

下边给出了WebSocket数据帧的会面格式。熟识TCP/IP协议的同班对这么的图应该不陌生。

  1. 从左到右,单位是比特。比如FINRSV1各占据1比特,opcode占据4比特。
  2. 内容囊括了标识、操作代码、掩码、数据、数据长度等。(下一小节会展开)

0 1 2 3 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
+-+-+-+-+——-+-+————-+——————————-+
|F|R|R|R| opcode|M| Payload len | Extended payload length | |I|S|S|S|
(4) |A| (7) | (16/64) | |N|V|V|V| |S| | (if payload len==126/127) | |
|1|2|3| |K| | | +-+-+-+-+——-+-+————-+ – – – – – – – – – – –

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
  0                   1                   2                   3
  0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
+-+-+-+-+——-+-+————-+——————————-+
|F|R|R|R| opcode|M| Payload len |    Extended payload length    |
|I|S|S|S|  (4)  |A|     (7)     |             (16/64)           |
|N|V|V|V|       |S|             |   (if payload len==126/127)   |
| |1|2|3|       |K|             |                               |
+-+-+-+-+——-+-+————-+ – – – – – – – – – – – – – – – +
|     Extended payload length continued, if payload len == 127  |
+ – – – – – – – – – – – – – – – +——————————-+
|                               |Masking-key, if MASK set to 1  |
+——————————-+——————————-+
| Masking-key (continued)       |          Payload Data         |
+——————————– – – – – – – – – – – – – – – – +
:                     Payload Data continued …                :
+ – – – – – – – – – – – – – – – – – – – – – – – – – – – – – – – +
|                     Payload Data continued …                |
+—————————————————————+

对此背后两点,没有探究过WebSocket协议正式的同室也许清楚起来不够直观,但不影响对WebSocket的读书和动用。

1、数据帧格式概览

下边给出了WebSocket数据帧的集合格式。谙习TCP/IP协议的同室对这样的图应该不陌生。

  1. 从左到右,单位是比特。比如FINRSV1各占据1比特,opcode占据4比特。
  2. 情节包括了标识、操作代码、掩码、数据、数据长度等。(下一小节会展开)

0 1 2 3 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
+-+-+-+-+——-+-+————-+——————————-+
|F|R|R|R| opcode|M| Payload len | Extended payload length | |I|S|S|S|
(4) |A| (7) | (16/64) | |N|V|V|V| |S| | (if payload len==126/127) | |
|1|2|3| |K| | | +-+-+-+-+——-+-+————-+ – – – – – – – – – – –

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
  0                   1                   2                   3
  0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
+-+-+-+-+——-+-+————-+——————————-+
|F|R|R|R| opcode|M| Payload len |    Extended payload length    |
|I|S|S|S|  (4)  |A|     (7)     |             (16/64)           |
|N|V|V|V|       |S|             |   (if payload len==126/127)   |
| |1|2|3|       |K|             |                               |
+-+-+-+-+——-+-+————-+ – – – – – – – – – – – – – – – +
|     Extended payload length continued, if payload len == 127  |
+ – – – – – – – – – – – – – – – +——————————-+
|                               |Masking-key, if MASK set to 1  |
+——————————-+——————————-+
| Masking-key (continued)       |          Payload Data         |
+——————————– – – – – – – – – – – – – – – – +
:                     Payload Data continued …                :
+ – – – – – – – – – – – – – – – – – – – – – – – – – – – – – – – +
|                     Payload Data continued …                |
+—————————————————————+

6.3 Sec-WebSocket-Accept的计算

Sec-WebSocket-Accept遵照客户端请求首部的Sec-WebSocket-Key总结出来。

总计公式为:

1)将Sec-WebSocket-Key跟258EAFA5-E914-47DA-95CA-C5AB0DC85B11拼接;

2)通过SHA1盘算出摘要,并转成base64字符串。

伪代码如下:

1>toBase64( sha1( Sec-WebSocket-Key +
258EAFA5-E914-47DA-95CA-C5AB0DC85B11 )  )

表达上面前的回到结果:

const crypto = require(‘crypto’);

const magic = ‘258EAFA5-E914-47DA-95CA-C5AB0DC85B11’;

const secWebSocketKey = ‘w4v7O6xFTi36lq3RNcgctw==’;

let secWebSocketAccept = crypto.createHash(‘sha1’)

    .update(secWebSocketKey + magic)

    .digest(‘base64’);

console.log(secWebSocketAccept);

// Oy4NRAQ13jhfONC7bP8dTKb4PTU=

2、数据帧格式详解

本着前边的格式概览图,这里逐个字段进展讲解,如有不通晓之处,可参照协议正式,或留言交换。

FIN:1个比特。

如倘诺1,表示那是消息(message)的结尾一个分片(fragment),淌假如0,表示不是是音信(message)的最终一个分片(fragment)。

RSV1, RSV2, RSV3:各占1个比特。

相似景色下全为0。当客户端、服务端协商选取WebSocket扩充时,这六个标志位可以非0,且值的意思由扩张举办定义。固然出现非零的值,且并从未运用WebSocket扩大,连接出错。

Opcode: 4个比特。

操作代码,Opcode的值决定了应该怎么样剖析后续的数码载荷(data
payload)。假如操作代码是不认识的,那么接收端应该断开连接(fail the
connection)。可选的操作代码如下:

Mask: 1个比特。

意味着是否要对数据载荷举办掩码操作。从客户端向服务端发送数据时,需要对数据开展掩码操作;从服务端向客户端发送数据时,不需要对数码进行掩码操作。

倘使服务端接收到的多少尚未展开过掩码操作,服务端需要断开连接。

假如Mask是1,那么在Masking-key中会定义一个掩码键(masking
key),并用那个掩码键来对数码载荷举行反掩码。所有客户端发送到服务端的数据帧,Mask都是1。

掩码的算法、用途在下一小节讲解。

Payload
length
:数据载荷的尺寸,单位是字节。为7位,或7+16位,或1+64位。

假设数Payload length === x,如果

此外,如若payload length占用了七个字节的话,payload
length的二进制表明接纳网络序(big endian,首要的位在前)。

Masking-key:0或4字节(32位)

拥有从客户端传送到服务端的数据帧,数据载荷都进展了掩码操作,Mask为1,且引导了4字节的Masking-key。假诺Mask为0,则尚未Masking-key。

备考:载荷数据的长短,不包括mask key的长度。

Payload data:(x+y) 字节

载荷数据:包括了扩张数据、应用数据。其中,扩充数据x字节,应用数据y字节。

扩大数据:假设没有协商使用扩大的话,扩充数据数据为0字节。所有的扩充都必须注明扩充数据的长短,或者能够怎么计算出恢弘数据的长度。另外,扩大咋样使用必须在拉手阶段就合计好。假若扩展数据存在,那么载荷数据长度必须将扩张数据的长度包含在内。

应用数据:任意的利用数据,在扩大数据将来(假设存在扩大数据),占据了多少帧剩余的职位。载荷数据长度
减去 扩张数据长度,就赢得运用数据的长短。

2、需要上学怎么样东西

2、数据帧格式详解

本着前边的格式概览图,这里逐个字段举办讲解,如有不亮堂之处,可参看协议正式,或留言互换。

FIN:1个比特。

如果是1,表示这是音讯(message)的末梢一个分片(fragment),即使是0,表示不是是信息(message)的尾声一个分片(fragment)。

RSV1, RSV2, RSV3:各占1个比特。

诚如景色下全为0。当客户端、服务端协商接纳WebSocket扩展时,这五个标志位可以非0,且值的意思由扩充实行定义。假诺出现非零的值,且并从未利用WebSocket扩张,连接出错。

Opcode: 4个比特。

操作代码,Opcode的值决定了应有怎么剖析后续的数码载荷(data
payload)。虽然操作代码是不认得的,那么接收端应该断开连接(fail the
connection)。可选的操作代码如下:

Mask: 1个比特。

表示是否要对数据载荷举行掩码操作。从客户端向服务端发送数据时,需要对数据开展掩码操作;从服务端向客户端发送数据时,不需要对数码开展掩码操作。

要是服务端接收到的多寡没有举行过掩码操作,服务端需要断开连接。

倘使Mask是1,那么在Masking-key中会定义一个掩码键(masking
key),并用这些掩码键来对数据载荷举办反掩码。所有客户端发送到服务端的数据帧,Mask都是1。

掩码的算法、用途在下一小节讲解。

Payload
length
:数据载荷的尺寸,单位是字节。为7位,或7+16位,或1+64位。

假设数Payload length === x,如果

其余,如若payload length占用了四个字节的话,payload
length的二进制表明拔取网络序(big endian,首要的位在前)。

Masking-key:0或4字节(32位)

具有从客户端传送到服务端的数据帧,数据载荷都举办了掩码操作,Mask为1,且引导了4字节的Masking-key。假诺Mask为0,则尚未Masking-key。

备考:载荷数据的尺寸,不包括mask key的长度。

Payload data:(x+y) 字节

载荷数据:包括了扩展数据、应用数据。其中,扩大数据x字节,应用数据y字节。

扩张数据:如若没有协商使用扩展的话,扩充数据数据为0字节。所有的恢弘都必须注明扩充数据的长短,或者能够什么统计出恢弘数据的长度。此外,扩充怎么着使用必须在拉手阶段就研究好。假如扩展数据存在,那么载荷数据长度必须将扩张数据的尺寸包含在内。

使用数据:任意的应用数据,在壮大数据未来(假如存在增添数据),占据了多少帧剩余的职务。载荷数据长度
减去 扩展数据长度,就赢得利用数据的长短。

7、数据帧格式

客户端、服务端数据的置换,离不开数据帧格式的概念。因而,在其实讲解数据互换从前,我们先来看下WebSocket的数据帧格式。

WebSocket客户端、服务端通信的很小单位是帧(frame),由1个或四个帧组成一条完整的信息(message)。

详情如下:

出殡端:将音信切割成五个帧,并发送给服务端;

接收端:接收音讯帧,并将关乎的帧重新组装成完全的音讯。

本节的第一,就是上课数据帧的格式。详细定义可参考 RFC6455
5.2节 。

3、掩码算法

掩码键(Masking-key)是由客户端挑选出去的32位的随机数。掩码操作不会影响多少载荷的尺寸。掩码、反掩码操作都利用如下算法:

首先,假设:

算法描述为: original-octet-i 与 masking-key-octet-j 异或后,得到transformed-octet-i。

j = i MOD 4
transformed-octet-i = original-octet-i XOR masking-key-octet-j

对网络应用层协议的学习来说,最根本的累累就是连接建立过程数据交流教程。当然,数据的格式是逃不掉的,因为它直接决定了商事本身的力量。好的数据格式能让协议更高效、扩展性更好。

3、掩码算法

掩码键(Masking-key)是由客户端挑选出来的32位的随机数。掩码操作不会潜移默化多少载荷的长短。掩码、反掩码操作都使用如下算法:

首先,假设:

算法描述为: original-octet-i 与 masking-key-octet-j 异或后,拿到transformed-octet-i。

j = i MOD 4
transformed-octet-i = original-octet-i XOR masking-key-octet-j

7.1 数据帧格式概览

下面给出了WebSocket数据帧的联结格式,熟谙TCP/IP协议的同校对那样的图应该不陌生:

从左到右,单位是比特。比如FIN、RSV1各占据1比特,opcode占据4比特;

情节囊括了标识、操作代码、掩码、数据、数据长度等。(下一小节会展开)

金沙国际 1

六、数据传递

只要WebSocket客户端、服务端建立连接后,后续的操作都是基于数据帧的传递。

WebSocket根据opcode来区别操作的连串。比如0x8意味着断开连接,0x00x2表示数据交互。

下文重要围绕下边几点举行:

六、数据传递

比方WebSocket客户端、服务端建立连接后,后续的操作都是按照数据帧的传递。

WebSocket根据opcode来区分操作的门类。比如0x8意味着断开连接,0x00x2表示数据交互。

7.2 数据帧格式详解

本着前面的格式概览图,这里逐个字段展开讲解,如有不领会之处,可参看协议正式,或阅读《WebSocket详解(三):深远WebSocket通信协议细节》。

FIN:1个比特

比方是1,表示这是音信(message)的末梢一个分片(fragment),假使是0,表示不是是音信(message)的结尾一个分片(fragment)。

RSV1, RSV2, RSV3:各占1个比特

一般景观下全为0。当客户端、服务端协商采纳WebSocket扩大时,这两个标志位能够非0,且值的意思由扩充举行定义。假如出现非零的值,且并没有利用WebSocket扩展,连接出错。

Opcode: 4个比特

操作代码,Opcode的值决定了应有什么剖析后续的数码载荷(data
payload)。假诺操作代码是不认识的,那么接收端应该断开连接(fail the
connection)。可选的操作代码如下:

%x0:表示一个延续帧。当Opcode为0时,表示此次数据传输拔取了数量分片,当前接受的数据帧为内部一个数目分片;

%x1:表示这是一个文本帧(frame);

%x2:表示这是一个二进制帧(frame);

%x3-7:保留的操作代码,用于后续定义的非控制帧;

%x8:表示连接断开;

%x8:表示这是一个ping操作;

%xA:表示这是一个pong操作;

%xB-F:保留的操作代码,用于后续定义的控制帧。

Mask: 1个比特

代表是否要对数码载荷举办掩码操作。从客户端向服务端发送数据时,需要对数据开展掩码操作;从服务端向客户端发送数据时,不需要对数码开展掩码操作。

假定服务端接收到的数量没有举行过掩码操作,服务端需要断开连接。

比方Mask是1,那么在Masking-key中会定义一个掩码键(masking
key),并用那多少个掩码键来对数据载荷举行反掩码。所有客户端发送到服务端的数据帧,Mask都是1。

掩码的算法、用途在下一小节讲解。

Payload
length:
数据载荷的尺寸,单位是字节。为7位,或7+16位,或1+64位

假设数Payload length === x,如果:

x为0~126:数据的尺寸为x字节;

x为126:后续2个字节代表一个16位的无符号整数,该无符号整数的值为多少的长短;

x为127:后续8个字节代表一个64位的无符号整数(最高位为0),该无符号整数的值为数量的长度。

其它,假若payload length占用了多个字节的话,payload
length的二进制表达采用网络序(big endian,重要的位在前)。

Masking-key:0或4字节(32位)

持有从客户端传送到服务端的数据帧,数据载荷都举办了掩码操作,Mask为1,且带领了4字节的Masking-key。假诺Mask为0,则从未Masking-key。

备注:载荷数据的长短,不包括mask key的长短。

Payload data:(x+y) 字节

载荷数据:

概括了扩展数据、应用数据。其中,扩充数据x字节,应用数据y字节;

扩充数据:

设若没有协议使用扩大的话,增加数据数据为0字节。所有的扩大都无法不阐明扩张数据的尺寸,或者可以怎么统计出恢弘数据的长短。另外,扩大如何行使必须在握手阶段就协商好。要是扩张数据存在,那么载荷数据长度必须将扩张数据的长短包含在内;

使用数据:

随便的采纳数据,在增加数据未来(假设存在扩充数据),占据了数额帧剩余的地点。载荷数据长度
减去 扩张数据长度,就拿走利用数据的长短。

1、数据分片

WebSocket的每条信息可能被切分成三个数据帧。当WebSocket的接收方收到一个多少帧时,会依照FIN的值来判断,是否业已接收新闻的末段一个数据帧。

FIN=1表示目前数据帧为新闻的结尾一个数据帧,此时接收方已经收到完整的消息,可以对音讯举办拍卖。FIN=0,则接收方还索要连续监听接收另外的数据帧。

此外,opcode在数据互换的现象下,表示的是数码的系列。0x01表示文本,0x02代表二进制。而0x00正如特别,表示延续帧(continuation
frame),顾名思义,就是完好信息对应的数据帧还没接过完。

怎么样建立连接

1、数据分片

WebSocket的每条音讯可能被切分成两个数据帧。当WebSocket的接收方收到一个数据帧时,会基于FIN的值来判定,是否早已吸收消息的末尾一个数据帧。

FIN=1表示近来数据帧为音信的尾声一个数据帧,此时接收方已经接受完整的音讯,可以对消息举行处理。FIN=0,则接收方还索要持续监听接收其它的数据帧。

此外,opcode在数据交流的场所下,表示的是数码的档次。0x01表示文本,0x02代表二进制。而0x00金沙国际 ,正如非凡,表示延续帧(continuation
frame),顾名思义,就是共同体信息对应的数据帧还没接过完。

7.3 掩码算法

掩码键(Masking-key)是由客户端挑选出去的32位的随机数。掩码操作不会影响多少载荷的长短。掩码、反掩码操作都使用如下算法。

首先,假设:

original-octet-i:为原本数据的第i字节。

transformed-octet-i:为转移后的数码的第i字节。

j:为i mod 4的结果。

masking-key-octet-j:为mask key第j字节。

算法描述为: 

original-octet-i 与 masking-key-octet-j 异或后,得到
transformed-octet-i。

即:

j = i MOD 4

transformed-octet-i = original-octet-i XOR masking-key-octet-j

2、数据分片例子

一向看例子更形象些。下边例子来自MDN,可以很好地示范数据的分片。客户端向服务端三遍发送信息,服务端收到音信后回应客户端,这里最紧要看客户端往服务端发送的信息。

率先条音信

FIN=1,
表示是眼下信息的末梢一个数据帧。服务端收到当前数据帧后,可以拍卖信息。opcode=0x1,表示客户端发送的是文本类型。

其次条信息

  1. FIN=0,opcode=0x1,表示发送的是文本类型,且音信还没发送完成,还有后续的数据帧。
  2. FIN=0,opcode=0x0,表示音信还没发送完成,还有继续的数据帧,当前的数据帧需要接在上一条数据帧之后。
  3. FIN=1,opcode=0x0,表示信息已经发送完成,没有继承的数据帧,当前的数据帧需要接在上一条数据帧之后。服务端可以将涉及的数据帧组装成完全的信息。

Client: FIN=1, opcode=0x1, msg=”hello” Server: (process complete message
immediately) Hi. Client: FIN=0, opcode=0x1, msg=”and a” Server:
(listening, new message containing text started) Client: FIN=0,
opcode=0x0, msg=”happy new” Server: (listening, payload concatenated to
previous message) Client: FIN=1, opcode=0x0, msg=”year!” Server:
(process complete message) Happy new year to you too!

1
2
3
4
5
6
7
8
Client: FIN=1, opcode=0x1, msg="hello"
Server: (process complete message immediately) Hi.
Client: FIN=0, opcode=0x1, msg="and a"
Server: (listening, new message containing text started)
Client: FIN=0, opcode=0x0, msg="happy new"
Server: (listening, payload concatenated to previous message)
Client: FIN=1, opcode=0x0, msg="year!"
Server: (process complete message) Happy new year to you too!

如何互换数据

2、数据分片例子

一向看例子更形象些。下面例子来自MDN,可以很好地示范数据的分片。客户端向服务端五遍发送音讯,服务端收到信息后回应客户端,这里首要看客户端往服务端发送的音信。

第一条音讯

FIN=1,
表示是眼前信息的末梢一个数据帧。服务端收到当前数据帧后,可以拍卖音讯。opcode=0x1,表示客户端发送的是文本类型。

其次条消息

  1. FIN=0,opcode=0x1,表示发送的是文本类型,且音信还没发送完成,还有后续的数据帧。
  2. FIN=0,opcode=0x0,表示消息还没发送完成,还有继续的数据帧,当前的数据帧需要接在上一条数据帧之后。
  3. FIN=1,opcode=0x0,表示音信一度发送完成,没有持续的数据帧,当前的数据帧需要接在上一条数据帧之后。服务端可以将涉嫌的数据帧组装成完全的信息。

Client: FIN=1, opcode=0x1, msg=”hello” Server: (process complete message
immediately) Hi. Client: FIN=0, opcode=0x1, msg=”and a” Server:
(listening, new message containing text started) Client: FIN=0,
opcode=0x0, msg=”happy new” Server: (listening, payload concatenated to
previous message) Client: FIN=1, opcode=0x0, msg=”year!” Server:
(process complete message) Happy new year to you too!

1
2
3
4
5
6
7
8
Client: FIN=1, opcode=0x1, msg="hello"
Server: (process complete message immediately) Hi.
Client: FIN=0, opcode=0x1, msg="and a"
Server: (listening, new message containing text started)
Client: FIN=0, opcode=0x0, msg="happy new"
Server: (listening, payload concatenated to previous message)
Client: FIN=1, opcode=0x0, msg="year!"
Server: (process complete message) Happy new year to you too!

8、数据传递

一经WebSocket客户端、服务端建立连接后,后续的操作都是按照数据帧的传递。WebSocket依据opcode来区别操作的档次。比如0x8意味断开连接,0x0-0x2意味数据交互。

七、连接保持+心跳

WebSocket为了维持客户端、服务端的实时双向通信,需要保证客户端、服务端之间的TCP通道保持连续没有断开。然而,对于长日子未曾多少往来的连日,倘使依旧长日子维系着,可能会浪费包括的接连资源。

但不清除有些场景,客户端、服务端即使长日子从没数量往来,但仍需要保障连续。这些时候,可以选用心跳来实现。

ping、pong的操作,对应的是WebSocket的五个控制帧,opcode分别是0x90xA

比喻,WebSocket服务端向客户端发送ping,只需要如下代码(拔取ws模块)

ws.ping(”, false, true);

1
ws.ping(”, false, true);

数码帧格式

七、连接保持+心跳

WebSocket为了保持客户端、服务端的实时双向通信,需要保证客户端、服务端之间的TCP通道保持连续没有断开。但是,对于长日子未曾多少往来的连年,假如仍旧长日子维系着,可能会浪费包括的接连资源。

但不清除有些场景,客户端、服务端即便长日子尚无数据往来,但仍需要保持连续。这多少个时候,可以接纳心跳来实现。

ping、pong的操作,对应的是WebSocket的多个控制帧,opcode分别是0x90xA

比方,WebSocket服务端向客户端发送ping,只需要如下代码(接纳ws模块)

ws.ping(”, false, true);

1
ws.ping(”, false, true);

8.1 数据分片

WebSocket的每条信息可能被切分成六个数据帧。当WebSocket的接收方收到一个数目帧时,会基于FIN的值来判断,是否曾经收取音讯的终极一个数据帧。

FIN=1表示目前数据帧为新闻的最终一个数据帧,此时接收方已经吸纳完整的音讯,可以对音信举行拍卖。FIN=0,则接收方还亟需连续监听接收其它的数据帧。

除此以外,opcode在数据交流的景色下,表示的是数量的体系。0x01表示文本,0x02象征二进制。而0x00相比较独特,表示延续帧(continuation
frame),顾名思义,就是全部信息对应的数据帧还没接到完。

八、Sec-WebSocket-Key/Accept的作用

后面提到了,Sec-WebSocket-Key/Sec-WebSocket-Accept在显要功效在于提供基础的警备,收缩恶意连接、意外连续。

效果大致归结如下:

  1. 制止服务端收到非法的websocket连接(比如http客户端不小心请求连接websocket服务,此时服务端可以一向拒绝连接)
  2. 管教服务端领悟websocket连接。因为ws握手阶段采取的是http协议,因而恐怕ws连接是被一个http服务器处理并回到的,此时客户端可以因此Sec-WebSocket-Key来保管服务端认识ws协议。(并非百分百保险,比如总是存在那些无聊的http服务器,光处理Sec-WebSocket-Key,但并没有实现ws协议。。。)
  3. 用浏览器里提倡ajax请求,设置header时,Sec-WebSocket-Key以及另外有关的header是被取缔的。这样可以避免客户端发送ajax请求时,意外请求协议升级(websocket
    upgrade)
  4. 可以制止反向代理(不了然ws协议)重回错误的数额。比如反向代理前后收到一回ws连接的提拔请求,反向代理把第五回呼吁的归来给cache住,然后第二次呼吁到来时直接把cache住的伸手给重临(无意义的归来)。
  5. Sec-WebSocket-Key重要目的并不是承保数据的安全性,因为Sec-WebSocket-Key、Sec-WebSocket-Accept的更换总括公式是公然的,而且相当简单,最要紧的效用是防范一些广大的意想不到意况(非故意的)。

强调:Sec-WebSocket-Key/Sec-WebSocket-Accept
的折算,只好带来基本的保障,但老是是否安全、数据是否平安、客户端/服务端是否合法的
ws客户端、ws服务端,其实并从未实际性的保险。

如何保持连接

八、Sec-WebSocket-Key/Accept的作用

前方提到了,Sec-WebSocket-Key/Sec-WebSocket-Accept在紧要功效在于提供基础的预防,缩小恶意连接、意外连续。

效率大致归结如下:

  1. 制止服务端收到非法的websocket连接(比如http客户端不小心请求连接websocket服务,此时服务端可以直接拒绝连接)
  2. 担保服务端了解websocket连接。因为ws握手阶段接纳的是http协议,因而可能ws连接是被一个http服务器处理并赶回的,此时客户端可以透过Sec-WebSocket-Key来担保服务端认识ws协议。(并非百分百保险,比如总是存在这些无聊的http服务器,光处理Sec-WebSocket-Key,但并不曾落实ws协议。。。)
  3. 用浏览器里提倡ajax请求,设置header时,Sec-WebSocket-Key以及此外有关的header是被禁止的。这样可以制止客户端发送ajax请求时,意外请求协议升级(websocket
    upgrade)
  4. 可以避免反向代理(不掌握ws协议)再次回到错误的数据。比如反向代理前后收到一遍ws连接的擢升请求,反向代理把第一次呼吁的回来给cache住,然后第二次呼吁到来时一贯把cache住的呼吁给重临(无意义的回来)。
  5. Sec-WebSocket-Key重要目标并不是确保数量的安全性,因为Sec-WebSocket-Key、Sec-WebSocket-Accept的转移总结公式是公然的,而且分外简单,最重点的意义是提防一些广阔的不测情况(非故意的)。

强调:Sec-WebSocket-Key/Sec-WebSocket-Accept
的折算,只好带来基本的维系,但连续是否平安、数据是否安全、客户端/服务端是否合法的
ws客户端、ws服务端,其实并不曾实际性的管教。

8.2 数据分片例子

直白看例子更形象些。下边例子来自MDN,可以很好地示范数据的分片。客户端向服务端五遍发送新闻,服务端收到消息后回应客户端,这里最紧要看客户端往服务端发送的信息。

率先条信息:

FIN=1,
表示是现阶段信息的最后一个数据帧。服务端收到当前数据帧后,可以拍卖消息。opcode=0x1,表示客户端发送的是文本类型。

其次条音讯:

1)FIN=0,opcode=0x1,表示发送的是文件类型,且音信还没发送完成,还有后续的数据帧;

2)FIN=0,opcode=0x0,表示音讯还没发送完成,还有后续的数据帧,当前的数据帧需要接在上一条数据帧之后;

3)FIN=1,opcode=0x0,表示音信一度发送完成,没有继承的数据帧,当前的数据帧需要接在上一条数据帧之后。服务端可以将涉及的数据帧组装成完全的新闻。

Client: FIN=1, opcode=0x1, msg=”hello”

Server: (process complete message immediately) Hi.

Client: FIN=0, opcode=0x1, msg=”and a”

Server: (listening, new message containing text started)

Client: FIN=0, opcode=0x0, msg=”happy new”

Server: (listening, payload concatenated to previous message)

Client: FIN=1, opcode=0x0, msg=”year!”

Server: (process complete message) Happy new year to you too!

九、数据掩码的功用

WebSocket协和中,数据掩码的法力是增强协商的安全性。但数目掩码并不是为了维护数量本身,因为算法本身是公开的,运算也不复杂。除了加密大道本身,似乎从未太多立竿见影的维护通信安全的方法。

那么为啥还要引入掩码总计呢,除了扩张统计机器的运算量外似乎并不曾太多的进项(这也是成千上万同室疑惑的点)。

答案还是五个字:安全。但并不是为着以防数据泄密,而是为了以防万一早期版本的协议中存在的代办缓存污染攻击(proxy
cache poisoning attacks)等问题。

三、入门例子

九、数据掩码的职能

WebSocket商讨中,数据掩码的功力是加强协商的安全性。但数目掩码并不是为了掩护数量我,因为算法本身是当着的,运算也不复杂。除了加密通道本身,似乎没有太多立竿见影的爱戴通信安全的主意。

这就是说为啥还要引入掩码统计呢,除了扩大总计机器的运算量外似乎并没有太多的获益(这也是很多同班疑惑的点)。

答案仍旧多个字:安全。但并不是为了以防万一数据泄密,而是为了制止早期版本的商议中留存的代理缓存污染攻击(proxy
cache poisoning attacks)等题材。

9、连接保持+心跳

WebSocket为了保障客户端、服务端的实时双向通信,需要确保客户端、服务端之间的TCP通道保持连续没有断开。但是,对于长日子尚未数量往来的接连,如果依旧长日子保持着,可能会浪费包括的连接资源。

但不免除有些场景,客户端、服务端固然长日子尚未数量往来,但仍亟需保持连续。

其一时候,可以采取心跳来实现:

发送方->接收方:ping

接收方->发送方:pong

ping、pong的操作,对应的是WebSocket的五个控制帧,opcode分别是0x9、0xA。

举例来说:WebSocket服务端向客户端发送ping,只需要如下代码(选用ws模块)

ws.ping(”, false, true);

1、代理缓存污染攻击

上面摘自二〇一〇年有关安全的一段讲话。其中提到了代理服务器在磋商落实上的通病或者引致的平安问题。相撞出处。

“We show, empirically, that the current version of the WebSocket
consent mechanism is vulnerable to proxy cache poisoning attacks. Even
though the WebSocket handshake is based on HTTP, which should be
understood by most network intermediaries, the handshake uses the
esoteric “Upgrade” mechanism of HTTP [5]. In our experiment, we find
that many proxies do not implement the Upgrade mechanism properly,
which causes the handshake to succeed even though subsequent traffic
over the socket will be misinterpreted by the proxy.”[TALKING]
Huang, L-S., Chen, E., Barth, A., Rescorla, E., and C.

Jackson, “Talking to Yourself for Fun and Profit”, 2010,

1
          Jackson, "Talking to Yourself for Fun and Profit", 2010,

在标准描述攻击步骤此前,咱们假设有如下出席者:

攻击步骤一:

  1. 攻击者浏览器 向 狰狞服务器
    发起WebSocket连接。遵照前文,首先是一个商事升级请求。
  2. 协商升级请求 实际到达 代理服务器
  3. 代理服务器 将协商升级请求转发到 狰狞服务器
  4. 狰狞服务器 同意连接,代理服务器 将响应转发给 攻击者

由于 upgrade 的实现上有缺陷,代理服务器
以为从前转发的是通常的HTTP信息。由此,当情商服务器
同意连接,代理服务器 以为本次对话已经完结。

攻击步骤二:

  1. 攻击者 在前头建立的连年上,通过WebSocket的接口向 狰狞服务器
    发送数据,且数据是周到布局的HTTP格式的公文。其中富含了 公正无私资源
    的地方,以及一个假冒的host(指向公平服务器)。(见前边报文)
  2. 呼吁到达 代理服务器 。尽管复用了事先的TCP连接,但 代理服务器
    以为是新的HTTP请求。
  3. 代理服务器狰狞服务器 请求 狰狞资源
  4. 狰狞服务器 返回 狰狞资源代理服务器 缓存住
    狰狞资源(url是对的,但host是 不分畛域服务器 的地址)。

到此处,受害者可以出台了:

  1. 受害者 通过 代理服务器 访问 公平服务器公允资源
  2. 代理服务器 检查该资源的url、host,发现当地有一份缓存(伪造的)。
  3. 代理服务器狰狞资源 返回给 受害者
  4. 受害者 卒。

附:前边提到的仔细社团的“HTTP请求报文”。

Client → Server: POST /path/of/attackers/choice HTTP/1.1 Host:
host-of-attackers-choice.com Sec-WebSocket-Key: Server → Client:
HTTP/1.1 200 OK Sec-WebSocket-Accept:

1
2
3
4
5
Client → Server:
POST /path/of/attackers/choice HTTP/1.1 Host: host-of-attackers-choice.com Sec-WebSocket-Key:
Server → Client:
HTTP/1.1 200 OK
Sec-WebSocket-Accept:

在规范介绍协议细节前,先来看一个简易的事例,有个直观感受。例子包括了WebSocket服务端、WebSocket客户端(网页端)。完整代码能够在
这里 找到。

1、代理缓存污染攻击

下边摘自二零一零年有关安全的一段讲话。其中提到了代理服务器在情商落实上的瑕疵或者导致的安全题材。相撞出处。

“We show, empirically, that the current version of the WebSocket
consent mechanism is vulnerable to proxy cache poisoning attacks. Even
though the WebSocket handshake is based on HTTP, which should be
understood by most network intermediaries, the handshake uses the
esoteric “Upgrade” mechanism of HTTP [5]. In our experiment, we find
that many proxies do not implement the Upgrade mechanism properly,
which causes the handshake to succeed even though subsequent traffic
over the socket will be misinterpreted by the proxy.”[TALKING]
Huang, L-S., Chen, E., Barth, A., Rescorla, E., and C.

Jackson, “Talking to Yourself for Fun and Profit”, 2010,

1
          Jackson, "Talking to Yourself for Fun and Profit", 2010,

在正式描述攻击步骤在此之前,大家假设有如下插手者:

攻击步骤一:

  1. 攻击者浏览器 向 狰狞服务器
    发起WebSocket连接。依据前文,首先是一个协商升级请求。
  2. 磋商升级请求 实际到达 代理服务器
  3. 代理服务器 将合计升级请求转发到 狰狞服务器
  4. 狰狞服务器 同意连接,代理服务器 将响应转发给 攻击者

出于 upgrade 的贯彻上有缺陷,代理服务器
以为在此以前转发的是常见的HTTP音讯。因此,当研究服务器
同意连接,代理服务器 以为这一次对话已经终止。

攻击步骤二:

  1. 攻击者 在前头建立的连日上,通过WebSocket的接口向 狰狞服务器
    发送数据,且数据是系数协会的HTTP格式的文书。其中饱含了 不分畛域资源
    的地方,以及一个冒充的host(指向正义服务器)。(见后边报文)
  2. 请求到达 代理服务器 。虽然复用了从前的TCP连接,但 代理服务器
    以为是新的HTTP请求。
  3. 代理服务器狰狞服务器 请求 狰狞资源
  4. 狰狞服务器 返回 狰狞资源代理服务器 缓存住
    狰狞资源(url是对的,但host是 不分轩轾服务器 的地址)。

到这边,受害者可以出台了:

  1. 受害者 通过 代理服务器 访问 正义服务器公平资源
  2. 代理服务器 检查该资源的url、host,发现当地有一份缓存(伪造的)。
  3. 代理服务器狰狞资源 返回给 受害者
  4. 受害者 卒。

附:后边提到的绵密社团的“HTTP请求报文”。

Client → Server: POST /path/of/attackers/choice HTTP/1.1 Host:
host-of-attackers-choice.com Sec-WebSocket-Key: Server → Client:
HTTP/1.1 200 OK Sec-WebSocket-Accept:

1
2
3
4
5
Client → Server:
POST /path/of/attackers/choice HTTP/1.1 Host: host-of-attackers-choice.com Sec-WebSocket-Key:
Server → Client:
HTTP/1.1 200 OK
Sec-WebSocket-Accept:

10、Sec-WebSocket-Key/Accept的作用

前方提到了,Sec-WebSocket-Key/Sec-WebSocket-Accept在关键效率在于提供基础的警备,减弱恶意连接、意外连续。

效益大致归结如下:

1)制止服务端收到非法的websocket连接(比如http客户端不小心请求连接websocket服务,此时服务端能够一向拒绝连接);

2)确保服务端领悟websocket连接。因为ws握手阶段拔取的是http协议,因而恐怕ws连接是被一个http服务器处理并回到的,此时客户端可以因而Sec-WebSocket-Key来担保服务端认识ws协议。(并非百分百保险,比如总是存在那些无聊的http服务器,光处理Sec-WebSocket-Key,但并不曾兑现ws协议。。。);

3)用浏览器里提倡ajax请求,设置header时,Sec-WebSocket-Key以及其他相关的header是被明令禁止的。这样可以避免客户端发送ajax请求时,意外请求协议升级(websocket
upgrade);

4)可以防范反向代理(不晓得ws协议)重临错误的数目。比如反向代理前后收到三回ws连接的晋级请求,反向代理把第一次呼吁的回来给cache住,然后第二次呼吁到来时一直把cache住的乞求给再次回到(无意义的归来);

5)Sec-WebSocket-Key紧要目的并不是确保数量的安全性,因为Sec-WebSocket-Key、Sec-WebSocket-Accept的转移总括公式是公然的,而且相当简单,最重点的效益是提防一些大面积的出人意料情形(非故意的)。

强调:Sec-WebSocket-Key/Sec-WebSocket-Accept
的折算,只好带来基本的保障,但一连是否平安、数据是否安全、客户端/服务端是否合法的
ws客户端、ws服务端,其实并不曾实际性的管教。

2、当前缓解方案

早期的提案是对数码举办加密处理。基于安全、功效的考虑,最后采纳了折中的方案:对数码载荷举行掩码处理。

急需专注的是,这里只是限制了浏览器对数据载荷举办掩码处理,可是坏人完全可以兑现自己的WebSocket客户端、服务端,不按规则来,攻击能够照常举办。

可是对浏览器加上这么些界定后,可以大大扩展攻击的难度,以及攻击的熏陶范围。即便没有这么些界定,只需要在网上放个钓鱼网站骗人去访问,一下子就足以在长期内开展大范围的口诛笔伐。

这里服务端用了 ws这多少个库。相相比我们熟习的 socket.io,
ws实现更轻量,更切合学习的目的。

2、当前缓解方案

最初的提案是对数码举行加密处理。基于安全、效能的考虑,最后采取了折中的方案:对数码载荷进行掩码处理。

亟待专注的是,这里只是限量了浏览器对数码载荷举办掩码处理,但是坏人完全可以兑现协调的WebSocket客户端、服务端,不按规则来,攻击可以照常举办。

唯独对浏览器加上这些限制后,可以大大扩展攻击的难度,以及攻击的熏陶范围。假设没有这么些界定,只需要在网上放个钓鱼网站骗人去拜谒,一下子就足以在长时间内开展大范围的口诛笔伐。

11、数据掩码的法力

WebSocket共商中,数据掩码的效用是提高协商的安全性。但数据掩码并不是为着珍重数量本身,因为算法本身是理解的,运算也不复杂。除了加密通道本身,似乎并未太多立竿见影的护卫通信安全的措施。

这就是说为何还要引入掩码总括呢,除了增添总计机器的运算量外似乎并不曾太多的入账(这也是成千上万同学疑惑的点)。

答案如故五个字:安全。但并不是为着避免数据泄密,而是为了防范早期版本的协议中存在的代理缓存污染攻击(proxy
cache poisoning attacks)等问题。

十、写在背后

WebSocket可写的东西还挺多,比如WebSocket扩充。客户端、服务端之间是哪些协商、使用扩大的。WebSocket扩张可以给协议本身扩展很多能力和设想空间,比如数据的削减、加密,以及多路复用等。

字数所限,那里先不开展,感兴趣的同班可以留言互换。随笔如有错漏,敬请指出。

1、服务端

十、写在后头

WebSocket可写的事物还挺多,比如WebSocket增加。客户端、服务端之间是何等协商、使用增添的。WebSocket扩大可以给协议本身增添很多能力和想象空间,比如数据的缩减、加密,以及多路复用等。

字数所限,这里先不举行,感兴趣的同桌可以留言互换。作品如有错漏,敬请指出。

11.1 代理缓存污染攻击

下面摘自二零一零年关于安全的一段讲话。其中提到了代理服务器在商事落实上的老毛病或者导致的平安问题(详情点此查看出处):

“We show, empirically, that the current version of the WebSocket
consent mechanism is vulnerable to proxy cache poisoning attacks. Even
though the WebSocket handshake is based on HTTP, which should be
understood by most network intermediaries, the handshake uses the
esoteric “Upgrade” mechanism of HTTP. In our experiment, we find that
many proxies do not implement the Upgrade mechanism properly, which
causes the handshake to succeed even though subsequent traffic over
the socket will be misinterpreted by the proxy.”

(TALKING) Huang, L-S., Chen, E., Barth, A., Rescorla, E., and C.

Jackson, “Talking to Yourself for Fun and Profit”, 2010

在正式描述攻击步骤在此之前,大家假如有如下参加者:

攻击者、攻击者自己说了算的服务器(简称“邪恶服务器”)、攻击者伪造的资源(简称“邪恶资源”);

事主、受害者想要访问的资源(简称“正义资源”);

被害人实际想要访问的服务器(简称“正义服务器”);

高中级代理服务器。

攻击步骤一:

1)攻击者浏览器 向 邪恶服务器
发起WebSocket连接。依照前文,首先是一个钻探升级请求;

2)协议升级请求 实际到达 代理服务器;

3)代理服务器 将合计升级请求转发到 邪恶服务器;

4)邪恶服务器 同意连接,代理服务器 将响应转发给 攻击者。

出于 upgrade 的贯彻上有缺陷,代理服务器
以为前面转发的是常常的HTTP音信。因而,当协议服务器 同意连接,代理服务器
以为本次对话已经完结。

攻击步骤二:

1)攻击者 在头里建立的接连上,通过WebSocket的接口向 邪恶服务器
发送数据,且数量是周全布局的HTTP格式的文书。其中带有了 正义资源
的地点,以及一个冒牌的host(指向正义服务器)。(见后边报文);

2)请求到达 代理服务器 。固然复用了事先的TCP连接,但 代理服务器
以为是新的HTTP请求;

3)代理服务器 向 邪恶服务器 请求 邪恶资源;

4)邪恶服务器 再次来到 邪恶资源。代理服务器 缓存住
邪恶资源(url是对的,但host是 正义服务器 的地点)。

到此处,受害者能够出台了:

1)受害者 通过 代理服务器 访问 正义服务器 的 正义资源;

2)代理服务器 检查该资源的url、host,发现当地有一份缓存(伪造的);

3)代理服务器 将 邪恶资源 重回给 受害者;

4)受害者 卒。

附:后面提到的精雕细刻社团的“HTTP请求报文”:

Client → Server:

POST /path/of/attackers/choiceHTTP/1.1 Host:
host-of-attackers-choice.com Sec-WebSocket-Key:

Server → Client:

HTTP/1.1 200 OK

Sec-WebSocket-Accept:

十一、相关链接

RFC6455:websocket规范
https://tools.ietf.org/html/r…

业内:数据帧掩码细节
https://tools.ietf.org/html/r…

正式:数据帧格式
https://tools.ietf.org/html/r…

server-example
https://github.com/websockets…

编写websocket服务器
https://developer.mozilla.org…

对网络基础设备的攻击(数据掩码操作所要预防的政工)
https://tools.ietf.org/html/r…

Talking to Yourself for Fun and Profit(含有攻击描述)
http://w2spconf.com/2011/pape…

What is Sec-WebSocket-Key for?
https://stackoverflow.com/que…

10.3. Attacks On Infrastructure (Masking)
https://tools.ietf.org/html/r…

Talking to Yourself for Fun and Profit
http://w2spconf.com/2011/pape…

Why are WebSockets masked?
https://stackoverflow.com/que…

How does websocket frame masking protect against cache poisoning?
https://security.stackexchang…

What is the mask in a WebSocket frame?
https://stackoverflow.com/que…

1 赞 3 收藏 1
评论

金沙国际 2

代码如下,监听8080端口。当有新的连日请求到达时,打印日志,同时向客户端发送音讯。当接到到来自客户端的音讯时,同样打印日志。

十一、相关链接

RFC6455:websocket规范
https://tools.ietf.org/html/r…

规范:数据帧掩码细节
https://tools.ietf.org/html/r…

标准:数据帧格式
https://tools.ietf.org/html/r…

server-example
https://github.com/websockets…

编写websocket服务器
https://developer.mozilla.org…

对网络基础设备的攻击(数据掩码操作所要预防的工作)
https://tools.ietf.org/html/r…

Talking to Yourself for Fun and Profit(含有攻击描述)
http://w2spconf.com/2011/pape…

What is Sec-WebSocket-Key for?
https://stackoverflow.com/que…

10.3. Attacks On Infrastructure (Masking)
https://tools.ietf.org/html/r…

Talking to Yourself for Fun and Profit
http://w2spconf.com/2011/pape…

Why are WebSockets masked?
https://stackoverflow.com/que…

How does websocket frame masking protect against cache poisoning?
https://security.stackexchang…

What is the mask in a WebSocket frame?
https://stackoverflow.com/que…

1 赞 1 收藏 1
评论

11.2 当前解决方案

初期的提案是对数码开展加密处理。基于安全、效率的设想,最后采用了折中的方案:对数据载荷举行掩码处理。

亟需小心的是,这里只是限量了浏览器对数据载荷进行掩码处理,可是坏人完全可以兑现协调的WebSocket客户端、服务端,不按规则来,攻击可以照常举行。

唯独对浏览器加上这一个限制后,可以大大扩大攻击的难度,以及攻击的震慑范围。倘使没有那多少个限制,只需要在网上放个钓鱼网站骗人去做客,一下子就可以在短期内举行大范围的攻击。

var app = require(‘express’)();

12、写在背后

WebSocket可写的事物还挺多,比如WebSocket扩充。客户端、服务端之间是怎么协商、使用扩充的。WebSocket扩展可以给协议本身扩大很多力量和设想空间,比如数据的收缩、加密,以及多路复用等。

篇幅所限,这里先不举办,感兴趣的同桌可以留言互换。著作如有错漏,敬请提议。

var server = require(‘http’).Server(app);

13、相关链接

[1]
RFC6455:websocket规范 https://tools.ietf.org/html/rfc6455

[2]
规范:数据帧掩码细节 https://tools.ietf.org/html/rfc6455\#section-5.3

[3]
规范:数据帧格式 https://tools.ietf.org/html/rfc6455\#section-5.1

[4]
server-example:https://github.com/websockets/ws\#server-example

[5]
编写websocket服务器 https://developer.mozilla.org/en-US/docs/Web/API/WebSockets\_API/Writing\_WebSocket\_servers

[6]
对网络基础设备的口诛笔伐(数据掩码操作所要预防的事体)https://tools.ietf.org/html/rfc6455\#section-10.3

[7] Talking to Yourself for Fun and
Profit(含有攻击描述)http://w2spconf.com/2011/papers/websocket.pdf

[8] What is Sec-WebSocket-Key
for? https://stackoverflow.com/questions/18265128/what-is-sec-websocket-key-for

[9] 10.3. Attacks On Infrastructure
(Masking) https://tools.ietf.org/html/rfc6455\#section-10.3

[10] Talking to Yourself for Fun and
Profit http://w2spconf.com/2011/papers/websocket.pdf

[11] Why are WebSockets
masked? https://stackoverflow.com/questions/33250207/why-are-websockets-masked

[12] How does websocket frame masking protect against cache
poisoning? https://security.stackexchange.com/questions/36930/how-does-websocket-frame-masking-protect-against-cache-poisoning

[13] What is the mask in a WebSocket
frame? https://stackoverflow.com/questions/14174184/what-is-the-mask-in-a-websocket-frame

var WebSocket = require(‘ws’);

附录:更多Web端即时通讯资料

[1] 有关WEB端即时通讯开发:

《新手入门贴:史上最全Web端即时通讯技术原理详解》

《Web端即时通讯技术盘点:短轮询、Comet、Websocket、SSE》

《SSE技术详解:一种崭新的HTML5服务器推送事件技术》

《Comet技术详解:基于HTTP长连接的Web端实时通信技术》

《新手急忙入门:WebSocket简明教程》

《WebSocket详解(一):起头认识WebSocket技术》

《WebSocket详解(二):技术原理、代码演示和行使案例》

《WebSocket详解(三):深刻WebSocket通信协议细节》

《WebSocket详解(四):刨根问底HTTP与WebSocket的关系(上篇)》

《WebSocket详解(五):刨根问底HTTP与WebSocket的涉及(下篇)》

《WebSocket详解(六):刨根问底WebSocket与Socket的关系》

《socket.io实现音信推送的少数进行及思路》

《LinkedIn的Web端即时通讯实践:实现单机几十万条长连接》

《Web端即时通讯技术的前进与WebSocket、Socket.io的技术实施》

《Web端即时通讯安全:跨站点WebSocket要挟漏洞详解(含示例代码)》

《开源框架Pomelo实践:搭建Web端高性能分布式IM聊天服务器》

《采取WebSocket和SSE技术实现Web端信息推送》

《详解Web端通信模式的朝三暮四:从Ajax、JSONP 到
SSE、Websocket》

《MobileIMSDK-Web的网络层框架为什么采取的是Socket.io而不是Netty?》

《辩护联系实际:从零了然WebSocket的通信原理、协议格式、安全性》

>> 更多同类作品……

[2] 开源Web端实时音视频技术WebRTC的稿子:

《开源实时音视频技术WebRTC的现状》

《简述开源实时音录像技术WebRTC的得失》

《访谈WebRTC标准之父:WebRTC的仙逝、现在和前景》

《良心分享:WebRTC
零基础开发者教程(中文)[附件下载]》

《WebRTC实时音视频技术的共同体架构介绍》

《新手入门:到底如何是WebRTC服务器,以及它是怎么样衔接通话的?》

《WebRTC实时音录像技术基础:基本架构和商谈栈》

《浅谈开发实时视频直播平台的技巧中央》

《[观点]
WebRTC应该采用H.264视频编码的四阳江由》

《基于开源WebRTC开发实时音视频靠谱吗?第3方SDK有什么样?》

《开源实时音视频技术WebRTC中RTP/RTCP数据传输协议的利用》

《简述实时音录像聊天中端到端加密(E2EE)的劳作规律》

《实时通信RTC技术栈之:摄像编解码》

《开源实时音录像技术WebRTC在Windows下的强烈编译教程》

《网页端实时音视频技术WebRTC:看起来很美,但离生产应用还有稍稍坑要填?》

>> 更多同类小说……

(本文同步发布于:http://www.52im.net/thread-1341-1-1.html)

var wss = new WebSocket.Server({ port: 8080 });

wss.on(‘connection’, function connection(ws) {

   console.log(‘server: receive connection.’);

   ws.on(‘message’, function incoming(message) {

       console.log(‘server: received: %s’, message);

   });

   ws.send(‘world’);

});

app.get(‘/’, function (req, res) {

 res.sendfile(__dirname + ‘/index.html’);

});

app.listen(3000);

2、客户端

代码如下,向8080端口发起WebSocket连接。连接建立后,打印日志,同时向服务端发送信息。接收到来自服务端的信息后,同样打印日志。

 var ws = new WebSocket(‘ws://localhost:8080’);

 ws.onopen = function () {

   console.log(‘ws onopen’);

   ws.send(‘from client: hello’);

 };

 ws.onmessage = function (e) {

   console.log(‘ws onmessage’);

   console.log(‘from server: ‘ + e.data);

 };

3、运行结果

可各自查看服务端、客户端的日志,这里不举办。

服务端输出:

server: receive connection.

server: received hello

客户端输出:

client: ws connection is open

client: received world

四、怎么样建立连接

面前提到,WebSocket复用了HTTP的拉手通道。具体指的是,客户端通过HTTP请求与WebSocket服务端协商升级协议。协议升级成功后,后续的数据交流则依据WebSocket的情商。

1、客户端:申请协议升级

先是,客户端发起协议升级请求。可以看来,采用的是业内的HTTP报文格式,且只帮忙GET方法。

GET / HTTP/1.1

Host: localhost:8080

相关文章

发表评论

电子邮件地址不会被公开。 必填项已用*标注

网站地图xml地图