【WebSocket】前端使用WebSocket实时通信

目录

  • 前言
  • 什么是WebSocket
  • WebSocket的工作原理
  • WebSocket与HTTP的关系
  • HTTP建立持久化连接
  • WebSocket类封装

前言

最近写项目,需要实现消息通知和实时聊天的功能,就去了解了一些关于websocket的知识,总结如下。

什么是WebSocket

WebSocket 是一种在 Web 应用中实现实时通信的协议。与传统的 HTTP 请求不同,WebSocket 连接在客户端和服务器之间建立一个持久性双向通信管道,使得数据可以在连接打开后随时传递。这消除了 HTTP 请求的开销,能更好的节省服务器资源和带宽,同时在实时应用中提供了更好的性能和响应性。

WebSocket 就像是你和服务器之间的一个电话线,可以在任何时候进行通话。和普通的浏览网页不同,WebSocket 让你能够实时地接收和发送信息,而不需要频繁地向服务器询问是否有新的消息。

WebSocket的工作原理

WebSocket 协议的工作原理基于握手(handshake)和消息传递。当客户端发起 WebSocket 握手请求时,服务器将进行握手确认,建立连接。一旦连接建立,客户端和服务器可以互相发送消息,而不必每次都进行新的握手。

  1. 建立连接: 在客户端(浏览器)发起 WebSocket 连接请求时,服务器会进行响应,建立一个持久的连接通道。这个过程类似于握手,它使用了 HTTP/HTTPS 协议来发起连接请求。
  2. 双向通信: 连接建立成功,客户端和服务器都可以通过这个通道实时地发送和接收数据,消息可以是文本或二进制数据。不像传统的 HTTP 请求,WebSocket 允许服务器主动向客户端推送数据,也允许客户端向服务器发送请求,实现双向通信。
  3. 保持连接: 一旦连接建立,客户端和服务器之间就会保持一个持久的连接通道,不需要每次都重新建立连接。这使得数据传输更加高效,减少了不必要的连接建立和关闭开销。
  4. 关闭连接: 当客户端或服务器希望终止连接时,可以发送一个特殊的关闭帧,告知对方要关闭连接。对方接收到关闭帧后,也会发送一个确认帧,并关闭连接。这是一个优雅的断开连接方式,不需要像传统的 HTTP 请求那样等待服务器的响应。类似于双方结束通话,然后挂断电话。

WebSocket与HTTP的关系

WebSocket 和 HTTP 是两种不同的协议,它们有着不同的通信方式、连接状态和数据传输方式。WebSocket在实现实时性通信方面更加高效,而 HTTP 更适用于请求-响应式的短期数据交换。

  • 共同点: WebSocket 和 HTTP 都是用于网络通信的协议,都是在应用层工作。它们都基于 TCP/IP 协议,用于在客户端和服务器之间传输数据。
  • 联系: WebSocket 协议最初是作为 HTTP 协议的扩展而提出的,因此在握手阶段使用了 HTTP 协议来建立连接。WebSocket 握手请求使用的是 HTTP 请求,然后在协议升级时切换到 WebSocket 协议,建立持久的双向连接。所以,WebSocket是在 HTTP 协议的基础上构建的。
  • 区别:
    1. HTTP是请求-响应式通信,数据通常单向传输。而WebSocket 是全双工通信,双向数据传输。
    2. 在 HTTP 中,每次请求和响应都会携带大量的头部信息,这些信息描述了请求和响应的性质。而在 WebSocket 握手时,也会有一些头部信息,但之后数据传输时的头部相对较少,从而减少了传输开销,且websocket没有像http那样可以只定义请求头的一些参数,只有一个Sec-WebSocket-Protocol属性用于自定义子协议。
    3. HTTP 适用于传输短期请求-响应式的数据,如网页的加载和表单提交。WebSocket 更适用于实时性要求较高的场景,如在线聊天、实时数据更新、多人协作等。

HTTP建立持久化连接

HTTP Keep-Alive (长连接): 长连接是一种保持连接打开的通信方式,客户端与服务器建立连接后,在一段时间内保持连接处于打开状态,以便后续的 HTTP 请求复用它。在长连接中,一次 TCP 连接可以被用来发送多个 HTTP 请求和响应,而不是每次请求都建立一个新的连接。

Keep-Alive 适用于需要实时数据传输的场景,如聊天应用、实时游戏、实时数据监控等。它可以实现低延迟的实时通信,提高通信效率。但需要维护长时间的连接状态,对服务器资源和网络负载有一定影响。

Long Polling(长轮询) :长轮询是一种模拟实时通信的方法。在长轮询中,客户端发送一个请求到服务器,服务器在等待新数据或事件的时候,保持连接打开,直到有新的数据或事件发生时才发送响应给客户端。客户端收到响应后立即处理,然后再次发送请求,以保持连接。

长轮询适用于不支持真正长连接的环境,如基于HTTP协议的环境。它可以模拟实时通信,但因为每次响应后都需要重新建立连接,所以在一些情况下可能会有较高的延迟和网络开销。

WebSocket类封装

class WebSocketClass {constructor(wsurl, time) {this.wsurl = wsurl //连接地址this.token = localStorage.getItem("accessToken")this.time = time //多少秒执行检测this.socketTask = nullthis.is_open_socket = false //避免重复连接this.heartbeatInterval = null //检测服务器端是否还活着this.reconnectTimeOut = null //重连之后多久再次重连this.connectSocketInit()}// 建立初始连接connectSocketInit() {this.socketTask = new WebSocket(this.wsurl, this.token)// 当连接成功时this.socketTask.onopen = (res) => {console.log("websocket连接成功!", res);this.is_open_socket = true//连接正常清除重连定时器this.clearReconnect();// this.startHeartbeat();}// 当收到消息时this.socketTask.onmessage = (res) => {console.log(res.data)}// 当连接出错时this.socketTask.onerror = (res) => {console.log("websocket连接出错!", res);this.is_open_socket = false// this.reconnect()}// 当连接关闭时this.socketTask.onclose = (res) => {console.log("websocket已经被关闭了!", res);this.is_open_socket = false// this.reconnect()}}// 发送消息send(value) {if (this.is_open_socket) {this.socketTask.send(value);} else {console.log("无法发送消息:WebSocket未连接");}}// 开启心跳检测startHeartbeat() {this.heartbeatInterval = setInterval(() => {const heartbeatMessage = {value: "测试一下服务器端是否在连接状态",method: "开启心跳机制"};this.send(JSON.stringify(heartbeatMessage)) // 发送心跳消息}, this.time * 1000)}//停止发送心跳stopHeartbeat() {clearInterval(this.heartbeatInterval);}// 清除重连定时器clearReconnect() {clearTimeout(this.reconnectTimeout);}// 重新连接reconnect() {//停止发送心跳this.stopHeartbeat()//如果不是人为关闭的话,进行重连if (!this.is_open_socket) {this.reconnectTimeOut = setTimeout(() => {this.connectSocketInit();}, 3000)}}//外部获取消息getMessage(callback) {this.socketTask.onmessage = (res) => {return callback(res) // 调用外部回调函数处理消息}}
}
export default WebSocketClass;
// 调用方法
// -------------------------------------------------------------------
// 单页面
// import WebSocketClass from '@/network/webSocket';
// let ws = new WebSocketClass("ws:****",5000)
// 发送消息
// let data={value:"传输内容",method:"方法名称"}
// ws.send(JSON.stringify(data));
// 接收消息
// ws.getMessage(res=>{
// 	console.log(res);
// })

可能学习的不够深刻、总结不到位,请谅解。如有误,请指正!
在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.hqwc.cn/news/81736.html

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

PL 侧驱动和fpga 重加载的方法

可以解决很多的问题 时钟稳定后加载特定fpga ip (要不内核崩的一塌糊涂)fpga 稳定复位软件决定fpga ip 加载的时序 dluash load /usr/local/scripts/si5512_setup.lua usleep 30 mkdir -p /lib/firmware cp -rf /usr/local/firmare/{*.bit.bin,*.dtbo} …

【JVM基础】JVM入门基础

目录 JVM的位置三种 JVMJVM体系结构类加载器双亲委派机制概念例子作用 沙箱安全机制组成沙箱的基本组件 NativeJNI:Java Native Interface(本地方法接口)Native Method Stack(本地方法栈) PC寄存器(Program…

List 去重两种方式:stream(需要JDK1.8及以上)、HashSet

1、使用Stream 方法 使用JDK1.8及以上 /*** Java合并两个List并去掉重复项的几种做法* param args*/public static void main(String[] args) {String[] str1 {"1", "2", "3", "4", "5", "6"};List<String&…

Redis数据结构之Set

Set 类型是一个无序并唯一的键值集合&#xff0c;它的存储顺序不会按照插入的先后顺序进行存储。Redis 中集合是通过哈希表实现的&#xff0c;所以添加&#xff0c;删除&#xff0c;查找的复杂度都是 O(1)。相对于列表&#xff0c;集合也有两个特点&#xff1a;无序、不可重复 …

QT6安装完成后,再安装低版本的MinGW或其他组件方式

首先进入点击安装的uinstall Qt 并不是真的卸载 通过下面几步 1&#xff0c;首先登录自己账户 2&#xff0c;然后进入欢迎中&#xff0c;点击“添加和移除组件” 3&#xff0c;然后检索自己需要的安装内容

OpenCV图片校正

OpenCV图片校正 背景几种校正方法1.傅里叶变换 霍夫变换 直线 角度 旋转3.四点透视 角度 旋转4.检测矩形轮廓 角度 旋转参考 背景 遇到偏的图片想要校正成水平或者垂直的。 几种校正方法 对于倾斜的图片通过矫正可以得到水平的图片。一般有如下几种基于opencv的组合方…

【3dsmax】练习——制作碗椅

目录 目标 步骤 一、制作主体部分 二、制作靠垫部分 三、制作支架部分 目标 制作如下图所示的碗椅 步骤 一、制作主体部分 1. 首先创建一个球体 2. 转换为可编辑多边形&#xff0c;然后切换到边层级&#xff0c;选中球体上部的所有边&#xff0c;然后删除 3. 通过“壳…

Mybatis的动态SQL分页及特殊字符的使用

目录 一、分页 ( 1 ) 应用场景 ( 2 ) 使用 二、特殊字符 2.1 介绍 2.2 使用 给我们带来的收获 一、分页 分页技术的出现是为了解决大数据量展示、页面加载速度、页面长度控制和用户体验等问题。通过将数据分成多个页面&#xff0c;用户可以根据需求选择查看不同页的数据…

很干的 Nginx

&#x1f3a8; 前言 本篇文章有些概念性的东西&#xff0c;是结合自己的理解表达出来的&#xff0c;可能有些理解不到位的地方。希望多多指教&#xff0c;谢谢大家。 红包献上 &#x1f9e7;&#x1f9e7;&#x1f9e7;&#x1f9e7;&#x1f9e7;&#x1f9e7;&#x1f9e7;…

行式存储与列式存储

1.概述 数据处理大致可分为两大类&#xff0c;联机事务处理OLTP(on-line transaction processing) 和联机分析处理OLAP(on-line analytical processing)。 OLTP是传统关系型数据库的主要应用&#xff0c;用来执行一些基本的、日常的事务处理&#xff0c;比如数据库记录的增、删…

Day14-2-NodeJS后端开发流程

Day14-NodeJS后端工程化流程 一 apifox工具 apifox是目前最好的接口调试工具 1 环境搭建 安装登录创建项目接口里面创建对应文件夹在指定的文件夹里面创建接口2 GET请求 1 apifox发送GET请求 2 后端接收GET请求 router.get("/getUserinfo"

恒运资本大盘走势:北向资金是什么?北向资金流出对A股有何影响?

在股票商场中&#xff0c;常常报导北向资金买入和卖出&#xff0c;那么&#xff0c;北向资金是什么意思&#xff1f;北向资金流出对A股有何影响&#xff1f;为大家预备了相关内容&#xff0c;以供参考。 恒运资本平台&#xff08;百度搜索恒运资本&#xff09;是深圳引力私募基…