package com.cloudhandson.ddsbackoffice.config;

import com.cloudhandson.vpdbackoffice.config.BackofficeProperties;
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.core.userdetails.User;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.crypto.factory.PasswordEncoderFactories;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.security.provisioning.InMemoryUserDetailsManager;
import org.springframework.security.web.SecurityFilterChain;

@Configuration
public class SecurityConfig {

  @Bean
  SecurityFilterChain securityFilterChain(
      HttpSecurity http,
      BackofficeProperties properties
  ) throws Exception {
    if (properties.security().requireHttps()) {
      http.requiresChannel(channel -> channel.anyRequest().requiresSecure());
    }

    return http
        .csrf(csrf -> csrf.ignoringRequestMatchers("/dds/mcp/messages"))
        .headers(headers -> headers.httpStrictTransportSecurity(hsts -> hsts
            .includeSubDomains(true)
            .maxAgeInSeconds(31_536_000)))
        .authorizeHttpRequests(auth -> auth
            .requestMatchers("/css/**", "/js/**", "/health", "/login",
                "/dds/mcp/sse", "/dds/mcp/messages").permitAll()
            .anyRequest().authenticated())
        .httpBasic(basic -> {
        })
        .formLogin(login -> login
            .loginPage("/login")
            .permitAll())
        .logout(logout -> logout.logoutSuccessUrl("/login?logout"))
        .build();
  }

  @Bean
  UserDetailsService userDetailsService(
      BackofficeProperties properties,
      PasswordEncoder passwordEncoder
  ) {
    var security = properties.security();
    var user = User.withUsername(security.adminUser())
        .password(passwordEncoder.encode(security.adminPassword()))
        .roles("ADMIN")
        .build();
    return new InMemoryUserDetailsManager(user);
  }

  @Bean
  PasswordEncoder passwordEncoder() {
    return PasswordEncoderFactories.createDelegatingPasswordEncoder();
  }
}
