对于最新的稳定版本,请使用 Spring Framework 7.0.6!spring-doc.cadn.net.cn

消息流

一旦暴露了STOMP端点,Spring应用程序就会成为连接客户端的STOMP代理。本节描述了服务器端的消息流。spring-doc.cadn.net.cn

The spring-messaging 模块包含最初源自Spring Integration的基础消息传递应用程序支持,并在后来被提取并纳入Spring Framework,以便在许多Spring项目和应用场景中更广泛地使用。 以下列表简要描述了可用的消息传递抽象:spring-doc.cadn.net.cn

Java配置(即,@EnableWebSocketMessageBroker)和XML命名空间配置(即,<websocket:message-broker>)都使用上述组件来组装消息流程。下图显示了启用简单内置消息代理时使用的组件:spring-doc.cadn.net.cn

message flow simple broker

前面的图表显示了三个消息通道:spring-doc.cadn.net.cn

下一个图显示了当配置外部代理(如 RabbitMQ)用于管理订阅和广播消息时所使用的组件:spring-doc.cadn.net.cn

message flow broker relay

前两个图的主要区别在于使用了“代理中继”来通过 TCP 将消息传递到外部 STOMP 代理,以及将消息从代理传递到已订阅的客户端。spring-doc.cadn.net.cn

当通过WebSocket连接接收到消息时,这些消息会被解码为STOMP帧, 转换为Spring Message表示形式,并发送到 clientInboundChannel进行进一步处理。例如,目标头以/app开头的STOMP消息 可能会被路由到带注解的控制器中的@MessageMapping方法,而/topic/queue消息则可能直接 路由到消息代理。spring-doc.cadn.net.cn

一个处理客户端STOMP消息的注解@Controller可以通过brokerChannel将消息发送到消息代理,代理通过clientOutboundChannel将消息广播给匹配的订阅者。同一个控制器也可以对HTTP请求做出相同的操作,因此客户端可以执行HTTP POST,然后@PostMapping方法可以将消息发送到消息代理以广播给已订阅的客户端。spring-doc.cadn.net.cn

我们可以通过一个简单的例子来跟踪流程。考虑以下示例,它设置了一个服务器:spring-doc.cadn.net.cn

@Configuration
@EnableWebSocketMessageBroker
public class WebSocketConfig implements WebSocketMessageBrokerConfigurer {

	@Override
	public void registerStompEndpoints(StompEndpointRegistry registry) {
		registry.addEndpoint("/portfolio");
	}

	@Override
	public void configureMessageBroker(MessageBrokerRegistry registry) {
		registry.setApplicationDestinationPrefixes("/app");
		registry.enableSimpleBroker("/topic");
	}
}

@Controller
public class GreetingController {

	@MessageMapping("/greeting")
	public String handle(String greeting) {
		return "[" + getTimestamp() + ": " + greeting;
	}
}

前面的示例支持以下流程:spring-doc.cadn.net.cn

  1. 客户端连接到 localhost:8080/portfolio,一旦建立WebSocket连接,STOMP帧就会开始在其上流动。spring-doc.cadn.net.cn

  2. 客户端发送一个带有目标头为 /topic/greeting 的 SUBSCRIBE 消息。一旦接收到并解码,该消息将被发送到 clientInboundChannel,然后被路由到消息代理,该代理存储客户端的订阅。spring-doc.cadn.net.cn

  3. 客户端发送一个 SEND 帧到 /app/greeting/app 前缀有助于将其路由到 带注解的控制器。在删除 /app 前缀后,目标的剩余 /greeting 部分被映射到 @MessageMapping 方法中的 GreetingControllerspring-doc.cadn.net.cn

  4. GreetingController返回的值被转换为一个Spring Message,其负载基于返回值,且默认目标头为/topic/greeting(从输入目标中通过将/app替换为/topic得到)。生成的消息被发送到brokerChannel,并由消息代理处理。spring-doc.cadn.net.cn

  5. 消息代理会找到所有匹配的订阅者,并通过 clientOutboundChannel 向每个订阅者发送 MESSAGE 帧,从那里消息会被编码为 STOMP 帧并通过 WebSocket 连接发送。spring-doc.cadn.net.cn

下一节将提供更多有关带注解方法的详细信息,包括支持的参数类型和返回值类型。spring-doc.cadn.net.cn