Wie zum senden von FEHLERMELDUNG, STOMP clients mit Spring WebSocket?
Ich bin mit Spring STOMP über WebSocket-Implementierung mit einer full-featured ActiveMQ broker. Wenn Benutzer SUBSCRIBE
zu einem Thema, es gibt einige Berechtigungen Logik, die Sie durchgehen müssen, bevor Sie erfolgreich angemeldet. Ich bin mit einem ChannelInterceptor, um die Berechtigungen anzuwenden Logik, wie unten konfiguriert:
WebSocketConfig.java:
@EnableWebSocketMessageBroker
public class WebSocketConfig extends AbstractWebSocketMessageBrokerConfigurer {
@Override
public void registerStompEndpoints(StompEndpointRegistry registry) {
registry.addEndpoint("/stomp")
.setAllowedOrigins("*")
.withSockJS();
}
@Override
public void configureMessageBroker(MessageBrokerRegistry registry) {
registry.enableStompBrokerRelay("/topic", "/queue")
.setRelayHost("relayhost.mydomain.com")
.setRelayPort(61613);
}
@Override
public void configureClientInboundChannel(ChannelRegistration registration) {
registration.setInterceptors(new MySubscriptionInterceptor());
}
}
WebSocketSecurityConfig.java:
public class WebSocketSecurityConfig extends AbstractSecurityWebSocketMessageBrokerConfigurer {
@Override
protected void configureInbound(MessageSecurityMetadataSourceRegistry messages) {
messages
.simpSubscribeDestMatchers("/stomp/**").authenticated()
.simpSubscribeDestMatchers("/user/queue/errors").authenticated()
.anyMessage().denyAll();
}
}
MySubscriptionInterceptor.java:
public class MySubscriptionInterceptor extends ChannelInterceptorAdapter {
@Override
public Message<?> preSend(Message<?> message, MessageChannel channel) {
StompHeaderAccessor headerAccessor= StompHeaderAccessor.wrap(message);
Principal principal = headerAccessor.getUser();
if (StompCommand.SUBSCRIBE.equals(headerAccessor.getCommand())) {
checkPermissions(principal);
}
return message;
}
private void checkPermissions(Principal principal) {
//apply permissions logic
//throw Exception permissions not sufficient
}
}
Wenn Kunden, die nicht über die entsprechenden Berechtigungen verfügen, versuchen Sie zu abonnieren, zu einem eingeschränkten Thema, die Sie in Wirklichkeit nie erhalten alle Nachrichten von diesem Thema, ABER auch nicht mitgeteilt von der Ausnahme, die geworfen wurde, die abgelehnt Ihre Abonnements. Stattdessen wird der client übergeben wird wieder eine tote Abonnements, dass der ActiveMQ-broker weiß, nichts über. (Normal, angemessen-permissioned client-Interaktionen mit der STOMP-Endpunkt, und die Themen funktionieren genau wie erwartet.)
Habe ich versucht abonnieren users/{subscribingUsername}/queue/errors
und einfach nur users/queue/errors
mit meinem Java test client, nachdem es erfolgreich verbunden, aber ich habe bisher keine Art von Fehlermeldung über das Abonnement Ausnahme vom server an den client übermittelt. Dies ist natürlich weniger als ideal, da die clients werden nicht benachrichtigt, dass Sie haben, wurde der Zugriff verweigert.
Du musst angemeldet sein, um einen Kommentar abzugeben.
Können Sie nicht nur werfen eine Ausnahme von der
MySubscriptionInterceptor
auf dieclientInboundChannel
, denn die Letzte istExecutorSubscribableChannel
daher istasync
Ausnahmen von diesen threads sind am Ende in die Protokolle mit jedem re-throw an den Aufrufer -StompSubProtocolHandler.handleMessageFromClient
.Aber was Sie tun können, ist so etwas wie
clientOutboundChannel
und verwenden Sie es wie diese:Andere option zu prüfen, ist die Annotation-mapping:
@SubscribeMapping
Methode und behandelt, indem die@MessageExceptionHandler
Methode, eine Nachricht an den client gesendet WIRD die Fehler-queue, ABER Ihr Abonnement wird noch an den Makler und der Kunde erhält noch nachträgliche Meldungen aus dem Thema.send
zu denclientOutboundChannel
aus, dass@MessageExceptionHandler
.