package com.xinyilu.system.service.classinfo.impl;

import com.xinyilu.common.constant.Constants;
import com.xinyilu.common.core.domain.AjaxResult;
import com.xinyilu.common.core.domain.entity.SysRole;
import com.xinyilu.common.core.page.TableDataInfo;
import com.xinyilu.common.exception.ServiceException;
import com.xinyilu.common.utils.DateUtils;
import com.xinyilu.common.utils.PageServiceUtil;
import com.xinyilu.common.utils.SecurityUtils;
import com.xinyilu.common.utils.regex.RegexUtil;
import com.xinyilu.system.domain.dto.ClassInfoDTO;
import com.xinyilu.system.domain.dto.ClassTypeDTO;
import com.xinyilu.system.domain.systemarea.SysArea;
import com.xinyilu.system.domain.sysuserclassrelation.SysUserClassRelation;
import com.xinyilu.system.domain.vo.ClassInfoVO;
import com.xinyilu.system.domain.vo.SysUserVO;
import com.xinyilu.system.mapper.SysUserMapper;
import com.xinyilu.system.mapper.classinfo.ClassInfoMapper;
import com.xinyilu.system.mapper.systemarea.SysAreaMapper;
import com.xinyilu.system.mapper.sysuserclassrelation.SysUserClassRelationMapper;
import com.xinyilu.system.service.classinfo.IClassInfoService;
import org.apache.commons.collections4.CollectionUtils;
import org.apache.commons.compress.utils.Lists;
import org.apache.commons.lang3.StringUtils;
import org.springframework.stereotype.Service;

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

/**
 * 班级信息Service业务层处理
 *
 * @author jihan
 * @date 2022-07-29
 */
@Service
public class ClassInfoServiceImpl implements IClassInfoService {

    @Resource
    private ClassInfoMapper classInfoMapper;
    @Resource
    private PageServiceUtil pageServiceUtil;
    @Resource
    private RegexUtil regexUtil;
    @Resource
    private SysUserMapper userMapper;
    @Resource
    private SysUserClassRelationMapper sysUserClassRelationMapper;
    @Resource
    private SysAreaMapper sysAreaMapper;


    /**
     * 查询班级信息
     *
     * @param id 班级信息主键
     * @return 班级信息
     */
    @Override
    public ClassInfoVO selectClassInfoById(Long id) {
        return classInfoMapper.selectClassInfoById(id);
    }

    /**
     * 查询班级信息列表
     *
     * @param classInfo 班级信息
     * @return 班级信息
     */
    @Override
    public TableDataInfo selectClassInfoList(ClassInfoDTO classInfo) {
        //判断当前用户角色，根据不同的角色显示不同的班级信息
        List<String> roleKeys = SecurityUtils.getLoginUser().getUser().getRoles()
                .stream().filter(Objects::nonNull)
                .filter(item -> StringUtils.isNotBlank(item.getRoleKey()))
                .map(SysRole::getRoleKey).collect(Collectors.toList());
        Long userId = SecurityUtils.getUserId();
        SysUserVO sysUserVO = userMapper.selectUserById(userId);
        if (roleKeys.contains(Constants.ADMIN_ROLE)) {
            //角色为管理员，查询所有的班级信息
            return getClassInfoList(classInfo);
        } else if (roleKeys.contains(Constants.CITY)) {
            //角色为市级角色，查询该市内的所有幼儿园的信息
            long areaId = Objects.isNull(SecurityUtils.getLoginUser().getUser().getAreaId()) ? 0 : SecurityUtils.getLoginUser().getUser().getAreaId();
            SysArea sysArea = new SysArea();
            sysArea.setParentId(areaId);
            List<Long> sysAreaIdList = sysAreaMapper.selectSysAreaList(sysArea).stream().filter(Objects::nonNull).filter(sysAreaId -> Objects.nonNull(sysAreaId.getId())).map(SysArea::getId).collect(Collectors.toList());
            List<Long> kindergartenIdList = Lists.newArrayList();
            if (CollectionUtils.isNotEmpty(sysAreaIdList)) {
                //获取该区域下的所有幼儿园信息
                kindergartenIdList = classInfoMapper.getKindergartenInfoByAreaId(sysAreaIdList, null);
            }
            if (CollectionUtils.isEmpty(kindergartenIdList)) {
                return null;
            }
            classInfo.setKindergartenIdList(kindergartenIdList);
            return getClassInfoList(classInfo);
        } else if (roleKeys.contains(Constants.REGION_ROLE)) {
            //角色为区域角色，查询该区域下所有幼儿园的班级信息
            long areaId = Objects.isNull(SecurityUtils.getLoginUser().getUser().getAreaId()) ? 0 : SecurityUtils.getLoginUser().getUser().getAreaId();
            List<Long> kindergartenIdList = Lists.newArrayList();
            List<Long> sysAreaIdList = new ArrayList<>();
            sysAreaIdList.add(areaId);
            if (CollectionUtils.isNotEmpty(sysAreaIdList)) {
                //获取该区域下的所有幼儿园信息
                kindergartenIdList = classInfoMapper.getKindergartenInfoByAreaId(sysAreaIdList, 3L);
            }
            if (CollectionUtils.isEmpty(kindergartenIdList)) {
                return null;
            }
            classInfo.setKindergartenIdList(kindergartenIdList);
            return getClassInfoList(classInfo);
        } else if (roleKeys.contains(Constants.ENCHOU_ROLE)) {
            //角色为幼儿园园长，查询其所属幼儿园下所有的班级信息
            Long kindergartenId = classInfoMapper.getKindergartenIdByPrincipalId(userId);
            if (Objects.isNull(kindergartenId) || kindergartenId == 0L) {
                return null;
            }
            classInfo.setKindergartenId(kindergartenId);
            return getClassInfoList(classInfo);
        } else if (roleKeys.contains(Constants.HEALTHCARE_ROLE)) {
            //角色是：保健师，查找出其所属的幼儿园信息
            if (Objects.isNull(sysUserVO) || Objects.isNull(sysUserVO.getKindergartenId()) || sysUserVO.getKindergartenId() == 0L) {
                return null;
            }
            classInfo.setKindergartenId(sysUserVO.getKindergartenId());
            return getClassInfoList(classInfo);
        } else if (roleKeys.contains(Constants.TEACHER_ROLE) && roleKeys.size() == 1) {
            //角色为老师，查询老师所属班级的信息
            List<Long> classIdList = sysUserClassRelationMapper.getSysUserClassRelationList(userId).stream().filter(Objects::nonNull).filter(classId -> Objects.nonNull(classId.getClassId())).map(SysUserClassRelation::getClassId).distinct().collect(Collectors.toList());
            if (CollectionUtils.isEmpty(classIdList)) {
                return null;
            }
            classInfo.setClassIdList(classIdList);
            return getClassInfoList(classInfo);
        } else if (roleKeys.contains(Constants.PARENT_ROLE) && roleKeys.size() == 1) {
            //角色为家长，查询其孩子所在班级信息
            if (Objects.isNull(sysUserVO) || Objects.isNull(sysUserVO.getPhonenumber())) {
                return null;
            }
            List<Long> classIdList = classInfoMapper.getClassIdByParentId(sysUserVO.getPhonenumber());
            if (CollectionUtils.isEmpty(classIdList)) {
                return null;
            }
            classInfo.setClassIdList(classIdList);
            return getClassInfoList(classInfo);
        } else if (roleKeys.contains(Constants.TEACHER_ROLE) && roleKeys.contains(Constants.PARENT_ROLE) && roleKeys.size() == 2) {
            //角色即是老师又是家长，查询老师和家长所属班级的信息
            List<Long> classIdList = Lists.newArrayList();
            List<Long> classIdByUserId = sysUserClassRelationMapper.getSysUserClassRelationList(userId).stream().filter(Objects::nonNull).filter(classId -> Objects.nonNull(classId.getClassId())).map(SysUserClassRelation::getClassId).distinct().collect(Collectors.toList());
            if (CollectionUtils.isNotEmpty(classIdByUserId)) {
                classIdList.addAll(classIdByUserId);
            }
            if (Objects.nonNull(sysUserVO) && Objects.nonNull(sysUserVO.getPhonenumber())) {
                List<Long> classIdByParentId = classInfoMapper.getClassIdByParentId(sysUserVO.getPhonenumber());
                if (CollectionUtils.isNotEmpty(classIdByParentId)) {
                    classIdList.addAll(classIdByParentId);
                }
            }
            List<Long> distinctList = Lists.newArrayList();
            if (CollectionUtils.isNotEmpty(classIdList)) {
                distinctList = classIdList.stream().distinct().collect(Collectors.toList());
            }
            if (CollectionUtils.isEmpty(distinctList)) {
                return null;
            }
            classInfo.setClassIdList(distinctList);
            return getClassInfoList(classInfo);
        }
        return null;
    }

    /**
     * 新增班级信息
     *
     * @param classInfo 班级信息
     * @return 结果
     */
    @Override
    public int insertClassInfo(ClassInfoDTO classInfo) {
        // 判断班级名称不能重复
        int classNameNumberInfo = classInfoMapper.getClassNameNumberInfo(classInfo.getKindergartenId(), classInfo.getClassName(), classInfo.getClassType());
        if (classNameNumberInfo > 0) {
            throw new ServiceException("班级名称不能重复");
        }
        int classPhoneCountInfo = classInfoMapper.getClassPhoneCountInfo(classInfo.getPhone());
        if (classPhoneCountInfo > 0) {
            throw new ServiceException("手机号码不能重复");
        }
        //创建时间
        classInfo.setCreateTime(DateUtils.getNowDate());
        //是否删除
        classInfo.setDelFlag(0);
        //用户id
        classInfo.setUserId(SecurityUtils.getUserId());
        return classInfoMapper.insertClassInfo(classInfo);
    }

    /**
     * 修改班级信息
     *
     * @param classInfo 班级信息
     * @return 结果
     */
    @Override
    public int updateClassInfo(ClassInfoDTO classInfo) {
        ClassInfoVO classInfoVO = classInfoMapper.selectClassInfoById(classInfo.getId());
        if (Objects.isNull(classInfoVO)) {
            throw new ServiceException("班级不存在");
        }
        // 判断班级名称不能重复
        if (!classInfo.getClassName().equals(classInfoVO.getClassName())) {
            int classNameNumberInfo = classInfoMapper.getClassNameNumberInfo(classInfo.getKindergartenId(), classInfo.getClassName(), classInfo.getClassType());
            if (classNameNumberInfo > 0) {
                throw new ServiceException("班级名称不能重复");
            }
        }
        if (!classInfo.getPhone().equals(classInfoVO.getPhone())) {
            int classPhoneCountInfo = classInfoMapper.getClassPhoneCountInfo(classInfo.getPhone());
            if (classPhoneCountInfo > 0) {
                throw new ServiceException("手机号码不能重复");
            }
        }
        //创建时间
        classInfo.setUpdateTime(DateUtils.getNowDate());
        //是否删除
        classInfo.setDelFlag(0);
        return classInfoMapper.updateClassInfo(classInfo);
    }

    /**
     * 批量删除班级信息
     *
     * @param ids 需要删除的班级信息主键
     * @return 结果
     */
    @Override
    public int deleteClassInfoByIds(Long[] ids) {
        return classInfoMapper.deleteClassInfoByIds(ids);
    }

    /**
     * 删除班级信息信息
     *
     * @param id 班级信息主键
     * @return 结果
     */
    @Override
    public int deleteClassInfoById(Long id) {
        return classInfoMapper.deleteClassInfoById(id);
    }

    /**
     * 逻辑删除班级信息
     *
     * @param ids 主键id
     * @return 数量
     */
    @Override
    public int updateClassInfoById(Long[] ids) {
        return classInfoMapper.updateClassInfoById(ids);
    }

    /**
     * 批量修改“班级类型”
     *
     * @param classTypeDTO 幼儿园id及班级信息
     * @return AjaxResult
     */
    @Override
    public AjaxResult updateClassType(ClassTypeDTO classTypeDTO) {
        classTypeDTO.setUpdateBy(SecurityUtils.getUsername());
        classTypeDTO.setUpdateTime(DateUtils.getNowDate());
        return AjaxResult.success(classInfoMapper.updateClassTypes(classTypeDTO));
    }

    /**
     * 分页查询学生列表信息
     *
     * @param classInfo 输入参数
     * @return 学生列表信息
     */
    private TableDataInfo getClassInfoList(ClassInfoDTO classInfo) {
        pageServiceUtil.startPage();
        List<ClassInfoVO> classInfoList = classInfoMapper.selectClassInfoList(classInfo);
        return pageServiceUtil.getDataTable(classInfoList);
    }
}
