package jnpf.personnels.service.impl;

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.collection.CollectionUtil;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.core.util.StrUtil;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import com.baomidou.mybatisplus.core.toolkit.StringPool;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.github.pagehelper.PageInfo;
import com.google.common.collect.Maps;
import io.seata.spring.annotation.GlobalTransactional;
import jnpf.attendance.AttendanceGroupApi;
import jnpf.base.ActionResult;
import jnpf.base.UserInfo;
import jnpf.base.vo.PageListVO;
import jnpf.entity.AttendanceGroup;
import jnpf.entity.FileEntity;
import jnpf.entity.StoreEntity;
import jnpf.enums.personnel.FtbPersonnelsCheckStatusCodeEnum;
import jnpf.enums.personnel.PhoneStatusEnum;
import jnpf.model.attendance.vo.AttendanceGroupVo;
import jnpf.model.cultivate.CultivatePage;
import jnpf.model.cultivate.req.paper.SavePaperReq;
import jnpf.model.enums.FtbPersonnelsAuditTaskEnum;
import jnpf.model.enums.FtbPersonnelsCofigEnum;
import jnpf.model.personnels.bo.FtbAddStaffImportRedisBO;
import jnpf.model.personnels.dto.audit.FtbPersonnelsAuditDto;
import jnpf.model.personnels.dto.salary.FtbPersonnelsSalaryInfo;
import jnpf.model.personnels.dto.staff.employment.FtbPersonnelsEmployApplyDto;
import jnpf.model.personnels.dto.staff.employment.FtbPersonnelsStaffEmploymentApplyDto;
import jnpf.model.personnels.dto.staff.roster.StaffBaseInfoDto;
import jnpf.model.personnels.po.*;
import jnpf.model.personnels.req.employment.*;
import jnpf.model.personnels.vo.app.FtbPersonnelsBubbleCountVO;
import jnpf.model.personnels.vo.employment.AddStaffEmploymentApplyExcelERRVO;
import jnpf.model.personnels.vo.employment.AddStaffEmploymentApplyExcelVO;
import jnpf.model.personnels.vo.employment.FtbPersonnelsStaffEmploymentApplyVO;
import jnpf.model.personnels.vo.task.FtbPersonnelsAuditInfoVO;
import jnpf.permission.OrganizeApi;
import jnpf.permission.PositionApi;
import jnpf.permission.entity.OrganizeEntity;
import jnpf.permission.entity.PositionEntity;
import jnpf.permission.entity.UserEntity;
import jnpf.permission.model.position.PositionGradesInfoVO;
import jnpf.personnels.listeners.BaseEasyExcelCommonListener;
import jnpf.personnels.mapper.FtbPersonnelsRegistrationFormFieldMapper;
import jnpf.personnels.mapper.FtbPersonnelsRegistrationFormFieldOptionMapper;
import jnpf.personnels.mapper.FtbPersonnelsStaffEmploymentApplyMapper;
import jnpf.personnels.mapper.FtbPersonnelsUchisuikePondMapper;
import jnpf.personnels.service.*;
import jnpf.personnels.utils.PersonalizedTenantWhitelistUtils;
import jnpf.personnels.utils.PersonnelOrgUtils;
import jnpf.personnels.utils.PersonnelPerUtils;
import jnpf.personnels.utils.SmsSendUtil;
import jnpf.util.JsonUtil;
import jnpf.util.RedisUtil;
import jnpf.util.UserProvider;
import jnpf.util.excel.EasyExcelUtils;
import lombok.SneakyThrows;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.jetbrains.annotations.Nullable;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.InputStream;
import java.math.BigDecimal;
import java.util.*;
import java.util.stream.Collectors;

@Service
@Slf4j
public class FtbPersonnelsStaffEmploymentApplyServiceImpl extends ServiceImpl<FtbPersonnelsStaffEmploymentApplyMapper, FtbPersonnelsStaffEmploymentApply> implements FtbPersonnelsStaffEmploymentApplyService {

    @Autowired
    private FtbPersonnelsStaffRegistrationFormDataService registrationFormDataService;

    @Autowired
    private OrganizeApi organizeApi;

    @Autowired
    private PositionApi positionApi;


    @Autowired
    private FtbPersonnelsAuditRunTaskService auditRunTaskService;

    @Autowired
    private PersonnelOrgUtils personnelOrgUtils;

    @Autowired
    private FtbPersonnelsStaffRosterService rosterService;

    @Resource
    private RedisUtil redisUtil;

    @Autowired
    private FtbPersonnelsAuditSubConfigService subConfigService;

    @Autowired
    private SmsSendUtil smsSendUtil;

    @Autowired
    private PersonnelPerUtils personnelPerUtils;

    @Autowired
    private FtbPersonnelsUchisuikePondMapper uchisuikePondMapper;

    @Resource
    private FtbPersonnelsBlacklistService ftbPersonnelsBlacklistService;

    @Resource
    private AttendanceGroupApi attendanceGroupApi;

    @Autowired
    FtbPersonnelsRegistrationFormFieldOptionMapper optionMapper;

    @Autowired
    PersonalizedTenantWhitelistUtils personalizedTenantWhitelistUtils;

    @Resource
    FtbPersonnelsRegistrationFormFieldMapper registrationFormFieldMapper;


    public static final String REDIS_KEY = "ftb:personnels:staff:employment:apply:%s";


    @Resource(name = "ftbPersonnelsService")
    private BaseEasyExcelCommonListener<AddStaffEmploymentApplyExcelVO, AddStaffEmploymentApplyExcelERRVO> baseEasyExcelCommonListener;


    @Override
    public PageInfo<FtbPersonnelsStaffEmploymentApplyDto> getPageList(QueryStaffEmploymentApplyListReq req) {

        Page<FtbPersonnelsStaffEmploymentApplyDto> queryPage = null;
        List<FtbPersonnelsStaffEmploymentApplyDto> records = new ArrayList<>();
        List<String> selectOrgList;
        List<String> authOrgList = personnelPerUtils.obtainPersonnelOrganizationIdDataPermissions();//获取用户组织权限
        if (CollectionUtil.isEmpty(authOrgList)) {
            authOrgList = new ArrayList<>();
        }
        if (StringUtils.isEmpty(req.getCurrOrg())) {
            selectOrgList = authOrgList;
        } else {
            if (CollectionUtil.isEmpty(authOrgList)) {
                selectOrgList = new ArrayList<>(List.of(req.getCurrOrg().split(StringPool.COMMA)));
            } else {
                List<String> userSubList = List.of(req.getCurrOrg().split(StringPool.COMMA));
                // 使用Stream API获取交集
                selectOrgList = authOrgList.stream()
                        .filter(userSubList::contains)
                        .collect(Collectors.toList());
                if (CollectionUtil.isEmpty(selectOrgList)) {
                    return new PageInfo<>(records);
                }
            }
        }
        Boolean whitelist = personalizedTenantWhitelistUtils.isItOnTheWhitelist();
        req.setExt(whitelist);
        req.setInnerSelectOrgList(selectOrgList);
        if (req.getListType() == 0) {
            queryPage = baseMapper.expectPagingQuery(Page.of(req.getCurrentPage(), req.getPageSize()), req);
            records = queryPage.getRecords();
        } else {
            queryPage = baseMapper.checkPagingQuery(Page.of(req.getCurrentPage(), req.getPageSize()), req);
            records = queryPage.getRecords();
        }
        if (CollectionUtil.isNotEmpty(records)) {
            //补充组织 岗位 职等 信息 推荐人、推荐门店
            personnelOrgUtils.fillOrgName(records);
            personnelOrgUtils.fillPositionName(records);
            personnelOrgUtils.fillRankName(records);
            personnelOrgUtils.fillExpireDayNum(records);
            //查询合同类型
            personnelOrgUtils.fillContractTypeName(records);
            // 数据补充
            if (whitelist) {
                List<String> intentionOrgIds = records.stream().map(FtbPersonnelsStaffEmploymentApplyDto::getIntentionOrgId).collect(Collectors.toList());
                List<OrganizeEntity> organizeList = organizeApi.getOrganizeName(intentionOrgIds);
                Map<String, String> orgMap = organizeList.stream().collect(Collectors.toMap(OrganizeEntity::getId, OrganizeEntity::getFullName));
                records.forEach(item -> {
                    if (orgMap.containsKey(item.getIntentionOrgId())) {
                        item.setIntentionOrgName(orgMap.get(item.getIntentionOrgId()));
                    }
                });
            }

        }
        //构建分页返回数据
        PageInfo<FtbPersonnelsStaffEmploymentApplyDto> pageInfo = new PageInfo<>();
        pageInfo.setList(records);
        pageInfo.setPageSize((int) queryPage.getSize());
        pageInfo.setPageNum((int) queryPage.getCurrent());
        pageInfo.setTotal((int) queryPage.getTotal());
        return pageInfo;
    }

    @Override
    public PageInfo<FtbPersonnelsStaffEmploymentApplyDto> getAppPageList(QueryAppStaffEmploymentApplyListReq req, String loginUserId) {
        Page<FtbPersonnelsStaffEmploymentApplyDto> queryPage = null;
        List<FtbPersonnelsStaffEmploymentApplyDto> records = new ArrayList<>();
        if (req.getListType() == 0) {
            List<String> authOrgList = personnelPerUtils.obtainPersonnelOrganizationIdDataPermissions();//获取用户组织权限
            if (CollectionUtil.isEmpty(authOrgList)) {
                authOrgList = new ArrayList<>();
            }
            req.setInnerSelectOrgList(authOrgList);
            queryPage = baseMapper.expectAppPagingQuery(Page.of(req.getCurrentPage(), req.getPageSize()), req);
        } else if (req.getListType() == 2) {
            // 2.我的审批
            Integer configType = FtbPersonnelsCofigEnum.ONBOARDING_APPROVAL_CONFIGURATION.getConfigType();
            // 待审批
            if (req.getCheckStatus() == 0 ){
                queryPage = baseMapper.pagingQueryWebMyCheckList(Page.of(req.getCurrentPage(),
                                req.getPageSize()),
                        loginUserId,
                        configType);
            }else {
                if (req.getCheckStatus() == 1) queryPage = baseMapper.getApprovedList(Page.of(req.getCurrentPage(), req.getPageSize()), loginUserId, configType,1);
                if (req.getCheckStatus() == 2) queryPage = baseMapper.getApprovedList(Page.of(req.getCurrentPage(), req.getPageSize()), loginUserId, configType,2);
                if (req.getCheckStatus() == 3) queryPage = baseMapper.getApprovedList(Page.of(req.getCurrentPage(), req.getPageSize()), loginUserId, configType,3);
            }

        } else if (req.getListType() == 3) {
            if (req.getCheckStatus() == 1) queryPage = baseMapper.getListForApp(Page.of(req.getCurrentPage(), req.getPageSize()), loginUserId, 1);
            if (req.getCheckStatus() == 2) queryPage = baseMapper.getListForApp(Page.of(req.getCurrentPage(), req.getPageSize()), loginUserId, 2);
            if (req.getCheckStatus() == 3) queryPage = baseMapper.getListForApp(Page.of(req.getCurrentPage(), req.getPageSize()), loginUserId, 3);
        }
        records = queryPage.getRecords();
        if (CollectionUtil.isNotEmpty(records)) {
            //补充组织 岗位 职等 信息 推荐人、推荐门店
            personnelOrgUtils.fillOrgName(records);
            personnelOrgUtils.fillPositionName(records);
            personnelOrgUtils.fillRankName(records);
            personnelOrgUtils.fillExpireDayNum(records);
            //查询合同类型
            personnelOrgUtils.fillContractTypeName(records);
        }
        //构建分页返回数据
        PageInfo<FtbPersonnelsStaffEmploymentApplyDto> pageInfo = new PageInfo<>();
        records.forEach(item -> {
            Boolean b = auditRunTaskService.checkIsTheCurrentBusinessInTheApprovalProcess(item.getId());
            if (b) {
                item.setIsItUnderReview("1");
            } else {
                item.setIsItUnderReview("0");
            }
        });
        pageInfo.setList(records);
        pageInfo.setPageSize((int) queryPage.getSize());
        pageInfo.setPageNum((int) queryPage.getCurrent());
        pageInfo.setTotal((int) queryPage.getTotal());
        return pageInfo;
    }

    @Override
    @Transactional
    public void approval(EmploymentApplyCheckDto dto) {
        String id = dto.getId();
        FtbPersonnelsStaffEmploymentApply entity = queryAndCheckStaffEmploymentApply(id);
        if (entity.getIsNeedCheck() == 1) {
            throw new RuntimeException("该员工入职不需要审核");
        }
        if (entity.getIsNeedCheck() == 0 && entity.getCheckStatus() == 2) {
            throw new RuntimeException("该员工入职审核已经通过");
        }
        if (entity.getIsNeedCheck() == 0 && entity.getCheckStatus() == 3) {
            throw new RuntimeException("该员工入职审核已经不通过");
        }
        if (entity.getIsNeedCheck() == 0 && entity.getCheckStatus() == 4) {
            throw new RuntimeException("该员工入职审核已经撤销");
        }
        FtbPersonnelsAuditDto checkDto = new FtbPersonnelsAuditDto();
        checkDto.setBusinessId(entity.getId());
        if (ObjectUtil.isNotEmpty(dto.getIsConformSalary())) {
            checkDto.setDoesTheSalaryComplyWith(dto.getIsConformSalary());
        }
        if (ObjectUtil.isNotEmpty(dto.getMsg())) {
            checkDto.setApprovalComments(dto.getMsg());
        }
        if (ObjectUtil.isNotEmpty(dto.getIsPass())) {
            checkDto.setFlag(String.valueOf(dto.getIsPass()));
        }
        FtbPersonnelsAuditTaskEnum code = auditRunTaskService.performReview(checkDto);
        switch (code) {
            case PENDING:
                entity.setCheckStatus(0);
                break;
            case UNDER_REVIEW:
                entity.setCheckStatus(1);
                break;
            case EXAMINATION_PASSED:
                personnelOrgUtils.sysWorkerStatusToUchisuike(entity.getPhone(), "301");
                entity.setCheckStatus(2);
                break;
            case AUDIT_NOT_PASSED:
                entity.setCheckStatus(3);
                break;
            case CANCEL:
                entity.setCheckStatus(4);
                break;
            default:
                entity.setCheckStatus(3);
                break;
        }
        baseMapper.updateById(entity);
    }

    @Override
    @Transactional
    public void reApproval(String id, AddStaffEmploymentApplyReq req) {
        FtbPersonnelsStaffEmploymentApply entity = queryAndCheckStaffEmploymentApply(id);
        if (entity.getIsNeedCheck() == 1) {
            throw new RuntimeException("该员工不需要审核");
        }
        if (entity.getIsNeedCheck() == 0 && entity.getCheckStatus() == 2) {
            throw new RuntimeException("该员工审核已经通过");
        }

        //查询手机号是否在已入职列表里面
        QueryWrapper<FtbPersonnelsStaffRoster> rosterWrapper = new QueryWrapper<>();
        rosterWrapper.lambda()
                .eq(FtbPersonnelsStaffRoster::getPhone, req.getPhone())
                .eq(FtbPersonnelsStaffRoster::getEnabledMark, 0)
        ;
        FtbPersonnelsStaffRoster oldRosterEntity = rosterService.getOne(rosterWrapper);
        if (null != oldRosterEntity) {
            if (!oldRosterEntity.getWorkerStatus().equals("305")) {
                throw new RuntimeException("手机号所属员工已经存在花名册中");
            }
        }
        String loginUserId = UserProvider.getLoginUserId();


        //写入数据库
        FtbPersonnelsStaffEmploymentApply newEntity = BeanUtil.copyProperties(req, FtbPersonnelsStaffEmploymentApply.class);
        newEntity.setStatus(0);
        newEntity.setEnabledMark(0);

        newEntity.setId(entity.getId());
        newEntity.setIsSubmitForm(entity.getIsSubmitForm());
        if (req.getIsNeedCheck() == 0) {
            newEntity.setCheckStatus(1);
        }
        newEntity.setJoinNum(1);
        if (oldRosterEntity != null && oldRosterEntity.getJoinNum() != null) {
            newEntity.setJoinNum(oldRosterEntity.getJoinNum() + 1);
        }
        //获取当前登录用户
        newEntity.setOpUser(loginUserId);
        newEntity.setOpUserName(UserProvider.getUser().getUserName());
        newEntity.setCreatorTime(new Date());
        baseMapper.updateById(newEntity);

        //判断是否需要发起审批 0、需要审批
        if (req.getIsNeedCheck() == 0) {
            // 创建审批
            String runTaskId = auditRunTaskService.startTheReviewProcess(newEntity.getId(),
                    FtbPersonnelsCofigEnum.ONBOARDING_APPROVAL_CONFIGURATION.getConfigType(),
                    newEntity.getCurrOrg(), entity.getId());
            // 同步id
            LambdaUpdateWrapper<FtbPersonnelsStaffEmploymentApply> lambdaUpdate = Wrappers.lambdaUpdate();
            lambdaUpdate.eq(FtbPersonnelsStaffEmploymentApply::getId, newEntity.getId());
            lambdaUpdate.set(FtbPersonnelsStaffEmploymentApply::getTaskInfoId, runTaskId);
            baseMapper.update(null, lambdaUpdate);
        } else {
            personnelOrgUtils.sysWorkerStatusToUchisuike(newEntity.getPhone(), "301");
        }
        //同步数据到formData
        Map<String, Object> formDataMap = BeanUtil.beanToMap(newEntity);
        formDataMap.put("expectedStartDate", personnelOrgUtils.dateToString(req.getExpectedStartDate(), ""));
        registrationFormDataService.syncData(formDataMap, newEntity.getPhone(), "");
    }



    @Override
    public void saveInRedis(List<AddStaffEmploymentApplyExcelVO> nomarlData, List<AddStaffEmploymentApplyExcelERRVO> errorData) {
        String redisKey = getRedisKey();
        redisUtil.insert(redisKey, JSON.toJSONString(new FtbAddStaffImportRedisBO(nomarlData, errorData)));
        // 30分钟自动过期
        redisUtil.expire(redisKey, 30 * 60);
    }

    @Override
    @Transactional(rollbackFor = {RuntimeException.class, Exception.class})
    public void importDataClick() {
        String redisKey = getRedisKey();
        if (!redisUtil.exists(redisKey)) {
            throw new RuntimeException("导入数据已经过期,请重新导入!");
        }
        FtbAddStaffImportRedisBO importRedisBO = getAddStaffImportRedisBO(redisKey);
        List<AddStaffEmploymentApplyExcelVO> nomarlData = importRedisBO.getNormalData();
        if (CollUtil.isEmpty(nomarlData)) {
            throw new RuntimeException("当前暂无数据导入!");
        }
        // 插入
        nomarlData.forEach(item -> {
            AddStaffEmploymentApplyReq convert = AddStaffEmploymentApplyReq.convert(item);
            convert.setIsNeedCheck(1);
            //有填考勤组的时候
            if (StrUtil.isBlank(item.getAttendanceGroup()) && StrUtil.isNotBlank(item.getAttendanceGroupName())) {
                //考勤组id查询
                AttendanceGroupVo attendanceGroupVo = attendanceGroupApi.getAttendanceGroupByName(item.getCurrOrgName(), item.getAttendanceGroupName()).getData();
                if (attendanceGroupVo != null) {
                    convert.setAttendanceGroup(attendanceGroupVo.getId());
                } else {
                    throw new RuntimeException("组织[" + item.getCurrOrgName() + "] 不存在考勤组[" + item.getAttendanceGroupName());
                }
            } else if (StrUtil.isNotBlank(item.getAttendanceGroup())) {
                convert.setAttendanceGroup(item.getAttendanceGroup());
            }

            insertData(convert);
        });
        redisUtil.remove(redisKey);
    }

    @SneakyThrows
    @Override
    public Map<String, Object> importData(InputStream inputStream) {
        EasyExcelUtils.universalImport(AddStaffEmploymentApplyExcelVO.class,
                inputStream,
                baseEasyExcelCommonListener,
                1);
        String redisKey = getRedisKey();
        if (!redisUtil.exists(redisKey)) {
            throw new RuntimeException("导入数据已经过期,请重新导入!");
        }
        FtbAddStaffImportRedisBO importRedisBO = getAddStaffImportRedisBO(redisKey);
        HashMap<String, Object> map = Maps.newHashMap();
        map.put("normalData", importRedisBO.getNormalData().size());
        map.put("errorData", importRedisBO.getErrorData().size());
        map.put("data", importRedisBO);
        return map;
    }

    @Nullable
    private FtbAddStaffImportRedisBO getAddStaffImportRedisBO(String redisKey) {
        if (!redisUtil.exists(redisKey)) {
            throw new RuntimeException("导入数据已经过期,请重新导入!");
        }
        Object utilString = redisUtil.getString(redisKey);
        return JSON.parseObject(utilString.toString(), FtbAddStaffImportRedisBO.class);
    }

    private String getRedisKey() {
        String loginUserId = UserProvider.getLoginUserId();
        return String.format(REDIS_KEY, loginUserId);
    }

    @SneakyThrows
    @Override
    public void exportErrData(HttpServletResponse response) {
        String redisKey = getRedisKey();
        FtbAddStaffImportRedisBO importRedisBO = getAddStaffImportRedisBO(redisKey);
        assert importRedisBO != null;
        List<AddStaffEmploymentApplyExcelERRVO> errorData = importRedisBO.getErrorData();
        String fileName = "预办理入职员工错误信息";
        EasyExcelUtils.exportExcel(response, fileName, errorData, AddStaffEmploymentApplyExcelERRVO.class);
    }

    @SneakyThrows
    @Override
    public void exportDate(BatchByPrimaryIdReq req, HttpServletResponse response) {
        if (CollectionUtil.isEmpty(req.getIds())) {
            throw new RuntimeException("请选择要导出的数据");
        }
        List<FtbPersonnelsStaffEmploymentApply> entityList = baseMapper.selectBatchIds(req.getIds());

        if (CollUtil.isEmpty(entityList)) {
            throw new RuntimeException("无数据导出!");
        }
        List<FtbPersonnelsStaffEmploymentApplyDto> list = BeanUtil.copyToList(entityList, FtbPersonnelsStaffEmploymentApplyDto.class);

        if (CollectionUtil.isNotEmpty(list)) {
            //补充组织 岗位 职等 信息 推荐人、推荐门店
            personnelOrgUtils.fillOrgName(list);
            personnelOrgUtils.fillPositionName(list);
            personnelOrgUtils.fillRankName(list);
            personnelOrgUtils.fillExpireDayNum(list);

            //查询合同类型
            personnelOrgUtils.fillContractTypeName(list);
        }
        List<AddStaffEmploymentApplyExcelVO> excelVOS = list.stream().map(FtbPersonnelsStaffEmploymentApplyDto::covert).collect(Collectors.toList());
        String fileName = "预办理入职员工信息";
        EasyExcelUtils.exportExcel(response, fileName, excelVOS, AddStaffEmploymentApplyExcelVO.class);
    }

    @Override
    public PageInfo<FtbPersonnelsStaffEmploymentApplyDto> getWebMyCheckList(MyWebEmploymentApplyCheckListReq req) {
        //审批状态：0、待审批  1、已审批
        String loginUserId = UserProvider.getLoginUserId();
        Page<FtbPersonnelsStaffEmploymentApplyDto> queryPage;
        Integer configType = FtbPersonnelsCofigEnum.ONBOARDING_APPROVAL_CONFIGURATION.getConfigType();
        if (0 == req.getCheckStatus()) {
            queryPage = baseMapper.pagingQueryWebMyCheckList(Page.of(req.getCurrentPage(), req.getPageSize()), loginUserId, configType);
        } else {
            queryPage = baseMapper.getApprovedList(Page.of(req.getCurrentPage(), req.getPageSize()), loginUserId, configType,7);
        }

        List<FtbPersonnelsStaffEmploymentApplyDto> records = queryPage.getRecords();

        if (CollectionUtil.isNotEmpty(records)) {
            // 移除主流程状态替换
            //补充组织 岗位 职等 信息 推荐人、推荐门店
            personnelOrgUtils.fillOrgName(records);
            personnelOrgUtils.fillPositionName(records);
            personnelOrgUtils.fillRankName(records);
        }
        //构建分页返回数据
        PageInfo<FtbPersonnelsStaffEmploymentApplyDto> pageInfo = new PageInfo<>();
        pageInfo.setList(records);
        pageInfo.setPageSize((int) queryPage.getSize());
        pageInfo.setPageNum((int) queryPage.getCurrent());
        pageInfo.setTotal((int) queryPage.getTotal());
        return pageInfo;
    }


    @Override
    public FtbPersonnelsStaffEmploymentApplyDto getInfo(String id) {
        //查询基本信息
        FtbPersonnelsStaffEmploymentApply entity = queryAndCheckStaffEmploymentApply(id);
        FtbPersonnelsStaffEmploymentApplyDto dto = JsonUtil.getJsonToBean(entity, FtbPersonnelsStaffEmploymentApplyDto.class);
//        FtbPersonnelsStaffEmploymentApplyDto dto = BeanUtil.copyProperties(entity, FtbPersonnelsStaffEmploymentApplyDto.class);
        fillOrgNameById(dto);
        fillPositionNameById(dto);
        fillRankNameById(dto);
        fillContactInfo(dto);
        //考勤组信息返回
        if (StrUtil.isNotBlank(entity.getAttendanceGroup())) {
            AttendanceGroup attendanceGroup = attendanceGroupApi.queryTheNameOfTheAttendanceGroup(entity.getAttendanceGroup());
            if (attendanceGroup != null) {
                dto.setAttendanceGroupName(attendanceGroup.getGroupName());
            }
        }
        //需要审批 并且审批还没有通过时需要返回
        if (dto.getIsNeedCheck() == 0) {
            FtbPersonnelsAuditInfoVO auditInfoVO = subConfigService.queryAuditSubConfig(entity.getCurrOrg(), FtbPersonnelsCofigEnum.ONBOARDING_APPROVAL_CONFIGURATION);
            dto.setAuditInfo(auditInfoVO);
        }
        //转换临时薪酬信息
        if (StrUtil.isNotBlank(entity.getSalaryData())) {
            dto.setSalaryItemList(JsonUtil.getJsonToList(entity.getSalaryData(), FtbPersonnelsSalaryInfo.class));
        }
        Boolean whitelist = personalizedTenantWhitelistUtils.isItOnTheWhitelist();
        if (whitelist) {
            // 封装 LambdaQueryWrapper 创建逻辑
            FtbPersonnelsRegistrationFormField field = getFieldByName("意向组织");
            if (ObjectUtil.isEmpty(field)) {
                return dto; // 如果字段不存在，直接退出
            }
            String phone = dto.getPhone();
            if (ObjectUtil.isEmpty(phone)) {
                return dto; // 如果电话号码为空，直接退出
            }
            FtbPersonnelsStaffRegistrationFormData formData = getFormDataByPhoneAndFieldId(phone, field.getId());
            if (formData == null || ObjectUtil.isEmpty(formData.getValue())) {
                return dto; // 如果表单数据不存在或值为空，直接退出
            }
            try {
                OrganizeEntity organizeList = organizeApi.getInfoById(formData.getValue());
                if (organizeList != null && ObjectUtil.isNotEmpty(organizeList.getFullName())) {
                    dto.setIntentionOrgName(organizeList.getFullName());
                }
            } catch (Exception e) {
                // 记录异常日志，确保程序不会因外部 API 异常而崩溃
                log.error("获取意向组织信息失败，phone: {}, formFieldId: {}", phone, field.getId(), e);
            }
        }
        return dto;
    }
    // 封装方法：根据名称获取字段
    private FtbPersonnelsRegistrationFormField getFieldByName(String name) {
        LambdaQueryWrapper<FtbPersonnelsRegistrationFormField> lambdaQuery = Wrappers.lambdaQuery();
        lambdaQuery.eq(FtbPersonnelsRegistrationFormField::getEnabledMark,0);
        lambdaQuery.eq(FtbPersonnelsRegistrationFormField::getStatus, 0);
        lambdaQuery.eq(FtbPersonnelsRegistrationFormField::getName, name);
        return registrationFormFieldMapper.selectOne(lambdaQuery);
    }

    // 封装方法：根据电话和字段 ID 获取表单数据
    private FtbPersonnelsStaffRegistrationFormData getFormDataByPhoneAndFieldId(String phone, String fieldId) {
        LambdaQueryWrapper<FtbPersonnelsStaffRegistrationFormData> wrapper = Wrappers.lambdaQuery();
        wrapper.eq(FtbPersonnelsStaffRegistrationFormData::getPhone, phone);
        wrapper.eq(FtbPersonnelsStaffRegistrationFormData::getFormFieldId, fieldId);
        return registrationFormDataService.getOne(wrapper);
    }
    private String queryRelationNameById(Integer source, String sourceId) {
        String sourceName = "";
        if (null == source || source == 0) {
            return sourceName;
        }
        if (source == 2) {
            StoreEntity storeEntity = personnelOrgUtils.queryStoreInfo(sourceId);
            if (null != storeEntity) {
                sourceName = storeEntity.getStorename();
            }
        } else if (source == 3) {
            OrganizeEntity organizeEntity = personnelOrgUtils.queryOrganizeInfo(sourceId);
            if (null != organizeEntity) {
                sourceName = organizeEntity.getFullName();
            }
        } else if (source == 1) {
            UserEntity userEntity = personnelOrgUtils.queryUserInfo(sourceId);
            if (null != userEntity) {
                sourceName = userEntity.getRealName();
            }
        }
        return sourceName;
    }

    private void fillContactInfo(FtbPersonnelsStaffEmploymentApplyDto dto) {
        if (StringUtils.isNotEmpty(dto.getContractType())) {
            String contractTypeName = personnelOrgUtils.queryContractTypeName(dto.getContractType());
            dto.setContractTypeName(contractTypeName);
        }
    }

    private <T extends StaffBaseInfoDto> void fillRankNameById(T dto) {
        ActionResult<PositionGradesInfoVO> gradesInfo = null;
        try {
            gradesInfo = positionApi.getGradesInfo(dto.getCurrRank());
            if (gradesInfo != null && gradesInfo.getData() != null) {
                dto.setCurrRankName(gradesInfo.getData().getFullName());
            }
        } catch (Exception e) {
            log.error("根据职等ID查询职等信息异常,rankId={},{}", dto.getCurrRank(), e);
        }

    }

    private <T extends StaffBaseInfoDto> void fillPositionNameById(T dto) {
        PositionEntity entity = positionApi.queryInfoById(dto.getCurrPosition());
        if (entity != null) {
            dto.setCurrPositionName(entity.getFullName());
        }
    }

    private <T extends StaffBaseInfoDto> void fillOrgNameById(T dto) {
        OrganizeEntity entity = organizeApi.getInfoById(dto.getCurrOrg());
        if (null != entity) {
            dto.setCurrOrgName(entity.getFullName());
        }
    }

    public FtbPersonnelsStaffEmploymentApply queryAndCheckStaffEmploymentApply(String id) {
        FtbPersonnelsStaffEmploymentApply entity = baseMapper.selectById(id);
        if (null == entity) {
            throw new RuntimeException("数据不存在");
        }
        if (entity.getEnabledMark() == 1) {
            throw new RuntimeException("数据已经删除");
        }
        return entity;
    }


    @Override
    @Transactional(rollbackFor = RuntimeException.class)
    public String insertData(AddStaffEmploymentApplyReq req) {
        if (null == req.getEntryMoney()) {
            req.setEntryMoney(BigDecimal.ZERO);
        }
        String phone = req.getPhone();
        // 手机号,离职黑名单校验
        if (ftbPersonnelsBlacklistService.hasItBeenBlacklisted(req.getPhone())) {
            throw new RuntimeException("当前人员处于黑名单中，请将其移出黑名单后再办理入职!");
        }
        //查询手机号是否在已入职列表里面
        QueryWrapper<FtbPersonnelsStaffRoster> rosterWrapper = new QueryWrapper<>();
        rosterWrapper.lambda()
                .eq(FtbPersonnelsStaffRoster::getPhone, req.getPhone())
        ;
        FtbPersonnelsStaffRoster oldRosterEntity = rosterService.getOne(rosterWrapper);
        if (null != oldRosterEntity) {
            if (oldRosterEntity.getEnabledMark() == 0) {
                if (oldRosterEntity.getWorkerStatus().equals("302") || oldRosterEntity.getWorkerStatus().equals("303") || oldRosterEntity.getWorkerStatus().equals("306")) {
                    throw new RuntimeException("该员工已经到岗，请勿重复操作!");
                }

                if (oldRosterEntity.getWorkerStatus().equals("304")) {
                    throw new RuntimeException("该员工已经在离职中!");
                }
            }
        }
        String loginUserId = UserProvider.getLoginUserId();

        //写入数据库
        FtbPersonnelsStaffEmploymentApply entity = BeanUtil.copyProperties(req, FtbPersonnelsStaffEmploymentApply.class);
        entity.setStatus(0);
        entity.setIsSubmitForm(0);
        entity.setEnabledMark(0);
        if (null == entity.getSource()) {
            entity.setSource(0);
        }
        entity.setSourceRelation(queryRelationNameById(req.getSource(), req.getSourceRelationId()));
        if (req.getIsNeedCheck() == 0) {
            entity.setCheckStatus(1);
        }
        entity.setJoinNum(1);
        if (oldRosterEntity != null && oldRosterEntity.getJoinNum() != null) {
            entity.setJoinNum(oldRosterEntity.getJoinNum() + 1);
        }
        //获取当前登录用户
        entity.setOpUser(loginUserId);

        //临时存储薪酬数据
        entity.setSalaryData(JsonUtil.getObjectToString(req.getSalaryItemList()));

        entity.setOpUserName(UserProvider.getUser().getUserName());
        LambdaQueryWrapper<FtbPersonnelsStaffEmploymentApply> queryWrapper = Wrappers.lambdaQuery();
        queryWrapper.eq(FtbPersonnelsStaffEmploymentApply::getPhone,phone);
        FtbPersonnelsStaffEmploymentApply employmentApply = baseMapper.selectOne(queryWrapper);
        if(employmentApply != null){
            entity.setId(employmentApply.getId());
            baseMapper.updateById(entity);
        } else {
            baseMapper.insert(entity);
        }
        personnelOrgUtils.sysWorkerStatusToUchisuike(entity.getPhone(), "301");
        //同步数据到formData
        Map<String, Object> formDataMap = BeanUtil.beanToMap(entity);
        formDataMap.put("expectedStartDate", personnelOrgUtils.dateToString(req.getExpectedStartDate(), ""));
        //查询内推池用户的基本信息
        QueryWrapper<FtbPersonnelsUchisuikePond> suikeWrap = new QueryWrapper<>();
        suikeWrap.lambda()
                .eq(FtbPersonnelsUchisuikePond::getPhone, phone)
                .eq(FtbPersonnelsUchisuikePond::getEnableMark, 0);
        List<FtbPersonnelsUchisuikePond> ftbPersonnelsUchisuikePonds = uchisuikePondMapper.selectList(suikeWrap);
        if (CollectionUtil.isNotEmpty(ftbPersonnelsUchisuikePonds)) {
            FtbPersonnelsUchisuikePond ftbPersonnelsUchisuikePond = ftbPersonnelsUchisuikePonds.get(0);
            //性别0男1女
            String workerSex = "0";
            if (ftbPersonnelsUchisuikePond.getSex() == null) {
                workerSex = "0";
            } else if (ftbPersonnelsUchisuikePond.getSex() == 0) {
                workerSex = "1";
            } else if (ftbPersonnelsUchisuikePond.getSex() == 1) {
                workerSex = "2";
            }
            formDataMap.put("workerSex", workerSex);
            formDataMap.put("idCardNum", ftbPersonnelsUchisuikePond.getIdCard());
            //考勤组id,来自于考勤组
            if (StrUtil.isNotBlank(req.getAttendanceGroup())) {
                formDataMap.put("attendanceGroup", req.getAttendanceGroup());
            }

        }
        registrationFormDataService.syncData(formDataMap, entity.getPhone(), "");

        return entity.getId();
    }

    @Override
    public  ActionResult<Void> handleJoinJobForOA(AddStaffEmploymentApplyReq req) {
        ActionResult<Void> result = new ActionResult<>();
        result.setCode(FtbPersonnelsCheckStatusCodeEnum.CHECK_PASS.getCode());
        result.setMsg(FtbPersonnelsCheckStatusCodeEnum.CHECK_PASS.getMsg());
        if (null == req.getEntryMoney()) {
            req.setEntryMoney(BigDecimal.ZERO);
        }
        String phone = req.getPhone();
        req.setPhone(phone);
        // 手机号,离职黑名单校验
        if (ftbPersonnelsBlacklistService.hasItBeenBlacklisted(req.getPhone())) {
            result.setCode(FtbPersonnelsCheckStatusCodeEnum.CHECK_REFUSE.getCode());
            result.setMsg("当前人员处于黑名单中，请将其移出黑名单后再办理入职!");
            return result;
        }
        if (req.getSpecialBusinessId() != null) {
            result = reApprovalForOA(req.getSpecialBusinessId(), req);
        } else{
            // 手动做校验数据
            if (!PersonnelOrgUtils.isValidPhoneNumber(phone)) {
                result.setCode(FtbPersonnelsCheckStatusCodeEnum.CHECK_REFUSE.getCode());
                result.setMsg("手机号格式不正确");
                return result;
            }
            //查询手机号是否在已入职列表里面
            QueryWrapper<FtbPersonnelsStaffRoster> rosterWrapper = new QueryWrapper<>();
            rosterWrapper.lambda()
                    .eq(FtbPersonnelsStaffRoster::getPhone, req.getPhone())
                    .eq(FtbPersonnelsStaffRoster::getEnabledMark, 0);
            FtbPersonnelsStaffRoster oldRosterEntity = rosterService.getOne(rosterWrapper);
            if (null != oldRosterEntity) {
                if (oldRosterEntity.getEnabledMark() == 0) {
                    if (oldRosterEntity.getWorkerStatus().equals("302") || oldRosterEntity.getWorkerStatus().equals("303") || oldRosterEntity.getWorkerStatus().equals("306")) {
                        result.setCode(FtbPersonnelsCheckStatusCodeEnum.CHECK_REFUSE.getCode());
                        result.setMsg("该员工已经到岗，请勿重复操作!");
                        return result;
                    }

                    if (oldRosterEntity.getWorkerStatus().equals("304")) {
                        result.setCode(FtbPersonnelsCheckStatusCodeEnum.CHECK_REFUSE.getCode());
                        result.setMsg("该员工已经在离职中!");
                        return result;
                    }
                }
            }
            String loginUserId = UserProvider.getLoginUserId();
            String photoFiles = req.getPhotoFiles();
            if (StringUtils.isNotEmpty(photoFiles)) {
                List<FileEntity> entities = JSONObject.parseArray(photoFiles, FileEntity.class);
                if (entities.size() > 1) {
                    result.setCode(FtbPersonnelsCheckStatusCodeEnum.CHECK_REFUSE.getCode());
                    result.setMsg("考勤人脸录入图片最多只能上传一张!");
                    return result;
                }
            }
            //写入数据库
            FtbPersonnelsStaffEmploymentApply entity = BeanUtil.copyProperties(req, FtbPersonnelsStaffEmploymentApply.class);
            entity.setStatus(0);
            entity.setIsSubmitForm(0);
            entity.setEnabledMark(0);
            if (null == entity.getSource()) {
                entity.setSource(0);
            }
            entity.setSourceRelation(queryRelationNameById(req.getSource(), req.getSourceRelationId()));
            entity.setIsNeedCheck(0);
            entity.setCheckStatus(1);
            if (oldRosterEntity != null && oldRosterEntity.getJoinNum() != null) {
                entity.setJoinNum(oldRosterEntity.getJoinNum() + 1);
            }
            //获取当前登录用户
            entity.setOpUser(loginUserId);
            //临时存储薪酬数据
            entity.setSalaryData(JsonUtil.getObjectToString(req.getSalaryItemList()));
            entity.setOpUserName(UserProvider.getUser().getUserName());
            entity.setVersionNum(1);
            entity.setTaskInfoId(req.getTaskId());
            LambdaQueryWrapper<FtbPersonnelsStaffEmploymentApply> queryWrapper = Wrappers.lambdaQuery();
            queryWrapper.eq(FtbPersonnelsStaffEmploymentApply::getPhone,phone);
            FtbPersonnelsStaffEmploymentApply employmentApply = baseMapper.selectOne(queryWrapper);
            if(employmentApply != null) entity.setId(employmentApply.getId());
            baseMapper.updateById(entity);
            //同步数据到formData
            Map<String, Object> formDataMap = BeanUtil.beanToMap(entity);
            formDataMap.put("expectedStartDate", personnelOrgUtils.dateToString(req.getExpectedStartDate(), ""));
            //查询内推池用户的基本信息
            QueryWrapper<FtbPersonnelsUchisuikePond> suikeWrap = new QueryWrapper<>();
            suikeWrap.lambda()
                    .eq(FtbPersonnelsUchisuikePond::getPhone, phone)
                    .eq(FtbPersonnelsUchisuikePond::getEnableMark, 0);
            List<FtbPersonnelsUchisuikePond> ftbPersonnelsUchisuikePonds = uchisuikePondMapper.selectList(suikeWrap);
            if (CollectionUtil.isNotEmpty(ftbPersonnelsUchisuikePonds)) {
                FtbPersonnelsUchisuikePond ftbPersonnelsUchisuikePond = ftbPersonnelsUchisuikePonds.get(0);
                //性别0男1女
                String workerSex = "0";
                if (ftbPersonnelsUchisuikePond.getSex() == null) {
                    workerSex = "0";
                } else if (ftbPersonnelsUchisuikePond.getSex() == 0) {
                    workerSex = "1";
                } else if (ftbPersonnelsUchisuikePond.getSex() == 1) {
                    workerSex = "2";
                }
                formDataMap.put("workerSex", workerSex);
                formDataMap.put("idCardNum", ftbPersonnelsUchisuikePond.getIdCard());
                //考勤组id,来自于考勤组
                if (StrUtil.isNotBlank(req.getAttendanceGroup())) {
                    formDataMap.put("attendanceGroup", req.getAttendanceGroup());
                }

            }
            registrationFormDataService.syncData(formDataMap, entity.getPhone(), "");

        }
        return result;
    }

    @Override
    public ActionResult<Void> reApprovalForOA(String id, AddStaffEmploymentApplyReq req) {
        ActionResult<Void> result = new ActionResult<>();
        result.setCode(FtbPersonnelsCheckStatusCodeEnum.CHECK_PASS.getCode());
        result.setMsg(FtbPersonnelsCheckStatusCodeEnum.CHECK_PASS.getMsg());

        FtbPersonnelsStaffEmploymentApply entity = queryAndCheckStaffEmploymentApply(id);
        if (!entity.getPhone().equals(req.getPhone())){
            result.setCode(FtbPersonnelsCheckStatusCodeEnum.CHECK_REFUSE.getCode());
            result.setMsg("重新办理选择用户不一致!请重新选择正确的用户!");
            return result;
        }
        if (entity.getIsNeedCheck() == 1) {
            result.setCode(FtbPersonnelsCheckStatusCodeEnum.CHECK_REFUSE.getCode());
            result.setMsg("该员工不需要审核");
            return result;
        }
        if (entity.getIsNeedCheck() == 0 && entity.getCheckStatus() == 2) {
            result.setCode(FtbPersonnelsCheckStatusCodeEnum.CHECK_REFUSE.getCode());
            result.setMsg("该员工审核已经通过");
            return result;
        }

        //查询手机号是否在已入职列表里面
        QueryWrapper<FtbPersonnelsStaffRoster> rosterWrapper = new QueryWrapper<>();
        rosterWrapper.lambda()
                .eq(FtbPersonnelsStaffRoster::getPhone, req.getPhone())
                .eq(FtbPersonnelsStaffRoster::getEnabledMark, 0)
        ;
        FtbPersonnelsStaffRoster oldRosterEntity = rosterService.getOne(rosterWrapper);
        if (null != oldRosterEntity) {
            if (!oldRosterEntity.getWorkerStatus().equals("305")) {
                result.setCode(FtbPersonnelsCheckStatusCodeEnum.CHECK_REFUSE.getCode());
                result.setMsg("手机号所属员工已经存在花名册中");
                return result;
            }
        }
        String loginUserId = UserProvider.getLoginUserId();
        //写入数据库
        FtbPersonnelsStaffEmploymentApply newEntity = BeanUtil.copyProperties(req, FtbPersonnelsStaffEmploymentApply.class);
        newEntity.setStatus(0);
        newEntity.setEnabledMark(0);
        newEntity.setId(id);
        newEntity.setIsSubmitForm(entity.getIsSubmitForm());
        if (req.getIsNeedCheck() == 0) {
            newEntity.setCheckStatus(1);
        }
        newEntity.setJoinNum(1);
        if (oldRosterEntity != null && oldRosterEntity.getJoinNum() != null) {
            newEntity.setJoinNum(oldRosterEntity.getJoinNum() + 1);
        }
        //获取当前登录用户
        newEntity.setOpUser(loginUserId);
        newEntity.setTaskInfoId(req.getTaskId());
        newEntity.setOpUserName(UserProvider.getUser().getUserName());
        newEntity.setCreatorTime(new Date());
        newEntity.setVersionNum(1);
        baseMapper.updateById(newEntity);
        //同步数据到formData
        Map<String, Object> formDataMap = BeanUtil.beanToMap(newEntity);
        formDataMap.put("expectedStartDate", personnelOrgUtils.dateToString(req.getExpectedStartDate(), ""));
        registrationFormDataService.syncData(formDataMap, newEntity.getPhone(),"" );
        return result;
    }

    @Override
    public PageListVO<FtbPersonnelsEmployApplyDto> onboardingList(QueryStaffEmploymentApplyListReq req) {
        Page<FtbPersonnelsEmployApplyDto> page = new Page<>();
        page.setCurrent(req.getCurrentPage());
        page.setSize(req.getPageSize());
        Integer checkStatus = req.getCheckStatus();
        if (checkStatus != null){
            boolean b = checkStatus == 4;
            if (b){
                req.setIsNeedCheck(1);
                req.setCheckStatus(null);
            }else {
                req.setIsNeedCheck(0);
            }
        }
        Boolean whitelist = personalizedTenantWhitelistUtils.isItOnTheWhitelist();
        req.setExt(whitelist);
        page = baseMapper.onboardingList(page, req);
        // 数据补全
        List<FtbPersonnelsEmployApplyDto> records = page.getRecords();
        if (CollUtil.isEmpty( records)) return CultivatePage.coverPageList(page);
        List<String> phoneList = records.stream().map(FtbPersonnelsEmployApplyDto::getPhone).collect(Collectors.toList());
        LambdaQueryWrapper<FtbPersonnelsStaffRegistrationFormData> wrapper = Wrappers.lambdaQuery();
        wrapper.in(FtbPersonnelsStaffRegistrationFormData::getPhone,phoneList);
        // idCardNum 身份证
        // flowerName 花名
        // birthday 出生日期
        wrapper.in(FtbPersonnelsStaffRegistrationFormData::getFormFieldId,"idCardNum","flowerName","birthday","workerSex");
        List<FtbPersonnelsStaffRegistrationFormData> formData = registrationFormDataService.list(wrapper);
        Map<String, List<FtbPersonnelsStaffRegistrationFormData>> formDataPhoneMap = formData.stream().collect(Collectors.groupingBy(FtbPersonnelsStaffRegistrationFormData::getPhone, Collectors.toList()));
        // 数据补充
        Map<String, String> orgMap  = new HashMap<>();
        if (whitelist) {
            List<String> intentionOrgIds = records.stream().map(FtbPersonnelsEmployApplyDto::getIntentionOrgId).collect(Collectors.toList());
            if (CollUtil.isNotEmpty(intentionOrgIds)) {
                List<OrganizeEntity> organizeList = organizeApi.getOrganizeName(intentionOrgIds);
                orgMap = organizeList.stream().collect(Collectors.toMap(OrganizeEntity::getId, OrganizeEntity::getFullName));
            }
        }
        Map<String, String> finalOrgMap = orgMap;
        records.forEach(item->{
            List<FtbPersonnelsStaffRegistrationFormData> registrationFormData = formDataPhoneMap.get(item.getPhone());
            if (CollUtil.isNotEmpty(registrationFormData)) {
                Map<String, String> stringMap = registrationFormData.stream().collect(Collectors.toMap(FtbPersonnelsStaffRegistrationFormData::getFormFieldId, FtbPersonnelsStaffRegistrationFormData::getValue, (a, b) -> a));
                item.setIdCardNum(stringMap.get("idCardNum"));
                item.setFlowerName(stringMap.get("flowerName"));
                item.setBirthday(stringMap.get("birthday"));
                String str = stringMap.getOrDefault("workerSex", null);
                if (StringUtils.isNotEmpty(str)) {
                    LambdaQueryWrapper<FtbPersonnelsRegistrationFormFieldOption> queryWrapper = Wrappers.lambdaQuery();
                    queryWrapper.eq(FtbPersonnelsRegistrationFormFieldOption::getFormFieldId, "workerSex");
                    queryWrapper.eq(FtbPersonnelsRegistrationFormFieldOption::getId, str);
                    FtbPersonnelsRegistrationFormFieldOption fieldOption = optionMapper.selectOne(queryWrapper);
                    item.setGender(fieldOption.getName());
                }
            }
            if (item.getIsNeedCheck() != null && 1 == item.getIsNeedCheck()){
                item.setIsNeedCheck(null);
                item.setCheckStatus(4);
            }
            if (whitelist &&  finalOrgMap.containsKey(item.getIntentionOrgId())) {
                item.setIntentionOrgName(finalOrgMap.get(item.getIntentionOrgId()));
            }
        });
        return CultivatePage.coverPageList(page);
    }

    @Override
    @GlobalTransactional(rollbackFor = RuntimeException.class)
    public  ActionResult<Void> approvalForOA(EmploymentApplyCheckDto dto) {
        ActionResult<Void> result = new ActionResult<>();
        result.setCode( FtbPersonnelsCheckStatusCodeEnum.CHECK_PASS.getCode());
        result.setMsg( FtbPersonnelsCheckStatusCodeEnum.CHECK_PASS.getMsg());
        LambdaQueryWrapper<FtbPersonnelsStaffEmploymentApply> queryWrapper = Wrappers.lambdaQuery();
        queryWrapper.eq(FtbPersonnelsStaffEmploymentApply::getTaskInfoId,dto.getTaskId());
        FtbPersonnelsStaffEmploymentApply entity = baseMapper.selectOne(queryWrapper);
        if (entity.getIsNeedCheck() == 1) {
            result.setCode( FtbPersonnelsCheckStatusCodeEnum.CHECK_REFUSE.getCode());
            result.setMsg( "该员工入职不需要审核");
            return result;
        }
        if (entity.getIsNeedCheck() == 0 && entity.getCheckStatus() == 2) {
            result.setCode( FtbPersonnelsCheckStatusCodeEnum.CHECK_REFUSE.getCode());
            result.setMsg( "该员工入职审核已经通过");
            return result;
        }
        if (entity.getIsNeedCheck() == 0 && entity.getCheckStatus() == 3) {
            result.setCode( FtbPersonnelsCheckStatusCodeEnum.CHECK_REFUSE.getCode());
            result.setMsg( "该员工入职审核已经不通过");
            return result;
        }
        if (entity.getIsNeedCheck() == 0 && entity.getCheckStatus() == 4) {
            result.setCode( FtbPersonnelsCheckStatusCodeEnum.CHECK_REFUSE.getCode());
            result.setMsg( "该员工入职审核已经撤销");
            return result;
        }
        FtbPersonnelsAuditDto checkDto = new FtbPersonnelsAuditDto();
        checkDto.setBusinessId(entity.getId());
        if (ObjectUtil.isNotEmpty(dto.getIsConformSalary())) {
            checkDto.setDoesTheSalaryComplyWith(dto.getIsConformSalary());
        }
        if (ObjectUtil.isNotEmpty(dto.getMsg())) {
            checkDto.setApprovalComments(dto.getMsg());
        }
        if (ObjectUtil.isNotEmpty(dto.getIsPass())) {
            checkDto.setFlag(String.valueOf(dto.getIsPass()));
        }
        // 根据这个OA审批结果，设置状态
        FtbPersonnelsAuditTaskEnum  code =   dto.getIsPass() == 0 ? FtbPersonnelsAuditTaskEnum.AUDIT_NOT_PASSED : FtbPersonnelsAuditTaskEnum.EXAMINATION_PASSED;
        switch (code) {
            case EXAMINATION_PASSED:
                personnelOrgUtils.sysWorkerStatusToUchisuike(entity.getPhone(), "301");
                entity.setCheckStatus(2);
                break;
            case AUDIT_NOT_PASSED:
                entity.setCheckStatus(3);
                break;
        }
        baseMapper.updateById(entity);
        return result;
    }


    /**
     * 根据手机号检测状态
     * 0、系统不存在该用户  1、该手机号等待入职 2、该手机号等待入职审批 3、该手机号入职审批流程不通过，请重新办理  302、试用 303、正式  304、待离职  305 离职 4-该手机号已被拉入黑名单
     *
     * @param phone
     * @return
     */
    @Override
    public String checkPhoneStatus(String phone) {

        //手机号黑名单校验
        if (ftbPersonnelsBlacklistService.hasItBeenBlacklisted(phone)) {
            return Integer.toString(PhoneStatusEnum.BASE_BLACKLIST.getCode());
        }
        QueryWrapper<FtbPersonnelsStaffEmploymentApply> wrapper = new QueryWrapper<>();
        wrapper.lambda()
                .eq(FtbPersonnelsStaffEmploymentApply::getPhone, phone)
                .eq(FtbPersonnelsStaffEmploymentApply::getEnabledMark, 0)
                .last("limit 1")
        ;

        FtbPersonnelsStaffEmploymentApply employmentApplyEntity = baseMapper.selectOne(wrapper);
        if (null != employmentApplyEntity) {
            if (employmentApplyEntity.getIsNeedCheck() == PhoneStatusEnum.BASE_ONBOARD_WAIT.getCode()) {//0、需要审批  1、不需要审批
                return Integer.toString(PhoneStatusEnum.BASE_ONBOARD_WAIT.getCode());
            } else {
                if (employmentApplyEntity.getCheckStatus() == PhoneStatusEnum.BASE_APPROVAL_WAIT.getCode() && employmentApplyEntity.getStatus() != PhoneStatusEnum.BASE_ONBOARD_WAIT.getCode()) {
                    return Integer.toString(PhoneStatusEnum.BASE_ONBOARD_WAIT.getCode());
                } else if ( employmentApplyEntity.getCheckStatus() == PhoneStatusEnum.BASE_ONBOARD_WAIT.getCode()) {
                    return Integer.toString(PhoneStatusEnum.BASE_APPROVAL_WAIT.getCode());
                } else if (( employmentApplyEntity.getCheckStatus() == PhoneStatusEnum.BASE_APPROVAL_WAIT.getCode())) {
                    return Integer.toString(PhoneStatusEnum.BASE_APPROVAL_WAIT.getCode());
                } else if (employmentApplyEntity.getCheckStatus() == PhoneStatusEnum.BASE_APPROVAL_REJECT.getCode()) {
                    return Integer.toString(PhoneStatusEnum.BASE_APPROVAL_REJECT.getCode());
                }
            }
        }



        //查询手机号是否在已入职列表里面
        QueryWrapper<FtbPersonnelsStaffRoster> rosterWrapper = new QueryWrapper<>();
        rosterWrapper.lambda()
                .eq(FtbPersonnelsStaffRoster::getPhone, phone)
                .eq(FtbPersonnelsStaffRoster::getEnabledMark, 0)
                .last("limit 1")
        ;
        FtbPersonnelsStaffRoster roster = rosterService.getOne(rosterWrapper);
        if (null != roster) {
            return roster.getWorkerStatus();
        }
        return "0";

    }

    @Override
    public void saveShortUrl(String id, String shortUrl) {
        FtbPersonnelsStaffEmploymentApply employmentApply = queryAndCheckStaffEmploymentApply(id);
        employmentApply.setShortUrl(shortUrl);
        baseMapper.updateById(employmentApply);
    }

    @Override
    public void sendPhoneMsg(String phone) {

        if (!personnelOrgUtils.isValidPhoneNumber(phone)) {
            throw new RuntimeException("手机号格式不正确");
        }
        Boolean isFill = checkFillRegistrationForm(phone);
        if (!isFill) {
            throw new RuntimeException("该手机号已经填写了入职登记表");
        }
//        if (personnelOrgUtils.queryIsSendPhoneMsg(phone)) {
//            throw new RuntimeException("今日已经发送了短信");
//        }
      //  Map<String, Object> map = new LinkedHashMap<>();
//        try {
//            UserInfo userInfo = UserProvider.getUser();
//            String storeCode = personnelOrgUtils.queryCodeForTenantId(userInfo.getTenantId());
//            map.put("code", storeCode);
//            smsSendUtil.sendSms(List.of(phone), "ENTRY_FORM", map);
//            personnelOrgUtils.setTodayIsSendPhoneMsg(phone);
//
//        } catch (Exception e) {
//            log.error("发送验证码异常：{}", e.getMessage());
//            throw new RuntimeException("短信发送失败", e);
//        }
    }

    /**
     * 检测是否需要填写入职登记表
     *
     * @param phone
     * @return true 需要填写 ，false 不需要填写
     */
    @Override
    public Boolean checkFillRegistrationForm(String phone) {
        LambdaQueryWrapper<FtbPersonnelsStaffEmploymentApply> queryWrapper = Wrappers.lambdaQuery();
        queryWrapper.eq(FtbPersonnelsStaffEmploymentApply::getPhone, phone);
        queryWrapper.eq(FtbPersonnelsStaffEmploymentApply::getIsSubmitForm, 1);
        queryWrapper.eq(FtbPersonnelsStaffEmploymentApply::getEnabledMark, 0);
        queryWrapper.last("limit 1");
        FtbPersonnelsStaffEmploymentApply apply = baseMapper.selectOne(queryWrapper);
        log.error("校验入职信息apply:{}", apply);
        if (ObjectUtil.isNotEmpty(apply)) {
            return false;
        }
        // 查询手机号是否在员工信息列表里面
        LambdaQueryWrapper<FtbPersonnelsStaffRoster> rosterWrapper = Wrappers.lambdaQuery();
        rosterWrapper.eq(FtbPersonnelsStaffRoster::getPhone, phone);
        rosterWrapper.notIn(FtbPersonnelsStaffRoster::getWorkerStatus, "305");
        rosterWrapper.eq(FtbPersonnelsStaffRoster::getEnabledMark, 0);
        FtbPersonnelsStaffRoster roster = rosterService.getOne(rosterWrapper);
        log.error("花名册 roster:{}", apply);
        if (ObjectUtil.isNotEmpty(roster)) {
            return false;
        }
        return true;
    }

    /**
     * 查询租户编码
     *
     * @return
     */

    @Override
    public String queryCode() {
        UserInfo userInfo = UserProvider.getUser();
        String storeCode = personnelOrgUtils.queryCodeForTenantId(userInfo.getTenantId());
        return storeCode;
    }

    @Override
    public void updateEmploymentApplyStatus() {
        //修改修改不需要审批的
        LambdaUpdateWrapper<FtbPersonnelsStaffEmploymentApply> wrapper = new LambdaUpdateWrapper<FtbPersonnelsStaffEmploymentApply>()
                .set(FtbPersonnelsStaffEmploymentApply::getStatus, 2)
                .lt(FtbPersonnelsStaffEmploymentApply::getExpectedStartDate, new Date())
                .eq(FtbPersonnelsStaffEmploymentApply::getIsNeedCheck, 1)
                .eq(FtbPersonnelsStaffEmploymentApply::getStatus,0)
                .eq(FtbPersonnelsStaffEmploymentApply::getEnabledMark, 0);
        baseMapper.update(null, wrapper);

        //修改需要审批的
        wrapper = new LambdaUpdateWrapper<FtbPersonnelsStaffEmploymentApply>()
                .set(FtbPersonnelsStaffEmploymentApply::getStatus, 2)
                .lt(FtbPersonnelsStaffEmploymentApply::getExpectedStartDate, new Date())
                .eq(FtbPersonnelsStaffEmploymentApply::getIsNeedCheck, 0)
                .eq(FtbPersonnelsStaffEmploymentApply::getCheckStatus, 2)
                .eq(FtbPersonnelsStaffEmploymentApply::getStatus,0)
                .eq(FtbPersonnelsStaffEmploymentApply::getEnabledMark, 0);
        baseMapper.update(null, wrapper);
    }

    @Override
    public void deleteByPhone(String phone) {
        QueryWrapper<FtbPersonnelsStaffEmploymentApply> applay = new QueryWrapper<>();
        applay.lambda().eq(FtbPersonnelsStaffEmploymentApply::getPhone, phone);
        baseMapper.delete(applay);
    }

    @Override
    public void verifyUserBound(String positionId, String positionGradesId) {

        if (StrUtil.isNotBlank(positionId)) {
            List<FtbPersonnelsStaffEmploymentApply> staffEmploymentApplies = this.list(Wrappers.<FtbPersonnelsStaffEmploymentApply>lambdaQuery()
                    .eq(FtbPersonnelsStaffEmploymentApply::getCurrPosition, positionId)
                    .eq(FtbPersonnelsStaffEmploymentApply::getIsNeedCheck, 0)
                    .in(FtbPersonnelsStaffEmploymentApply::getCheckStatus,0,1)
            );
            if (CollUtil.isNotEmpty(staffEmploymentApplies)) {
                throw new RuntimeException("该岗位存在于办理入职的用户中，不允许删除");
            }
        }
        if (StrUtil.isNotBlank(positionGradesId)) {
            List<FtbPersonnelsStaffEmploymentApply> staffEmploymentApplies = this.list(Wrappers.<FtbPersonnelsStaffEmploymentApply>lambdaQuery()
                    .eq(FtbPersonnelsStaffEmploymentApply::getCurrRank, positionGradesId)
                    .eq(FtbPersonnelsStaffEmploymentApply::getIsNeedCheck, 0)
                    .in(FtbPersonnelsStaffEmploymentApply::getCheckStatus,0,1)
            );
            if (CollUtil.isNotEmpty(staffEmploymentApplies)) {
                throw new RuntimeException("该职等存在于办理入职的用户中，不允许删除");
            }
        }
    }

    @Override
    public FtbPersonnelsBubbleCountVO getListCont(String flag) {
        //  flag "1" 我的审批 "2" 抄送
        FtbPersonnelsBubbleCountVO countVO = new FtbPersonnelsBubbleCountVO();
        String userId = UserProvider.getUser().getUserId();
        Integer configType = FtbPersonnelsCofigEnum.ONBOARDING_APPROVAL_CONFIGURATION.getConfigType();
        if ("1".equals(flag)) {
            // 待审批
            Page<FtbPersonnelsStaffEmploymentApplyDto> dtoPage = baseMapper.pagingQueryWebMyCheckList(Page.of(1, 1), userId, configType);
            countVO.setPendingCount(dtoPage.getTotal());
            // 审核中
            Page<FtbPersonnelsStaffEmploymentApplyDto> quantityUnderCount = baseMapper.getApprovedList(Page.of(1, 1), userId, configType, 1);
            countVO.setQuantityUnderCount(quantityUnderCount.getTotal());
            // 审核通过
            Page<FtbPersonnelsStaffEmploymentApplyDto> approvedCount = baseMapper.getApprovedList(Page.of(1, 1), userId, configType, 2);
            countVO.setApprovedCount(approvedCount.getTotal());
            // 审核不通过
            Page<FtbPersonnelsStaffEmploymentApplyDto> approvalFailedCount =   baseMapper.getApprovedList(Page.of(1, 1), userId, configType,3);
            countVO.setApprovalFailedCount(approvalFailedCount.getTotal());
        } else {
            Page<FtbPersonnelsStaffEmploymentApplyDto> quantityUnderCount = baseMapper.getListForApp(Page.of(1, 1), userId, 1);
            countVO.setQuantityUnderCount(quantityUnderCount.getTotal());
            Page<FtbPersonnelsStaffEmploymentApplyDto>  approvedCount = baseMapper.getListForApp(Page.of(1, 1), userId, 2);
            countVO.setApprovedCount(approvedCount.getTotal());
            Page<FtbPersonnelsStaffEmploymentApplyDto> approvalFailedCount = baseMapper.getListForApp(Page.of(1, 1), userId, 3);
            countVO.setApprovalFailedCount(approvalFailedCount.getTotal());
        }
        return countVO;
    }

    @Override
    public void exportDateNew(QueryStaffEmploymentApplyListReq req, HttpServletResponse response) throws IOException {
        req.setPageSize(Integer.MAX_VALUE);
        PageInfo<FtbPersonnelsStaffEmploymentApplyDto> pageVo = this.getPageList(req);
        List<FtbPersonnelsStaffEmploymentApplyVO> list = pageVo.getList()
                .parallelStream()
                .map(FtbPersonnelsStaffEmploymentApplyVO::convert)
                .collect(Collectors.toList());
        String fileName = "预办理入职员工信息";
        EasyExcelUtils.exportExcel(response, fileName, list, FtbPersonnelsStaffEmploymentApplyVO.class);
    }


    @Override
    public void updateData(SavePaperReq req) {

    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void deleteData(String id) {
        FtbPersonnelsStaffEmploymentApply entity = queryAndCheckStaffEmploymentApply(id);
        //检测是否可以删除
        //不需要审批 未到岗可以删除
        if (entity.getIsNeedCheck() == 1) {
            if (entity.getStatus() == 1) {
                throw new RuntimeException("该员工已经到岗,不能删除");
            }
        } else {
            //需要审批，审批不通过可以删除
            if (entity.getCheckStatus() == 0) {
                throw new RuntimeException("该员工等待审批,不能删除");
            } else if (entity.getCheckStatus() == 1) {
                throw new RuntimeException("该员工审批中,不能删除");
            } else if (entity.getCheckStatus() == 2 && entity.getStatus() == 1) {
                throw new RuntimeException("该员工已经入职,不能删除");
            }
        }
        //删除
        baseMapper.deleteById(id);
        //删除表单字段
        QueryWrapper<FtbPersonnelsStaffRegistrationFormData> wrapper = new QueryWrapper<>();
        wrapper.lambda().eq(FtbPersonnelsStaffRegistrationFormData::getPhone, entity.getPhone());
        registrationFormDataService.remove(wrapper);
        //重置今日发送短信
        personnelOrgUtils.resetTodaySendPhoneMsg(entity.getPhone());
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void deleteBatchData(List<String> ids) {
        //查询数据
        List<FtbPersonnelsStaffEmploymentApply> employmentApplyList = baseMapper.selectBatchIds(ids);
        if (CollectionUtil.isEmpty(employmentApplyList)) {
            return;
        }
        for (FtbPersonnelsStaffEmploymentApply entity : employmentApplyList) {
            //检测是否可以删除
            //不需要审批 未到岗可以删除
            if (entity.getIsNeedCheck() == 1) {
                if (entity.getStatus() == 1) {
                    throw new RuntimeException("员工[" + entity.getWorkerName() + "]已经到岗,不能删除");
                }
            } else {
                //需要审批，审批不通过可以删除
                if (entity.getCheckStatus() == 0) {
                    throw new RuntimeException("员工[" + entity.getWorkerName() + "]待审批,不能删除");
                } else if (entity.getCheckStatus() == 1) {
                    throw new RuntimeException("员工[" + entity.getWorkerName() + "]入职审批中,不能删除");
                } else if (entity.getCheckStatus() == 2 && entity.getStatus() == 1) {
                    throw new RuntimeException("员工[" + entity.getWorkerName() + "]已经入职,不能删除");
                }
            }
        }

        //批量删除
        baseMapper.deleteBatchIds(ids);
        //批量删除表单字段
        List<String> phoneList = employmentApplyList.stream()
                .map(FtbPersonnelsStaffEmploymentApply::getPhone) // 提取每个元素的电话号码
                .filter(Objects::nonNull) // 过滤掉null值（如果电话号码可能为null的话）
                .collect(Collectors.toList());

//        查询花名册是否存在

        if(CollectionUtil.isNotEmpty(phoneList)) {
            List<FtbPersonnelsStaffRoster> rosterList = rosterService.list(new QueryWrapper<FtbPersonnelsStaffRoster>().lambda()
                    .in(FtbPersonnelsStaffRoster::getPhone, phoneList)
                    .eq(FtbPersonnelsStaffRoster::getEnabledMark, 0)
                    .ne(FtbPersonnelsStaffRoster::getWorkerStatus, "305")
            );
            if(CollectionUtil.isNotEmpty(rosterList)){
                List<String> deletePhoneList = new ArrayList<>();
                List<String> notDeletePhoneList = new ArrayList<>();
                for (FtbPersonnelsStaffRoster roster : rosterList) {
                    notDeletePhoneList.add(roster.getPhone());
                }
                for (String phone : phoneList) {
                    if(!notDeletePhoneList.contains(phone)){
                        deletePhoneList.add(phone);
                    }
                }
                if(CollectionUtil.isNotEmpty(deletePhoneList)){
                    QueryWrapper<FtbPersonnelsStaffRegistrationFormData> wrapper = new QueryWrapper<>();
                    wrapper.lambda().in(FtbPersonnelsStaffRegistrationFormData::getPhone, deletePhoneList);
                    registrationFormDataService.remove(wrapper);
                }
            }else {
                QueryWrapper<FtbPersonnelsStaffRegistrationFormData> wrapper = new QueryWrapper<>();
                wrapper.lambda().in(FtbPersonnelsStaffRegistrationFormData::getPhone, phoneList);
                registrationFormDataService.remove(wrapper);
            }
        }

        //重置今日发送短信
        for (FtbPersonnelsStaffEmploymentApply entity : employmentApplyList) {
            personnelOrgUtils.resetTodaySendPhoneMsg(entity.getPhone());
        }
    }

    @Override
    public void updateConfirmArrivalStatus(String id) {
        // baseMapper.deleteById(id);
        FtbPersonnelsStaffEmploymentApply employmentApply = new FtbPersonnelsStaffEmploymentApply();
        employmentApply.setId(id);
        employmentApply.setStatus(1);
        baseMapper.updateById(employmentApply);
    }
}
