zoukankan      html  css  js  c++  java
  • springboot2 -广播式WebSocket

    1.WebSocket,STOMP,SockJS含义

    WebSocket:WebSocket是HTML5开始提供的一种在单个 TCP 连接上进行全双工通讯的协议。

    SockJS:SockJS 是 WebSocket 技术的一种模拟。为了应对许多浏览器不支持WebSocket协议的问题,设计了备选SockJs。开启并使SockJS后,它会优先选用Websocket协议作为传输协议,如果浏览器不支持Websocket协议,则会在其他方案中,选择一个较好的协议进行通讯。

    STOMP:用于定义websocket的消息体格式.

    2.springboot代码

    定义websocket传输消息的内容格式。

    浏览器向服务端发送消息:

    package com.dyq.demo.DTO;
    
    public class SocketRequestMessage {
        private String requestMessage;
    
        public String getRequestMessage() {
            return requestMessage;
        }
    }

    服务端向浏览器发送消息:

    package com.dyq.demo.DTO;
    
    public class SocketResponseMessage {
        private String responseMessage;
    
        public SocketResponseMessage(String responseMessage){
            this.responseMessage = responseMessage;
        }
    
        public String getResponseMessage() {
            return responseMessage;
        }
    }

    WebSocket配置文件:

    package com.dyq.demo.config;
    
    import org.springframework.context.annotation.Configuration;
    import org.springframework.messaging.simp.config.MessageBrokerRegistry;
    import org.springframework.web.socket.config.annotation.*;
    
    
    @Configuration
    @EnableWebSocketMessageBroker//启用STOMP协议来传输基于代理(message broker)的消息
    public class WebSocketConfig implements WebSocketMessageBrokerConfigurer {
        @Override
        public void registerStompEndpoints(StompEndpointRegistry registry) {
            //注册一个stomp的节点,使用SockJS协议
            registry.addEndpoint("/customendpoint").withSockJS();
        }
    
        @Override
        public void configureMessageBroker(MessageBrokerRegistry config) {
            //config.setApplicationDestinationPrefixes("/app");
            //使用内置的消息代理进行订阅和广播;路由消息的目标头以“/topic”或“/queue”开头。
            config.enableSimpleBroker("/topic", "/queue");
        }
    }
    

    控制器代码:

    package com.dyq.demo.controller;
    
    import com.dyq.demo.DTO.SocketRequestMessage;
    import com.dyq.demo.DTO.SocketResponseMessage;
    import org.springframework.messaging.handler.annotation.MessageMapping;
    import org.springframework.messaging.handler.annotation.SendTo;
    import org.springframework.stereotype.Controller;
    
    @Controller
    public class WebSocketController {
        @MessageMapping("/socket")//浏览器向服务器发送请求时,通过MessageMapping映射/socket地址
        @SendTo("/topic/getResponse")//当服务器有消息时,会对订阅了@SendTo中路径的浏览器发送消息
        public SocketResponseMessage say(SocketRequestMessage message) throws InterruptedException {
            Thread.sleep(3000);
            return new SocketResponseMessage("接收到RequestMessage:"+message.getRequestMessage()+"!");
        }
    }
    

    前端页面代码websocket.html:
    前端需要三个js文件,大家可以到http://www.bootcdn.cn/去搜索下载
    目前最新版:
    sockjs.min.js:https://cdn.bootcss.com/sockjs-client/1.1.4/sockjs.min.js
    stomp.min.js:https://cdn.bootcss.com/stomp.js/2.3.3/stomp.min.js
    jquery.min.js:https://cdn.bootcss.com/jquery/3.3.1/jquery.min.js

    <!DOCTYPE html>
    <html xmlns:th="http://www.thymeleaf.org">
    <head>
        <meta charset="UTF-8">
        <title>websocket</title>
    </head>
    <body>
        <noscript>Your browser does not support JavaScript!</noscript>
        <div>
            <div>
                <button id="connect" onclick="connect()">连接</button>
                <button id="disconnect" onclick="disconnect()">断开连接</button><br/>
                <p id="connectStatus">未连接</p>
                <br/><br/>
            </div>
            <div id="conversation">
                <label>输入发送信息</label>
                <input type="text" id="requestMessage">
                <button id="sendMessage" onclick="sendMessage()">发送</button>
                <p id="responseMessage"></p>
            </div>
        </div>
        <script th:src="@{js/sockjs.min.js}"></script>
        <script th:src="@{js/stomp.min.js}"></script>
        <script th:src="@{js/jquery.min.js}"></script>
        <script type="text/javascript">
            var stompClient = null;
            $(function () {
                setConnected(false);
            });
            function setConnected(connected) {
                if(connected){
                    $("#connect").attr("disabled",true);
                    $("#disconnect").attr("disabled",false);
                    $("#conversation").show();
                    $("#connectStatus").html("已连接");
                }else{
                    $("#connect").attr("disabled",false);
                    $("#disconnect").attr("disabled",true);
                    $("#conversation").hide();
                    $("#connectStatus").html("未连接");
                }
                $("#responseMessage").html();
            }
            function connect() {
                var socket = new SockJS("/customendpoint");//连接SockJs的endpoint-/customendpoint
                stompClient = Stomp.over(socket)//使用STOMP子协议的WebSocket客户端
                stompClient.connect({},function (frame) {
                    setConnected(true);
                    console.log("Connected:"+frame);
                    stompClient.subscribe("/topic/getResponse",function (response) {
                        showResponseMessage(JSON.parse(response.body).responseMessage);
                    });
                });
            }
            function disconnect() {
                if(stompClient!=null){
                    stompClient.disconnect();
                    setConnected(false);
                    console.log("Disconnected")
                }
            }
            function showResponseMessage(message) {
                $("#responseMessage").html(message);
            }
            function sendMessage() {
                var requseMessage = $("#requestMessage").val();
                console.log("requseMessage:"+requseMessage);
                stompClient.send("/socket",{},JSON.stringify({"requestMessage":requseMessage}));
            }
        </script>
    </body>
    </html>

    需要在Mvc配置文件:

    package com.dyq.demo.config;
    
    
    import org.apache.catalina.Context;
    import org.apache.catalina.connector.Connector;
    import org.apache.tomcat.util.descriptor.web.SecurityCollection;
    import org.apache.tomcat.util.descriptor.web.SecurityConstraint;
    import org.springframework.boot.web.embedded.tomcat.TomcatServletWebServerFactory;
    import org.springframework.boot.web.servlet.server.ServletWebServerFactory;
    import org.springframework.context.annotation.Bean;
    import org.springframework.context.annotation.Configuration;
    import org.springframework.web.servlet.config.annotation.*;
    
    
    @Configuration
    public class MVCConfig implements WebMvcConfigurer {
    
        public void addViewControllers(ViewControllerRegistry registry) {
            registry.addViewController("/").setViewName("/index");
            registry.addViewController("/index").setViewName("/index");
            registry.addViewController("/websocket").setViewName("/websocket");
        }
    }
    

    运行,开多个浏览器窗口,连接上,如果一个浏览器发送消息到服务器,其他窗口能接受到信息。
    然后运行效果:

  • 相关阅读:
    centos“You don't have permission to access /index.html on this server.”
    使用yum来安装或卸载CentOS图形界面包
    PHP上IIS上显示服务器应用程序不可用
    Windows 2003 远程桌面连接数超过最大连接数终极解决方案
    perl清理电脑上重复的文件
    wordpress在IIS6上首页访问不了
    WordPress首页出现循环重定向解决办法四则(转载)
    windows server 2003 如何在远程链接时更改用户密码
    Ubuntu下安装php5gd库,支持jpg、png、gif等格式图片处理
    wordpress设置用163邮箱账号发送邮件
  • 原文地址:https://www.cnblogs.com/sufferingStriver/p/9032336.html
Copyright © 2011-2022 走看看