I am using Spring Boot 3, Spring Security 6. My Security configuration doesn't work properly. I have 2 paths on which any request should be permitted, and for everything else one needs to authenticate.
Both GET
and POST
method work on those that need authentication.
On those with permitAll()
, only GET
requests work. For POST
, I get 401 Unauthorised.
I took care of CSRF, and anyway I expect all the POST
requests to work, not only those with authentication.
On Postman, I selected POST
, No Auth, put a RAW body and selected JSON. I really don't know why is it not working.
Here is my code:
@Configuration
@EnableWebSecurity
public class SecurityConfig {
@Bean
protected SessionAuthenticationStrategy sessionAuthenticationStrategy() {
return new RegisterSessionAuthenticationStrategy(new SessionRegistryImpl());
}
@Bean
public SecurityFilterChain filterChain(HttpSecurity http, KeycloakLogoutHandler keycloakLogoutHandler) throws Exception {
http
.authorizeHttpRequests()
.requestMatchers("/firstpath/**", "/secondpath/**").permitAll()
.and()
.authorizeHttpRequests()
.anyRequest().authenticated()
.and()
.oauth2ResourceServer(oauth2 -> oauth2.jwt());
http
.oauth2Login()
.and()
.logout()
.addLogoutHandler(keycloakLogoutHandler)
.logoutSuccessUrl("/");
http
.csrf()
.csrfTokenRepository(CookieCsrfTokenRepository.withHttpOnlyFalse());
return http.build();
}
}
@Slf4j
@RestController
@RequestMapping("/firstpath")
public class NameitController {
@PostMapping(value = "path", produces = WSConstants.JSON_MEDIATYPE)
@ResponseBody
public ResponseEntity saveMyObject(@RequestBody ObjectDTO dto) {
[...] //my code
}
}
I also tried http.authorizeHttpRequests().requestMatchers(HttpMethod.POST, "/firstpath/path").permitAll()
, but at no use.
Edit: It still has to do with CSRF protection, because when I tired http.csrf().disable();
, everything worked fine. But I still want CSRF protection, it seems like the token is not sent with permitAll()
?...
Edit2: After adding Spring Security logs:
CodePudding user response:
THe order in which you define in security config please have a look order like this
`@Override
protected void configure(HttpSecurity http) throws Exception {
http
.authorizeRequests()
.antMatchers(HttpMethod.POST, "/api/auth/**")
.permitAll()
.antMatchers("/",
"/favicon.ico",
"/**/*.png",
"/**/*.gif",
"/**/*.svg",
"/**/*.jpg",
"/**/*.html",
"/**/*.css",
"/**/*.js")
.permitAll()
.anyRequest()
.authenticated()
.and()
.cors()
.and()
.exceptionHandling()
.authenticationEntryPoint(this.jwtAuthenticationEntryPoint)
.and()
.sessionManagement()
.sessionCreationPolicy(SessionCreationPolicy.STATELESS)
.and()
.csrf()
.disable();
// Add our custom JWT security filter
http.addFilterBefore(jwtAuthenticationFilter(),
UsernamePasswordAuthenticationFilter.class);
}`
CodePudding user response:
Changing
http.csrf().csrfTokenRepository(CookieCsrfTokenRepository.withHttpOnlyFalse());
to
http.csrf().ignoringRequestMatchers("/infoboard/**").csrfTokenRepository(CookieCsrfTokenRepository.withHttpOnlyFalse());
did the trick. But I don't understand what it is doing or why.