package com.yeejoin.amos.boot.module.tcm.biz.service.impl;

import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.yeejoin.amos.boot.module.common.biz.event.CommonPublisher;
import com.yeejoin.amos.boot.module.common.biz.refresh.DataRefreshEvent;
import com.yeejoin.amos.boot.module.tcm.api.dto.AccountDto;
import com.yeejoin.amos.boot.module.tcm.api.dto.BaseInstitutionRegisterDto;
import com.yeejoin.amos.boot.module.tcm.api.dto.BaseUnitLicenceDto;
import com.yeejoin.amos.boot.module.tcm.api.dto.TzsBaseInstitutionDto;
import com.yeejoin.amos.boot.module.tcm.api.entity.BaseUnitLicence;
import com.yeejoin.amos.boot.module.tcm.api.entity.TzBaseEnterpriseInfo;
import com.yeejoin.amos.boot.module.tcm.api.entity.TzsBaseInstitution;
import com.yeejoin.amos.boot.module.tcm.api.enums.EnterpriseEnums;
import com.yeejoin.amos.boot.module.tcm.api.mapper.TzsBaseInstitutionMapper;
import com.yeejoin.amos.boot.module.tcm.api.service.ITzsBaseInstitutionService;
import com.yeejoin.amos.boot.module.tcm.flc.api.dto.RegUnitInfoDto;
import com.yeejoin.amos.boot.module.tcm.flc.api.entity.RegUnitInfo;
import com.yeejoin.amos.boot.module.tcm.flc.biz.service.impl.RegUnitInfoServiceImpl;
import com.yeejoin.amos.component.feign.model.FeignClientResult;
import com.yeejoin.amos.feign.privilege.Privilege;
import com.yeejoin.amos.feign.privilege.model.AgencyUserModel;
import com.yeejoin.amos.feign.privilege.model.CompanyModel;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.ObjectUtils;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.typroject.tyboot.core.foundation.utils.Bean;
import org.typroject.tyboot.core.foundation.utils.ValidationUtil;
import org.typroject.tyboot.core.rdbms.service.BaseService;
import org.typroject.tyboot.core.restful.exception.instance.BadRequest;

import java.util.Collections;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

/**
 * 服务实现类
 *
 * @author system_generator
 * @date 2023-08-31
 */
@Slf4j
@Service
public class TzsBaseInstitutionServiceImpl extends BaseService<TzsBaseInstitutionDto,TzsBaseInstitution,TzsBaseInstitutionMapper> implements ITzsBaseInstitutionService {

    @Autowired
    RegUnitInfoServiceImpl regUnitInfoService;

    @Autowired
    BaseUnitLicenceServiceImpl baseUnitLicenceService;

    @Autowired
    StartPlatformTokenService startPlatformTokenService;

    @Autowired
    private CommonPublisher publisher;

    /**
     * 分页查询
     */
    public Page<TzsBaseInstitutionDto> queryForTzsBaseInstitutionPage(Page<TzsBaseInstitutionDto> page)   {
        return this.queryForPage(page, null, false);
    }

    /**
     * 列表查询 示例
     */
    public List<TzsBaseInstitutionDto> queryForTzsBaseInstitutionList()   {
        return this.queryForList("" , false);
    }


    @Transactional
    public void register(BaseInstitutionRegisterDto dto) {
        dto.setUnitCodeType("1060");
        dto.setUnitCodeTypeName("营业执照");
        String unitType = StringUtils.join(dto.getUnitTypeList(), ",");
        String unitTypeCode = StringUtils.join(dto.getUnitTypeCodeList(), ",");
        CompanyModel companyInfo = new CompanyModel();
        companyInfo.setAddress(dealNull2EmptyString(dto.getProvince())
                + dealNull2EmptyString(dto.getCity()) + dealNull2EmptyString(dto.getDistrict())
                + dealNull2EmptyString(dto.getStree()) + dealNull2EmptyString(dto.getCommunity())
                + dealNull2EmptyString(dto.getAddress()));
        companyInfo.setAgencyCode("tzs");
        companyInfo.setParentId(Long.parseLong(dto.getManagementUnitId()));
        companyInfo.setLevel("company");
        companyInfo.setCompanyName(dto.getRegUnitMessage().getUnitName());
        companyInfo.setCompanyCode(dto.getUnitCode());
        companyInfo.setContact(dto.getLegalPerson());
        companyInfo.setCompanyType(unitType);
        companyInfo.setLandlinePhone(dto.getLegalPersonTel());
        dto.setName(dto.getRegUnitMessage().getUnitName());
        TzBaseEnterpriseInfo baseEnterpriseInfo;
        try {
            startPlatformTokenService.setRequestContext();
            FeignClientResult<CompanyModel> companyResult = Privilege.companyClient.create(companyInfo);
            if (companyResult == null || companyResult.getResult() == null) {
                throw new BadRequest("单位注册失败");
            }
            CompanyModel company = companyResult.getResult();
            dto.setAmosCompanySeq(company.getSequenceNbr().toString());
            AccountDto accountDto = new AccountDto();
            accountDto.setCompanyId(company.getSequenceNbr());
            accountDto.setUnitTypeCode(unitTypeCode);
            accountDto.setAdminTel(dto.getAdminTel());
            accountDto.setPwd(dto.getAdminLoginPwd());
            accountDto.setLoginName(dto.getAdminLoginName());
            accountDto.setAdminUserName(dto.getAdminName());
            AgencyUserModel user = regUnitInfoService.createUser(accountDto,null);
            dto.setAdminUserId(user.getUserId());
            RegUnitInfoDto regUnitInfoDto = new RegUnitInfoDto();
            BeanUtils.copyProperties(dto, regUnitInfoDto);
            regUnitInfoDto.setAppId(regUnitInfoService.createAppId(user));
            baseEnterpriseInfo = regUnitInfoService.createBaseEnterpriseInfo(regUnitInfoDto, EnterpriseEnums.SY_DW.getType());
            TzsBaseInstitution tzsBaseInstitution = new TzsBaseInstitution();
            BeanUtils.copyProperties(dto.getRegUnitMessage(), tzsBaseInstitution);
            tzsBaseInstitution.setUseCode(dto.getUnitCode());
            tzsBaseInstitution.setEnterpriseId(baseEnterpriseInfo.getSequenceNbr());
            this.save(tzsBaseInstitution);
            // 插入tz_flc_reg_unit_info
            RegUnitInfo regUnitInfo = new RegUnitInfo();
            Bean.copyExistPropertis(dto, regUnitInfo);
            if (!ObjectUtils.isEmpty(regUnitInfo.getAdminName())){
                regUnitInfo.setContactPerson(regUnitInfo.getAdminName());
            }
            if (!ObjectUtils.isEmpty(regUnitInfo.getAdminTel())){
                regUnitInfo.setContactPersonTel(regUnitInfo.getAdminTel());
            }
            if(!ValidationUtil.isEmpty(dto.getUnitLicences())){
                //添加不在字典中的登记机关
                List<String> approvedOrganList = dto.getUnitLicences().stream()
                        .map(BaseUnitLicenceDto::getApprovedOrgan)
                        .distinct()
                        .collect(Collectors.toList());
                regUnitInfoService.addNotInDJJGDictionary(approvedOrganList);
            }
            regUnitInfoService.save(regUnitInfo);
            // 3.插入单位注册许可信息表：tz_base_unit_licence
            Map<?, ?> dictOfDJJGMap = regUnitInfoService.dictOfDJJG();
            List<BaseUnitLicence> baseUnitLicences = dto.getUnitLicences().stream().map(s -> {
                s.setUnitCode(dto.getUnitCode());
                s.setUnitName(dto.getName());
                BaseUnitLicence target = new BaseUnitLicence();
                Bean.copyExistPropertis(s, target);
                target.setApprovedOrganCode((String) dictOfDJJGMap.get(target.getApprovedOrgan()));
                return target;
            }).collect(Collectors.toList());
            if (!baseUnitLicences.isEmpty()) {
                baseUnitLicenceService.saveOrUpdateBatch(baseUnitLicences);
            }
        } catch (Exception e) {
            log.error("awds:"+e.getMessage(), e);
            try {
                // 失败后回滚：删除已经创建的企业信息
                if (StringUtils.isNotEmpty(dto.getAmosCompanySeq())) {
                    FeignClientResult<CompanyModel> feignClientResult = Privilege.companyClient.seleteOne(Long.parseLong(dto.getAmosCompanySeq()));
                    if (feignClientResult != null && feignClientResult.getResult() != null) {
                        Privilege.companyClient.deleteCompany(dto.getAmosCompanySeq());
                    }
                }
                // 失败后回滚：删除已经创建的管理员账号
                if (StringUtils.isNotEmpty(dto.getAdminUserId())) {
                    FeignClientResult<AgencyUserModel> feignClientResult = Privilege.agencyUserClient.queryByUserId(dto.getAdminUserId());
                    if (feignClientResult != null && feignClientResult.getResult() != null) {
                        Privilege.agencyUserClient.multDeleteUser(dto.getAdminUserId());
                    }
                }
            } catch (Exception rollbackException) {
                log.error("回滚操作发生异常: {}", rollbackException.getMessage(), rollbackException);
            }

            throw new RuntimeException("事业单位注册失败，请联系管理员！");
        }
        publisher.publish(new DataRefreshEvent(this,  Collections.singletonList(baseEnterpriseInfo.getSequenceNbr() + ""), DataRefreshEvent.DataType.enterprise.name(), DataRefreshEvent.Operation.INSERT));
    }

    private String dealNull2EmptyString(String t) {
        return StringUtils.isEmpty(t) ? "" : t;
    }

}