Spring Boot聊天应用报错:Expected destination pattern "/user/{userId}/**" 如何解决?
解决Spring Boot WebSocket中"Expected destination pattern '/user/{userId}/**'"错误
这个错误的核心原因是客户端发送的用户目标地址不符合Spring STOMP用户目的地的格式规范。
问题分析
当你通过registry.setUserDestinationPrefix("/user")配置了用户目的地前缀后,Spring要求所有以/user开头的目标地址必须遵循/user/{userId}/**的格式({userId}为用户标识,**表示后续任意路径段)。如果客户端发送的地址是/user/xxx这类缺少后续路径层级的格式,就会触发断言失败,抛出该错误。
解决方案
修正客户端的目标地址格式
- 确保客户端发送或订阅的用户目标地址符合规范:
- 发送给指定用户:使用
/user/{userId}/queue/xxx或/user/{userId}/topic/xxx格式 - 发送给自己:直接用
/user/queue/xxx或/user/topic/xxx,Spring会自动将{userId}替换为当前登录用户的标识
- 发送给指定用户:使用
- 错误示例:
/user/chat(缺少/queue或/topic等后续路径段) - 正确示例(Stomp.js客户端):
// 订阅当前用户的私有消息队列 stompClient.subscribe("/user/queue/private-chat", (msg) => { // 处理收到的消息 }); // 发送消息给指定用户 stompClient.send("/app/sendToUser", {}, JSON.stringify({ targetUserId: "user123", content: "Hello!" }));
- 确保客户端发送或订阅的用户目标地址符合规范:
确认服务端配置的正确性
你的当前配置符合要求,无需修改,只需确保enableSimpleBroker包含了客户端使用的消息代理前缀(比如/queue、/topic):@Override public void configureMessageBroker(MessageBrokerRegistry registry) { registry.enableSimpleBroker("/topic","/queue"); registry.setApplicationDestinationPrefixes("/app"); registry.setUserDestinationPrefix("/user"); } @Override public void registerStompEndpoints(StompEndpointRegistry registry) { registry.addEndpoint("/ws").withSockJS(); }服务端控制器示例
配合客户端的正确格式,控制器可参考如下写法:@MessageMapping("/sendToUser") public void sendToUser(@Payload ChatMessage message, SimpMessageHeaderAccessor headerAccessor) { // 获取当前用户标识 String currentUserId = headerAccessor.getUser().getName(); // 发送消息给目标用户 messagingTemplate.convertAndSendToUser( message.getTargetUserId(), "/queue/private-chat", new ChatMessage(currentUserId, message.getContent()) ); }
内容的提问来源于stack exchange,提问作者Satya Prasad
相关产品推荐
相关产品推荐

