赣州住房和建设局网站,263企业邮箱怎么修改密码,做网站的学校,营销型网站改版STOMP#xff08;Simple Text Oriented Messaging Protocol#xff0c;简单面向文本的消息传递协议#xff09;是一种轻量级、基于文本的协议#xff0c;旨在为消息代理#xff08;消息队列#xff09;和客户端之间的通信#xff08;websocket#xff09;提供一种简单的…STOMPSimple Text Oriented Messaging Protocol简单面向文本的消息传递协议是一种轻量级、基于文本的协议旨在为消息代理消息队列和客户端之间的通信websocket提供一种简单的接口。它通常运行在TCP或WebSocket之上并广泛用于实现发布/订阅、点对点消息传递等模式。 STOMP提供了一种简单的机制来发送和接收消息适用于各种消息中间件系统如ActiveMQ、RabbitMQ和Apache Kafka等。
特点
基于文本的协议简单易用适合快速开发。支持多种消息传递模式如发布/订阅、点对点。支持事务和消息确认机制。轻量级适用于资源受限的环境宽带低等。支持多种消息代理如RabbitMQ、ActiveMQ。支持客户端之间的通信如websocket
适用场景
实时通信应用如聊天系统、社交网络。微服务之间的异步通信。IoT设备之间的轻量级通信。
1、STOMP基本概念
1、目的地Destination
目的地是消息发送或接收的目标地址。
常见的目的地类型包括
队列Queue点对点消息传递模式每条消息只会被一个消费者处理。主题Topic发布/订阅模式每条消息会被所有订阅者处理。
2、命令Commands
STOMP定义了若干命令用于控制消息的发送、接收和管理。
常见的命令包括
CONNECT建立连接。SEND发送消息到指定的目的地。SUBSCRIBE订阅某个目的地接收该目的地的消息。UNSUBSCRIBE取消订阅某个目的地。ACK确认消息已被成功处理。NACK拒绝或无法处理消息。DISCONNECT断开连接。
3、头信息Headers
头信息是伴随每个命令的键值对用于传递额外的元数据。
常见的头信息包括
destination消息的目的地。id订阅的唯一标识符。receipt请求服务器返回一个收据确认命令已执行。
4、消息体Body
消息体包含实际的消息内容可以是任意格式的数据如JSON、XML、纯文本等。消息体必须以空字节\u0000结束。
2、STOMP消息格式
每条STOMP消息由命令行、头信息和消息体组成各部分之间用换行符\n分隔整个消息以两个连续的换行符\n\n结束。
示例CONNECT命令
CONNECT
accept-version:1.2
host:stomp.example.com^解释
CONNECT命令名称。accept-version:1.2表示支持的STOMP版本。host:stomp.example.com目标主机。^表示消息体为空用一个空字节ASCII码为0来表示。
示例SEND命令
SEND
destination:/queue/workHello, STOMP!
^解释
SEND命令名称。destination:/queue/work消息的目的地。Hello, STOMP!消息的内容。^表示消息结束。
示例SUBSCRIBE命令
SUBSCRIBE
id:sub-001
destination:/topic/greetings^解释
SUBSCRIBE命令名称。id:sub-001订阅的唯一标识符。destination:/topic/greetings要订阅的主题地址。^表示消息体为空。
3、STOMP工作流程
原理示意图
1、连接
客户端首先需要通过CONNECT命令与STOMP服务器建立连接。如果连接成功服务器会返回一个CONNECTED响应。
客户端示例
CONNECT
accept-version:1.2
host:stomp.example.com^服务器响应示例
CONNECTED
version:1.2
session:session-id-12345^2、订阅
客户端可以通过SUBSCRIBE命令订阅某个目的地接收该目的地的消息。
客户端示例
SUBSCRIBE
id:sub-001
destination:/topic/greetings^3、发送消息
客户端可以通过SEND命令向某个目的地发送消息。
客户端示例
SEND
destination:/queue/workHello, STOMP!
^4、接收消息
当有消息到达客户端订阅的目的地时服务器会将消息推送到客户端。
消息示例
MESSAGE
subscription:sub-001
message-id:message-id-67890
destination:/topic/greetingsHello, World!
^5、断开连接
客户端可以通过DISCONNECT命令断开与服务器的连接。
客户端示例
DISCONNECT^4、在WebSocket上使用STOMP
在WebSocket之上使用STOMP时STOMP消息作为WebSocket数据帧的有效载荷进行传输。这种方式结合了WebSocket的全双工通信能力和STOMP的结构化消息传递功能。
示例JavaScript中使用WebSocket和STOMP
const socket new WebSocket(ws://example.com/stomp-endpoint); // 建立websocket连接socket.onopen function() {// 发送CONNECT命令const connectMessage CONNECT\naccept-version:1.2\nhost:example.com\n\n\u0000;socket.send(connectMessage);// 发送SUBSCRIBE命令const subscribeMessage SUBSCRIBE\nid:sub-001\ndestination:/topic/greetings\n\n\u0000;socket.send(subscribeMessage);
};socket.onmessage function(event) {console.log(Received:, event.data);// 解析收到的STOMP消息if (event.data.startsWith(MESSAGE)) {console.log(New message:, event.data.split(\n\n)[1].trim());}
};5、代码示例
依赖库
dependencygroupIdorg.springframework.boot/groupIdartifactIdspring-boot-starter-websocket/artifactId
/dependency
dependencygroupIdorg.springframework.boot/groupIdartifactIdspring-boot-starter-messaging/artifactId
/dependency发送消息
import org.springframework.messaging.converter.MappingJackson2MessageConverter;
import org.springframework.messaging.simp.stomp.StompFrameHandler;
import org.springframework.messaging.simp.stomp.StompHeaders;
import org.springframework.messaging.simp.stomp.StompSession;
import org.springframework.messaging.simp.stomp.StompSessionHandlerAdapter;
import org.springframework.web.socket.client.standard.StandardWebSocketClient;
import org.springframework.web.socket.messaging.WebSocketStompClient;
import org.springframework.web.socket.sockjs.client.SockJsClient;
import org.springframework.web.socket.sockjs.client.Transport;
import org.springframework.web.socket.sockjs.client.WebSocketTransport;
import java.lang.reflect.Type;
import java.util.Collections;
import java.util.concurrent.ExecutionException;public class StompProducer {public static void main(String[] args) throws ExecutionException, InterruptedException {// 创建 WebSocket 客户端StandardWebSocketClient wsClient new StandardWebSocketClient();SockJsClient sockJsClient new SockJsClient(Collections.singletonList(new WebSocketTransport(wsClient)));// 创建STOMP客户端WebSocketStompClient stompClient new WebSocketStompClient(sockJsClient);stompClient.setMessageConverter(new MappingJackson2MessageConverter());// 连接到STOMP代理StompSession session stompClient.connect(ws://localhost:8080/ws, new StompSessionHandlerAdapter() {}).get();// 发送消息StompHeaders headers new StompHeaders();headers.setDestination(/app/hello);session.send(headers, Hello, STOMP!);System.out.println(Message sent);}
}接收消息
import org.springframework.messaging.converter.MappingJackson2MessageConverter;
import org.springframework.messaging.simp.stomp.StompFrameHandler;
import org.springframework.messaging.simp.stomp.StompHeaders;
import org.springframework.messaging.simp.stomp.StompSession;
import org.springframework.messaging.simp.stomp.StompSessionHandlerAdapter;
import org.springframework.web.socket.client.standard.StandardWebSocketClient;
import org.springframework.web.socket.messaging.WebSocketStompClient;
import org.springframework.web.socket.sockjs.client.SockJsClient;
import org.springframework.web.socket.sockjs.client.Transport;
import org.springframework.web.socket.sockjs.client.WebSocketTransport;
import java.lang.reflect.Type;
import java.util.Collections;
import java.util.concurrent.ExecutionException;public class StompConsumer {public static void main(String[] args) throws ExecutionException, InterruptedException {// 创建WebSocket客户端StandardWebSocketClient wsClient new StandardWebSocketClient();SockJsClient sockJsClient new SockJsClient(Collections.singletonList(new WebSocketTransport(wsClient)));// 创建STOMP客户端WebSocketStompClient stompClient new WebSocketStompClient(sockJsClient);stompClient.setMessageConverter(new MappingJackson2MessageConverter());// 连接到STOMP代理StompSession session stompClient.connect(ws://localhost:8080/ws, new StompSessionHandlerAdapter() {}).get();// 订阅主题并设置回调session.subscribe(/topic/greetings, new StompFrameHandler() {Overridepublic Type getPayloadType(StompHeaders headers) {return String.class;}Overridepublic void handleFrame(StompHeaders headers, Object payload) {System.out.println(Received message: payload);}});// 保持连接Thread.sleep(Long.MAX_VALUE);}
}6、总结
STOMP是一种简单而强大的消息传递协议特别适合于需要灵活消息路由的应用场景。通过运行在WebSocket或其他传输协议之上。
STOMP提供了以下优势
易用性基于文本的协议易于实现和调试。灵活性支持多种消息传递模式适应不同的应用场景。跨平台可以在多种编程语言和平台上使用具有良好的互操作性。
通过理解STOMP的基本概念、命令和工作流程开发者可以有效地利用这一协议构建高效的消息传递系统。
乘风破浪Dare to Be