package jnpf.personnels.controller.web.roster;

import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.util.StrUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import jnpf.base.ActionResult;
import jnpf.base.UserInfo;
import jnpf.base.entity.SuperBaseEntity;
import jnpf.config.ConfigValueUtil;
import jnpf.database.util.TenantDataSourceUtil;
import jnpf.exception.LoginException;
import jnpf.model.enums.EmployeeMetaDataType;
import jnpf.model.personnels.dto.roster.meta.PersonnelsMetaDTO;
import jnpf.model.personnels.dto.salary.FtbXcCustomFieldDto;
import jnpf.model.personnels.po.*;
import jnpf.model.personnels.req.roster.FtbPersonnelsMetaDataReq;
import jnpf.model.personnels.req.roster.FtbPersonnelsMetaFuctionReq;
import jnpf.model.personnels.vo.salary.FtbXcCustomFieldVo;
import jnpf.personnels.FtbPersonnelsMetaDataManagerApi;
import jnpf.personnels.mapper.*;
import jnpf.personnels.service.FtbPersonnelsMetaDataService;
import jnpf.util.NoDataSourceBind;
import jnpf.util.StringUtil;
import jnpf.util.UserProvider;
import jnpf.util.data.DataSourceContextHolder;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.util.Assert;
import org.springframework.web.bind.annotation.*;

import javax.annotation.Resource;
import java.util.*;
import java.util.function.Function;
import java.util.stream.Collectors;

/**
 * web查询人事元数据信息
 *
 * @author xxxxx
 */
@RestController
@Slf4j
@RequestMapping("/web/personnels/metaData")
public class FtbPersonnelsMetaDataController implements FtbPersonnelsMetaDataManagerApi {

    @Autowired
    FtbPersonnelsMetaDataService metaDataService;

    @Autowired
    private ConfigValueUtil configValueUtil;
    @Resource
    private FtbPersonnelsStaffRosterMapper ftbPersonnelsStaffRosterMapper;
    @Resource
    private FtbPersonnelsRegistrationFormTypeMapper ftbPersonnelsRegistrationFormTypeMapper;
    @Resource
    private FtbPersonnelsRegistrationFormFieldMapper ftbPersonnelsRegistrationFormFieldMapper;
    @Resource
    private FtbPersonnelsRegistrationFormFieldOptionMapper ftbPersonnelsRegistrationFormFieldOptionMapper;
    @Resource
    private FtbPersonnelsStaffRegistrationFormDataMapper ftbPersonnelsStaffRegistrationFormDataMapper;
    /**
     * 查询元数据信息
     * @param req
     * @return
     */
    @Override
    @PostMapping("/getMetaData")
    @NoDataSourceBind
    public List<PersonnelsMetaDTO> getMetaData(@RequestBody FtbPersonnelsMetaDataReq req) {
        switchTenantId(req.getTenantCode());
        List<PersonnelsMetaDTO> list = metaDataService.getMetaData(req);
        return list;
    }

    @GetMapping("/test")
    public ActionResult test(@RequestParam("userIds") List<String > userIds) {
        List<EmployeeMetaDataType> employeeMetaDataTypes = Arrays.asList(EmployeeMetaDataType.BASIC_INFO,
                EmployeeMetaDataType.EDUCATION_INFO,
                EmployeeMetaDataType.JOB_INFO,
                EmployeeMetaDataType.CONTRACT_INFO,
                EmployeeMetaDataType.PERSONAL_MATERIAL,
                EmployeeMetaDataType.ORGANIZATION_INFO,
                EmployeeMetaDataType.ROLE
        );
        FtbPersonnelsMetaDataReq ftbPersonnelsMetaDataReq = new FtbPersonnelsMetaDataReq();
        ftbPersonnelsMetaDataReq.setDataType(employeeMetaDataTypes);
        ftbPersonnelsMetaDataReq.setTenantCode("yawen");
        ftbPersonnelsMetaDataReq.setUserIds(userIds);
        List<PersonnelsMetaDTO> list = metaDataService.getMetaData(ftbPersonnelsMetaDataReq);
        return ActionResult.success(list);
    }

    /**
     * 查询用户当月是否已经离职
     *
     * @param userId   用户ID
     * @param tenantId 租户ID
     * @return true-已经离职  false-未离职
     */
    @GetMapping("/queryCurrMonthDepartStatus/{userId}/{tenantId}")
    @NoDataSourceBind
    public Boolean queryCurrMonthDepartStatus(@PathVariable("userId") String userId, @PathVariable("tenantId") String tenantId) {
        switchTenantId(tenantId);
        return metaDataService.queryCurrMonthDepartStatus(userId, tenantId);
    }

    @PostMapping("/queryCurrMonthDepartStatusByDate")
    @NoDataSourceBind
    @Override
    public Boolean queryCurrMonthDepartStatusByDate(@RequestBody FtbPersonnelsMetaFuctionReq req) {
        switchTenantId(req.getTenantId());
        return metaDataService.queryCurrMonthDepartStatusByDate(req.getUserId(), req.getTenantId(),req.getStartDate(),req.getEndDate());
    }

    @PostMapping("/query-current-month-leave")
    @NoDataSourceBind
    @Override
    public Map<String,Boolean> queryCurrMonthLeave(@RequestBody FtbPersonnelsMetaFuctionReq req) {
        switchTenantId(req.getTenantId());
        return metaDataService.queryCurrMonthLeave(req);
    }

    /**
     * 批量查询员工自定义字段
     */
    @PostMapping("/query-custom-filed")
    @Override
    public List<FtbXcCustomFieldVo> queryCustomFiled(@RequestBody FtbXcCustomFieldDto req) {
        if (CollUtil.isEmpty(req.getUserIds())) {
            return List.of();
        }
        // 自定义类型
        LambdaQueryWrapper<FtbPersonnelsRegistrationFormType> formTypeLambdaQueryWrapper = Wrappers.lambdaQuery();
        formTypeLambdaQueryWrapper.eq(FtbPersonnelsRegistrationFormType::getEnabledMark,0);
        formTypeLambdaQueryWrapper.eq(FtbPersonnelsRegistrationFormType::getStatus,0);
        List<FtbPersonnelsRegistrationFormType> ftbPersonnelsRegistrationFormTypes = ftbPersonnelsRegistrationFormTypeMapper.selectList(formTypeLambdaQueryWrapper);
        if (CollUtil.isEmpty(ftbPersonnelsRegistrationFormTypes)) {
            return List.of();
        }
        // 自定义字段查询
        List<String> forTypeIds = ftbPersonnelsRegistrationFormTypes.stream().map(SuperBaseEntity.SuperIBaseEntity::getId).collect(Collectors.toList());
        LambdaQueryWrapper<FtbPersonnelsRegistrationFormField> registrationFormFieldLambdaQueryWrapper = Wrappers.lambdaQuery();
        registrationFormFieldLambdaQueryWrapper.eq(FtbPersonnelsRegistrationFormField::getStatus,0);
        registrationFormFieldLambdaQueryWrapper.eq(FtbPersonnelsRegistrationFormField::getEnabledMark,0);
        registrationFormFieldLambdaQueryWrapper.eq(FtbPersonnelsRegistrationFormField::getSystemType,1);
        registrationFormFieldLambdaQueryWrapper.notIn(FtbPersonnelsRegistrationFormField::getType,5,6);
        registrationFormFieldLambdaQueryWrapper.in(FtbPersonnelsRegistrationFormField::getFormTypeId,forTypeIds);
        List<FtbPersonnelsRegistrationFormField> ftbPersonnelsRegistrationFormFields = ftbPersonnelsRegistrationFormFieldMapper.selectList(registrationFormFieldLambdaQueryWrapper);
        if (CollUtil.isEmpty(ftbPersonnelsRegistrationFormFields)) {
            return List.of();
        }
        // 自定义选项，翻译汉字
        List<String> formFields = ftbPersonnelsRegistrationFormFields.stream().map(SuperBaseEntity.SuperIBaseEntity::getId).collect(Collectors.toList());
        Map<String, FtbPersonnelsRegistrationFormField> formFieldMap = ftbPersonnelsRegistrationFormFields.stream().collect(Collectors.toMap(SuperBaseEntity.SuperIBaseEntity::getId, Function.identity()));
        LambdaQueryWrapper<FtbPersonnelsRegistrationFormFieldOption> fieldOptionLambdaQueryWrapper = Wrappers.lambdaQuery();
        fieldOptionLambdaQueryWrapper.eq(FtbPersonnelsRegistrationFormFieldOption::getEnabledMark,0);
        fieldOptionLambdaQueryWrapper.in(FtbPersonnelsRegistrationFormFieldOption::getFormFieldId,formFields);
        List<FtbPersonnelsRegistrationFormFieldOption> ftbPersonnelsRegistrationFormFieldOptions = ftbPersonnelsRegistrationFormFieldOptionMapper.selectList(fieldOptionLambdaQueryWrapper);
        Map<String, String> fieldOptionMaps = ftbPersonnelsRegistrationFormFieldOptions.stream()
                .collect(Collectors.toMap(SuperBaseEntity.SuperIBaseEntity::getId, FtbPersonnelsRegistrationFormFieldOption::getName));
        // 查询信息
        LambdaQueryWrapper<FtbPersonnelsStaffRoster> staffRosterLambdaQueryWrapper = Wrappers.lambdaQuery();
        staffRosterLambdaQueryWrapper.in(FtbPersonnelsStaffRoster::getUserId,req.getUserIds());
        List<FtbPersonnelsStaffRoster> ftbPersonnelsStaffRosters = ftbPersonnelsStaffRosterMapper.selectList(staffRosterLambdaQueryWrapper);
        Map<String, String> rostUserIdMap = ftbPersonnelsStaffRosters.stream().collect(Collectors.toMap(SuperBaseEntity.SuperIBaseEntity::getId, FtbPersonnelsStaffRoster::getUserId));
        List<String> rosterIds = ftbPersonnelsStaffRosters.stream().map(SuperBaseEntity.SuperIBaseEntity::getId).collect(Collectors.toList());
        // 获取档案信息
        LambdaQueryWrapper<FtbPersonnelsStaffRegistrationFormData> formDataLambdaQueryWrapper = Wrappers.lambdaQuery();
        formDataLambdaQueryWrapper.in(FtbPersonnelsStaffRegistrationFormData::getRosterId,rosterIds);
        formDataLambdaQueryWrapper.in(FtbPersonnelsStaffRegistrationFormData::getFormTypeId,forTypeIds);
        formDataLambdaQueryWrapper.in(FtbPersonnelsStaffRegistrationFormData::getFormFieldId,formFields);
        List<FtbPersonnelsStaffRegistrationFormData> ftbPersonnelsStaffRegistrationFormData = ftbPersonnelsStaffRegistrationFormDataMapper.selectList(formDataLambdaQueryWrapper);
        if (CollUtil.isEmpty(ftbPersonnelsStaffRegistrationFormData)) {
            return List.of();
        }
        Map<String, List<FtbPersonnelsStaffRegistrationFormData>> forDataGroupBys = ftbPersonnelsStaffRegistrationFormData.stream()
                .collect(Collectors.groupingBy(FtbPersonnelsStaffRegistrationFormData::getRosterId));

        List<FtbXcCustomFieldVo> result = forDataGroupBys.entrySet().stream().map(entry -> {
            FtbXcCustomFieldVo ftbXcCustomFieldVo = new FtbXcCustomFieldVo();
            String userId = rostUserIdMap.get(entry.getKey());
            ftbXcCustomFieldVo.setUserId(userId);
            if (CollUtil.isNotEmpty(entry.getValue())) {
                List<FtbXcCustomFieldVo.CustomField> customFields = entry.getValue().stream().map(a -> {
                    if (StrUtil.isBlank(a.getValue())) {
                        return null;
                    }
                    FtbXcCustomFieldVo.CustomField customField = new FtbXcCustomFieldVo.CustomField();
                    FtbPersonnelsRegistrationFormField registrationFormField = formFieldMap.get(a.getFormFieldId());
                    customField.setCustomFieldName(registrationFormField.getName());
                    if (registrationFormField.getType() == 2) {
                        customField.setCustomFieldValue(fieldOptionMaps.getOrDefault(a.getValue(),""));
                    } else if (registrationFormField.getType() == 3) {
                        // 多选逗号隔开
                        String multiSelect = Arrays.stream(a.getValue().split(","))
                                .map(b -> fieldOptionMaps.getOrDefault(b, ""))
                                .filter(StrUtil::isNotBlank)
                                .collect(Collectors.joining(","));
                        customField.setCustomFieldValue(multiSelect);
                    } else {
                        customField.setCustomFieldValue(a.getValue());
                    }
                    return customField;
                }).filter(Objects::nonNull).collect(Collectors.toList());
                ftbXcCustomFieldVo.setCustomFieldList(customFields);
            }
            return ftbXcCustomFieldVo;
        }).collect(Collectors.toList());
        return result;
    }

    private void switchTenantId(String tenantId) {
        // 判断是否为多租户
        if (configValueUtil.isMultiTenancy()) {
            // 判断是不是从外面直接请求
            if (StringUtil.isNotEmpty(tenantId)) {
                //切换成租户库
                try {
                    TenantDataSourceUtil.switchTenant(tenantId);
                } catch (LoginException e) {
                    throw new RuntimeException("切换租户失败");
                }
            } else {
                UserInfo userInfo = UserProvider.getUser();
                Assert.notNull(userInfo.getUserId(), "缺少租户信息");
                DataSourceContextHolder.setDatasource(userInfo.getTenantId(), userInfo.getTenantDbConnectionString(), userInfo.isAssignDataSource());
            }
        }
    }
}
