SpringMVC整合websocket實現(xiàn)消息推送及觸發(fā)功能
本文為大家分享了SpringMVC整合websocket實現(xiàn)消息推送,供大家參考,具體內(nèi)容如下
1.創(chuàng)建websocket握手協(xié)議的后臺
(1)HandShake的實現(xiàn)類
/**
*Project Name: price
*File Name: HandShake.java
*Package Name: com.yun.websocket
*Date: 2016年9月3日 下午4:44:27
*Copyright (c) 2016,578888218@qq.com All Rights Reserved.
*/
package com.yun.websocket;
import java.util.Map;
import org.springframework.http.server.ServerHttpRequest;
import org.springframework.http.server.ServerHttpResponse;
import org.springframework.http.server.ServletServerHttpRequest;
import org.springframework.web.socket.WebSocketHandler;
import org.springframework.web.socket.server.HandshakeInterceptor;
/**
*Title: HandShake<br/>
*Description:
*@Company: 青島勵圖高科<br/>
*@author: 劉云生
*@version: v1.0
*@since: JDK 1.7.0_80
*@Date: 2016年9月3日 下午4:44:27 <br/>
*/
public class HandShake implements HandshakeInterceptor{
@Override
public boolean beforeHandshake(ServerHttpRequest request, ServerHttpResponse response, WebSocketHandler wsHandler,
Map<String, Object> attributes) throws Exception {
// TODO Auto-generated method stub
String jspCode = ((ServletServerHttpRequest) request).getServletRequest().getParameter("jspCode");
// 標記用戶
//String userId = (String) session.getAttribute("userId");
if(jspCode!=null){
attributes.put("jspCode", jspCode);
}else{
return false;
}
return true;
}
@Override
public void afterHandshake(ServerHttpRequest request, ServerHttpResponse response, WebSocketHandler wsHandler,
Exception exception) {
// TODO Auto-generated method stub
}
}
(2)MyWebSocketConfig的實現(xiàn)類
/**
*Project Name: price
*File Name: MyWebSocketConfig.java
*Package Name: com.yun.websocket
*Date: 2016年9月3日 下午4:52:29
*Copyright (c) 2016,578888218@qq.com All Rights Reserved.
*/
package com.yun.websocket;
import javax.annotation.Resource;
import org.springframework.stereotype.Component;
import org.springframework.web.servlet.config.annotation.EnableWebMvc;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurerAdapter;
import org.springframework.web.socket.config.annotation.EnableWebSocket;
import org.springframework.web.socket.config.annotation.WebSocketConfigurer;
import org.springframework.web.socket.config.annotation.WebSocketHandlerRegistry;
/**
*Title: MyWebSocketConfig<br/>
*Description:
*@Company: 青島勵圖高科<br/>
*@author: 劉云生
*@version: v1.0
*@since: JDK 1.7.0_80
*@Date: 2016年9月3日 下午4:52:29 <br/>
*/
@Component
@EnableWebMvc
@EnableWebSocket
public class MyWebSocketConfig extends WebMvcConfigurerAdapter implements WebSocketConfigurer{
@Resource
MyWebSocketHandler handler;
@Override
public void registerWebSocketHandlers(WebSocketHandlerRegistry registry) {
// TODO Auto-generated method stub
registry.addHandler(handler, "/wsMy").addInterceptors(new HandShake());
registry.addHandler(handler, "/wsMy/sockjs").addInterceptors(new HandShake()).withSockJS();
}
}
(3)MyWebSocketHandler的實現(xiàn)類
/**
*Project Name: price
*File Name: MyWebSocketHandler.java
*Package Name: com.yun.websocket
*Date: 2016年9月3日 下午4:55:12
*Copyright (c) 2016,578888218@qq.com All Rights Reserved.
*/
package com.yun.websocket;
import java.io.IOException;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;
import java.util.Map.Entry;
import org.springframework.stereotype.Component;
import org.springframework.web.socket.CloseStatus;
import org.springframework.web.socket.TextMessage;
import org.springframework.web.socket.WebSocketHandler;
import org.springframework.web.socket.WebSocketMessage;
import org.springframework.web.socket.WebSocketSession;
import com.google.gson.GsonBuilder;
/**
*Title: MyWebSocketHandler<br/>
*Description:
*@Company: 青島勵圖高科<br/>
*@author: 劉云生
*@version: v1.0
*@since: JDK 1.7.0_80
*@Date: 2016年9月3日 下午4:55:12 <br/>
*/
@Component
public class MyWebSocketHandler implements WebSocketHandler{
public static final Map<String, WebSocketSession> userSocketSessionMap;
static {
userSocketSessionMap = new HashMap<String, WebSocketSession>();
}
@Override
public void afterConnectionEstablished(WebSocketSession session) throws Exception {
// TODO Auto-generated method stub
String jspCode = (String) session.getHandshakeAttributes().get("jspCode");
if (userSocketSessionMap.get(jspCode) == null) {
userSocketSessionMap.put(jspCode, session);
}
for(int i=0;i<10;i++){
//broadcast(new TextMessage(new GsonBuilder().create().toJson("\"number\":\""+i+"\"")));
session.sendMessage(new TextMessage(new GsonBuilder().create().toJson("\"number\":\""+i+"\"")));
}
}
@Override
public void handleMessage(WebSocketSession session, WebSocketMessage<?> message) throws Exception {
// TODO Auto-generated method stub
//Message msg=new Gson().fromJson(message.getPayload().toString(),Message.class);
//msg.setDate(new Date());
// sendMessageToUser(msg.getTo(), new TextMessage(new GsonBuilder().setDateFormat("yyyy-MM-dd HH:mm:ss").create().toJson(msg)));
session.sendMessage(message);
}
@Override
public void handleTransportError(WebSocketSession session, Throwable exception) throws Exception {
// TODO Auto-generated method stub
if (session.isOpen()) {
session.close();
}
Iterator<Entry<String, WebSocketSession>> it = userSocketSessionMap
.entrySet().iterator();
// 移除Socket會話
while (it.hasNext()) {
Entry<String, WebSocketSession> entry = it.next();
if (entry.getValue().getId().equals(session.getId())) {
userSocketSessionMap.remove(entry.getKey());
System.out.println("Socket會話已經(jīng)移除:用戶ID" + entry.getKey());
break;
}
}
}
@Override
public void afterConnectionClosed(WebSocketSession session, CloseStatus closeStatus) throws Exception {
// TODO Auto-generated method stub
System.out.println("Websocket:" + session.getId() + "已經(jīng)關(guān)閉");
Iterator<Entry<String, WebSocketSession>> it = userSocketSessionMap
.entrySet().iterator();
// 移除Socket會話
while (it.hasNext()) {
Entry<String, WebSocketSession> entry = it.next();
if (entry.getValue().getId().equals(session.getId())) {
userSocketSessionMap.remove(entry.getKey());
System.out.println("Socket會話已經(jīng)移除:用戶ID" + entry.getKey());
break;
}
}
}
@Override
public boolean supportsPartialMessages() {
// TODO Auto-generated method stub
return false;
}
/**
* 群發(fā)
* @Title: broadcast
* @Description: TODO
* @param: @param message
* @param: @throws IOException
* @return: void
* @author: 劉云生
* @Date: 2016年9月10日 下午4:23:30
* @throws
*/
public void broadcast(final TextMessage message) throws IOException {
Iterator<Entry<String, WebSocketSession>> it = userSocketSessionMap
.entrySet().iterator();
// 多線程群發(fā)
while (it.hasNext()) {
final Entry<String, WebSocketSession> entry = it.next();
if (entry.getValue().isOpen()) {
new Thread(new Runnable() {
public void run() {
try {
if (entry.getValue().isOpen()) {
entry.getValue().sendMessage(message);
}
} catch (IOException e) {
e.printStackTrace();
}
}
}).start();
}
}
}
/**
* 給所有在線用戶的實時工程檢測頁面發(fā)送消息
*
* @param message
* @throws IOException
*/
public void sendMessageToJsp(final TextMessage message,String type) throws IOException {
Iterator<Entry<String, WebSocketSession>> it = userSocketSessionMap
.entrySet().iterator();
// 多線程群發(fā)
while (it.hasNext()) {
final Entry<String, WebSocketSession> entry = it.next();
if (entry.getValue().isOpen() && entry.getKey().contains(type)) {
new Thread(new Runnable() {
public void run() {
try {
if (entry.getValue().isOpen()) {
entry.getValue().sendMessage(message);
}
} catch (IOException e) {
e.printStackTrace();
}
}
}).start();
}
}
}
}
2.創(chuàng)建websocket握手處理的前臺
<script>
var path = '<%=basePath%>';
var userId = 'lys';
if(userId==-1){
window.location.href="<%=basePath2%>" rel="external nofollow" ;
}
var jspCode = userId+"_AAA";
var websocket;
if ('WebSocket' in window) {
websocket = new WebSocket("ws://" + path + "wsMy?jspCode=" + jspCode);
} else if ('MozWebSocket' in window) {
websocket = new MozWebSocket("ws://" + path + "wsMy?jspCode=" + jspCode);
} else {
websocket = new SockJS("http://" + path + "wsMy/sockjs?jspCode=" + jspCode);
}
websocket.onopen = function(event) {
console.log("WebSocket:已連接");
console.log(event);
};
websocket.onmessage = function(event) {
var data = JSON.parse(event.data);
console.log("WebSocket:收到一條消息-norm", data);
alert("WebSocket:收到一條消息");
};
websocket.onerror = function(event) {
console.log("WebSocket:發(fā)生錯誤 ");
console.log(event);
};
websocket.onclose = function(event) {
console.log("WebSocket:已關(guān)閉");
console.log(event);
}
</script>
3.通過Controller調(diào)用進行websocket的后臺推送
/**
*Project Name: price
*File Name: GarlicPriceController.java
*Package Name: com.yun.price.garlic.controller
*Date: 2016年6月23日 下午3:23:46
*Copyright (c) 2016,578888218@qq.com All Rights Reserved.
*/
package com.yun.price.garlic.controller;
import java.io.IOException;
import java.util.Date;
import java.util.List;
import javax.annotation.Resource;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpSession;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.context.request.RequestContextHolder;
import org.springframework.web.context.request.ServletRequestAttributes;
import org.springframework.web.servlet.ModelAndView;
import org.springframework.web.socket.TextMessage;
import com.google.gson.GsonBuilder;
import com.yun.common.entity.DataGrid;
import com.yun.price.garlic.dao.entity.GarlicPrice;
import com.yun.price.garlic.model.GarlicPriceModel;
import com.yun.price.garlic.service.GarlicPriceService;
import com.yun.websocket.MyWebSocketHandler;
/**
* Title: GarlicPriceController<br/>
* Description:
*
* @Company: 青島勵圖高科<br/>
* @author: 劉云生
* @version: v1.0
* @since: JDK 1.7.0_80
* @Date: 2016年6月23日 下午3:23:46 <br/>
*/
@Controller
public class GarlicPriceController {
@Resource
MyWebSocketHandler myWebSocketHandler;
@RequestMapping(value = "GarlicPriceController/testWebSocket", method ={RequestMethod.POST,RequestMethod.GET}, produces = "application/json; charset=utf-8")
@ResponseBody
public String testWebSocket() throws IOException{
myWebSocketHandler.sendMessageToJsp(new TextMessage(new GsonBuilder().create().toJson("\"number\":\""+"GarlicPriceController/testWebSocket"+"\"")), "AAA");
return "1";
}
}
4.所用到的jar包
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-websocket</artifactId>
<version>4.0.1.RELEASE</version>
</dependency>
5.運行的環(huán)境
至少tomcat8.0以上版本,否則可能報錯
以上就是本文的全部內(nèi)容,希望對大家的學習有所幫助,也希望大家多多支持腳本之家。
相關(guān)文章
IDEA?mybatis?Mapper.xml報紅的最新解決辦法
這篇文章主要介紹了IDEA?mybatis?Mapper.xml報紅的解決辦法,本文給大家介紹的非常詳細,對大家的學習或工作具有一定的參考借鑒價值,需要的朋友可以參考下2023-04-04
Java實現(xiàn)圖片上文字內(nèi)容的動態(tài)修改的操作步驟
在數(shù)字圖像處理領(lǐng)域,Java提供了強大的庫來處理圖片,包括讀取、修改和寫入圖片,如果你需要在Java應(yīng)用程序中修改圖片上的文字內(nèi)容,可以通過圖像處理技術(shù)來實現(xiàn),這篇博文將介紹如何使用Java實現(xiàn)圖片上文字內(nèi)容的動態(tài)修改,需要的朋友可以參考下2024-07-07
Java8 使用工廠方法supplyAsync創(chuàng)建CompletableFuture實例
這篇文章主要介紹了Java8 使用工廠方法supplyAsync創(chuàng)建CompletableFuture實例,具有很好的參考價值,希望對大家有所幫助。如有錯誤或未考慮完全的地方,望不吝賜教2021-11-11
淺談springMVC接收前端json數(shù)據(jù)的總結(jié)
下面小編就為大家分享一篇淺談springMVC接收前端json數(shù)據(jù)的總結(jié),具有很好的參考價值,希望對大家有所幫助。一起跟隨小編過來看看吧2018-03-03
minio的下載和springboot整合minio使用方法
本文介紹了如何通過Docker拉取MinIO鏡像,并創(chuàng)建MinIO容器的過程,首先,需要在本地創(chuàng)建/data和/conf兩個目錄用于掛載MinIO的數(shù)據(jù)和配置文件,接下來,通過docker?run命令啟動容器,設(shè)置MinIO的訪問端口、用戶名、密碼等信息,感興趣的朋友一起看看吧2024-09-09
Java日期接收報錯:could?not?be?parsed,?unparsed?text?found?a
在做Java開發(fā)時肯定會碰到傳遞時間參數(shù)的情況,這篇文章主要給大家介紹了關(guān)于Java日期接收報錯:could?not?be?parsed,?unparsed?text?found?at?index?10的解決辦法,文中通過代碼介紹的非常詳細,需要的朋友可以參考下2024-01-01

