当前位置: 首页 > article >正文

Spring Cloud Gateway整合基于STOMP协议的WebSocket实战及遇到问题解决

本实例介绍了Spring Cloud Gateway整合基于STOMP协议的WebSocket的实现。开发了聊天功能,和用户在线状态。解决了协议gateway整合websocket出现的问题

技术点

  • Spring Cloud Gateway
  • Nacos
  • WebSocket
  • STOMP

WebSocket与STOMP协议详解

1. WebSocket

WebSocket 是一种通信协议,提供了在客户端和服务器之间建立全双工通信的功能。这意味着客户端和服务器可以在任意时间相互发送数据,而不必遵循请求-响应的传统模式(如HTTP)。

特点:
  • 双向通信:与传统的HTTP不同,WebSocket允许服务器主动向客户端推送数据,而不必等待客户端请求。

  • 持久连接:WebSocket连接一旦建立,可以一直保持连接,直到任意一方关闭它。这减少了频繁建立连接的开销。

  • 低延迟:由于WebSocket消除了HTTP请求的头部开销和连接延迟,因此它适合于对延迟敏感的应用,如在线游戏、股票交易和聊天应用。

工作流程:
  1. 连接建立:客户端通过HTTP的升级机制(Upgrade header)请求建立WebSocket连接。

  2. 数据传输:一旦连接建立,客户端和服务器可以通过这个连接双向传输数据,使用一种轻量级的帧格式。

  3. 连接关闭:任意一方可以随时关闭连接,通知对方连接已关闭。

使用场景:
  • 实时聊天应用

  • 实时数据流(如股票行情、体育比赛更新)

  • 在线多人游戏

  • 实时协作工具(如Google Docs)

2. STOMP

STOMP(Simple Text Oriented Messaging Protocol) 是一种简单的文本协议,用于在客户端和消息代理(例如,RabbitMQ、ActiveMQ)之间交换消息。它是应用层的协议,常用于消息传递系统,提供了一种基于消息的通信方式。

特点:
  • 简单易用:STOMP使用类似于HTTP的文本格式,非常容易理解和实现。

  • 基于订阅/发布模型:STOMP支持基于主题(topic)的订阅/发布模型,这使得消息可以广播给多个客户端。

  • 支持消息队列:STOMP支持将消息发送到队列,多个消费者可以从同一个队列中读取消息,确保负载均衡。

常用命令:
  • CONNECT:客户端请求连接到STOMP服务器。

  • SEND:客户端发送一条消息到指定的目的地(如某个队列或主题)。

  • SUBSCRIBE:客户端订阅某个目的地,以接收该目的地的所有消息。

  • UNSUBSCRIBE:取消订阅。

  • DISCONNECT:断开与STOMP服务器的连接。

STOMP和WebSocket的结合:

虽然WebSocket本身是一个很好的低延迟双向通信工具,但它只提供了一种基础的传输方式,没有定义消息的格式或通信模式。STOMP可以在WebSocket之上运行,提供了消息格式、路由、确认等高级功能。

例如,在一个实时聊天应用中,WebSocket用于底层的双向通信,而STOMP则负责处理消息的路由和格式化:

  • 客户端通过WebSocket连接到服务器,并通过STOMP发送或订阅消息。

  • 服务器使用STOMP协议将消息广播给所有订阅了相应主题的客户端。

WebSocket服务端

依赖

<!-- WebSocket依赖 -->
<dependency>
  <groupId>org.springframework.boot</groupId>
  <artifactId>spring-boot-starter-websocket</artifactId>
</dependency>
<!-- nacos依赖 -->
<dependency>
  <groupId>com.alibaba.cloud</groupId>
  <artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
</dependency>
<dependency>
  <groupId>com.alibaba.nacos</groupId>
  <artifactId>nacos-client</artifactId>
</dependency>
<dependency>
  <groupId>com.alibaba.cloud</groupId>
  <artifactId>spring-cloud-starter-alibaba-nacos-config</artifactId>
</dependency>

枚举类

package com.inspur.message.constant;

import lombok.AccessLevel;
import lombok.AllArgsConstructor;

@AllArgsConstructor(access = AccessLevel.PRIVATE)
public enum MessageTypeEnum {
    TEXT("文本"),
    IMAGE("图片"),
    VOICE("语音"),
    FILE("文件"),
    EMOJI("表情"),
    SYSTEM_NOTIFICATION("系统通知"),
    LOCATION("位置"),
    LINK("链接"),
    RECALL("撤回"),
    MENTION("@提及"),
    SYSTEM_MESSAGE("系统提示"),
    VIDEO("视频"),
    RED_PACKET("红包"),
    VOTE("投票"),
    FRIEND_SHARE("好友分享");

    // 其他可能的消息类型...
    private String description;

    public String getDescription() {
        return description;
    }

    public static boolean isFileMessageType(MessageTypeEnum messageType) {
        return messageType == IMAGE || messageType == VOICE || messageType == FILE || messageType == VIDEO;
    }
}

WebSocket配置类

package com.inspur.message.config;

import org.springframework.context.annotation.Configuration;
import org.springframework.messaging.simp.config.MessageBrokerRegistry;
import org.springframework.web.socket.config.annotation.EnableWebSocketMessageBroker;
import org.springframework.web.socket.config.annotation.StompEndpointRegistry;
import org.springframework.web.socket.config.annotation.WebSocketMessageBrokerConfigurer;

@Configuration
@EnableWebSocketMessageBroker//注解开启STOMP协议来传输基于代理的信息,实现实时双向通信和消息传递
public class WebSocketConfig implements WebSocketMessageBrokerConfigurer {
    /**
     * 客户端在订阅或发布消息到目的地路径前,要连接到该端点
     *
     * @param registry
     */
    @Override
    public void registerStompEndpoints(StompEndpointRegistry registry) {
        registry.addEndpoint("/ws").setAllowedOrigins("*").withSockJS();// 启用 SockJS (浏览器不支持WebSocket,SockJS 将会提供兼容性支持)
    }

    /**
     * 配置消息代理
     *
     * @param register
     */
    @Override
    public void configureMessageBroker(MessageBrokerRegistry register) {
        /**
         * 放开的前缀路由,客户端才能接收对应路由开头的信息
   

http://www.kler.cn/a/294159.html

相关文章:

  • 【代码审计】常见漏洞专项审计-业务逻辑漏洞审计
  • 大模型研究报告 | 2024年中国金融大模型产业发展洞察报告|附34页PDF文件下载
  • 机器学习、深度学习面试知识点汇总
  • 「QT」文件类 之 QDataStream 数据流类
  • Linux—进程学习-02
  • SQL面试题——奔驰SQL面试题 车辆在不同驾驶模式下的时间
  • 基于单片机的家居环境监测系统的设计
  • 项目7-音乐播放器7(测试报告)
  • MATLAB 中的矩阵拼接技巧
  • bash反弹shell分析
  • C#编程语言及.NET 平台快速入门指南
  • Facebook群控系统,零门槛营销
  • 基于人工智能的聊天情感分析系统
  • 使用Selenium WebDriver捕获网络请求
  • 【60天备战软考高级系统架构设计师——第七天:架构风格】
  • Python炒股自动化,怎样理解股票交易性质
  • 如何构建你自己的实时人脸识别系统
  • django学习入门系列之第十点《django中数据库操作--创建与删除表》
  • OpenCV下的无标定校正(stereoRectifyUncalibrated)
  • 如何解决PCDN技术与边缘计算技术融合后的安全和隐私问题(壹)?
  • Linux——redis
  • day47——面向对象特征之继承
  • 【AI】Pytorch_模型构建
  • Form 表单的 resetFields() 失效原因
  • 站在 AI 与 Web3 的交汇路口,EraAI 如何带领投资者进入智能化决策时代?
  • C++中匿名命名空间的主要使用方法