Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to configure Spring Security for a single page application?

I faced with a problem configuration Spring Security for single page application.

So, defualt config looks like

@Configuration
@EnableWebSecurity
public class SecurityConfiguration extends WebSecurityConfigurerAdapter {

    @Autowired
    @Qualifier("customUserDetailsService")
    UserDetailsService userDetailsService;

    @Autowired
    public void configureGlobalSecurity(AuthenticationManagerBuilder auth) throws Exception {
        auth.userDetailsService(userDetailsService);
    }

    @Override
    protected void configure(HttpSecurity http) throws Exception {
        http.authorizeRequests()
                .antMatchers("/", "/list").permitAll()
                .antMatchers("/admin/**").access("hasRole('ADMIN')")
                .and().formLogin().loginPage("/login").permitAll()
                .usernameParameter("ssoId").passwordParameter("password")
                .and().csrf()
                .and().exceptionHandling().accessDeniedPage("/Access_Denied");
    }

    @Bean(name="authenticationManager")
    @Override
    public AuthenticationManager authenticationManagerBean() throws Exception {
        return super.authenticationManagerBean();
    }


}

From the documentation for the methods for Login().loginPage("/login") says the it use for redirecting to the login page. For single page this configuration doesn't relevant. How I should configure spring for single page application? I mean how to configure login, logout in controller and in configuration file.

like image 364
user2483213 Avatar asked Oct 02 '15 20:10

user2483213


People also ask

How do I add security to my spring application?

For adding a Spring Boot Security to your Spring Boot application, we need to add the Spring Boot Starter Security dependency in our build configuration file. Maven users can add the following dependency in the pom. xml file. Gradle users can add the following dependency in the build.

Will Spring Security secures all the applications?

If Spring Security is on the classpath, Spring Boot automatically secures all HTTP endpoints with “basic” authentication. However, you can further customize the security settings. The first thing you need to do is add Spring Security to the classpath.


1 Answers

Spring Lemon can be a complete example for this, but let me summarize the things below.

By default, when a user successfully logs in, Spring Security redirects him to the home page. When a login fails, or after a successful logout, the user is redirected back to the login page. Also, on trying to access URLs for which a user does not have sufficient rights, he is redirected to the login page.

As you say, this behavior won't suit for single page applications. Your API should instead send a 200 response along with the user data, or a 4xx response. This can be done by supplying your own handlers, like this:

@Override
protected void configure(HttpSecurity http) throws Exception {
http
    .formLogin()
        ...
        .successHandler(your authentication success handler object)
        .failureHandler(your authentication failure handler object)
        .and()
    .logout()
        ...
        .logoutSuccessHandler(your logout success handler object)
        .and()
    .exceptionHandling()
        .authenticationEntryPoint(new Http403ForbiddenEntryPoint())
    ...
}

You will find many examples in the Internet on how to code these handler classes. For example, in the spring-lemon project, these are coded as below.

Authentication Success Handler

@Component
public class AuthenticationSuccessHandler
    extends SimpleUrlAuthenticationSuccessHandler {

    @Autowired    
    private ObjectMapper objectMapper;

    @Autowired    
    private LemonService<?,?> lemonService;

    @Override
    public void onAuthenticationSuccess(HttpServletRequest request,
            HttpServletResponse response,
            Authentication authentication)
    throws IOException, ServletException {

        response.setStatus(HttpServletResponse.SC_OK);
        response.setContentType(MediaType.APPLICATION_JSON_VALUE);

        AbstractUser<?,?> currentUser = lemonService.userForClient();

        response.getOutputStream().print(
                objectMapper.writeValueAsString(currentUser));

        clearAuthenticationAttributes(request);
    }
}

In summary, it returns a 200 response with the JSONified current-user in the response data.

Authentication Failure Handler

In fact, there is no need to code a class for the authentication failure handler - the SimpleUrlAuthenticationFailureHandler provided by Spring, if instantiated without any arguments, works as desired.

Logout Success Handler

public class LemonLogoutSuccessHandler
    implements LogoutSuccessHandler {

    @Override
    public void onLogoutSuccess(HttpServletRequest request,
        HttpServletResponse response, Authentication authentication)
        throws IOException, ServletException {

          response.setStatus(HttpServletResponse.SC_OK);
    }
}

For a detailed example, referring Spring Lemon's LemonWebSecurityConfig class and other classes in it's security packages of various modules can be helpful.

like image 124
Sanjay Avatar answered Oct 11 '22 03:10

Sanjay