asp.net html5 sse,SSE和WebSocket的用法和比较

在我们日常开发中,会遇到服务端和客户端的通讯,今天我们就来比较一下HTML5新特性SSE和WebSocket的用法。

一,SSE

简介

SSE(Server-Sent Events,服务器发送事件)是围绕只读Comet 交互推出的API 或者模式。

SSE API允许网页获得来自服务器的更新(HTML5),用于创建到服务器的单向连接,服务器通过这个连接可以发送任意数量的数据。服务器响应的MIME类型必须是text/event-stream,而且是浏览器中的JavaScript API 能解析格式输出。SSE 支持短轮询、长轮询和HTTP 流,而且能在断开连接时自动确定何时重新连接。

客户端

//判断是否支持SSE

if('EventSource' in window){

//初始化SSE

var url="http:localhost:8080/test/push";

var source=new EventSource(url);

//开启时调用

source.onopen=(event)=>{

console.log("开启SSE");

}

//监听message事件

source.onmessage=(event)=>{

var data=event.data;

$("body").append($("

").text(data));

}

//监听like事件

source.addEventListener('like',function(event){

var data=event.data;

$("body").append($("

").text(data));

},false);

//发生异常时调用

source.οnerrοr=(event)=>{

console.log(event);

}

客户端只需要直接使用**window.EventSource**对象,然后调用该对象的相应方法即可。

服务端

/**

* SSE后台controller

* @author like

*

*/

@Controller

@RequestMapping(value="/test")

public class TestSSEController {

@ResponseBody

@RequestMapping(value="/push",produces="text/event-stream;charset=UTF-8")

public String push(HttpServletResponse res){

res.setHeader("Access-Control-Allow-Origin","*");

Date date=new Date();

SimpleDateFormat sdf=new SimpleDateFormat("YYYY-MM-dd HH:mm:ss");

String nowDate=sdf.format(date);

return "data: 我是一个data 现在时间是"+nowDate+" \nevent:like\n retry:5000\n\n";

}

}

由于SSE是http请求,但是又限定是一个长连接,所以要设置MIME类型为text/event-stream。返回的为字符串。

消息的格式

服务器向浏览器发送的 SSE 数据,必须是 UTF-8 编码的文本;

每一次发送的信息,由若干个message组成,每个message之间用\n\n分隔。每个message内部由若干行组成;

格式

[field]:value\n

其中field可以为四种

data

event

id

retry

data代表数据,event代表事件名称,id代表id,retry代表多少时间轮训一次。

所以我的服务端写的消息就可以翻译为:事件名称为**like**,数据为**我是一个data 现在时间是+当前时间**,每5秒轮训一次

data: 我是一个data 现在时间是"+nowDate+" \nevent:like\n retry:5000\n\n

下面是接收消息:

b9cd44ae2d622e9e6a74e3d0f7437113.png

二,Websocket

简介

WebSocket是HTML5开始提供的一种在单个 TCP 连接上进行全双工通讯的协议。

客户端

var websocket = null;

//判断当前浏览器是否支持WebSocket

if ('WebSocket' in window) {

websocket = new WebSocket("ws://localhost:8080/WebSocketTest/websocket");

}

else {

alert('当前浏览器 Not support websocket')

}

//连接发生错误的回调方法

websocket.onerror = function () {

setMessageInnerHTML("WebSocket连接发生错误");

};

//连接成功建立的回调方法

websocket.onopen = function () {

setMessageInnerHTML("WebSocket连接成功");

}

//接收到消息的回调方法

websocket.onmessage = function (event) {

setMessageInnerHTML(event.data);

}

//连接关闭的回调方法

websocket.onclose = function () {

setMessageInnerHTML("WebSocket连接关闭");

}

//监听窗口关闭事件,当窗口关闭时,主动去关闭websocket连接,防止连接还没断开就关闭窗口,server端会抛异常。

window.onbeforeunload = function () {

closeWebSocket();

}

//将消息显示在网页上

function setMessageInnerHTML(innerHTML) {

document.getElementById('message').innerHTML += innerHTML + '
';

}

//关闭WebSocket连接

function closeWebSocket() {

websocket.close();

}

//发送消息

function send() {

var message = document.getElementById('text').value;

websocket.send(message);

}

可以看到客户端直接调用ws地址就可以了。

服务端

/**

* websocket服务

* @author like

*

*/

@ServerEndpoint("/websocket")

public class WebsocketTest {

private static int onlineCount=0;//记录当前在线人数

//确保线程安全

private static CopyOnWriteArraySet webSocketSet=new CopyOnWriteArraySet();

private Session session;

@OnOpen

public void onOpen(Session session){

this.session=session;

webSocketSet.add(this);

addOnlineCount();

System.out.println("有新连接加入!当前在线人数为" + getOnlineCount());

}

@OnClose

public void OnClose(){

webSocketSet.remove(this); //从set中删除

subOnlineCount(); //在线数减1

System.out.println("有一连接关闭!当前在线人数为" + getOnlineCount());

}

@OnMessage

public void OnMessage(String message, Session session){

System.out.println("来自客户端的消息:" + message);

//群发消息

for(WebsocketTest item: webSocketSet){

try {

item.sendMessage(message);

} catch (IOException e) {

e.printStackTrace();

continue;

}

}

}

@OnError

public void OnError(Session session, Throwable error){

System.out.println("发生错误");

error.printStackTrace();

}

public void sendMessage(String message) throws IOException{

this.session.getBasicRemote().sendText(message);

//this.session.getAsyncRemote().sendText(message);

}

public static synchronized int getOnlineCount() {

return onlineCount;

}

public static synchronized void addOnlineCount() {

WebsocketTest.onlineCount++;

}

public static synchronized void subOnlineCount() {

WebsocketTest.onlineCount--;

}

}

演示

1abfc897382c7db23b71a99d71adf9a9.png

后台输出:

有新连接加入!当前在线人数为1

来自客户端的消息:123

来自客户端的消息:456

三,总结

SSE与WebSocket有相似功能,都是用来建立浏览器与服务器之间的通信渠道。两者的区别在于:

WebSocket是全双工通道,可以双向通信,功能更强;SSE是单向通道,只能服务器向浏览器端发送。

WebSocket是一个新的协议,需要服务器端支持;SSE则是部署在 HTTP协议之上的,现有的服务器软件都支持。

SSE是一个轻量级协议,相对简单;WebSocket是一种较重的协议,相对复杂。

SSE默认支持断线重连,WebSocket则需要额外部署。

SSE支持自定义发送的数据类型。

SSE不支持CORS 参数url就是服务器网址,必须与当前网页的网址在同一个网域(domain),而且协议和端口都必须相同。

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值