// Path: src/main/java/com/jeanchampemont/notedown/utils/SecurityInterceptor.java
// @Component
// public class SecurityInterceptor extends HandlerInterceptorAdapter {
//     @Override
//     public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
//         if (modelAndView != null) {
//             FilterInvocation filterInvocation = new FilterInvocation(request, response, new FilterChain() {
//                 public void doFilter(ServletRequest request, ServletResponse response) throws IOException, ServletException {
//                     throw new UnsupportedOperationException();
//                 }
//             });
// 
//             Authentication authentication = SecurityContextHolder.getContext().getAuthentication();
//             if (authentication != null) {
//                 WebSecurityExpressionRoot sec = new WebSecurityExpressionRoot(authentication, filterInvocation);
//                 sec.setTrustResolver(new AuthenticationTrustResolverImpl());
//                 modelAndView.getModel().put("sec", sec);
//             }
//         }
//     }
// }


import com.jeanchampemont.notedown.utils.SecurityInterceptor;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.security.web.authentication.rememberme.JdbcTokenRepositoryImpl;
import org.springframework.security.web.authentication.rememberme.PersistentTokenRepository;
import org.springframework.security.web.servlet.support.csrf.CsrfRequestDataValueProcessor;
import org.springframework.security.web.util.matcher.AntPathRequestMatcher;
import org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping;
import org.springframework.web.servlet.support.RequestDataValueProcessor;
import javax.sql.DataSource;
                .formLogin().loginPage("/login").failureUrl("/login?error")
                .usernameParameter("email").passwordParameter("password")
                .defaultSuccessUrl("/app")
            .and()
                .logout().logoutRequestMatcher(new AntPathRequestMatcher("/logout", "GET")).logoutSuccessUrl("/login?logout")
            .and()
                .rememberMe().tokenRepository(persistentTokenRepository()).tokenValiditySeconds(tokenValiditySeconds)
            .and()
                .csrf();
    }

    @Bean
    public PersistentTokenRepository persistentTokenRepository() {
        JdbcTokenRepositoryImpl repo = new JdbcTokenRepositoryImpl();
        repo.setDataSource(dataSource);
        return repo;
    }

    @Bean
    public PasswordEncoder passwordEncoder() {
        PasswordEncoder encoder = new BCryptPasswordEncoder();
        return encoder;
    }

    @Bean
    public RequestDataValueProcessor requestDataValueProcessor() {
        return new CsrfRequestDataValueProcessor();
    }

    @Bean
// Path: src/main/java/com/jeanchampemont/notedown/utils/SecurityInterceptor.java
// @Component
// public class SecurityInterceptor extends HandlerInterceptorAdapter {
//     @Override
//     public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
//         if (modelAndView != null) {
//             FilterInvocation filterInvocation = new FilterInvocation(request, response, new FilterChain() {
//                 public void doFilter(ServletRequest request, ServletResponse response) throws IOException, ServletException {
//                     throw new UnsupportedOperationException();
//                 }
//             });
// 
//             Authentication authentication = SecurityContextHolder.getContext().getAuthentication();
//             if (authentication != null) {
//                 WebSecurityExpressionRoot sec = new WebSecurityExpressionRoot(authentication, filterInvocation);
//                 sec.setTrustResolver(new AuthenticationTrustResolverImpl());
//                 modelAndView.getModel().put("sec", sec);
//             }
//         }
//     }
// }


// Path: src/main/java/com/jeanchampemont/notedown/config/WebSecurityConfiguration.java
import com.jeanchampemont.notedown.utils.SecurityInterceptor;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.security.web.authentication.rememberme.JdbcTokenRepositoryImpl;
import org.springframework.security.web.authentication.rememberme.PersistentTokenRepository;
import org.springframework.security.web.servlet.support.csrf.CsrfRequestDataValueProcessor;
import org.springframework.security.web.util.matcher.AntPathRequestMatcher;
import org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping;
import org.springframework.web.servlet.support.RequestDataValueProcessor;
import javax.sql.DataSource;

                .formLogin().loginPage("/login").failureUrl("/login?error")
                .usernameParameter("email").passwordParameter("password")
                .defaultSuccessUrl("/app")
            .and()
                .logout().logoutRequestMatcher(new AntPathRequestMatcher("/logout", "GET")).logoutSuccessUrl("/login?logout")
            .and()
                .rememberMe().tokenRepository(persistentTokenRepository()).tokenValiditySeconds(tokenValiditySeconds)
            .and()
                .csrf();
    }

    @Bean
    public PersistentTokenRepository persistentTokenRepository() {
        JdbcTokenRepositoryImpl repo = new JdbcTokenRepositoryImpl();
        repo.setDataSource(dataSource);
        return repo;
    }

    @Bean
    public PasswordEncoder passwordEncoder() {
        PasswordEncoder encoder = new BCryptPasswordEncoder();
        return encoder;
    }

    @Bean
    public RequestDataValueProcessor requestDataValueProcessor() {
        return new CsrfRequestDataValueProcessor();
    }

    @Bean
    public RequestMappingHandlerMapping requestMappingHandlerMapping(SecurityInterceptor securityInterceptor) {