i am trying to use Vaadin along with spring boot and i'm using spring-security as well. this is the configuration that i've done in the WebSecurityConfigurerAdapter
class.
@Override
protected void configure(final HttpSecurity http) throws Exception {
http
.csrf().disable()
.authorizeRequests()
.antMatchers("/VAADIN/**", "/PUSH/**", "/UIDL/**", "/login", "/login/**", "/error/**", "/accessDenied/**", "/vaadinServlet/**","/myui/**","/test/**").permitAll()
.anyRequest().authenticated()
.and()
.formLogin().permitAll().defaultSuccessUrl("/myui", true).and()
.sessionManagement().sessionAuthenticationStrategy(sessionControlAuthenticationStrategy());
}
and this is my login view .
@Route("login")
@Theme(value = Lumo.class, variant = Lumo.DARK)
public class LoginForm extends Div {
public LoginForm(){
init();
}
public void init(){
FormLayout nameLayout = new FormLayout();
TextField username = new TextField();
username.setLabel("UserName");
username.setPlaceholder("username");
PasswordField passwordField = new PasswordField();
passwordField.setLabel("password");
passwordField.setPlaceholder("*****");
Button loginButton = new Button("login");
loginButton.addClickListener(event -> {
});
nameLayout.add(username,passwordField);
add(nameLayout);
}
}
the problem that i'm having is i always see an empty page when user is redirected to /login
but after inspecting the Html page i can see that there are vaadin elements but they doesn't appear in the browser.
This is my working configuration:
@Override
protected void configure(HttpSecurity http) throws Exception {
http
.csrf().disable() // CSRF handled by Vaadin
.exceptionHandling()
.authenticationEntryPoint(new LoginUrlAuthenticationEntryPoint("/login"))
.accessDeniedPage("/accessDenied")
.and()
.authorizeRequests()
// allow Vaadin URLs without authentication
.regexMatchers("/frontend/.*", "/VAADIN/.*", "/login.*", "/accessDenied.*").permitAll()
.regexMatchers(HttpMethod.POST, "/\\?v-r=.*").permitAll()
// deny other URLs until authenticated
.antMatchers("/**").fullyAuthenticated();
}
All requests are redirected to login view until authenticated. I didn't try @Push
so far, so it may needs additional URLs to be always allowed.
With Firefox developer tool, you can inspect XHR calls in the console. If any of the XHR calls fail with 403 or something, you may need to adapt your security configuration.
package com.example.test.spring.security;
import com.vaadin.flow.server.ServletHelper;
import com.vaadin.flow.shared.ApplicationConstants;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.builders.WebSecurity;
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
import org.springframework.security.core.userdetails.User;
import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.provisioning.InMemoryUserDetailsManager;
import javax.servlet.http.HttpServletRequest;
import java.util.stream.Stream;
@Configuration
@EnableWebSecurity
public class WebSecurityConfig extends WebSecurityConfigurerAdapter {
@Override
protected void configure(HttpSecurity http) throws Exception {
http.csrf().disable()
.authorizeRequests()
.antMatchers("/VAADIN/**", "/HEARTBEAT/**", "/UIDL/**", "/resources/**"
, "/login", "/login**", "/login/**", "/manifest.json", "/icons/**", "/images/**",
// (development mode) static resources
"/frontend/**",
// (development mode) webjars
"/webjars/**",
// (development mode) H2 debugging console
"/h2-console/**",
// (production mode) static resources
"/frontend-es5/**", "/frontend-es6/**").permitAll()
.anyRequest().authenticated()
.and()
.formLogin()
.loginPage("/login")
.permitAll()
.successForwardUrl("/something")
.and()
.logout()
.permitAll();
}
@Bean
@Override
public UserDetailsService userDetailsService() {
UserDetails user =
User.withDefaultPasswordEncoder()
.username("user")
.password("password")
.roles("USER")
.build();
return new InMemoryUserDetailsManager(user);
}
@Override
public void configure(WebSecurity web) throws Exception {
web.ignoring().antMatchers(
// Vaadin Flow static resources
"/VAADIN/**",
// the standard favicon URI
"/favicon.ico",
// web application manifest
"/manifest.json",
// icons and images
"/icons/**",
"/images/**",
// (development mode) static resources
"/frontend/**",
// (development mode) webjars
"/webjars/**",
// (development mode) H2 debugging console
"/h2-console/**",
// (production mode) static resources
"/frontend-es5/**", "/frontend-es6/**");
}
static boolean isFrameworkInternalRequest(HttpServletRequest request) {
final String parameterValue = request.getParameter(ApplicationConstants.REQUEST_TYPE_PARAMETER);
return parameterValue != null
&& Stream.of(ServletHelper.RequestType.values()).anyMatch(r -> r.getIdentifier().equals(parameterValue));
}
}
after changing the web configuration to this i was able to fix the problem