Spring Boot Security WebFlux functional, cannot created configuration for two authentication methods - spring

I would like to have two ways of authentication in Spring Boot application. App is written with WebFlux and with functional approach. For some of my endpoints I'd like to have authentication with basicHttp and for some endpoints I would like to have JWT authentication using custom HTTP header. However I cannot merge two WebFilterChains or make it work as one. Only one of the methods works at the time, cannot make them both work. Code for JWT is not finished, but I would like to see 401 when I send request with httpBasic auth method. Paths in examples are fake.
My atttemps:
1)
First bean:
http
.securityMatcher(ServerWebExchangeMatchers.pathMatchers(HttpMethod.GET, "/api/1/**"))
.csrf().disable()
.formLogin().disable()
.logout().disable()
.httpBasic().and()
.authenticationManager(authenticationManager(userService))
.build();
Second bean:
http
.securityMatcher(ServerWebExchangeMatchers.pathMatchers("/api/2/**"))
.httpBasic().disable()
.csrf().disable()
.formLogin().disable()
.logout().disable()
.authenticationManager(tokenAuthManager)
.authorizeExchange()
.anyExchange().authenticated()
.and()
.build();
2)
http
.securityMatcher(ServerWebExchangeMatchers.pathMatchers(HttpMethod.GET, "/api/1/**"))
.csrf().disable()
.formLogin().disable()
.logout().disable()
.httpBasic().and()
.authenticationManager(authenticationManager(userService))
.securityMatcher(ServerWebExchangeMatchers.pathMatchers("/api/2/**"))
.httpBasic().disable()
.csrf().disable()
.formLogin().disable()
.logout().disable()
.authenticationManager(tokenAuthManager)
.authorizeExchange()
.anyExchange().authenticated()
.and()
.build();

Related

spring boot permitAll only works with HttpSecurity.authorizeRequests()

I am creating an api using spring boot
but I am getting the error below
permitAll only works with HttpSecurity.authorizeRequests()
http
.csrf().disable()
.authorizeRequests()
.antMatchers("/", "index", "/css/*", "/js/*")
.permitAll()
.antMatchers("/api/**").hasRole(STUDENT.name())
.antMatchers("/admin/api/**").hasRole(ADMIN.name())
.antMatchers("/management/api/**").hasAnyRole(ADMIN.name(), ADMINTRAINEE.name())
.anyRequest()
.authenticated()
.and()
.formLogin()
.loginPage("/login").permitAll();
How do I fix this?

swagger ui with spring security

I need specific role to access swagger ui
snippet to access swagger-ui with role 2 ( tried following with no joy)
http
.csrf()
.disable()
.authorizeRequests()
.antMatchers("/api/**").hasAuthority("ROLE_ROLE1")
.antMatchers("/login/**").permitAll()
.antMatchers("/info/**").permitAll()
.antMatchers(
"/configuration/ui",
"/v2/api-docs",
"/swagger-resources",
"/configuration/security",
"/swagger-ui.html",
"/webjars/**").hasAuthority("ROLE_ROLE2")
.and()
.formLogin()
.loginPage("/login.html")
.loginProcessingUrl("/perform_login")
.defaultSuccessUrl("/swagger-ui.html", true)
.failureUrl("/login.html?error=true")
.and().logout().logoutSuccessUrl("/login.html")
Permit all works - this checks all the resources are granted access
http
.csrf()
.disable()
.authorizeRequests()
.antMatchers("/api/**").hasAuthority("ROLE_ROLE1")
.antMatchers("/login/**").permitAll()
.antMatchers("/info/**").permitAll()
.antMatchers(
"/configuration/ui",
"/v2/api-docs",
"/swagger-resources",
"/configuration/security",
"/swagger-ui.html",
"/webjars/**").permitAll()
.and()
.formLogin()
.loginPage("/login.html")
.loginProcessingUrl("/perform_login")
.defaultSuccessUrl("/swagger-ui.html", true)
.failureUrl("/login.html?error=true")
.and().logout().logoutSuccessUrl("/login.html")
there is in memory user for role2
auth
.inMemoryAuthentication()
.withUser("user1").password("userpassword").roles("ROLE2");;
but when I login it doesnt bring up the swagger-ui , is there any thing missing ?
permitAll does show the swagger-ui
any help appreciated
I tried
http
.csrf()
.disable()
.requestMatchers().antMatchers(
"/swagger-ui.html",
"/swagger-resources",
"/configuration/ui",
"/configuration/security",
"/v2/api-docs",
"/webjars/**", "/**")
.and()
.authorizeRequests()
.antMatchers("/api/**").hasAuthority("ROLE_ROLE1")
.antMatchers("/login/**").permitAll()
.antMatchers("/info/**").permitAll()
.antMatchers(
"/swagger-ui.html",
"/swagger-resources",
"/configuration/ui",
"/configuration/security",
"/v2/api-docs",
"/webjars/**").hasRole("ROLE2")

SpringBoot app - server context Path

I've generated a Spring Boot web application using Spring Initializer, embedded Tomcat, Thymeleaf template engine, and package as an executable JAR file.
Technologies used:
Spring Boot 2.0.0.M6 , Java 8, maven
Here my security config
#Override
protected void configure(HttpSecurity http) throws Exception {
final List<String> activeProfiles = Arrays.asList(env.getActiveProfiles());
if (activeProfiles.contains("dev")) {
http.csrf().disable();
http.headers().frameOptions().disable();
}
http
.authorizeRequests()
.antMatchers(publicMatchers()).permitAll()
.anyRequest().authenticated()
.and()
.formLogin().loginPage("/login").defaultSuccessUrl("/iberia/list")
.failureUrl("/login?error").permitAll()
.and()
.logout().permitAll();
}
in my application.properties
server.contextPath=/iberiaWebUtils
server.port=1234
But when I run the app at http://localhost:1234/iberiaWebUtils, instead of going to http://localhost:1234/iberiaWebUtils/login, the app. redirects to http://localhost:1234/login
I also tried with
server.context-path=/iberiaWebUtils
with the same result
Starting from Spring Boot 2.0.0 M1 servlet-specific server properties were moved to server.servlet:
Spring Boot 2.0.0 M1 Release Notes
Therefore, you should use the server.servlet.context-path property.
Try adding .loginProcessingUrl("/iberiaWebUtils/login") after loginPage("/login")
http
.authorizeRequests()
.antMatchers(publicMatchers()).permitAll()
.anyRequest().authenticated()
.and()
.formLogin().loginPage("/login")
.loginProcessingUrl("/iberiaWebUtils/login")
.defaultSuccessUrl("/iberia/list")
.failureUrl("/login?error").permitAll()
.and()
.logout().permitAll();

How to configure AuthenticationSuccessHandler etc. only for /api/**

We are developing a standard Spring Boot web application with Thymeleaf templating, but have an API at /api/** which is called through AJAX.
We're using Spring Security's standard cookie based form authentication both for the application and the API. Whereas for the application we want Spring Security to behave in the default way, for the API, we want to provide custom AuthenticationSuccessHandler etc. for returning 200 OK etc., instead of redirecting to success or failure urls.
I am unable to figure out how to configure this, using Java configuration. In the configure method, I tried to configure http two times, as below, but it doesn't seem to work:
// For the API
http.antMatcher("/api/**")
.formLogin()
.successHandler(authenticationSuccessHandler)
.failureHandler(authenticationFailureHandler())
.and()
.logout()
.logoutSuccessHandler(logoutSuccessHandler)
.invalidateHttpSession(true)
.deleteCookies("JSESSIONID")
.and()
.exceptionHandling()
.authenticationEntryPoint(new Http403ForbiddenEntryPoint())
.and()
.rememberMe()
.key(properties.getRememberMeKey())
.rememberMeServices(rememberMeServices())
.and()
.csrf()
.csrfTokenRepository(csrfTokenRepository())
.and()
.addFilterAfter(new LemonCsrfFilter(), CsrfFilter.class)
.addFilterAfter(switchUserFilter(), FilterSecurityInterceptor.class)
.authorizeRequests()
.antMatchers("/login/impersonate*").hasRole(GOOD_ADMIN)
.antMatchers("/logout/impersonate*").authenticated()
.antMatchers("/**").permitAll();
// For the application pages
http
.authorizeRequests()
.antMatchers("/login/impersonate*").hasRole(GOOD_ADMIN)
.antMatchers("/logout/impersonate*").authenticated()
.anyRequest().permitAll()
.and()
.formLogin()
.loginPage("/login").permitAll()
.and()
.logout().permitAll()
.and()
.rememberMe()
.key(properties.getRememberMeKey())
.rememberMeServices(rememberMeServices())
.and()
.csrf()
.csrfTokenRepository(csrfTokenRepository())
.and()
.addFilterAfter(new LemonCsrfFilter(), CsrfFilter.class)
.addFilterAfter(switchUserFilter(), FilterSecurityInterceptor.class);

Spring - Security - Trouble with authorizeRequests chain

I can't understand, how to correctly make chain of the authorizeRequests chain.
If I write
http
.addFilterBefore(characterEncodingFilter(), CsrfFilter.class)
.addFilterAfter(cacheControllerFilter(), CsrfFilter.class)
.authorizeRequests()
.antMatchers("/**").permitAll()
.and()
.authorizeRequests()
.antMatchers("/admin/**").hasRole("ADMIN").anyRequest().authenticated()
.and()
.formLogin()
.loginPage("/admin/login.html")
.defaultSuccessUrl("/admin/")
.permitAll()
.and()
.logout()
.permitAll();
in this case all is permitAll, including /admin/** .
If I have
http
.addFilterBefore(characterEncodingFilter(), CsrfFilter.class)
.addFilterAfter(cacheControllerFilter(), CsrfFilter.class)
.authorizeRequests()
.antMatchers("/**").permitAll()
.and()
.authorizeRequests()
.antMatchers("/admin/**").hasRole("ADMIN").anyRequest().authenticated()
.and()
.formLogin()
.loginPage("/admin/login.html")
.defaultSuccessUrl("/admin/")
.permitAll()
.and()
.logout()
.permitAll();
in this case everything, including /admin/** requires authentication of the user.
Found solution
http://docs.spring.io/spring-security/site/docs/3.2.5.RELEASE/reference/htmlsingle/#authorize-requests
In my case solution is
http
.addFilterBefore(characterEncodingFilter(), CsrfFilter.class)
.addFilterAfter(cacheControllerFilter(), CsrfFilter.class)
.authorizeRequests()
.antMatchers("/admin/**").hasRole("ADMIN")
.anyRequest().permitAll()
.and()
.formLogin()
.loginPage("/admin/login.html")
.defaultSuccessUrl("/admin/")
.permitAll()
.and()
.logout()
.permitAll();

Resources