spring - 如何使用 Spring-websocket 拒绝基于用户权限的主题订阅

标签 spring spring-security websocket publish-subscribe spring-websocket

我正在实现一个版本的股票应用程序,其中服务器能够根据用户权限拒绝特定主题的主题订阅。 spring-websocket 中有没有办法做到这一点?

例如:

在股票示例项目中,我们有 3 种工具的价格主题:Apple、Microsoft、Google 并有两个用户:User1、User2

User1 应该有权访问 Apple 和 Microsoft User2 应该只能访问 Google

如果用户 1 订阅了谷歌,他应该得到拒绝响应,并且消息不应该广播给他。

最佳答案

感谢罗森·斯托扬切夫 answer on github我设法通过向入站 channel 添加拦截器来解决这个问题。 spring-websocket-portfolio 中所需的更改演示应用如下:

更改 websocket 配置:

public void configureClientInboundChannel(ChannelRegistration registration) {
    registration.setInterceptors(new TopicSubscriptionInterceptor());
}

拦截器是这样的:

public class TopicSubscriptionInterceptor extends ChannelInterceptorAdapter {
    private static Logger logger = org.slf4j.LoggerFactory.getLogger(TopicSubscriptionInterceptor.class);

    @Override
    public Message<?> preSend(Message<?> message, MessageChannel channel) {
        StompHeaderAccessor headerAccessor= StompHeaderAccessor.wrap(message);
        if (StompCommand.SUBSCRIBE.equals(headerAccessor.getCommand())) {
            Principal userPrincipal = headerAccessor.getUser();
            if (!validateSubscription(userPrincipal, headerAccessor.getDestination())) {
                throw new IllegalArgumentException("No permission for this topic");
            }
        }
        return message;
    }

    private boolean validateSubscription(Principal principal, String topicDestination) {
        if (principal == null) {
            // Unauthenticated user
            return false;
        }
        logger.debug("Validate subscription for {} to topic {}", principal.getName(), topicDestination);
        // Additional validation logic coming here
        return true;
    }
}

关于spring - 如何使用 Spring-websocket 拒绝基于用户权限的主题订阅,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21554230/

相关文章:

spring - 如何使用嵌入式 tomcat 运行 Spring MVC 项目?

java - 基于环境变量的条件 Bean 加载

java - 使用@Transactional时无法捕获的异常

java - 在哪里以及如何下载 Spring jar?

azure - 如何使用 @WebMvcTest、MockMvc 和 OAuth 安全性测试 Controller

python - websocket数据采集设计

java - 不使用 cookie 的 Spring Security session

spring-security - 我可以在单个 Web 应用程序中将 SAML 与其他身份验证提供程序一起使用吗

java - 如何使用 Spring-boot 处理越来越多的 STOMP 主题

ios - 套接字未在 iOS Swift 中连接?