package com.hotent.base.login.custom.provider;

import cn.hutool.core.lang.Assert;
import com.fasterxml.jackson.databind.JsonNode;
import com.hotent.base.constants.PlatformConsts;
import com.hotent.base.exception.BaseException;
import com.hotent.base.feign.UCFeignService;
import com.hotent.base.login.custom.token.CustomAuthenticationToken;
import com.hotent.base.security.CustomPwdEncoder;
import com.hotent.base.util.BeanUtils;
import org.springframework.beans.factory.InitializingBean;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.authentication.AuthenticationProvider;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.AuthenticationException;
import org.springframework.security.core.GrantedAuthority;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.stereotype.Component;

import java.util.ArrayList;
import java.util.Collection;

@Component
public class CustomAuthenticationProvider implements AuthenticationProvider, InitializingBean {

    @Autowired
    private AuthenticationManager authenticationManager;
    @Autowired
    private UserDetailsService detailsService;
    @Autowired
    private UCFeignService feignService;

    private PasswordEncoder passwordEncoder = new CustomPwdEncoder();

    
    @Override
    public void afterPropertiesSet() throws Exception {
        Assert.notNull(this.authenticationManager, "authenticationManager is mandatory");
    }

    @Override
    public Authentication authenticate(Authentication authentication) throws AuthenticationException {
        String customKey = authentication.getPrincipal().toString();
        if(authentication.getCredentials() == null){
            throw new BaseException("密码不能为空");
        }
        Object credentials = authentication.getCredentials();
        String customSecret = credentials == null ? null : credentials.toString();
        JsonNode custom = feignService.loadCustomByCustomKey(customKey);
        if(BeanUtils.isNotEmpty(custom)){
            if(BeanUtils.isEmpty(custom.get("customSecret"))){
                throw new BaseException("账号不存在");
            }else{
                if(!passwordEncoder.matches(customSecret, custom.get("customSecret").asText())){
                    throw new BaseException("账号或密码错误");
                }
            }
        }else{
            throw new BaseException("账号不存在");
        }
        Collection<GrantedAuthority> authorities=new ArrayList<GrantedAuthority>();
        authorities.add(PlatformConsts.CUSTOM_USER);
        return new CustomAuthenticationToken(customKey, customSecret, authorities);
    }

    @Override
    public boolean supports(Class<?> authentication) {
        return (CustomAuthenticationToken.class.isAssignableFrom(authentication));
    }

    public AuthenticationManager getAuthenticationManager() {
        return authenticationManager;
    }

    public void setAuthenticationManager(AuthenticationManager authenticationManager) {
        this.authenticationManager = authenticationManager;
    }

    public UserDetailsService getDetailsService() {
        return detailsService;
    }

    public void setDetailsService(UserDetailsService detailsService) {
        this.detailsService = detailsService;
    }
}
