Это мои конфиг-классы:
@Configuration
@EnableWebSecurity
public class WebSecurityConfig extends WebSecurityConfigurerAdapter {
@Autowired
private CustomUserServiceDetails customUserServiceDetails;
@Override
protected void configure(HttpSecurity http) throws Exception {
http
.authorizeRequests()
.antMatchers("/", "/home", "/proc/**", "/css/**", "/js/**", "/webjars/**", "/voting-socket/topic/**").permitAll()
.anyRequest().authenticated()
.and()
.formLogin()
.loginPage("/login")
.permitAll()
.and()
.logout()
.permitAll();
}
@Autowired
public void configureAuth(AuthenticationManagerBuilder auth) throws Exception {
auth.userDetailsService(customUserServiceDetails);
}
}
@Configuration
@EnableWebSocketMessageBroker
public class WebSocketConfig implements WebSocketMessageBrokerConfigurer {
@Override
public void configureMessageBroker(MessageBrokerRegistry config) {
config.enableSimpleBroker("/topic");
config.setApplicationDestinationPrefixes("/app");
}
@Override
public void registerStompEndpoints(StompEndpointRegistry registry) {
registry.addEndpoint("/voting-socket").withSockJS();
}
}
@Configuration
public class WebSocketSecurityConfig extends AbstractSecurityWebSocketMessageBrokerConfigurer {
@Override
protected void configureInbound(MessageSecurityMetadataSourceRegistry messages) {
messages
.nullDestMatcher().authenticated() // 1
.simpSubscribeDestMatchers("/topic/**").permitAll()
.simpDestMatchers("/app/**").hasRole("ADMIN")
.anyMessage().denyAll(); // 2
}
}
И код клиента JavaScript:
функция connect (vm) {
let socket = new SockJS('/voting-socket');
stompClient = Stomp.over(socket);
let headers = {};
headers[headerName] = token;
stompClient.connect(headers, function (frame) {
console.log('Connected: ' + frame);
stompClient.subscribe('/topic/voting/' + procId, function (data) {
console.log("data: " + data.body);
});
});
Теперь, насколько я понимаю, я должен иметь возможность подписываться и получать данные от /voting-socket/topic
конечной точки websocket без какой-либо аутентификации, однако я получаю эту ошибку: (журналы из консоли Chrome)
Opening Web Socket...
stomp.min.js:8 Web Socket Opened...
stomp.min.js:8 >>> CONNECT
X-CSRF-TOKEN:e0193869-8753-4eb7-b5fe-bc130796c3b1
accept-version:1.1,1.0
heart-beat:10000,10000
stomp.min.js:8 <<< ERROR
message:Failed to send message to ExecutorSubscribableChannel[clientInboundChannel]; nested exception is org.springframework.security.access.AccessDeniedException\c Access is denied
content-length:0
Итак, я хочу, чтобы этот код выполнял подписку и получал данные из /voting-socket/topic/proc/**
без какой-либо аутентификации (входа в систему) и разрешал отправлять данные в /voting-socket/app/proc/**
только зарегистрированным пользователям с определенной ролью.
В некоторых тестах мне удалось заставить его работать с удалением строк 1 и 2, но я не был уверен, что это правильное решение. Может ли кто-нибудь помочь мне с этим?