Mastering Spring Security Logout: Custom Handlers and Configurations

This article walks through the inner workings of Spring Security after login, explains session and token based authentication, and provides step‑by‑step guidance on customizing logout logic with LogoutFilter, LogoutConfigurer, and custom LogoutHandler and LogoutSuccessHandler implementations in Java.

Programmer DD
Programmer DD
Programmer DD
Mastering Spring Security Logout: Custom Handlers and Configurations

1. Introduction

The previous article introduced all built‑in Filters of Spring Security. Today we practice how to safely log out of an application.

2. What Spring Security does after login

Generally after login the server issues a credential. Two common types are:

Session‑based: the client stores a cookie with a sessionId, and the server stores a Session.

Token‑based: the client stores a token string, and the server stores token information in a cache for verification.

3. What we need to do for logout

Invalidate the current user's login state, i.e., clear server‑side user state.

The logout endpoint must not be permitAll; only requests carrying the appropriate credentials can log out.

Return the logout result to the caller.

After logout the user can log in again to authenticate.

4. Logout in Spring Security

Now we analyze and practice how to customize logout logic. First we need to understand LogoutFilter.

4.1 LogoutFilter

Logout logic is executed by the built‑in filter LogoutFilter. It holds three interface‑type properties: RequestMatcher logoutRequestMatcher – matches the logout request URL. LogoutHandler handler – handles the actual logout logic. LogoutSuccessHandler logoutSuccessHandler – logic executed after successful logout.

By implementing these interfaces we can customize logout behavior.

4.2 LogoutConfigurer

Usually we configure LogoutFilter via LogoutConfigurer. Use HttpSecurity#logout() to obtain a LogoutConfigurer.

4.2.1 Define custom logout request URL

LogoutConfigurer

provides logoutRequestMatcher(RequestMatcher) or logoutUrl(String) to define the logout URL; choose either.

4.2.2 Handle specific logic

By default Spring Security uses Session. LogoutConfigurer offers options such as clearAuthentication(boolean), deleteCookies(String...), and invalidateHttpSession(boolean). If these are insufficient, implement a custom LogoutHandler.

4.2.3 Logout success logic

logoutSuccessUrl(String)

– URL to redirect after successful logout. You can write a controller to handle GET and anonymous access.

defaultLogoutSuccessHandlerFor(LogoutSuccessHandler, RequestMatcher)

– construct a default LogoutSuccessHandler; you can add multiple to handle different URLs. LogoutSuccessHandler logoutSuccessHandler – abstract interface for post‑logout logic.

4.3 Spring Security logout practice

In a front‑end‑back‑end separated architecture, logout returns JSON and only online users can log out.

4.3.1 Custom LogoutHandler

@Slf4j
public class CustomLogoutHandler implements LogoutHandler {
    @Override
    public void logout(HttpServletRequest request, HttpServletResponse response, Authentication authentication) {
        User user = (User) authentication.getPrincipal();
        String username = user.getUsername();
        log.info("username: {}  is offline now", username);
    }
}

This handler runs after SecurityContextLogoutHandler.

4.3.2 Custom LogoutSuccessHandler

@Slf4j
public class CustomLogoutSuccessHandler implements LogoutSuccessHandler {
    @Override
    public void onLogoutSuccess(HttpServletRequest request, HttpServletResponse response, Authentication authentication) throws IOException, ServletException {
        User user = (User) authentication.getPrincipal();
        String username = user.getUsername();
        log.info("username: {}  is offline now", username);
        responseJsonWriter(response, RestBody.ok("退出成功"));
    }

    private static void responseJsonWriter(HttpServletResponse response, Rest rest) throws IOException {
        response.setStatus(HttpServletResponse.SC_OK);
        response.setCharacterEncoding("utf-8");
        response.setContentType(MediaType.APPLICATION_JSON_VALUE);
        ObjectMapper objectMapper = new ObjectMapper();
        String resBody = objectMapper.writeValueAsString(rest);
        PrintWriter printWriter = response.getWriter();
        printWriter.print(resBody);
        printWriter.flush();
        printWriter.close();
    }
}

4.3.4 Custom Spring Security configuration for logout

For testing, log in via http://localhost:8080/login and log out via http://localhost:8080/logout.

@Override
protected void configure(HttpSecurity http) throws Exception {
    http.csrf().disable()
        .cors()
        .and()
        .authorizeRequests().anyRequest().authenticated()
        .and()
        .formLogin().loginProcessingUrl(LOGIN_PROCESSING_URL)
            .successForwardUrl("/login/success")
            .failureForwardUrl("/login/failure")
        .and()
        .logout()
            .addLogoutHandler(new CustomLogoutHandler())
            .logoutSuccessHandler(new CustomLogoutSuccessHandler());
}
Javabackend developmentSpring SecuritylogoutCustom Handler
Programmer DD
Written by

Programmer DD

A tinkering programmer and author of "Spring Cloud Microservices in Action"

0 followers
Reader feedback

How this landed with the community

Sign in to like

Rate this article

Was this worth your time?

Sign in to rate
Discussion

0 Comments

Thoughtful readers leave field notes, pushback, and hard-won operational detail here.