您现在的位置是:亿华云 > 域名
Springboot整合Websocket实现后端向前端主动推送消息案例
亿华云2025-10-09 03:58:35【域名】7人已围观
简介在手机上相信都有来自服务器的推送消息,比如一些及时的新闻信息,这篇文章主要就是实现这个功能,只演示一个基本的案例。使用的是websocket技术。一、什么是websocketWebSocket协议是基
在手机上相信都有来自服务器的整合主动推送消息,比如一些及时的现后消息新闻信息,这篇文章主要就是前端实现这个功能,只演示一个基本的推送案例。使用的案例是websocket技术。
一、整合主动什么是现后消息websocke
tWebSocket协议是基于TCP的一种新的网络协议。它实现了客户端与服务器全双工通信,前端学过计算机网络都知道,推送既然是案例全双工,就说明了服务器可以主动发送信息给客户端。整合主动这与我们的现后消息推送技术或者是多人在线聊天的功能不谋而合。
为什么不使用HTTP 协议呢?前端这是因为HTTP是单工通信,通信只能由客户端发起,推送客户端请求一下,服务器托管案例服务器处理一下,这就太麻烦了。于是websocket应运而生。
下面我们就直接开始使用Springboot开始整合。以下案例都在我自己的电脑上测试成功,你可以根据自己的功能进行修改即可。
二、整合websocket
1、环境配置
Idea 2018专业版(已破解)
Maven 4.0.0
SpringBoot 2.2.2
websocket 2.1.3
jdk 1.8
下面我们新建一个普通的Springboot项目。
2、添加依赖
<dependencies> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-web</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-test</artifactId> <scope>test</scope> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-websocket</artifactId> <version>2.1.3.RELEASE</version> </dependency> </dependencies>3、在application.properties文件修改端口号
一句话:server.port=8081
4、新建config包,创建WebSocketConfig类
1@Configuration 2public class WebSocketConfig { 3 @Bean 4 public ServerEndpointExporter serverEndpointExporter() { 5 return new ServerEndpointExporter(); 6 } 7}5、新建service包,创建WebSocketServer类
@ServerEndpoint("/websocket/{ sid}") @Component public class WebSocketServer { static Log log= LogFactory.getLog(WebSocketServer.class); //静态变量,用来记录当前在线连接数。应该把它设计成线程安全的。 private static int onlineCount = 0; //concurrent包的线程安全Set,用来存放每个客户端对应的MyWebSocket对象。 private static CopyOnWriteArraySet<WebSocketServer> webSocketSet = new CopyOnWriteArraySet<WebSocketServer>(); //与某个客户端的连接会话,需要通过它来给客户端发送数据 private Session session; //接收sid private String sid=""; /** * 连接建立成功调用的高防服务器方法 */ @OnOpen public void onOpen(Session session,@PathParam("sid") String sid) { this.session = session; webSocketSet.add(this); //加入set中 addOnlineCount(); //在线数加1 log.info("有新窗口开始监听:"+sid+",当前在线人数为" + getOnlineCount()); this.sid=sid; try { sendMessage("连接成功"); } catch (IOException e) { log.error("websocket IO异常"); } } /** * 连接关闭调用的方法 */ @OnClose public void onClose() { webSocketSet.remove(this); //从set中删除 subOnlineCount(); //在线数减1 log.info("有一连接关闭!当前在线人数为" + getOnlineCount()); } /** * 收到客户端消息后调用的方法 * @param message 客户端发送过来的消息 */ @OnMessage public void onMessage(String message, Session session) { log.info("收到来自窗口"+sid+"的信息:"+message); //群发消息 for (WebSocketServer item : webSocketSet) { try { item.sendMessage(message); } catch (IOException e) { e.printStackTrace(); } } } @OnError public void onError(Session session, Throwable error) { log.error("发生错误"); error.printStackTrace(); } //实现服务器主动推送 public void sendMessage(String message) throws IOException { this.session.getBasicRemote().sendText(message); } //群发自定义消息 public static void sendInfo(String message,@PathParam("sid") String sid) throws IOException { log.info("推送消息到窗口"+sid+",推送内容:"+message); for (WebSocketServer item : webSocketSet) { try { //这里可以设定只推送给这个sid的,为null则全部推送 if(sid==null) { item.sendMessage(message); }else if(item.sid.equals(sid)){ item.sendMessage(message); } } catch (IOException e) { continue; } } } public static synchronized int getOnlineCount() { return onlineCount; } public static synchronized void addOnlineCount() { WebSocketServer.onlineCount++; } public static synchronized void subOnlineCount() { WebSocketServer.onlineCount--; }6、新建controller包,创建Mycontroller类
@Controller public class MyController { //页面请求 @GetMapping("/socket/{ cid}") public ModelAndView socket(@PathVariable String cid) { ModelAndView mav=new ModelAndView("/socket"); mav.addObject("cid", cid); return mav; } //推送数据接口 @ResponseBody @RequestMapping("/socket/push/{ cid}") public String pushToWeb(@PathVariable String cid,String message) { try { WebSocketServer.sendInfo(message,cid); } catch (IOException e) { e.printStackTrace(); return "推送失败"; } return "发送成功"; } }}7、新建一个websocket.html页面
<html> <head> <meta name="viewport" content="initial-scale=1.0, user-scalable=no" /> <script type="text/javascript"> var socket; if (typeof (WebSocket) == "undefined") { console.log("您的浏览器不支持WebSocket"); } else { console.log("您的浏览器支持WebSocket"); //实现化WebSocket对象,指定要连接的服务器地址与端口 建立连接 socket = new WebSocket("ws://localhost:8081/websocket/1"); //打开事件 socket.onopen = function () { console.log("Socket 已打开"); socket.send("这是来自客户端的消息" + location.href + new Date()); }; //获得消息事件 socket.onmessage = function (msg) { console.log(msg.data); }; //关闭事件 socket.onclose = function () { console.log("Socket已关闭"); }; //发生了错误事件 socket.onerror = function () { alert("Socket发生了错误"); } } </script> </head> </html>现在开发服务器和网页就可以看到效果了。一般情况下Springboot2+Netty+Websocket的组合方式更加的常用一下。这个只是给出了一个基本的案例,你可以根据自己的需求进行更改。
本文转载自微信公众号「愚公要移山」,可以通过以下二维码关注。转载本文请联系愚公要移山公众号。
很赞哦!(88)
热门文章
站长推荐
3、不明先知,根据相关征兆预测可能发生的事件,以便提前做好准备,赶紧注册相关域名。;不差钱域名;buchaqian抢先注册,就是这种敏感类型。预言是最敏感的状态。其次,你应该有眼力。所谓眼力,就是善于从社会上时不时出现的各种热点事件中获取与事件相关的域名资源。眼力的前提是对域名领域的熟悉和丰富的知识。
MySQL转Oracle遇到的问题:表名长度及大小写问题
Async/Await 你是会用,但是你知道怎么处理错误吗?
Golang 语言 Vendor 在 Gopath 和 Modules 中的区别
域后缀首选.com,.net,然后是.cn。后缀选择不当,导致流量损失。域名是企业与互联网网址之间的链接,关键是企业在网络上存在的标志。因此,选择好域名是开展网上工作的首要重要条件。
为啥SQL Profile不起作用了,你知道吗?
如何选择正确的Kubernetes监控工具
国产数据库适合国家标准吗?