package org.dromara.main.service.impl;

import cn.hutool.core.util.ObjectUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;

import lombok.RequiredArgsConstructor;
import org.dromara.common.core.exception.ServiceException;
import org.dromara.common.core.utils.MapstructUtils;
import org.dromara.common.core.utils.StringUtils;
import org.dromara.common.mybatis.core.page.PageQuery;
import org.dromara.common.mybatis.core.page.TableDataInfo;
import org.dromara.common.satoken.utils.LoginHelper;
import org.dromara.main.domain.MainAudit;
import org.dromara.main.domain.MainCompanyApply;
import org.dromara.main.domain.MainPosition;
import org.dromara.main.domain.MainPostApply;
import org.dromara.main.domain.bo.MainAuditBo;
import org.dromara.main.domain.vo.MainAuditVo;
import org.dromara.main.mapper.MainAuditMapper;
import org.dromara.main.mapper.MainCompanyApplyMapper;
import org.dromara.main.mapper.MainPostApplyMapper;
import org.dromara.main.service.IMainAuditService;
import org.dromara.main.service.IMainPositionService;
import org.dromara.system.domain.bo.SysPostBo;
import org.dromara.system.domain.bo.SysTenantBo;
import org.dromara.system.service.ISysPostService;
import org.dromara.system.service.ISysTenantService;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.Collection;
import java.util.Date;
import java.util.List;

import static org.dromara.common.mybatis.core.mapper.BaseMapperPlus.log;

@RequiredArgsConstructor
@Service
public class MainAuditServiceImpl implements IMainAuditService {

    private final MainAuditMapper baseMapper;
    private final MainCompanyApplyMapper companyApplyMapper;
    private final MainPostApplyMapper postApplyMapper;
    private final ISysTenantService tenantService;
    private final ISysPostService sysPostService;
    private final IMainPositionService mainPositionService;
    @Override
    public TableDataInfo<MainAuditVo> queryPageList(MainAuditBo bo, PageQuery pageQuery) {
        LambdaQueryWrapper<MainAudit> lqw = buildQueryWrapper(bo);
        Page<MainAuditVo> result = baseMapper.selectVoPage(pageQuery.build(), lqw);
        return TableDataInfo.build(result);
    }

    @Override
    public TableDataInfo<MainAuditVo> queryDetailPageList(MainAuditBo bo, PageQuery pageQuery) {
        LambdaQueryWrapper<MainAudit> lqw = buildQueryWrapper(bo);
        Page<MainAuditVo> page = new Page<>(pageQuery.getPageNum(), pageQuery.getPageSize());
        IPage<MainAuditVo> result = baseMapper.selectAuditDetailPage(page, lqw);
        return TableDataInfo.build(result);
    }

    @Override
    public List<MainAuditVo> queryList(MainAuditBo bo) {
        LambdaQueryWrapper<MainAudit> lqw = buildQueryWrapper(bo);
        return baseMapper.selectVoList(lqw);
    }

    @Override
    public List<MainAuditVo> queryDetailList(MainAuditBo bo) {
        LambdaQueryWrapper<MainAudit> lqw = buildQueryWrapper(bo);
        return baseMapper.selectAuditDetailList(lqw);
    }

    @Override
    public MainAuditVo queryById(Long id) {
        return baseMapper.selectVoById(id);
    }

    @Override
    public MainAuditVo queryDetailById(Long id) {
        return baseMapper.selectAuditDetailById(id);
    }

    @Override
    public Boolean insertByBo(MainAuditBo bo) {
        MainAudit add = MapstructUtils.convert(bo, MainAudit.class);
        validEntityBeforeSave(add);
        boolean flag = baseMapper.insert(add) > 0;
        if (flag) {
            bo.setId(add.getId());
        }
        return flag;
    }

    @Override
    public Boolean updateByBo(MainAuditBo bo) {
        MainAudit update = MapstructUtils.convert(bo, MainAudit.class);
        validEntityBeforeSave(update);
        return baseMapper.updateById(update) > 0;
    }

    @Override
    public Boolean deleteWithValidByIds(Collection<Long> ids, Boolean isValid) {
        return baseMapper.deleteBatchIds(ids) > 0;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public Boolean auditPass(Long id, String remark) {
        MainAudit audit = baseMapper.selectById(id);
        if (audit == null) {
            return false;
        }

        // 更新审核状态
        audit.setAuditResult(1);
        audit.setAuditRemark(remark);
        audit.setAuditTime(new Date());
        audit.setAuditBy(LoginHelper.getUserId());
        boolean updateSuccess = baseMapper.updateById(audit) > 0;

        if (!updateSuccess) {
            return false;
        }

        // 根据审核类型同步数据
        try {
            if (audit.getAuditType() == 1) {
                // 企业审核通过 - 同步到 sys_tenant 表
                syncCompanyToTenant(audit.getTargetId());
            } else if (audit.getAuditType() == 2) {
                // 岗位审核通过 - 保存到 main_post_apply 表（标记为已通过）
                syncPostApplyToMainPosition(audit.getTargetId());
            }
        } catch (Exception e) {
            log.error("审核通过后数据同步失败", e);
            throw new ServiceException("审核通过后数据同步失败：" + e.getMessage());
        }

        return true;
    }

    /**
     * 将企业申请数据同步到租户表
     */
    /**
     * 将企业申请数据同步到租户表
     */
    private void syncCompanyToTenant(Long applyId) {
        // 1. 查询企业申请信息
        MainCompanyApply companyApply = companyApplyMapper.selectById(applyId);
        if (companyApply == null) {
            throw new ServiceException("企业申请信息不存在");
        }

        // 2. 检查是否已经同步过（避免重复）
        if (StringUtils.isNotBlank(companyApply.getTenantId())) {
            return; // 已经有租户ID，说明已同步过
        }

        // 3. 构建租户对象
        SysTenantBo tenantBo = new SysTenantBo();
        tenantBo.setCompanyName(companyApply.getCompanyName());
        tenantBo.setLicenseNumber(companyApply.getCreditCode());
        tenantBo.setAddress(companyApply.getOfficeAddress());
        tenantBo.setContactUserName(companyApply.getSurname() + companyApply.getName());
        tenantBo.setContactPhone(companyApply.getMobile());
        tenantBo.setCompanyEntrustProof(companyApply.getAuthLetter()); // 暂时注释
        tenantBo.setLogo(companyApply.getAvatar());
        tenantBo.setStatus("0"); // 正常状态

        // 必需字段：创建系统用户的用户名和密码
        tenantBo.setUsername(companyApply.getMobile()); // 使用手机号作为用户名
        tenantBo.setPassword("666666"); // 设置默认密码
        tenantBo.setEmail(companyApply.getOfficialAccount()); // 设置邮箱

        // 4. 创建租户
        Boolean success = tenantService.insertByBo(tenantBo);
        if (!success) {
            throw new ServiceException("创建租户失败");
        }

        // 5. 更新企业申请表的 tenant_id 和 apply_status
        companyApply.setTenantId(tenantBo.getTenantId());
        companyApply.setApplyStatus(2); // 已通过
        companyApplyMapper.updateById(companyApply);
    }

    /**
     * 将岗位申请标记为已通过
     */
    /**
     * 将岗位申请数据同步到 sys_post 表
     */
    private void syncPostApplyToMainPosition(Long applyId) {
        // 1. 查询岗位申请信息
        MainPostApply postApply = postApplyMapper.selectById(applyId);
        if (postApply == null) {
            throw new ServiceException("岗位申请信息不存在");
        }

        // 2. 检查是否已经同步过（避免重复）
        if (postApply.getPostId() != null) {
            return; // 已经有岗位ID，说明已同步过
        }

        // 3. 构建 MainPosition 对象，从 MainPostApply 复制数据
        MainPosition position = new MainPosition();
        position.setTenantId(postApply.getTenantId());
        position.setPostName(postApply.getPostName());
        position.setPostDescription(postApply.getPostDescription());
        position.setWorkProvince(postApply.getWorkProvince());
        position.setWorkCity(postApply.getWorkCity());
        position.setWorkDistrict(postApply.getWorkDistrict());
        position.setWorkAddress(postApply.getWorkAddress());
        position.setPostType(postApply.getPostType());
        position.setEducationRequirement(postApply.getEducationRequirement());
        position.setSalaryType(postApply.getSalaryType());
        position.setSalaryRange(postApply.getSalaryRange());
        position.setMinSalary(postApply.getMinSalary());
        position.setMaxSalary(postApply.getMaxSalary());
        position.setRecruitNum(postApply.getRecruitNum());
        position.setRegistrationStartDate(postApply.getRegistrationStartDate());
        position.setRegistrationEndDate(postApply.getRegistrationEndDate());
        position.setIsUrgent(postApply.getIsUrgent());
        position.setSchoolRequirement(postApply.getSchoolRequirement());
        position.setGenderRequirement(postApply.getGenderRequirement());
        position.setGradeRequirement(postApply.getGradeRequirement());
        position.setArrivalTime(postApply.getArrivalTime());
        position.setInternshipDuration(postApply.getInternshipDuration());
        position.setWillingToTravel(postApply.getWillingToTravel());
        position.setWelfareTags(postApply.getWelfareTags());
        position.setJobRequirement(postApply.getJobRequirement());
        position.setPostLevel(postApply.getPostLevel());
        position.setAssessmentTime(postApply.getAssessmentTime());
        position.setGradeA(postApply.getGradeA());
        position.setGradeB(postApply.getGradeB());
        position.setGradeC(postApply.getGradeC());

        // 4. 插入到 main_position 表
        boolean success = mainPositionService.save(position);
        if (!success) {
            throw new ServiceException("创建岗位失败");
        }

        // 5. 更新 main_post_apply 表
        postApply.setPostId(position.getId()); // 保存新创建的岗位ID
        postApply.setApplyStatus(2); // 已通过
        postApplyMapper.updateById(postApply);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public Boolean auditReject(Long id, String remark) {
        MainAudit audit = baseMapper.selectById(id);
        if (audit == null) {
            return false;
        }

        audit.setAuditResult(2);
        audit.setAuditRemark(remark);
        audit.setAuditTime(new Date());
        audit.setAuditBy(LoginHelper.getUserId());

        // 更新申请表的拒绝原因
        if (audit.getAuditType() == 1) {
            MainCompanyApply companyApply = companyApplyMapper.selectById(audit.getTargetId());
            if (companyApply != null) {
                companyApply.setApplyStatus(3); // 已驳回
                companyApply.setRejectReason(remark);
                companyApplyMapper.updateById(companyApply);
            }
        } else if (audit.getAuditType() == 2) {
            MainPostApply postApply = postApplyMapper.selectById(audit.getTargetId());
            if (postApply != null) {
                postApply.setApplyStatus(3); // 已驳回
                postApply.setRejectReason(remark);
                postApplyMapper.updateById(postApply);
            }
        }

        return baseMapper.updateById(audit) > 0;
    }

    private LambdaQueryWrapper<MainAudit> buildQueryWrapper(MainAuditBo bo) {
        LambdaQueryWrapper<MainAudit> lqw = Wrappers.lambdaQuery();
        lqw.eq(ObjectUtil.isNotNull(bo.getAuditType()), MainAudit::getAuditType, bo.getAuditType());
        lqw.eq(ObjectUtil.isNotNull(bo.getTargetId()), MainAudit::getTargetId, bo.getTargetId());
        lqw.eq(ObjectUtil.isNotNull(bo.getAuditResult()), MainAudit::getAuditResult, bo.getAuditResult());
        lqw.orderByDesc(MainAudit::getCreateTime);
        return lqw;
    }

    private void validEntityBeforeSave(MainAudit entity) {
    }
}
