日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

spring WebSocket详解

發布時間:2024/4/13 编程问答 21 豆豆
生活随笔 收集整理的這篇文章主要介紹了 spring WebSocket详解 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

場景

websocket是Html5新增加特性之一,目的是瀏覽器與服務端建立全雙工的通信方式, 解決http請求-響應帶來過多的資源消耗,同時對特殊場景應用提供了全新的實現方式, 比如聊天、股票交易、游戲等對對實時性要求較高的行業領域。

背景

在瀏覽器中通過http僅能實現單向的通信,HTML5定義了WebSocket協議, 能更好的節省服務器資源和帶寬并達到實時通訊。目前各大主流瀏覽器都支持websocket,IE瀏覽器要IE10+

一、POM依賴

POM依賴,spring4.1.4.RELEASE,spring核心依賴請自行添加,下面是websocket相關jar <dependency><groupId>javax.websocket</groupId><artifactId>javax.websocket-api</artifactId><version>1.0</version><scope>provided</scope> </dependency> <dependency><groupId>org.springframework</groupId><artifactId>spring-websocket</artifactId><version>4.1.4.RELEASE</version> </dependency>

二、WebSocket入口

@Configuration @EnableWebMvc @EnableWebSocket public class WebSocketConfig extends WebMvcConfigurerAdapter implements WebSocketConfigurer {@Overridepublic void registerWebSocketHandlers(WebSocketHandlerRegistry registry) {//允許連接的域,只能以http或https開頭String[] allowsOrigins = {"http://www.xxx.com"};//WebIM WebSocket通道registry.addHandler(chatWebSocketHandler(),"/ webSocketIMServer").setAllowedOrigins(allowsOrigins).addInterceptors(myInterceptor());registry.addHandler(chatWebSocketHandler(), "/sockjs/w ebSocketIMServer").setAllowedOrigins(allowsOrigins).addInterceptors(myInterceptor()).withSockJS();}@Beanpublic ChatWebSocketHandler chatWebSocketHandler() {return new ChatWebSocketHandler();}@Beanpublic WebSocketHandshakeInterceptor myInterceptor(){return new WebSocketHandshakeInterceptor();} } 1.實現WebSocketConfigurer接口,重寫registerWebSocketHandlers方法,這是一個核心實現方法, 配置websocket入口,允許訪問的域、注冊Handler、SockJs支持和攔截器。 2.registry.addHandler注冊和路由的功能,當客戶端發起websocket連接,把/path交給對應的handler 處理,而不實現具體的業務邏輯,可以理解為收集和任務分發中心。 3.setAllowedOrigins(String[] domains),允許指定的域名或IP(含端口號)建立長連接,如果只允許 自家域名訪問,這里輕松設置。如果不限時使用"*"號,如果指定了域名,則必須要以http或https開頭。 4.addInterceptors,顧名思義就是為handler添加攔截器,可以在調用handler前后加入我們自己的邏輯代碼。 5.spring websocket也支持STOMP協議,下回再分享。

三、攔截器實現

public class WebSocketHandshakeInterceptor implements HandshakeInterceptor {@Overridepublic boolean beforeHandshake(ServerHttpRequest request, ServerHttpResponse response, WebSocketHandler wsHandler, Map<String, Object> attributes) throws Exception {if (request instanceof ServletServerHttpRequest) {attributes.put("username",userName);}return true;}@Overridepublic void afterHandshake(ServerHttpRequest request, ServerHttpResponse response, WebSocketHandler wsHandler, Exception exception) {} } beforeHandshake,在調用handler前處理方法。常用在注冊用戶信息,綁定WebSocketSession, 在handler里根據用戶信息獲取WebSocketSession發送消息。

四、Handler處理類

public class ChatWebSocketHandler extends TextWebSocketHandler{private final static List<WebSocketSession> sessions = Collections.synchronizedList(new ArrayList<WebSocketSession>());//接收文本消息,并發送出去@Overrideprotected void handleTextMessage(WebSocketSession session, TextMessage message) throws Exception {chatTextMessageHandler(message.getPayload());super.handleTextMessage(session, message);}//連接建立后處理@SuppressWarnings("unchecked")@Overridepublic void afterConnectionEstablished(WebSocketSession session) throws Exception {logger.debug("connect to the websocket chat success......");sessions.add(session);//處理離線消息}//拋出異常時處理@Overridepublic void handleTransportError(WebSocketSession session, Throwable exception) throws Exception {if(session.isOpen()){session.close();}logger.debug("websocket chat connection closed......");sessions.remove(session);}//連接關閉后處理@Overridepublic void afterConnectionClosed(WebSocketSession session, CloseStatus closeStatus) throws Exception {logger.debug("websocket chat connection closed......");sessions.remove(session);}@Overridepublic boolean supportsPartialMessages() {return false;} }

五、客戶端連接

var host = window.location.host; var websocket; if ('WebSocket' in window) {websocket = new ReconnectingWebSocket("ws://"+ host + "/webSocketIMServer", null, {debug:true, maxReconnectAttempts:4}); } else if ('MozWebSocket' in window) {websocket = new MozWebSocket("ws://" + host+ "/webSocketIMServer"); } else {websocket = new SockJS("http://" + host+ "/sockjs/webSocketIMServer"); } websocket.onopen = function(evnt) {console.log("websocket連接上"); }; websocket.onmessage = function(evnt) {messageHandler(evnt.data); }; websocket.onerror = function(evnt) {console.log("websocket錯誤"); }; websocket.onclose = function(evnt) {console.log("websocket關閉"); }

================================================================================================

spring對websocket的集成和使用

WebSocket是HTML5提出的一個用于通信的協議規范,該協議通過一個握手機制, 在客戶端和服務端之間建立一個類似于TCP的連接,從而方便客戶端和服務端之間的通信。WebSocket協議本質上是一個基于TCP的協議,是先通過HTTP/HTTPS協議發起一條特殊的HTTP請求進行握手后 創建一個用于交換數據的TCP連接,此后服務端與客戶端通過此TCP連接進行實時通信。websocket是建立在物理層上的連接,相比于基于網絡層的長連接可以節約資源, 相比于AJAX輪詢可以降低服務器壓力。spring在4.0后將websocket集成進去,要使用spring的websocket的話,spring的版本要在4.0及以上。

spring使用websocket需要的jar(pom.xml)

<dependency><groupId>org.springframework</groupId><artifactId>spring-websocket</artifactId><version>4.0.6.RELEASE</version> </dependency> <dependency><groupId>org.springframework</groupId><artifactId>spring-messaging</artifactId><version>4.0.6.RELEASE</version> </dependency>

web.xml中對websocket的配置

  <servlet> <servlet-name>springMVC</servlet-name> <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class> <init-param><param-name>contextConfigLocation</param-name><param-value>classpath:/springMVC/spring-webSocket.xml</param-value></init-param><load-on-startup>1</load-on-startup> <async-supported>true</async-supported></servlet> <servlet-mapping> <servlet-name>springMVC</servlet-name> <url-pattern>/</url-pattern> </servlet-mapping>

springMVC中對websocket的xml配置

<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-4.0.xsd http://www.springframework.org/schema/websockethttp://www.springframework.org/schema/websocket/spring-websocket-4.0.xsd"><!-- websocket處理類 --><bean id="msgHandler" class="com.test.websocket.MyWebSocketHandler" /><!-- 握手接口/攔截器 ,看項目需求是否需要--><bean id="handshakeInterceptor" class="com.test.websocket.MyHandshakeInterceptor" /><websocket:handlers><websocket:mapping path="/websocket" handler="msgHandler" /><websocket:handshake-interceptors><ref bean="handshakeInterceptor" /></websocket:handshake-interceptors></websocket:handlers><!-- 注冊 sockJS,sockJs是spring對不能使用websocket協議的客戶端提供一種模擬 --><websocket:handlers><websocket:mapping path="/sockjs/websocket" handler="msgHandler" /><websocket:handshake-interceptors><ref bean="handshakeInterceptor" /></websocket:handshake-interceptors><websocket:sockjs /></websocket:handlers> </beans>

springMVC中對websocket的注解配置

@Configuration @EnableWebSocket public class WebSocketServerConfig implements WebSocketConfigurer {@Overridepublic void registerWebSocketHandlers(WebSocketHandlerRegistry registry) {// 添加攔截地址以及相應的websocket消息處理器WebSocketHandlerRegistration registration = registry.addHandler(new MyWebSocketHandler(), "/websocket","sockjs/websocket");SockJsServiceRegistration sockJS = registration.withSockJS();// 添加攔截器registration.addInterceptors(new MyHandshakeInterceptor());}}

握手攔截器,繼承HttpSessionHandshakeInterceptor類,做一些連接握手或者握手后的一些處理

public class MyHandshakeInterceptor extends HttpSessionHandshakeInterceptor {// 握手前@Overridepublic boolean beforeHandshake(ServerHttpRequest request,ServerHttpResponse response, WebSocketHandler wsHandler,Map<String, Object> attributes) throws Exception {System.out.println("++++++++++++++++ HandshakeInterceptor: beforeHandshake ++++++++++++++"+ attributes);return super.beforeHandshake(request, response, wsHandler, attributes);}// 握手后@Overridepublic void afterHandshake(ServerHttpRequest request,ServerHttpResponse response, WebSocketHandler wsHandler,Exception ex) {System.out.println("++++++++++++++++ HandshakeInterceptor: afterHandshake ++++++++++++++");super.afterHandshake(request, response, wsHandler, ex);} }

創建MyWebSocketHandler類繼承WebSocketHandler類(Spring提供的有AbstractWebSocketHandler類、TextWebSocketHandler類、BinaryWebSocketHandler類,看自己需要進行繼承),該類主要是用來處理消息的接收和發送

public class MyWebSocketHandler implements WebSocketHandler {private Logger logger = LoggerFactory.getLogger(MsgWebSocketHandler.class);//保存用戶鏈接private static ConcurrentHashMap<String, WebSocketSession> users = new ConcurrentHashMap<String, WebSocketSession>();// 連接 就緒時@Overridepublic void afterConnectionEstablished(WebSocketSession session)throws Exception {users.put(session.getId(), session);}// 處理信息@Overridepublic void handleMessage(WebSocketSession session,WebSocketMessage<?> message) throws Exception {System.err.println(session + "---->" + message + ":"+ message.getPayload().toString());}// 處理傳輸時異常@Overridepublic void handleTransportError(WebSocketSession session,Throwable exception) throws Exception {}// 關閉 連接時@Overridepublic void afterConnectionClosed(WebSocketSession session,CloseStatus closeStatus) {logger.debug("用戶: " + session.getRemoteAddress() + " is leaving, because:" + closeStatus);}//是否支持分包@Overridepublic boolean supportsPartialMessages() {return false;} }

要進行發送消息的操作,自己可以寫方法,利用保存的已經完成連接的WebSocketSession,通過調用sendMessage(WebScoketMessage<?> message)方法進行消息的發送,參數message是發送的消息內容,Spring提供的類型有TextMessage、BinaryMessage、PingMessage、PongMessage。

前端客戶端JS

<!DOCTYPE html> <html lang="en"> <head><meta charset="UTF-8"><title>websocket</title> </head> <style type="text/css">#div {color: red;} </style> <body><h1>WEBSOCKET----TEST</h1><div id="div"></div> </script> <script type="text/javascript"> var div = document.getElementById('div'); var socket = new WebSocket('ws://127.0.0.1:8088/websocket'); socket.onopen = function(event){console.log(event);socket.send('websocket client connect test'); }socket.onclose = function(event){console.log(event); }socket.onerror = function(event){console.log(event); }socket.onmessage = function(event){console.log(event)div.innerHTML += (' @_@ ' + event.data + ' ~_~ '); } </script> </body> </html>

?

總結

以上是生活随笔為你收集整理的spring WebSocket详解的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。