WebSocket协议定义了一种web应用的新功能,它实现了服务器端和客户端的全双工通讯。全双工通讯即通讯的双方能够同时发送和接收信息 的信息交互方式。它是继Java applets, XMLHttpRequest, Adobe Flash, ActiveXObject等使web应用更具交互性的新技术。javascript
在实现连线过程当中,浏览器和服务器经过TCP三次握手创建链接。 若是和服务器链接成功后,浏览器经过HTTP发送握手请求,若是服务器赞成握手链接,客户端和服务端以后就能互相之间发送信息。HTTP只用于开始的握手,一旦成功创建握手链接,HTTP不会参与数据传输,使用TCP链接来传输数据。java
轮询web
长轮询就是客户端按照一个固定的时间按期向服务器发送请求,一般这个时间间隔的长度受到服务端的更新频率和客户端处理更新数据时间的影响。这种方式缺点很明显,就是浏览器要不断发请求到服务器以获取最新信息,形成服务器压力过大,占用宽带资源。ajax
使用streaming AJAXspring
streaming ajax是一种经过ajax实现的长链接维持机制。主要目的就是在数据传输过程当中对返回的数据进行读取,而且不会关闭链接。api
iframe方式浏览器
iframe能够在页面中嵌套一个子页面,经过将iframe的src指向一个长链接的请求地址,服务端就能不断往客户端传输数据。服务器
最适合websocket的web应用的就是那些客户端和服务器端须要高频繁、低延迟交换信息的应用。websocket
Spring提供了一个是适应于各类websocket引擎的websocket api,例如是Tomcat (7.0.47+)和GlassFish (4.0+),也适应于支持原生websocket的Jetty (9.0+)。而不一样的浏览器对websocket的支持程度也有所不一样,若是浏览器websocket不支持,那么能够用SocketJs代替websocket。session
建立和配置WebSocketHandler
WebSocketHandler用于处理websocket的消息。
public class MyHandler extends TextWebSocketHandler { @Override public void handleTextMessage(WebSocketSession session, TextMessage message) {
session.sendMessage(message); } }
建立和配置HandshakeInterceptor
HandshakeInterceptor
用于处理握手先后的预处理工做。
public class HandshakeInterceptor extends HttpSessionHandshakeInterceptor { @Override public void afterHandshake(ServerHttpRequest request, ServerHttpResponse response, WebSocketHandler wsHandler, Exception ex) { System.out.println("After Handshake"); super.afterHandshake(request, response, wsHandler, ex); } @Override public boolean beforeHandshake(ServerHttpRequest request, ServerHttpResponse response, WebSocketHandler wsHandler,Map<String, Object> attributes) throws Exception { System.out.println("Before Handshake");
return super.beforeHandshake(request, response, wsHandler, attributes); } }
同时配置spring-websocket.xml
<?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:websocket="http://www.springframework.org/schema/websocket" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/websocket http://www.springframework.org/schema/websocket/spring-websocket.xsd"> <websocket:handlers> <websocket:mapping handler="myHandler" path="/myHandler"/> <websocket:handshake-interceptors> <bean class="org.springframework.samples.HandshakeInterceptor"></bean> </websocket:handshake-interceptors> </websocket:handlers> <!--兼容低版本浏览器--> <websocket:handlers> <websocket:mapping handler="myHandler" path="/js/myHandler"/> <websocket:handshake-interceptors> <bean class="org.springframework.samples.HandshakeInterceptor"></bean> </websocket:handshake-interceptors> <websocket:sockjs /> </websocket:handlers> <bean id="myHandler" class="org.springframework.samples.MyHandler"></bean> </beans>
在页面上添加JavaScript
<script type="text/javascript" src="js/sockjs.min.js"></script> <script type="text/javascript"> //websocket-demo是project name var sock=null; if (window['WebSocket']) { sock= new WebSocket('ws://' + window.location.host+'/websocket-demo/myHandler'); } else sock= new SockJS('/websocket-demo/js/myHandler');//兼容低版本浏览器 sock.onopen = function() { console.log('Opening'); sayHello(); }; sock.onmessage = function(e) { alert('Received message: '+ e.data); }; sock.onclose = function() { console.log('Closing'); }; function sayHello() { console.log('Sending Hello!'); sock.send("Hello!"); } </script>
若是要兼容低版本浏览器,还要在web.xml添加
<async-supported>true</async-supported>
须要注意的地方:
一、应用服务器的版本,若是版本太低是不支持websocket的
二、JavaScript的websocket的url应该和spring-websocket.xml的<websocket:mapping path="">一致
三、要兼容低版本浏览器,要使用web3.0,还有必须在一个请求涉及的全部Servlet及Filter中都声明asyncSupported=true。