构建即时通讯应用:Spring boot高效集成WebSocket、Stomp协议完成前后端持续通信

1. 引入依赖

在你的Spring Boot项目的pom.xml中添加以下依赖:

<dependencies>

        <!-- Spring Boot Starter Thymeleaf -->
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-thymeleaf</artifactId>
        </dependency>

        <!-- Spring Boot Starter WebSocket -->
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-websocket</artifactId>
        </dependency>

        <!-- https://mvnrepository.com/artifact/com.fasterxml.jackson.core/jackson-databind -->
        <dependency>
            <groupId>com.fasterxml.jackson.core</groupId>
            <artifactId>jackson-databind</artifactId>
        </dependency>

        <!-- https://mvnrepository.com/artifact/com.fasterxml.jackson.core/jackson-core -->
        <dependency>
            <groupId>com.fasterxml.jackson.core</groupId>
            <artifactId>jackson-core</artifactId>
        </dependency>

        <!-- https://mvnrepository.com/artifact/com.fasterxml.jackson.core/jackson-annotations -->
        <dependency>
            <groupId>com.fasterxml.jackson.core</groupId>
            <artifactId>jackson-annotations</artifactId>
        </dependency>
    </dependencies>

2. 配置WebSocket

创建一个配置类来设置WebSocket连接端点、STOMP协议和消息传输路径:

@Configuration
@EnableWebSocketMessageBroker
public class WebsocketMessageBrokerConfig implements WebSocketMessageBrokerConfigurer {

    @Override
    public void registerStompEndpoints(StompEndpointRegistry registry) {
        registry.addEndpoint("/ws") // WebSocket握手端口
                .setAllowedOriginPatterns("*") // 设置跨域
                .withSockJS(); // 开启SockJS回退机制
    }

    @Override
    public void configureMessageBroker(MessageBrokerRegistry registry) {
        registry.setApplicationDestinationPrefixes("/app") // 发送到服务端目的地前缀
                .enableSimpleBroker("/topic");// 开启简单消息代理,指定消息订阅前缀
    }

}


3. 创建消息处理器

创建一个控制器来处理客户端发送的消息,并将消息广播给订阅了相关主题的客户端:

/**
 * 功能描述:
 *
 * @author Songxianyang
 * @date 2024-08-05 17:24
 */
@Controller
@Slf4j
@RequiredArgsConstructor
public class StompController {

    private final SimpMessagingTemplate messagingTemplate;

    @GetMapping("stomp")
    public ModelAndView stomp() {
        return new ModelAndView("stomp");
    }


    /**
     * 数据通过前端发送到后端,处理完数据后在响应给前端的订阅者“/topic/public”
     * @param chatMessage
     * @return
     */

    // 这个注解的作用是映射客户端发送到服务器的消息路径
    @MessageMapping("/chat.sendMessage")
    @SendTo("/topic/public")
    public ChatMessage sendMessage(ChatMessage chatMessage) {
        return chatMessage;
    }

    @MessageMapping("/chat.addUser")
    @SendTo("/topic/public")
    public ChatMessage addUser(ChatMessage chatMessage, SimpMessageHeaderAccessor headerAccessor) {
        // 将用户名存储在WebSocket会话中
        headerAccessor.getSessionAttributes().put("username", chatMessage.getSender());
        return chatMessage;
    }

    /**
     * 服务端主动给客户端发送消息
     * @return
     */
    @GetMapping("s-to-c")
    @SendTo("/topic/public")
    @ResponseBody
    public ChatMessage sToC() {
        ChatMessage chatMessage = new ChatMessage();
        chatMessage.setContent("西瓜视频");
        chatMessage.setSender("Server");
        chatMessage.setType(ChatMessage.MessageType.CHAT);
        // 发送消息
        messagingTemplate.convertAndSend("/topic/public", chatMessage);
        return chatMessage;
    }




    @GetMapping("/html/greeting")
    public ModelAndView turnToGreetingPage() {
        return new ModelAndView("greeting");
    }

    @MessageMapping("/greeting")
    public String sayGreeting(String name) {
        log.info("Message received: {}", name);
        return "Hello, " + name;
    }


}

4. 创建消息模型

创建一个简单的Java类来表示聊天消息:

/**
 * 聊天消息对象
 */
@Data
public class ChatMessage {
    /**
     * 消息的类型
     */
    private MessageType type;
    /**
     * 消息的内容
     */
    private String content;
    /**
     * 发送者
     */
    private String sender;

    public enum MessageType {
        //普通聊天消息
        CHAT,
        // 加入聊天
        JOIN,
        // 离开聊天
        LEAVE
    }
}

5. 创建前端代码(stomp.html)

在前端(例如使用HTML和JavaScript)中集成WebSocket和STOMP。以下是一个简单的示例:

<!DOCTYPE html>
<html>
<head>
    <title>WebSocket-Chat-stomp</title>
    <script src="https://cdnjs.cloudflare.com/ajax/libs/sockjs-client/1.6.1/sockjs.min.js"></script>
    <script src="https://cdnjs.cloudflare.com/ajax/libs/stomp.js/2.3.3/stomp.min.js"></script>
    <script>
        var stompClient = null;
        // 接收消息
        function connect() {
            var socket = new SockJS('/ws');
            stompClient = Stomp.over(socket);
            stompClient.connect({}, function (frame) {
                console.log('Connected: ' + frame);
                // 客户端订阅服务端消息
                stompClient.subscribe('/topic/public', function (message) {
                    showMessage(JSON.parse(message.body));
                });
            });
        }
        // 发送消息
        function sendMessage() {
            var messageContent = document.getElementById("message").value;
            // 往客户端发送消息
            stompClient.send("/app/chat.sendMessage", {}, JSON.stringify({
                sender: "User",
                content: messageContent,
                type: 'CHAT'
            }));
        }
        // 展示消息
        function showMessage(message) {
            var response = document.getElementById("response");
            var p = document.createElement("p");
            p.appendChild(document.createTextNode(message.sender + ": " + message.content));
            response.appendChild(p);
        }

        // 用户加入
        function addUser() {
            var userName = document.getElementById('username').value;
            if (userName && stompClient) {
                var chatMessage = {
                    sender: userName,
                    content: userName + "已加入聊天!请注意财产安全",
                    type: 'JOIN'
                };
                stompClient.send("/app/chat.addUser", {}, JSON.stringify(chatMessage));
            }
        }

    </script>
</head>
<body onload="connect()">
<div>

    <input type="text" id="username" placeholder="Enter your name" />
    <button onclick="addUser()">用户加入</button>

    <input type="text" id="message" />
    <button onclick="sendMessage()">发送信息</button>
</div>
<div id="response"></div>
</body>
</html>

7. yml配置

server:
  port: 9999
#  servlet:
#    context-path: /demo
spring:
  freemarker:
    request-context-attribute: request
    suffix: .html
    content-type: text/html
    enabled: true
    cache: false
    charset: UTF-8
    allow-request-override: false
    expose-request-attributes: true
    expose-session-attributes: true
    expose-spring-macro-helpers: true

8. 运行应用程序

启动Spring Boot应用程序,并打开你的HTML页面,你应该能够通过WebSocket连接发送和接收消息了。

连接
http://localhost:9999/stomp
http://localhost:9999/stomp
1.前端

在这里插入图片描述

2.用户加入

在这里插入图片描述

3.聊天消息

在这里插入图片描述

4.服务端主动给客户端发送消息

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

总结

通过以上步骤,你可以在Spring Boot项目中集成WebSocket和STOMP协议,实现实时的双向通信功能。这是一个基本的示例,你可以根据需要进行扩展和自定义,例如添加更多的消息处理逻辑、安全认证等。

源码

持续更新 (集群、优化这个应用)

  • 6
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
好的,以下是一个简单的 Spring Boot 集成 WebSocket 的 Demo,可以实现简单的对话功能: 1. 首先,在 pom.xml 中引入 Spring BootWebSocket 的依赖: ```xml <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-websocket</artifactId> </dependency> ``` 2. 创建一个 WebSocket 配置类,用于配置 WebSocket 相关的内容: ```java @Configuration @EnableWebSocket public class WebSocketConfig implements WebSocketConfigurer { @Override public void registerWebSocketHandlers(WebSocketHandlerRegistry registry) { registry.addHandler(new WebSocketHandler(), "/chat"); } } ``` 3. 创建一个 WebSocketHandler 类,用于处理 WebSocket 的连接和消息: ```java public class WebSocketHandler extends TextWebSocketHandler { private final List<WebSocketSession> sessions = new ArrayList<>(); @Override public void afterConnectionEstablished(WebSocketSession session) { sessions.add(session); } @Override protected void handleTextMessage(WebSocketSession session, TextMessage message) throws Exception { for (WebSocketSession s : sessions) { s.sendMessage(message); } } } ``` 4. 在 Controller 中添加一个映射,用于返回聊天页面: ```java @Controller public class ChatController { @GetMapping("/") public String index() { return "chat"; } } ``` 5. 创建一个 HTML 页面,用于展示聊天界面和发送消息: ```html <!DOCTYPE html> <html> <head> <title>Chat</title> </head> <body> <div id="messages"></div> <form id="message-form"> <input type="text" id="message-input"> <button type="submit">Send</button> </form> <script src="/webjars/jquery/jquery.min.js"></script> <script src="/webjars/sockjs-client/sockjs.min.js"></script> <script src="/webjars/stomp-websocket/stomp.min.js"></script> <script> var stompClient = Stomp.over(new SockJS("/chat")); stompClient.connect({}, function() { stompClient.subscribe("/chat", function(message) { $("#messages").append("<p>" + message.body + "</p>"); }); }); $("#message-form").submit(function(event) { event.preventDefault(); var message = $("#message-input").val(); stompClient.send("/chat", {}, message); $("#message-input").val(""); }); </script> </body> </html> ``` 这个 Demo 中,前端使用了 SockJS 和 STOMP.js 这两个库来实现 WebSocket 的连接和消息发送。后端使用了 Spring BootWebSocket 功能来处理 WebSocket 的连接和消息。前端和后端通过 /chat 这个 URL 进行连接。 这个 Demo 可以在本地启动后,通过访问 http://localhost:8080/ 来进入聊天界面。多个浏览器窗口之间可以进行简单的对话。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

SteveCode.

永远年轻,永远热泪盈眶

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值