package cn.iocoder.yudao.module.base.service.impl;


import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.collection.CollectionUtil;
import cn.hutool.core.util.ObjectUtil;
import cn.iocoder.yudao.common.CommonErrorCodeConstants;
import cn.iocoder.yudao.common.SystemEnum;
import cn.iocoder.yudao.framework.security.core.util.SecurityFrameworkUtils;
import cn.iocoder.yudao.module.base.entity.RepairStaffSaveVo;
import cn.iocoder.yudao.module.base.service.RepairStaffService;
import cn.iocoder.yudao.module.constant.InspectionConstants;
import cn.iocoder.yudao.module.inspection.service.IInspectionFileService;
import cn.iocoder.yudao.module.staff.entity.CompanyStaff;
import cn.iocoder.yudao.module.staff.service.CompanyStaffService;
import cn.iocoder.yudao.module.staff.service.UniqueCodeService;
import cn.iocoder.yudao.module.system.api.dept.DeptApi;
import cn.iocoder.yudao.module.system.api.dept.dto.DeptRespDTO;
import cn.iocoder.yudao.module.system.api.user.AdminUserApi;
import cn.iocoder.yudao.module.system.api.user.dto.AdminUserRespDTO;
import cn.iocoder.yudao.module.system.api.user.dto.UserDTO;
import cn.iocoder.yudao.module.system.dal.dataobject.user.AdminUserDO;
import cn.iocoder.yudao.module.system.service.permission.PermissionService;
import cn.iocoder.yudao.module.system.service.permission.RoleService;
import cn.iocoder.yudao.module.system.service.user.AdminUserService;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import java.util.ArrayList;
import java.util.List;
import java.util.Set;
import java.util.stream.Collectors;

import static cn.iocoder.yudao.framework.common.exception.util.ServiceExceptionUtil.exception;

@Service
@RequiredArgsConstructor
@Slf4j
public class RepairStaffServiceImpl implements RepairStaffService {

    private final AdminUserService userService;

    private final RoleService roleService;

    private final PermissionService permissionService;

    private final CompanyStaffService companyStaffService;

    private final DeptApi deptApi;

    private final AdminUserApi adminUserApi;

    private final UniqueCodeService uniqueCodeService;

    private final IInspectionFileService inspectionFileService;

    public void addStaff(RepairStaffSaveVo repairStaff) {
        // 获取当前登录用户的详细信息
        AdminUserRespDTO loginUser = getLoginUser();
        // 1. 分配角色
        repairStaff.getRepairStaffs().forEach(item -> {
            permissionService.assignUserRoleByServicePackageId(item.getId(), repairStaff.getRoleIds(), SystemEnum.REPAIR.getCode());
        });
        // 2. 查看员工表中是否存在
        List<Long> oldIds = repairStaff.getRepairStaffs().stream().map(UserDTO::getId).collect(Collectors.toList());
        List<CompanyStaff> staffList = companyStaffService.list(Wrappers.<CompanyStaff>lambdaQuery()
                .in(CompanyStaff::getUserId, oldIds));

        // 获取员工表中已有的用户ID集合
        Set<Long> existUserIds = staffList.stream()
                .map(CompanyStaff::getUserId)
                .collect(Collectors.toSet());

        // 找出不存在于员工表中的用户ID
        List<UserDTO> notExistUsers = repairStaff.getRepairStaffs().stream()
                .filter(user -> !existUserIds.contains(user.getId()))
                .collect(Collectors.toList());

        /* 插入员工库 */
        DeptRespDTO loginDept = getLoginDept(loginUser.getDeptId());

        // 添加员工
        if (CollectionUtil.isNotEmpty(notExistUsers)) {
            List<CompanyStaff> companyStaffs = new ArrayList<>();
            for (UserDTO notExistUser : notExistUsers) {
                CompanyStaff companyStaff = new CompanyStaff();

                // 1 获取当前登录用户的企业信息给添加的员工
                // 2 生成唯一推广码
                String uniqueCode = uniqueCodeService.createUniqueCode();
                if (!ObjectUtil.isNotEmpty(uniqueCode)) {
                    throw exception(CommonErrorCodeConstants.UNIQUE_CODE_CREATE_REPEAT);
                }
                companyStaff.setCorpId(loginDept.getCorpId());
                companyStaff.setUserId(notExistUser.getId());
                companyStaff.setName(notExistUser.getNickname());
                companyStaff.setTel(notExistUser.getUsername());
                companyStaff.setUniqueCode(uniqueCode);

                companyStaffs.add(companyStaff);
            }
            companyStaffService.saveBatch(companyStaffs);
        }
    }

    /**
     * 删除员工
     *
     * @param id
     */
    @Override
    public void deleteStaff(List<Long> ids) {
        boolean remove = companyStaffService.remove(Wrappers.<CompanyStaff>lambdaQuery()
                .in(CompanyStaff::getUserId, ids));
    }

    /**
     * @param userId
     * @description: 员工新增文件夹
     * @param: userId
     * @return: java.lang.Long
     * @author 許
     * @date: 2025/8/11 11:51
     */
    @Override
    @Transactional
    public Long addFolder(Long userId) {
        AdminUserDO user = userService.getUser(userId);
        if (ObjectUtil.isNotEmpty(user)) {
            Long folderId = inspectionFileService.addFolderForWx(user.getNickname(), InspectionConstants.WX_DRIVER_STAFF_KEY);

            //修改文件夹id
            companyStaffService.update(Wrappers.<CompanyStaff>lambdaUpdate().eq(CompanyStaff::getUserId, userId).set(CompanyStaff::getFolderId, folderId));

            return folderId;
        } else {
            log.error("用户不存在");
            return null;
        }
    }

    /**
     * @param id
     * @description: 查询员工信息
     * @return: cn.iocoder.yudao.module.system.api.user.dto.UserDTO
     * @author 許
     * @date: 2025/8/11 13:22
     */
    @Override
    public UserDTO getStaff(Long id) {
        return companyStaffService.getStaff(id);
    }

    /**
     * @return void
     * @Author 许
     * @Description 新增员工
     * @Date 16:17 2025/8/20
     * @Param [repairStaff]
     */
    @Override
    public void insert(RepairStaffSaveVo repairStaff) {
        // 获取当前登录用户的详细信息
        AdminUserRespDTO loginUser = getLoginUser();

        // 判断用户是否存在
        AdminUserRespDTO checkUserName = adminUserApi.getUserByUsername(repairStaff.getRepairStaffs().get(0).getUsername());

        if (ObjectUtil.isEmpty(checkUserName)) {
            // 新增
            Long user = adminUserApi.createUser(repairStaff.getRepairStaffs().get(0));
            repairStaff.getRepairStaffs().get(0).setId(user);
        }

        // 1. 分配角色
        repairStaff.getRepairStaffs().forEach(item -> {
            permissionService.assignUserRoleByServicePackageId(item.getId(), repairStaff.getRoleIds(), SystemEnum.REPAIR.getCode());
        });
        // 2. 查看员工表中是否存在
        List<Long> oldIds = repairStaff.getRepairStaffs().stream().map(UserDTO::getId).collect(Collectors.toList());
        List<CompanyStaff> staffList = companyStaffService.list(Wrappers.<CompanyStaff>lambdaQuery()
                .in(CompanyStaff::getUserId, oldIds));

        // 获取员工表中已有的用户ID集合
        Set<Long> existUserIds = staffList.stream()
                .map(CompanyStaff::getUserId)
                .collect(Collectors.toSet());

        // 找出不存在于员工表中的用户ID
        List<UserDTO> notExistUsers = repairStaff.getRepairStaffs().stream()
                .filter(user -> !existUserIds.contains(user.getId()))
                .collect(Collectors.toList());

        /* 插入员工库 */
        DeptRespDTO loginDept = getLoginDept(loginUser.getDeptId());

        // 添加员工
        if (CollectionUtil.isNotEmpty(notExistUsers)) {
            List<CompanyStaff> companyStaffs = new ArrayList<>();
            for (UserDTO notExistUser : notExistUsers) {
                CompanyStaff companyStaff = new CompanyStaff();
                BeanUtil.copyProperties(notExistUser, companyStaff);
                companyStaff.setId(null);
                companyStaff.setCreateTime(null);
                companyStaff.setUpdateTime(null);
                companyStaff.setCreator(null);
                companyStaff.setUpdater(null);

                // 1 获取当前登录用户的企业信息给添加的员工
                // 2 生成唯一推广码
                String uniqueCode = uniqueCodeService.createUniqueCode();
                if (!ObjectUtil.isNotEmpty(uniqueCode)) {
                    throw exception(CommonErrorCodeConstants.UNIQUE_CODE_CREATE_REPEAT);
                }
                companyStaff.setCorpId(loginDept.getCorpId());
                companyStaff.setUserId(notExistUser.getId());
                companyStaff.setName(notExistUser.getNickname());
                companyStaff.setTel(notExistUser.getUsername());
                companyStaff.setUniqueCode(uniqueCode);

                companyStaffs.add(companyStaff);
            }
            companyStaffService.saveBatch(companyStaffs);
        }
    }

    /**
     * @return void
     * @Author 许
     * @Description
     * @Date 10:44 2025/8/21
     * @Param [repairStaff]
     */
    @Override
    public void updateStaff(RepairStaffSaveVo repairStaff) {
        UserDTO staff = repairStaff.getRepairStaff();
        CompanyStaff companyStaff = BeanUtil.copyProperties(staff, CompanyStaff.class);
        companyStaff.setCreator(null);
        companyStaff.setUpdater(null);
        companyStaff.setUpdateTime(null);
        companyStaff.setCreateTime(null);
        companyStaff.setDeptId(null);
        companyStaff.setId(null);
        companyStaffService.update(companyStaff, Wrappers.<CompanyStaff>lambdaUpdate()
                .eq(CompanyStaff::getUserId, staff.getId()));
    }

    /**
     * 获取当前登录用户的部门详细信息
     *
     * @param deptId 部门ID
     * @author 小李
     * @date 17:28 2024/8/9
     **/
    private DeptRespDTO getLoginDept(Long deptId) {
        return deptApi.getDept(deptId);
    }

    /**
     * 获取当前登录用户的详细信息
     *
     * @author 小李
     * @date 17:27 2024/8/9
     **/
    private AdminUserRespDTO getLoginUser() {
        Long userId = SecurityFrameworkUtils.getLoginUserId();
        return adminUserApi.getUser(userId);
    }
}
