文章详情

短信预约-IT技能 免费直播动态提醒

请输入下面的图形验证码

提交验证

短信预约提醒成功

前端实时通信的8种方式及其优缺点和实现方式

2024-04-02 19:55

关注

1.短轮询

短轮询的原理很简单,每隔一段时间客户端就发出一个请求,去获取服务器最新的数据,一定程度上模拟实现了即时通讯。

created(){
	this.shortPolling = setInterval(function(){
	    that.getRuset()
	},5000)
},
...
getResult(){
	var that = this
	this.$axios('xxx,',post).then(res=>{
		if(res.code === 200){//拿到想要的结果
			 ...
			 //定时器是否清除由业务场景决定
			 clearInterval(this.shortPolling)
		}
	})
}

2.comet(长轮询、长连接)

comet有两种主要实现手段,一种是基于 AJAX 的长轮询(long-polling)方式,另一种是基于 Iframe 及 htmlfile 的流(streaming)方式,通常被叫做长连接。
具体两种手段的操作方法请移步Comet技术详解:基于HTTP长连接的Web端实时通信技术

2.1、长轮询

客户端向服务器发送Ajax请求,服务器接到请求后hold住连接,直到有新消息才返回响应信息并关闭连接,客户端处理完响应信息后再向服务器发送新的请求。

getResult(){
	var that = this
	this.$axios('xxx,',post).then(res=>{
		if(res.code === 200){
			...
		}else{
			this.getResult()
		}
		...
	})
}

正常来说我们前端会设置请求超时时间,那么我们就和后端约定,在超时范围内必须返回结果在前端即可。

2.2、长连接

在页面里嵌入一个隐蔵iframe,将这个隐蔵iframe的src属性设为对一个长连接的请求或是采用xhr请求,服务器端就能源源不断地往客户端输入数据。 此方法已经过时,我推荐使用,毕竟现在都已经放弃iframe

//在vue中嵌入iframe
<iframe ref="iframe" v-show="iframeShow"></iframe>

watchIframe(){
	//先找到iframe的窗口
	this.iframeWin = this.$refs.iframe.contentWindow;
	//向iframe发送信息,大括号内是发送的内容;
	this.iframeWin.postMessage(
	     { 
	
	      },"*"
	);
	//怎样监听iframe传过来的信息
	window.addEventListener("message", this.handleMessage);
	//获取iframe传过来的信息
	handleMessage(res){
	  //res为传过来的信息
	 ...//渲染页面
	}
}

3.SSE 使用指南请看Server-Sent Events 教程

SSE(Server-Sent Event,服务端推送事件)是一种允许服务端向客户端推送新数据的HTML5技术

source.addEventListener('open', function (event) {
  // ...
}, false);
//客户端收到服务器发来的数据,就会触发message事件,可以在onmessage属性的回调函数。
source.addEventListener('message', function (event) {
  var data = event.data;
  // handle message
}, false);

//如果发生通信错误(比如连接中断),就会触发error事件,可以在onerror属性定义回调函数。
source.addEventListener('error', function (event) {
  // handle error event
}, false);

//close方法用于关闭 SSE 连接。
source.close();

我们也可以自定义事件,Server-Sent Events 教程里都有明确的使用方法

4.Websocket

Websocket是一个全新的、独立的协议,基于TCP协议,与http协议兼容、却不会融入http协议,仅仅作为html5的一部分,其作用就是在服务器和客户端之间建立实时的双向通信。

浏览器为 HTTP 通信提供了 XMLHttpRequest 对象,同样的,也为 WebSocket 通信提供了一个通信操作接口:WebSocket。

 var ws = new WebSocket("wss://echo.websocket.org");

  // 当连接建立成功,触发 open 事件
  ws.onopen = function(evt) {
    console.log("建立连接成功 ...");

    // 连接建立成功以后,就可以使用这个连接对象通信了
    // send 方法发送数据
    ws.send("Hello WebSockets!");
  };

  // 当接收到对方发送的消息的时候,触发 message 事件
  // 我们可以通过回调函数的 evt.data 获取对方发送的数据内容
  ws.onmessage = function(evt) {
    console.log("接收到消息: " + evt.data);

    // 当不需要通信的时候,可以手动的关闭连接
    // ws.close();
  };

  // 当连接断开的时候触发 close 事件
  ws.onclose = function(evt) {
    console.log("连接已关闭.");
  }

5.Web Worker

Web Worker 的作用,就是为 JavaScript 创造多线程环境,允许主线程创建 Worker 线程,将一些任务分配给后者运行

Web workers可分为两种类型:专用线程、共享线程。
专用线程随当前页面的关闭而结束;这意味着专用线程只能被创建它的页面访问。
与之相对应的共享线程可以被多个页面访问。

5.1、专用线程

使用 onmessage() , postmessage()通信


//注册专用线程
let worker = new Worker ('worker.js')
worker.onmessage = (e) => {
  console.log(e.data) // I post a message to main thread
}
worker.postMessage('main thread got a message')
 

onmessage = (e) => {
    console.log(e.data) // main thread got a message
}
postMessage('I post a message to main thread')

// 在主线程中终止
worker.terminate()
 
// 在子线程中终止自身
self.close()

5.2、共享线程

SharedWorker需要用到port属性,接收需要先connect

//注册共享线程
let worker = new SharedWorker("sharedworker.js");

worker.port.onmessage = function(e){}
worker.port.postMessage('data');
 

addEventListener('connect', function(event){
    var port = event.ports[0]
    //接收
    port.onmessage = function(event){
        console.log(event.data);
    };
    //发送
    port.postMessage("data");
    port.start();
});

// 在主线程中终止
worker.terminate()
 
// 在子线程中终止自身
self.close()

两种方式的错误监听同SSE一样

worker.addEventListener("error", function(evt){  
	alert("Line #" + evt.lineno + " - " + evt.message + " in " + evt.filename);  
	}, false);  
	worker.postMessage(10000);  
});  

6.Service workers

Service workers 本质上充当Web应用程序与浏览器之间的代理服务器,也可以在网络可用时作为浏览器和网络间的代理,创建有效的离线体验。 它是 Web Worker 的一个类型

// serviceWorker.js
import { register } from 'register-service-worker'

if (process.env.NODE_ENV === 'production') {
  register('service-worker.js', {
    ready () {
      console.log(
        'App is being served from cache by a service worker.'
      )
    },
    registered () {
      console.log('Service worker has been registered.')
    },
    cached () {
      console.log('Content has been cached for offline use.')
    },
    updatefound () {
      console.log('New content is downloading.')
    },
    updated () {
      console.log('New content is available; please refresh.')
      window.location.reload(true)   // 这里需要刷新页面
    },
    offline () {
      console.log('No internet connection found. App is running in offline mode.')
    },
    error (error) {
      console.error('Error during service worker registration:', error)
    }
  })
}

在 plugins 加入

plugins: [
    new SWPrecacheWebpackPlugin({
      cacheId: 'my-project-name',
      filename: 'service-worker.js',
      staticFileGlobs: ['dist*.{js,html,css}'],
      minify: true,
      stripPrefix: 'dist/'
    }),

    new WebpackPwaManifest({
      name: 'My Progressive Web App',
      short_name: 'MyPWA',
      description: 'My awesome Progressive Web App!',
      background_color: '#ffffff',
      crossorigin: 'use-credentials', //can be null, use-credentials or anonymous
      icons: [
        {
          src: path.resolve('src/assets/icon.png'),
          sizes: [96, 128, 192, 256, 384, 512] // multiple sizes
        },
        {
          src: path.resolve('src/assets/large-icon.png'),
          size: '1024x1024' // you can also use the specifications pattern
        }
      ]
    }),
    // ...
]

这个时候打包出来的代码根目录里面多了个 service-worker.js ,html文件里面 pwa 相关元素也加上了。
在入口 main.js 引入该文件:

import './serviceWorker'

7、Flash Socket

在页面中内嵌入一个使用了Socket类的 Flash 程序JavaScript通过调用此Flash程序提供的Socket接口与服务器端的Socket接口进行通信,JavaScript在收到服务器端传送的信息后控制页面的显示。 一般用在网络游戏中,web端基本不适用,加上早在 2017 年 7 月,Flash 的娘家 Adobe 已宣布在 2020年 底终止对 Flash 的支持。各个浏览器也在2020年底左右终止对 Flash 的支持

8、总结

更多关于前端实时通信方式及其优缺点和实现方式请查看下面的相关链接

阅读原文内容投诉

免责声明:

① 本站未注明“稿件来源”的信息均来自网络整理。其文字、图片和音视频稿件的所属权归原作者所有。本站收集整理出于非商业性的教育和科研之目的,并不意味着本站赞同其观点或证实其内容的真实性。仅作为临时的测试数据,供内部测试之用。本站并未授权任何人以任何方式主动获取本站任何信息。

② 本站未注明“稿件来源”的临时测试数据将在测试完成后最终做删除处理。有问题或投稿请发送至: 邮箱/279061341@qq.com QQ/279061341

软考中级精品资料免费领

  • 历年真题答案解析
  • 备考技巧名师总结
  • 高频考点精准押题
  • 2024年上半年信息系统项目管理师第二批次真题及答案解析(完整版)

    难度     807人已做
    查看
  • 【考后总结】2024年5月26日信息系统项目管理师第2批次考情分析

    难度     351人已做
    查看
  • 【考后总结】2024年5月25日信息系统项目管理师第1批次考情分析

    难度     314人已做
    查看
  • 2024年上半年软考高项第一、二批次真题考点汇总(完整版)

    难度     433人已做
    查看
  • 2024年上半年系统架构设计师考试综合知识真题

    难度     221人已做
    查看

相关文章

发现更多好内容

猜你喜欢

AI推送时光机
位置:首页-资讯-服务器
咦!没有更多了?去看看其它编程学习网 内容吧
首页课程
资料下载
问答资讯