Web实时通讯技术简介

一、概述

1.Web端即时通讯技术

即时通讯技术简单的说就是实现这样一种功能:服务器端可以即时地将数据的更新或变化反应到客户端,例如消息即时推送等功能都是通过这种技术实现的。但是在Web中,由于浏览器的限制,实现即时通讯需要借助一些方法。这种限制出现的主要原因是,一般的Web通信都是浏览器先发送请求到服务器,服务器再进行响应完成数据的现实更新。

2.实现Web端即时通讯的方法

实现即时通讯主要有四种方式,它们分别是短轮询、长轮询(comet)、长连接(SSE)、WebSocket。它们大体可以分为两类,一种是在HTTP基础上实现的,包括短轮询、comet和SSE;另一种不是在HTTP基础上实现是,即WebSocket。下面分别介绍一下这四种轮询方式,以及它们各自的优缺点。

(1)短轮询

短轮询的基本思路就是浏览器每隔一段时间向浏览器发送http请求,服务器端在收到请求后,不论是否有数据更新,都直接进行响应。这种方式实现的即时通信,本质上还是浏览器发送请求,服务器接受请求的一个过程,通过让客户端不断的进行请求,使得客户端能够模拟实时地收到服务器端的数据的变化。

这种方式的优点是比较简单,易于理解,实现起来也没有什么技术难点。缺点是显而易见的,这种方式由于需要不断的建立http连接,严重浪费了服务器端和客户端的资源。尤其是在客户端,距离来说,如果有数量级想对比较大的人同时位于基于短轮询的应用中,那么每一个用户的客户端都会疯狂的向服务器端发送http请求,而且不会间断。人数越多,服务器端压力越大,这是很不合理的。

因此短轮询不适用于那些同时在线用户数量比较大,并且很注重性能的Web应用。

(2)comet

comet指的是,当服务器收到客户端发来的请求后,不会直接进行响应,而是先将这个请求挂起,然后判断服务器端数据是否有更新。如果有更新,则进行响应,如果一直没有数据,则到达一定的时间限制(服务器端设置)后关闭连接。

长轮询和短轮询比起来,明显减少了很多不必要的http请求次数,相比之下节约了资源。长轮询的缺点在于,连接挂起也会导致资源的浪费。

(3)SSE

SSE是HTML5新增的功能,全称为Server-Sent Events。它可以允许服务推送数据到客户端。SSE在本质上就与之前的长轮询、短轮询不同,虽然都是基于http协议的,但是轮询需要客户端先发送请求。而SSE最大的特点就是不需要客户端发送请求,可以实现只要服务器端数据有更新,就可以马上发送到客户端。

SSE的优势很明显,它不需要建立或保持大量的客户端发往服务器端的请求,节约了很多资源,提升应用性能。并且后面会介绍道,SSE的实现非常简单,并且不需要依赖其他插件。

(4)WebSocket

WebSocket是HTML5定义的一个新协议,与传统的http协议不同,该协议可以实现服务器与客户端之间全双工通信。简单来说,首先需要在客户端和服务器端建立起一个连接,这部分需要http。连接一旦建立,客户端和服务器端就处于平等的地位,可以相互发送数据,不存在请求和响应的区别。

WebSocket的优点是实现了双向通信,缺点是服务器端的逻辑非常复杂。现在针对不同的后台语言有不同的插件可以使用。

3.四种Web即时通信技术比较

从兼容性角度考虑,短轮询>长轮询>长连接SSE>WebSocket;

从性能方面考虑,WebSocket>长连接SSE>长轮询>短轮询

二、短轮询

1.原理

短轮询利用http的请求/响应模式,通过每隔一定时间向服务器发送请求来获得服务器数据的更新。在开发过程中,可以利用ajax,然后通过setInterval()方法,实现每隔一段时间向服务器发送请求的功能。

2.实现

后端以php为例进行实现。

客户端代码:

<!doctype html>
<html>
<head>
<meta charset="utf-8">
<title>短轮询ajax实现</title>
<script type="text/javascript" src="../jquery.min.js"></script>
</head>
<body>
    <form id="form1" runat="server">
    	<div id="news"></div>
    </form>
</body>
<script type="text/javascript">
 	function showUnreadNews(){
            $(document).ready(function() {
//使用jquery的ajax方法
            	$.ajax({
                  type: "GET",
                  url: “do.php",  //请求发送到的后台php文件
                  dataType: "json",
 	   //请求成功的回调方法,遍历获取到的数据进行客户度界面的更新
                  success: function(msg) {
                      $.each(msg, function(id, title) {
                          $("#news").append("<a>" + title + "</a><br>");
                      });
                  }
               });
            });
        }
 //设置每2s执行一次showUnreadNews()方法,向服务器发送请求
        setInterval('showUnreadNews()',2000);
</script>
</html>

服务器端代码(php):

<?php
$arr = array('title'=>'新闻','text'=>'新闻内容');   //服务器端更新的数据
echo json_encode($arr);  //返回的öson数据
?>

三、comet

1.原理

comet与传统的ajax区别在于,客户端会与服务器端保持一个长连接,只有当客户端需要的数据更新时,服务器才会主动将数据推送给客户端。comet的实现有两种方式,一种方式是使用基于ajax的长轮询,另一种方式是基于Iframe及htmlfile的流方式。基于ajax的长轮询方式中,服务器端在接受到客户端ajax发送的请求后,不立即返回响应,而是阻塞请求直到超时或有数据更新。当服务器端在上述情况下返回响应后,客户端通过js再次发送请求建立连接,重复上述步骤。

2.实现

客户端代码:

<!doctype html>
<html>
<head>
<meta charset="utf-8">
<title>长轮询ajax实现</title>
<script type="text/javascript" src="../jquery.min.js"></script>
</head>
<body>
<input type="button" id="btn" value="click">
<div id="msg">数据情况</div>
</body>
<script type="text/javascript">
$(function(){
        $("#btn").bind('click',{btn:$('#btn')},function(e){
            $.ajax({
               	type: 'POST',
               	dataType: 'json',
               	url: 'ajax.php',
               	timeout: '20000',//设置请求超时时间
               	data: {time: '2000000'},// 每次请求等待时间,将其传到后台用来挂起请求
               	success: function(data,status){
//对返回的数据进行判断和读取
                   	if(data.success == '1'){
                   	$("#msg").append('<br>[有数据]'+data.text);
                   	e.data.btn.click();  //再此发送请求
               	}
                   	// 未从服务器中获的数据
                      if(data.success == '0'){
                      	$("#msg").append('<br>[无数据]');
                      	 	e.data.btn.click();
                   	}
                },
                // ajax超时,继续查询
                error:function(XMLHttpRequest,textStatus,errorThrown){
                     if(textStatus == "timeout"){
                        $("#msg").append('超时');
                        e.data.btn.click();
                     }
                }
          });
        });
    });
</script>
</html>

服务器端代码(php):

<?php
  set_time_limit(0);// 无限请求超时时间
  usleep($_POST['time’]);//通过前台传过来的数据设置挂起时间
  while(true){   //无限循环
      $rand = rand(1,999);
      if($rand < 500){
          $arr = array('success'=>'1','name'=>'有值','text'=>$rand);
          echo json_encode($arr);
          exit();
      }else{
          $arr = array('success'=>'0','name'=>'无值','text'=>$rand);
          echo json_encode($arr);
          exit();
      }
   }
?>

四、SSE

1.原理

SSE不需要依赖客户端向服务器发送请求,而是可以直接在服务器端有数据更新时进行发送到客户端,相比于轮询的“拉数据”,这种“推数据” 有着低延迟、高性能的优势。

这种方法的服务器端非常简介,只要维护一个服务器和客户端之间的协议即可。前端使用EventSource对象。

服务器端需要提供的协议基本代码如下:

data: first event

data: second event

id: 100

event: myevent

data: third event

id: 101

: this is a comment

data: fourth event

data: fourth event continue

下面解释一下基本用法。要定义各个事件,每一个事件之间使用一个换行符隔开。每个事件内部可以有多行,每一行都是type:value的形式。type有以下集中选择:

(1)类型为空白,表示该行是注释,会在处理时被忽略。

(2)类型为 data,表示该行包含的是数据。以 data 开头的行可以出现多次。所有这些行都是该事件的数据。

(3)类型为 event,表示该行用来声明事件的类型。浏览器在收到数据时,会产生对应类型的事件。

(4)类型为 id,表示该行用来声明事件的标识符。

(5)类型为 retry,表示该行用来声明浏览器在连接断开之后进行再次连接之前的等待时间。

比如上面的第一个事件,只传输了一个数据,数据内容为first event。服务器端通过这个清单发送到客户端,就可以通过前端进行响应的处理,诸如读取新数据、更新界面等。

客户端需要在JavaScript中使用EventSource对象。

首先需要初始化一个EventSource对象,实例化的时候需要传入与其交互的服务器端的文件地址,如:

var es = new EventSource(“sse.php”);

接下来,可以对进行事件的监听。EventSource给出了三种标准事件,它们的名称和触发时机如下表:

open                 当成功与服务器建立连接时执行

message             当收到服务器发送的事件时执行

error                 当出现错误时执行

和普通的事件一样,可以通过以下两种方法使用这些事件:

es.onmessage = function(e){};

es.addEventListener(“message”,function(e){});

2.实现

服务器端代码(php):

<?php
    header('Content-Type: text/event-stream'); //这是专门为sse设置的数据格式
    $time = date('Y-m-d H:i:s');
    //下面这些echo出来的东西就是上面说的服务器端和客户端之间的协议
    echo 'retry: 3000'.PHP_EOL;   //retry类型的数据,规定了浏览器在连接断开之后进行再次连接之前的等待时间
    echo 'data: The server time is: '.$time.PHP_EOL.PHP_EOL;
?>

注意必须要先设定content-type为text/event-stream,这是为SSE专门定义的数据传输格式。

接下来通过php的echo输出协议,上面的代码输出的结果如下:

retry:3000

data:The server time is...

输出了一个事件,这个事件中分别定义了retry类型和data类型的行。

客户端代码:

<html>
    <head>
        <meta charset="UTF-8">
        <title>basic SSE test</title>
    </head>
    <body>
        <div id=”content”></div>
    </body>
    <script>
        var es = new EventSource("sse.php");
        es.addEventListener("message",function(e){
            document.getElementById("content").innerHTML += "\n"+e.data;
        });
    </script>
</html>

上面的代码首先实例化了一个EventSource对象,并传入与之通信的服务器端文件sse.php。利用addEventListener()方法,为对象绑定一个message事件(上面提到message在收到服务器发送的事件时执行)。当客户端收到服务器传来的协议时,为页面中添加数据,通过e.data获取,对应了服务器端文件中协议表的data类型定义的数据,即The server time is...。

五、WebSocket

1.原理

WebSocket的实现了一次连接,双方通信的功能。首先由客户端发出WebSocket请求,服务器端进行响应,实现类似TCP握手的动作。这个连接一旦建立起来,就保持在客户端和服务器之间,两者之间可以直接的进行数据的互相传送。服务器端的逻辑比较复杂,如果是java或者node开发,都有很多封装好的组件可以使用。

2.前端API

(1)创建WebSocket对象

var ws = new WebSocket(“ws//localhost:8080”);

WebSocket是一个不同于HTTP的协议,其参数传递中的ws://前缀类似于http://,用于进行协议的声明。

(2)事件操作

WebSocket提供了四个事件操作,如下表:

onmessage         收到服务器响应时执行

onerroe   出现异常时执行

onopen   建立起连接时执行

onclose   断开连接时执行

时间: 2024-10-13 13:06:09

Web实时通讯技术简介的相关文章

简述Web Service通讯技术的搭建流程

Web Service 基本概念 Web Service也叫XML Web Service WebService是一种可以接收从Internet或者Intranet上的其它系统中传递过来的请求,轻量级的独立的通讯技术. 是通过SOAP在 Web上提供的软件服务,使用WSDL文件进行说明,并通过UDDI进行注册. ---------------------------------------------------------分割线-----直接演示好了------ 一.打开MyEclipse,新

Java Web应用开发技术简介

java web应用一般定义为:一个有HTML/XML文档,java Servlet,JSP(java Server Pages),JSTL(Java Server Pages Standard Tag Library),类以及其他任何种类文件可以捆绑起来,并在来自多个厂商的多个Web容器上运行的Web资源构成的集合. 一:Java Web应用开发是基于JavaEE框架的,而JavaEE是建立在java平台上的企业级应用的解决方案,所以java web需要javaEE的容器和组件. 1.容器:指

XMPP - 即时通讯技术

XMPP-即时通讯技术简介 (IM -- Instant Messaging)支持用户在线实时交谈.如果要发送一条信息,用户需要打开一个小窗口,以便让用户及其朋友在其中输入信息并让交谈双方都看到交谈的内容 有许多的IM系统,如AOL.Yahoo IM. MSN以及QQ,它们最大的区别在于各自通讯协议的实现,所以即时通讯技术的核心在于它的传输协议 协议用来说明信息在网络上如何传输,如果有了统一的传输协议,那么应当可以实现各个IM之间的直接通讯,为了创建即时通讯的统一标准,目前已经出现过的IM协议包

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

前言 有关IM(InstantMessaging)聊天应用(如:微信,QQ).消息推送技术(如:现今移动端APP标配的消息推送模块)等即时通讯应用场景下,大多数都是桌面应用程序或者native应用较为流行,而网上关于原生IM(相关文章请参见:<IM架构篇>.<IM综合资料>.<IM/推送的通信格式.协议篇>.<IM心跳保活篇>.<IM安全篇>.<实时音视频开发>).消息推送应用(参见:<推送技术好文>)的通信原理介绍也较多

Web端即时通讯技术原理详解

前言 有关IM(InstantMessaging)聊天应用(如:微信,QQ).消息推送技术(如:现今移动端APP标配的消息推送模块)等即时通讯应用场景下,大多数都是桌面应用程序或者native应用较为流行,而网上关于原生IM(相关文章请参见:<IM架构篇>.<IM综合资料>.<IM/推送的通信格式.协议篇>.<IM心跳保活篇>.<IM安全篇>.<实时音视频开发>).消息推送应用(参见:<推送技术好文>)的通信原理介绍也较多

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

摘要 Web端即时通讯技术因受限于浏览器的设计限制,一直以来实现起来并不容易,主流的Web端即时通讯 方案大致有4种:传统Ajax短轮询.Comet技术.WebSocket技术.SSE(Server-sent Events).本文将简要介绍这4种技术的原理,并指出各自的异同点.优缺点等. 1. 前言 Web端即时通讯技术因受限于浏览器的设计限制,一直以来实现起来并不容易,主流的Web端即时通讯方案大致有4种:传统Ajax短轮询. Comet技术.WebSocket技术.SSE(Server-se

JAVA WEB 环境的搭建及所需的技术简介

web 开发,有点头疼,从最初一点一点开始查找,服务器查了好久才知道是什么意思,╮(╯▽╰)╭ 还有,最近再练盲打, 祝我成功咯~ 一.基本概念 1.1.WEB开发的相关知识 WEB,在英语中web即表示网页的意思,它用于表示Internet主机上供外界访问的资源. Internet上供外界访问的Web资源分为: 静态web资源(如html 页面):指web页面中供人们浏览的数据始终是不变. 动态web资源:指web页面中供人们浏览的数据是由程序产生的,不同时间点访问web页面看到的内容各不相同

Python web实时消息服务器后台推送技术方案---GoEasy

Goeasy, 它是一款第三方推送服务平台,使用它的API可以轻松搞定实时推送!个人感觉goeasy推送更稳定,推送速度快,代码简单易懂上手快浏览器兼容性:GoEasy推送支持websocket 和polling两种连接方式,从而可以支持IE6及其以上的所有版本,同时还支持其它浏览器诸如Firefox, Chrome, Safari 等等.支 持不同的开发语言:   GoEasy推送提供了Restful API接口,无论你的后台程序用的是哪种语言都可以通过RestfulAPI来实现后台实时推送.

C(++) web实时消息服务器后台推送技术方案---GoEasy

Goeasy, 它是一款第三方推送服务平台,使用它的API可以轻松搞定实时推送!个人感觉goeasy推送更稳定,推送速度快,代码简单易懂上手快浏览器兼容性:GoEasy推送支持websocket 和polling两种连接方式,从而可以支持IE6及其以上的所有版本,同时还支持其它浏览器诸如Firefox, Chrome, Safari 等等.支 持不同的开发语言:   GoEasy推送提供了Restful API接口,无论你的后台程序用的是哪种语言都可以通过RestfulAPI来实现后台实时推送.