当前位置:   article > 正文

WebSocket 原理详解_websocket原理

websocket原理

WebSocket 原理详解

在这里插入图片描述

一、引言

1.1 http的局限性

HTTP是一种无状态协议,客户端发送请求,服务器响应,通信是单向的。这意味着服务器不能主动向客户端发送消息,而需要客户端不断轮询服务器来获取更新。

高延迟: HTTP请求-响应模式在某些情况下会导致较高的延迟,因为每次通信都需要建立连接、发送请求、等待服务器响应,然后关闭连接

资源消耗: 对于需要实时更新的应用程序(如在线游戏、股票报价等),使用HTTP长轮询短轮询会增加服务器负担和网络带宽消耗。

头部开销: 每个HTTP请求都需要包含头部信息,这会增加通信的开销,特别是在频繁通信的情况下。

1.2 使用HTTP不断轮询

那么怎么样才能在用户不做任何操作的情况下,网页能收到消息并发生变更。
最常见的解决方案是,网页的前端代码里不断定时发HTTP请求到服务器,服务器收到请求后给客户端响应消息。这其实时一种伪服务器推的形式。

它其实并不是服务器主动发消息到客户端,而是客户端自己不断偷偷请求服务器,只是用户无感知而已。

比如微信公众号平台,登录页面二维码出现之后,前端网页根本不知道用户扫没扫,于是不断去向后端服务器询问来确定用户是否扫码。而且是以大概1到2秒的间隔去不断发出请求,这样可以保证用户在扫码后能在1到2s内得到及时的反馈,不至于等太久。
在这里插入图片描述这样有个明显的坏处就是消耗带宽,同时也会增加下游服务器的负担。
最坏情况下,用户在扫码后,需要等个1~2s,正好才触发下一次http请求,然后才跳转页面,用户会感到明显的卡顿。

1.3 长轮询

我们知道,HTTP请求发出后,一般会给服务器留一定的时间做响应,比如3s,规定时间内没返回,就认为是超时。

如果我们的HTTP请求将超时设置的很大,比如30s,在这30s内只要服务器收到了扫码请求,就立马返回给客户端网页如果超时,那就立马发起下一次请求。

这样就减少了HTTP请求的个数,并且由于大部分情况下,用户都会在某个30s的区间内做扫码操作,所以响应也是及时的。
比如百度云网盘就是这么干的。所以你会发现一扫码,手机上点个确认,电脑端网页就秒跳转,体验很好。
像这种发起一个请求,在较长时间内等待服务器响应的机制,就是所谓的长训轮机制。
以上两种本质上,其实还是客户端主动去取数据。
对于像扫码登录这样的简单场景还能用用。
但如果是网页游戏呢,游戏一般会有大量的数据需要从服务器主动推送到客户端。

二、WebSocket 协议概述

现在实时性需求的应用场景越来越多。传统的 HTTP 协议在处理实时性需求方面存在很多局限,导致无法高效地支持实时通信应用。于是WebSocket 协议应运而生,通过在单个 TCP 连接上实现全双工通信,解决了传统 HTTP 协议在实时通信中的不足,成为了现代实时网络应用的基础技术之一。

WebSocket 是一种在单个 TCP 连接上进行全双工通信的协议。它由 IETF 于 2011 年制定,RFC 6455 标准中定义了 WebSocket 协议。与传统的 HTTP 协议不同,WebSocket 协议允许客户端和服务器之间进行实时、双向的数据传输。

三、WebSocket 连接的建立

WebSocket 连接的建立过程始于客户端向服务器发起的一个标准 HTTP 请求,该请求包含一个特殊的头部字段 Upgrade: websocket,表示希望升级到 WebSocket 协议。以下是一个典型的 WebSocket 请求头示例:

GET /chat HTTP/1.1
Host: example.com
Upgrade: websocket
Connection: Upgrade
Sec-WebSocket-Key: dGhlIHNhbXBsZSBub25jZQ==
Sec-WebSocket-Version: 13
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6

服务器收到这个请求后,会返回一个 HTTP 响应,指示同意升级到 WebSocket 协议,并包括必要的握手信息:

HTTP/1.1 101 Switching Protocols
Upgrade: websocket
Connection: Upgrade
Sec-WebSocket-Accept: s3pPLMBiTxaQ9kYGzzhZRbK+xOo=
  • 1
  • 2
  • 3
  • 4

上述握手过程完成后,HTTP 连接被升级为 WebSocket 连接,客户端和服务器可以通过这个连接进行双向通信。
在这里插入图片描述

四、WebSocket 数据传输

WebSocket 数据传输采用帧(frame)的形式。每个 WebSocket 帧包含了帧的类型、长度、负载数据等信息。WebSocket 支持文本数据帧二进制数据帧两种基本帧类型:

  1. 文本帧:文本帧用于传输 UTF-8 编码的文本数据。
  2. 二进制帧:二进制帧用于传输二进制数据,如图像、文件等。

除了基本帧类型,WebSocket 还支持控制帧,如关闭帧(Close Frame)、Ping 帧和 Pong 帧。关闭帧用于终止连接,Ping 和 Pong 帧用于检测连接是否仍然活跃。

以下是一个简单的 WebSocket 数据帧结构:

0               1               2               3               4
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 ...                |
+---------------------------------------------------------------+
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18

五、 WebSocket 的优势

  1. 持久连接:WebSocket 通过单个持久的 TCP 连接实现客户端和服务器之间的通信,避免了频繁建立和关闭连接的开销,减少了资源消耗。

  2. 双向通信:与传统的 HTTP 请求-响应模式不同,WebSocket 允许客户端和服务器同时发送和接收数据,实现了真正的全双工通信。这对于实时性要求高的应用,如在线聊天、股票行情推送等非常重要。

  3. 低延迟:由于 WebSocket 连接一旦建立后就保持活跃状态,数据可以在客户端和服务器之间低延迟地传输,满足实时应用的需求。

  4. 减少带宽消耗:WebSocket 数据帧的头部信息比传统的 HTTP 请求要小得多,减少了带宽消耗。特别是在高频率的数据交换场景下,WebSocket 的优势更加明显。

六、WebSocket 的应用场景

  1. 即时通讯:WebSocket 允许即时发送和接收消息,非常适合用于在线聊天应用,如 Slack、WhatsApp Web 等。

  2. 实时数据更新:对于股票市场、体育赛事等需要实时更新数据的应用,WebSocket 可以实时推送数据更新,用户无需刷新页面即可获取最新信息。

  3. 在线游戏:在线多人游戏需要低延迟的实时通信,WebSocket 可以满足这种需求,提供流畅的游戏体验。

  4. 协同编辑:如 Google Docs 等在线协同编辑工具,通过 WebSocket 实现用户间的实时同步编辑。

  5. 物联网(IoT):在物联网应用中,设备与服务器之间需要进行实时的数据交换,WebSocket 可以提供高效的通信机制。

七、WebSocket 与 HTTP/2

虽然 WebSocket 提供了高效的实时通信方式,但 HTTP/2 也通过多路复用等技术提高了 HTTP 的性能。HTTP/2 允许在单个连接上并发处理多个请求和响应,减少了延迟和资源消耗。然而,HTTP/2 依然是基于请求-响应模式,而 WebSocket 则实现了真正的全双工通信。因此,在需要实时、双向通信的场景下,WebSocket 依然是更好的选择。

八、WebSocket 的安全性

WebSocket 使用 ws://wss:// 协议,分别对应不加密和加密的连接。wss:// 使用 TLS(传输层安全性)加密,可以确保数据传输的安全性。然而,由于 WebSocket 连接一旦建立后就保持持久状态,开发者需要特别注意防止一些常见的安全漏洞,如跨站脚本攻击(XSS)和跨站请求伪造(CSRF)。

九、 WebSocket 的实现

在现代 Web 开发中,WebSocket 的实现非常简单。以下是一个使用 JavaScript 和 Node.js 实现的简单 WebSocket 服务器和客户端示例:

服务器端(Node.js)

const WebSocket = require('ws');
const server = new WebSocket.Server({ port: 8080 });

server.on('connection', ws => {
    ws.on('message', message => {
        console.log(`Received message => ${message}`);
        ws.send(`Hello, you sent -> ${message}`);
    });
    ws.send('Hi there, I am a WebSocket server');
});
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10

客户端(JavaScript)

<!DOCTYPE html>
<html>
<head>
    <title>WebSocket Example</title>
</head>
<body>
    <script>
        const socket = new WebSocket('ws://localhost:8080');

        socket.addEventListener('open', function (event) {
            socket.send('Hello Server!');
        });

        socket.addEventListener('message', function (event) {
            console.log('Message from server ', event.data);
        });
    </script>
</body>
</html>
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19

在上面这个示例中,WebSocket 服务器使用 ws 模块创建,当接收到客户端消息时,会将其回显给客户端。客户端通过浏览器内置的 WebSocket API 连接到服务器,并发送和接收消息。

总结

WebSocket 作为一种高效、实时的双向通信协议,解决了传统 HTTP 协议在实时性和效率方面的不足。它通过持久连接、低延迟和双向通信的特性,为实时网络应用提供了强大的支持。在未来,随着实时应用场景的不断增多,WebSocket 将继续发挥重要作用,为用户带来更加流畅和高效的体验。

参考链接

本文内容由网友自发贡献,转载请注明出处:https://www.wpsshop.cn/w/秋刀鱼在做梦/article/detail/893971
推荐阅读
相关标签
  

闽ICP备14008679号