При отключении анонимуса в Spring Security все url-ы автоматически выдают 403
Есть Spring Boot проект, где используется Spring Security.
Процесс авторизации идет через сессию и при успешной авторизации приложение сохраняет в cookie информацию.
Для /login и /logout я сделал доступ url-ов как permitAll, а остальные url-ы расписал как authenticated.
Когда пользователь стучится в защищенные url-ы без авторизации пишет что работает anonymousUser.
При отладке видно что Spring Security если не получает запрос от авторизованного пользователя, то автоматом подставляет anonymousUser.
Как решение в Spring Security Configuration я выключил в http.build анонимный доступ(anonymous.disable()), но таким образом все мои url-ы, в том числе и /login и /logout попадают под 403 Forbidden.
В чем дело и как можно решить проблему?
@Configuration
@EnableWebSecurity
public class SecurityConfiguration {
public static final String SESSION_ATTRIBUTE = "JSESSIONID";
@Bean
public SessionRegistry sessionRegistry() {
return new SessionRegistryImpl();
}
@Bean
public AuthenticationManager authenticationManager(AuthenticationConfiguration authenticationConfiguration)
throws Exception {
return authenticationConfiguration.getAuthenticationManager();
}
@Bean
public WebSecurityCustomizer webSecurityCustomizer() {
return (web) -> web.ignoring()
.antMatchers("/v3/api-docs/**")
.antMatchers("configuration/**")
.antMatchers("/swagger*/**")
.antMatchers("/webjars/**")
.antMatchers("/swagger-ui/**");
}
@Bean
public CorsConfiguration corsConfiguration() {
CorsConfiguration corsConfiguration = new CorsConfiguration();
corsConfiguration.setAllowCredentials(true);
corsConfiguration.setAllowedMethods(List.of("GET", "POST", "PUT", "DELETE", "OPTIONS"));
corsConfiguration.setAllowedOriginPatterns(List.of("*:[*]"));
corsConfiguration.setAllowedHeaders(List.of("*"));
corsConfiguration.setExposedHeaders(List.of("*"));
corsConfiguration.setMaxAge(1000L);
return corsConfiguration;
}
@Bean
public SecurityFilterChain filterChain(HttpSecurity http) throws Exception {
http
.cors().configurationSource(cors -> corsConfiguration()).and()
.csrf().disable()
.anonymous().disable()
.httpBasic().disable()
.logout().invalidateHttpSession(true).deleteCookies(SESSION_ATTRIBUTE)
.and()
.authorizeRequests()
.antMatchers("/api/authentication/login", "/api/authentication/logout").permitAll()
.antMatchers("/api/file/*", "/api/report/*", "/api/user/information/*").authenticated();
return http.build();
}
}
build.gradle:
dependencies {
implementation group: 'org.springframework.boot', name: 'spring-boot-starter-web', version: '2.7.2'
implementation group: 'org.springframework.boot', name: 'spring-boot-starter-jdbc', version: '2.7.2'
implementation group: 'org.springframework.boot', name: 'spring-boot-starter-security', version: '2.7.2'
implementation group: 'org.springframework.boot', name: 'spring-boot-starter-validation', version: '2.7.2'
implementation group: 'com.microsoft.sqlserver', name: 'mssql-jdbc', version: '9.4.1.jre16'
implementation group: 'org.json', name: 'json', version: '20220320'
implementation group: 'org.springdoc', name: 'springdoc-openapi-ui', version: '1.6.10'
implementation group: 'javax.xml.bind', name: 'jaxb-api', version: '2.3.1'
compileOnly 'org.projectlombok:lombok:1.18.24'
annotationProcessor 'org.projectlombok:lombok:1.18.24'
}
Ответы (2 шт):
Может я конечно с недосыпа не понимаю ничего, но тут вроде все банально.
Спринг делает ровно то, что у Вас написано:
Вы ему к этим страницам не разрешаете никого пускать - он и не пускает!
Просто разрешите доступ к старницам /login, /logout в filterChain()
.formLogin()
.loginPage("/login")
.permitAll()
.and()
.logout()
.permitAll()
либо банально:
.antMatchers("/login", "/logout").permitAll()
Итого весь метод:
@Bean
public SecurityFilterChain filterChain(HttpSecurity http) throws Exception {
http
.cors().configurationSource(cors -> corsConfiguration()).and()
.csrf().disable()
.anonymous().disable()
.httpBasic().disable()
.formLogin()
.loginPage("/login")
.permitAll()
.and()
.logout()
.permitAll()
.invalidateHttpSession(true) // дополнил вашими правилами
.deleteCookies(SESSION_ATTRIBUTE) // дополнил вашими правилами
.and()
.authorizeRequests()
.antMatchers("/api/authentication/login", "/api/authentication/logout").permitAll()
.antMatchers("/api/file/*", "/api/report/*", "/api/user/information/*").authenticated();
return http.build();
}
Если настроить filterChain подобным образом, то проблем с amonymous пользователем не будет:
@Bean
public SecurityFilterChain filterChain(HttpSecurity http) throws Exception {
http
.cors().configurationSource(cors -> corsConfiguration()).and()
.csrf().disable()
.httpBasic().disable()
.logout().invalidateHttpSession(true).deleteCookies(SESSION_ATTRIBUTE)
.and()
.authorizeRequests()
.antMatchers("/api/authentication/login", "/api/authentication/logout").permitAll()
.antMatchers("/api/**").authenticated();
return http.build();
}