server-sent events--One Way Messaging

  

  


  

  允许网页获得来自服务器的更新,并且自动更新

  • Server-Sent Events: allow a web page to get updates from a server
  • This was also possible before, but the web page would have to ask if any updates were available. With server-sent events, the updates come automatically.
  • Examples: Facebook/Twitter updates, stock price updates, news feeds, sport results, etc.

  原理如下:

  1. client利用regular http请求webpage
  2. 请求的webpage 执行javascript脚本,open a connection to server.
  3. 当有新的信息时服务器将信息发送给client

浏览器支持情况:

desktop:

mobile:

使用入门:


receive Server-Sent Event Notifications: (接收Server-sent事件通知)

利用EventSource的onmessage获取消息

EventSource事件如下:

  1. onopen 当服务器连接被打开时 When a connection to the server is opened
  2.  
  3. onmessage 当接收到消息 When a message is received
  4.  
  5. onerror

创建和关闭

  1. var source = new EventSource();
  2.  
  3. source.close();

数据格式:

  1. data: My message\n\n

如果数据比较长时,可以采用多行data:然后使用event.data.split('\n').join('')组合数据

  1. data: first line\n
  2. data: second line\n\n

简单例子:

eg:html页面:

  1. <!DOCTYPE html>
  2. <html>
  3. <head>
  4. <style>
  5. div{
  6. border-radius: 10px;
  7. border: 2px solid pink;
  8. }
  9. </style>
  10. </head>
  11. <body>
  12. <h1></h1>
  13. <div id="result"></div>
  14.  
  15. <script>
  16. if(typeof(EventSource)!=="undefined") //监测是否支持EventSource
  17. {
  18. var source=new EventSource("sseServer.jsp");
  19. source.onmessage=function(event)
  20. {
  21. document.getElementById("result").innerHTML+=event.data + "<br />";
  22. };
  23. }
  24. else
  25. {
  26. document.getElementById("result").innerHTML="Sorry, your browser does not support server-sent events...";
  27. }
  28. </script>
  29.  
  30. </body>
  31. </html>

服务器sseServer.jsp代码:

  1. <%@ page language="java" contentType="text/event-stream; charset=UTF-8"
  2. pageEncoding="UTF-8"%>
  3. <%@ page import="java.util.Date"%>
  4. <%@ page import="java.io.*"%>
  5. <%
  6. Date date = new Date();
  7. System.out.println(date);
  8. response.setContentType("text/event-stream"); //设置contentType
  9. response.setHeader("Cache-Control", "no-cache"); //设置不缓存
  10. response.setHeader("Pragma","no-cache");
  11. response.setDateHeader("Expires",0);
  12. PrintWriter pw = response.getWriter();
  13. pw.print("data: today is "+date.toString()+" wish you happy~~~"); //注意必须以data:开头
  14. pw.flush();
  15. %>

结果:


eg2:传送多行数据:

  1. if(typeof(EventSource)!=="undefined"){
  2. var source=new EventSource("multiLineServer.jsp");
  3. source.onmessage=function(event)
  4. {
  5. document.getElementById("result").innerHTML+=event.data.split('\n').join('') + "<br />";
  6. };
  7.  
  8. }else{
  9. document.getElementById("result").innerHTML="Sorry, your browser does not support server-sent events...";
  10. }
  1. Date date = new Date();
  2. System.out.println(date);
  3. response.setContentType("text/event-stream");
  4. response.setHeader("Cache-Control", "no-cache");
  5. response.setHeader("Pragma","no-cache");
  6. response.setDateHeader("Expires",0);
  7. PrintWriter pw = response.getWriter();
  8. pw.println("data: today is "+date.toString()+" wish you happy~~~");
  9. pw.println("data: have a nice day");
  10. pw.flush();

结果如下:


eg3:以json格式封装数据:

  1. if(typeof(EventSource)!=="undefined"){
  2. var source=new EventSource("jsonServer.jsp");
  3. source.onmessage=function(event)
  4. {
  5.  
  6. var data = JSON.parse(event.data);
  7. document.getElementById("result").innerHTML+="date:"+data.date + "<br />";
  8. document.getElementById("result").innerHTML+="name:"+data.name + "<br />";
  9. };
  10.  
  11. }else{
  12. document.getElementById("result").innerHTML="Sorry, your browser does not support server-sent events...";
  13. }

server:

  1. Date date = new Date();
  2. System.out.println(date);
  3. response.setContentType("text/event-stream");
  4. response.setHeader("Cache-Control", "no-cache");
  5. response.setHeader("Pragma","no-cache");
  6. response.setDateHeader("Expires",0);
  7. PrintWriter pw = response.getWriter();
  8. pw.println("data: {");
  9. pw.println("data: \"date\":\""+date.toString()+"\",");
  10. pw.println("data: \"name\":\"wish\"");
  11. pw.println("data:}");
  12.  
  13. pw.flush();

结果如下:

添加监听事件:

事件如下:

  1. message
  2.  
  3. open
  4.  
  5. error

eg:

  1. if(typeof(EventSource)!=="undefined"){
  2. var source=new EventSource("sseServer.jsp");
  3. source.addEventListener('message',function(event){
  4. //Connection was opended
  5. document.getElementById("result").innerHTML+=event.data + "<br />";
  6.  
  7. },false);
  8. }else{
  9. document.getElementById("result").innerHTML="Sorry, your browser does not support server-sent events...";
  10. }

服务器端代码相同,结果与上例相同:

open和error事件如下:

  1. source.addEventListener('open', function(event) {
  2. // Connection was opened.
  3. }, false);
  4.  
  5. source.addEventListener('error', function(event) {
  6. if (event.readyState == EventSource.CLOSED) {
  7. // Connection was closed.
  8. }
  9. }, false);

 注意:当连接关闭时,浏览器会自动在3秒后重新连接,可以在服务器端设置时间

设置事件id和reconnect time


设置id

在stream前加上id:, 可以让浏览器跟踪最后一次触发的事件,如果服务器死掉时,可以在新的请求设置HTTP header,通过event.lastEventId可以获取该值

eg:

  1. id: 1222\n
  2. data: ...\n

设置reconnection time

默认是在连接关闭3秒后reconnect,可以通过设置stream更改

eg:设置5秒

  1. retry: 50000\n
  2. data: ......\n

自定义事件名称

eg:设置update事件

stream:

  1. event: update\n
  2. data: {"username": "wish", "emotion": "happy"}\n

js:

  1. source.addEventListener('update', function(event) {
  2. var data = JSON.parse(event.data);
  3. console.log(data.username + ' is now ' + data.emotion);
  4. }, false);

Security

在stream中增加origin

  1. source.addEventListener('message', function(event) {
  2. if (event.origin != 'http://cnblogs.com') {
  3. //................
  4. return;
  5. }
  6. ...
  7. }, false);

其他请参考:Cross-document messaging security

polling相关技术比较


Regular http:

  1. client发送请求.
  2. server计算
  3. server sends the response to the client.


AJAX Polling:

  1. client利用regular http请求webpage
  2. 请求的webpage 执行javascript脚本以一定间隔向服务器请求file
  3. server计算每个reqponse,发送给client


AJAX Long-Polling:

  1. client利用regular http请求webpage
  2. 请求的webpage 执行javascript脚本向服务器请求file
  3. 服务器并不立即响应,而是等到有新的信息时才响应
  4. client收到response后立即发送新的请求,重复上面过程


HTML5 Websockets:

  1. client利用regular http请求webpage
  2. 请求的webpage 执行javascript脚本,open a connection to server.
  3. 有新的信息时服务器和客户端可以相互发送信息(Real-time traffic from the server to the client and from the client to the server)

  4. 使用请查看:https://developer.mozilla.org/en-US/docs/WebSockets/Writing_WebSocket_client_applications


Comet:

Comet 是HTML5技术之前使用streaming 和long-polling来实现实时应用程序的技术(Streaming and long polling for responsive communication between your server and client)更多了解http://www.ibm.com/developerworks/web/library/wa-reverseajax1/index.html

Comet is a web application model where a request is sent to the server and kept alive for a long time, until a time-out or a server event occurs. When the request is completed, another long-lived Ajax request is sent to wait for other server events. With Comet, web servers can send the data to the client without having to explicitly request it. 

相关博文:HTML5 Web socket和socket.io

参考:http://www.w3schools.com/html/html5_serversentevents.asp

    http://jaxenter.com/tutorial-jsf-2-and-html5-server-sent-events-42932.html

     http://www.html5rocks.com/en/tutorials/eventsource/basics/

      http://www.whatwg.org/specs/web-apps/current-work/multipage/comms.html#authors

      http://stackoverflow.com/questions/11077857/what-are-long-polling-websockets-server-sent-events-sse-and-comet

    http://www.ibm.com/developerworks/web/library/wa-reverseajax1/index.html

SSE及相关技术(web sockets, long polling等)的更多相关文章

  1. Ajax、Comet、HTML 5 Web Sockets技术比较分析

    最近因为考虑研究B/S结构网站即时消息处理 参考了 JAVA怎么样实现即时消息提醒http://bbs.csdn.net/topics/330015611http://www.ibm.com/deve ...

  2. 关于Web开发里并发、同步、异步以及事件驱动编程的相关技术

    一.开篇语 我的上篇文章<关于如何提供Web服务端并发效率的异步编程技术>又成为了博客园里“编辑推荐”的文章,这是对我写博客很大的鼓励,也许是被推荐的原因很多童鞋在这篇文章里发表了评论,有 ...

  3. Java Web相关技术(汇聚页)

    Java Web相关技术(汇聚页) 初学Java Web(2)——搭建Java Web开发环境

  4. HTML5权威指南--Web Storage,本地数据库,本地缓存API,Web Sockets API,Geolocation API(简要学习笔记二)

    1.Web Storage HTML5除了Canvas元素之外,还有一个非常重要的功能那就是客户端本地保存数据的Web Storage功能. 以前都是用cookies保存用户名等简单信息.   但是c ...

  5. 【原】http缓存与cdn相关技术

    摘要:最近要做这个主题的组内分享,所以准备了一个星期,查了比较多的资料.准备的过程虽然很烦很耗时间,不过因为需要查很多的资料,因此整个过程下来,对这方面的知识影响更加深刻.来来来,接下来总结总结 一 ...

  6. 关于全站https必要性http流量劫持、dns劫持等相关技术

    关于全站https必要性http流量劫持.dns劫持等相关技术 微信已经要求微信支付,申请退款功能必须12月7号之前必须使用https证书了(其他目前为建议使用https),IOS也是2017年1月1 ...

  7. SAAS相关技术要点

    这篇文章本来是我们开发组内部用的一个小文档.因为我们公司以前没有做SAAS的经验,就成立了一个小组做一做这方面的技术前探,我是成员之一.这篇文档想从宏观的层面把开发一个SAAS应用所要用到的技术点稍微 ...

  8. Websocket 与代理服务器如何交互? How HTML5 Web Sockets Interact With Proxy Servers

    How HTML5 Web Sockets Interact With Proxy Servers Posted by Peter Lubberson Mar 16, 2010 With the re ...

  9. http缓存与cdn相关技术

    阅读目录 一 http缓存 二.Http缓存概念解析 三.cdn相关技术 摘要:最近要做这个主题的组内分享,所以准备了一个星期,查了比较多的资料.准备的过程虽然很烦很耗时间,不过因为需要查很多的资料, ...

随机推荐

  1. GIT使用指南

    安装git,svn,ant,maven并配置环境变量 1.拷贝settings.xml到用户目录的.m2目录下. 2.打开git命令行,使用如下命令生成公钥私钥 ssh-keygen -t rsa 3 ...

  2. Java EE 7 / JAX-RS 2.0: Simple REST API Authentication & Authorization with Custom HTTP Header--reference

    REST has made a lot of conveniences when it comes to implementing web services with the already avai ...

  3. uva 1146 Now or late (暴力2-SAT)

    /* 裸地2-SAT问题 关键是模型转化 最小的最大 显然二分 关键是Judge的时候怎么判断 每个航班是早是晚直接影响判断 早晚只能选一个 如果我们定义bool变量xi表示 i航班是否早到 每个航班 ...

  4. Android Service生命周期及用法

    Service概念及用途:Android中的服务,它与Activity不同,它是不能与用户交互的,不能自己启动的,运行在后台的程序,如果我们退出应用时,Service进程并没有结束,它仍然在后台运行, ...

  5. IE8 placeholder兼容+Password兼容

    对于placeholder兼容问题 IE系列的大部分不兼容 使用JQ插件解决这个问题,确实用法很简单 jS下载地址http://www.ijquery.cn/js/jquery.placeholder ...

  6. 跟我一起学CMake

    如今CMake使用的人数越来越多,包括我项目组里,很多大牛们在写Qt程序的时候都不用自带的qmake,貌似会出现很多问题,他们往往都用自己写的CMake来编译系统,今天我也和大家一起来学学这个高大上的 ...

  7. Jquery练手之-贪吃蛇

    记得以前刚出来工作的时候,什么都不懂.老板让用Jquery写一个功能,我不会写,然后跟老板说,我就是个.net程序员,为什么要写Jquery...后面我们老大给我写了!现在我才知道net程序员要会多少 ...

  8. Bootstrap_排版_列表

    一.基本列表 <h5>普通列表</h5> <ul> <li>列表项目</li> <li>列表项目</li> < ...

  9. Linux imagemagic(转载)

    原文地址:http://linux.chinaitlab.com/c/803455.html 更多详细使用示例请参考:http://www.ibm.com/developerworks/cn/open ...

  10. javascript 字符串滚动显示

    <html> <head> <script type="text/javascript"> var chars = "JavaScri ...