如何解决在特定的浏览器标签上限制@SendToUser广播
我在Springboot上使用STOMP websocket
,并且想限制广播到特定页面。这是我的过程:
-
User
将消息填充为HTML输入。 - 浏览器将通过STOMP客户端发送邮件。
- 服务器接收到消息并对其进行验证。如果消息有效,它将向用户处理的所有选项卡广播
User
已发出消息。如果无效,它将仅将错误消息发送回发送该消息的特定浏览器选项卡,而不与其他选项卡一起发送,即使这些选项卡具有相同的User
登录。 / li>
尽管我不能限制将错误消息发送到特定选项卡,但我已经使它的某些部分起作用了,它总是将错误消息广播到共享相同User
的所有选项卡。这是我的初始代码:
@MessageMapping("/api/secure/message")
@SendToUser("/api/secure/broadcast")
public HttpEntity createMessage(Message message,Authentication authentication) throws Exception {
Set<String> errors = TreeSet<String>();
// Process Message message and add every exceptions encountered to Set errors.
boolean valid = (errors.size() > 0);
if(valid) {
// Broadcast to all.
return new ResponseEntity(message,HttpStatus.OK);
}
else {
// Send the message to that particular tab only.
return new ResponseEntity(errors,HttpStatus.UNPROCESSABLE_ENTITY);
}
}
通过websocket
是否可以实现?还是应该回到XHR
?
解决方法
在每个选项卡中,您都将创建一个新的websocket会话,因此您的stomp session-id也将有所不同。因此,我们可以决定是发送到特定会话还是特定用户的所有会话。
@Autowired
private SimpMessagingTemplate template;
....
@MessageMapping(...)
public void sendMessage(Message<?> message...) {
.....
StompHeaderAccessor headerAccessor =
StompHeaderAccessor.wrap(message);
String sessionId = headerAccessor.getSessionId();
....
if(valid) {
//Not specifying session Id so sends all users of
<user_name>
template.cnvertAndSendToUser(<user_name>,<destination>,<payload>)
}
else {
SimpMessageHeaderAccessor headerAccessor =
SimpMessagingHeaderAccessor.create(SimpMessageType.MESSAGE);
headerAccessor.setSessionId(sessionId);
//This will send it to particular session.
template.convertAndSendToUser(<user_name>,<payload>,headerAccessor.getMessageHeaders());
}
}
有用的参考文献:
,用户@Srinivas提供了一个很好的起点。我已使用工作代码修改了问题中的代码块:
sudo chmod +x on the folder or file.
如果在控制器方法参数上使用// inject the [messagingTemplate] bean.
// class org.springframework.messaging.simp.SimpMessagingTemplate
@Autowired
private SimpMessagingTemplate messagingTemplate;
@MessageMapping("/api/secure/message")
// Remove the @SendToUser annotation and change return type to void.
// @SendToUser("/api/secure/broadcast")
// public HttpEntity createMessage(Message message…
public void createMessage(Message message,Authentication authentication) throws Exception {
Set<String> errors = TreeSet<String>();
// Process Message message and add every exceptions encountered to Set errors.
boolean valid = (errors.size() > 0);
if(valid) {
// Broadcast to all.
// Instead of returning to send the message,use the [messagingTemplate] instead.
// return new ResponseEntity(message,HttpStatus.OK);
messagingTemplate.convertAndSendToUser("/api/secure/broadcast",errors);
}
else {
// Send the message to that particular tab only.
// Each STOMP WebSocket connection has a unique ID that effectively differentiate
// it to the other browser tabs. Retrieve that ID so we can target that specific
// tab to send our error message with.
// class org.springframework.messaging.simp.stomp.StompHeaderAccessor
StompHeaderAccessor stompHeaderAccessor = StompHeaderAccessor.wrap(message);
String sessionId = stompHeaderAccessor.getSessionId();
// class org.springframework.messaging.simp.SimpMessageHeaderAccessor
// class org.springframework.messaging.simp.SimpMessageType
// class org.springframework.util.MimeType
// class java.nio.charset.StandardCharsets
SimpMessageHeaderAccessor simpHeaderAccessor =
SimpMessageHeaderAccessor.create(SimpMessageType.MESSAGE);
simpHeaderAccessor.setSessionId(sessionId);
simpHeaderAccessor.setContentType(new MimeType("application","json",StandardCharsets.UTF_8));
simpHeaderAccessor.setLeaveMutable(true);
// Instead of returning to send the message,use the [messagingTemplate] instead.
// It will ensure that it will only broadcast the message to the specific
// STOMP WebSocket sessionId.
// return new ResponseEntity(errors,HttpStatus.UNPROCESSABLE_ENTITY);
messagingTemplate.convertAndSendToUser(sessionId,"/api/secure/broadcast",errors,simpHeaderAccessor.getMessageHeaders());
}
}
,则必须将逻辑线移至@ResponseBody @Valid
ControllerAdvice
。
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。