package com.netwisd.base.main;

import cn.hutool.core.collection.CollectionUtil;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.core.util.StrUtil;
import com.alibaba.cloud.commons.lang.StringUtils;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.github.dozermapper.core.Mapper;
import com.netwisd.base.main.dto.MdmHbytUserDto;
import com.netwisd.base.main.entity.User;
import com.netwisd.base.main.service.UserService;
import com.netwisd.base.main.vo.MdmOrgAllVo;
import com.netwisd.base.mdm.entity.MdmOrg;
import com.netwisd.base.mdm.service.MdmOrgService;
import com.netwisd.base.mdm.service.MdmRoleService;
import com.netwisd.base.mdm.service.MdmUserService;
import com.netwisd.common.core.exception.IncloudException;
import com.netwisd.common.core.util.DozerUtils;
import com.netwisd.pojo.common.constants.YesNo;
import com.netwisd.pojo.mdm.constants.OrgTypeEnum;
import com.netwisd.pojo.mdm.dto.MdmOrgDto;
import com.netwisd.pojo.mdm.dto.MdmUserDto;
import lombok.SneakyThrows;
import lombok.extern.slf4j.Slf4j;
import org.apache.http.HttpEntity;
import org.apache.http.HttpResponse;
import org.apache.http.client.HttpClient;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.impl.client.HttpClientBuilder;
import org.apache.http.util.EntityUtils;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.autoconfigure.json.JsonTest;
import org.springframework.boot.test.context.SpringBootTest;

import java.io.File;
import java.io.FileInputStream;
import java.io.FileReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.Reader;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

/**
 * 同步用户方法
 */
@SpringBootTest
@Slf4j
public class UserSyncDataTest {

    private HttpClient httpClient = HttpClientBuilder.create().build();

    private static String userUrl = "http://10.188.246.192:8002/api/pub/staff/all";

    @Autowired
    private Mapper dozerMapper;

    @Autowired
    private MdmUserService mdmUserService;

    @Autowired
    private MdmRoleService mdmRoleService;

    @Autowired
    private MdmOrgService mdmOrgService;

    @Autowired
    private UserService userService;

    /**
     * 默认root信息
     */
    private static Long defaultRootId = 0l;

    private final String ptUserRole = "PT_USER_ROLE";//普通用户角色


    /**
     * 读取数据库信息，同步组织信息
     */
    @Test
    public void syncHbytUserInfoByDb() {
        LambdaQueryWrapper<User> queryWrapper = new LambdaQueryWrapper<>();
        List<User> userList = userService.getBaseMapper().selectList(queryWrapper);

        MdmOrgDto getAllMdmOrg = new MdmOrgDto();
        getAllMdmOrg.setIsDefault(YesNo.NO.code);
        List<MdmOrgAllVo> mdmOrgAllVoList = this.treeList(getAllMdmOrg);

        //获取入库后的所有部门信息
        Map<Integer, List<MdmOrgAllVo>> mdmOrgAllTypeGrop = mdmOrgAllVoList.stream().collect(Collectors.groupingBy(MdmOrgAllVo::getOrgType));
        List<MdmOrgAllVo> allDeptList = mdmOrgAllTypeGrop.get(OrgTypeEnum.ORG.code);

        //根据部门，获取对应的部门下的用户
        Map<String, List<User>> groupDeptUserMap = userList.stream().filter(d -> null != d.getOrgCode()).collect(Collectors.groupingBy(User::getOrgCode));
        //处理人员 以及主岗信息
        List<MdmUserDto> userReList = handleUserByDb(allDeptList, groupDeptUserMap);
        boolean saveResult = mdmUserService.saveList(userReList);
        log.info("保存的用户结果：{}", saveResult);
        log.debug("同步用户信息完成！");
    }


    /**
     * 处理人员 同时处理主岗信息
     *
     * @param deptList
     * @param groupDeptUserMap
     */
    public List<MdmUserDto> handleUserByDb(List<MdmOrgAllVo> deptList, Map<String, List<User>> groupDeptUserMap) {
        log.info("start---------------------------------------------------------------------------");
        log.info("部门：{}", deptList.size());
        log.info("根据部门CODE分组：{}", groupDeptUserMap.size());
        log.info("end---------------------------------------------------------------------------");
        List<MdmUserDto> resultList = new ArrayList<>();
        for (MdmOrgAllVo mdmOrgAllVo : deptList) {
            List<User> listUser = groupDeptUserMap.get(mdmOrgAllVo.getOrgCode());
            if (CollectionUtil.isNotEmpty(listUser)) {
                for (User user : listUser) {
                    //组装mdm User
                    MdmUserDto mdmUser = new MdmUserDto();
                    mdmUser.setOrgId(mdmOrgAllVo.getId());
                    mdmUser.setOrgName(mdmOrgAllVo.getOrgName());
                    //登录时用这个字段
                    mdmUser.setUserName(user.getLoginName());
                    mdmUser.setUserCode(user.getLoginName());
                    mdmUser.setUserRank(user.getStaffRank());
                    //汉字名称
                    mdmUser.setUserNameCh(user.getUserName());
                    mdmUser.setCardType(0);//默认身份证号
                    if (StrUtil.isNotEmpty(user.getSex())) {//华北0男 1女  平台 1男2女
                        mdmUser.setSex(user.getSex().equals("0") ? 1 : 2);
                    }
                    //mdmUser.setIdCard(user.getIdentityCard());
                    //mdmUser.setPhoneNum(user.getPhonenumber());
                    //mdmUser.setOfficePhone(user.getPhone());
                    mdmUser.setPassWord("Sjzx@123456"); //明文Sjzx@123456  现值为AES加密后
                    //mdmUser.setEmail(user.getEmail());
                    mdmUser.setEmploymentForm(1);
                    mdmUser.setEmploymentType(0);
                    mdmUser.setStatus(1); //股份 1在职 2离职；本系统： 1启用 2停用
                    resultList.add(mdmUser);
                }
            }
        }
        log.info("user-- save ---start---------------------------------------------------------------------------");
        log.info("保存的用户集合；{}", resultList.size());
        log.info("user---save ----end---------------------------------------------------------------------------");
        return resultList;
    }


    //json同步用戶
    @Test
    public void syncjsonUserInfo() {
        String path = JsonTest.class.getClassLoader().getResource("renyuan.json").getPath();
        String s = readJsonFile(path);
        JSONObject jobj = JSON.parseObject(s);
        try {
            // 判断返回状态是否为200
            if (ObjectUtil.isNotEmpty(jobj)) { // true
                JSONArray datasUser = jobj.getJSONArray("data");
                List<MdmHbytUserDto> listUser = JSONObject.parseArray(datasUser.toJSONString(), MdmHbytUserDto.class);
                //查询所有机构
                MdmOrgDto getAllMdmOrg = new MdmOrgDto();
                getAllMdmOrg.setIsDefault(YesNo.NO.code);
                //getAllMdmOrg.setOrgClass(OrgClassEnum.BIZ.code);
                List<MdmOrgAllVo> mdmOrgAllVoList = this.treeList(getAllMdmOrg);
                //获取入库后的所有部门信息
                Map<Integer, List<MdmOrgAllVo>> mdmOrgAllTypeGrop = mdmOrgAllVoList.stream().collect(Collectors.groupingBy(MdmOrgAllVo::getOrgType));
                List<MdmOrgAllVo> allDeptList = mdmOrgAllTypeGrop.get(OrgTypeEnum.DEPT.code);
                //根据部门，获取对应的部门下的用户
                Map<String, List<MdmHbytUserDto>> _groupDeptUserMap = listUser.stream().filter(d -> null != d.getOrgCode()).collect(Collectors.groupingBy(MdmHbytUserDto::getOrgCode));
                //处理人员 以及主岗信息
                handleUser(allDeptList, _groupDeptUserMap);
                log.debug("同步人员信息完成！");
            } else {
                log.error("同步人员信息失败，错误代码：{}");
                throw new IncloudException("同步人员信息失败！");
            }
        } catch (Exception e) {
            log.error("错误:{}",e);
            throw new IncloudException("同步人员信息失败!" + e.getMessage());
        }
    }

    //读取json文件
    public static String readJsonFile(String fileName) {
        String jsonStr = "";
        try {
            File jsonFile = new File(fileName);
            FileReader fileReader = new FileReader(jsonFile);
            Reader reader = new InputStreamReader(new FileInputStream(jsonFile), "utf-8");
            int ch = 0;
            StringBuffer sb = new StringBuffer();
            while ((ch = reader.read()) != -1) {
                sb.append((char) ch);
            }
            fileReader.close();
            reader.close();
            jsonStr = sb.toString();
            return jsonStr;
        } catch (IOException e) {
            log.error("错误:{}",e);
            return null;
        }
    }

    /**
     * 处理人员 同时处理主岗信息
     *
     * @param deptList
     * @param _groupDeptUserMap
     */
    public void handleUser(List<MdmOrgAllVo> deptList, Map<String, List<MdmHbytUserDto>> _groupDeptUserMap) {
        log.info("start---------------------------------------------------------------------------");
        log.info("部门：{}", deptList.size());
        log.info("根据部门CODE分组：{}", _groupDeptUserMap.size());
        log.info("end---------------------------------------------------------------------------");
        List<MdmUserDto> resultList = new ArrayList<>();
        for (MdmOrgAllVo mdmOrgAllVo : deptList) {
            List<MdmHbytUserDto> listUser = _groupDeptUserMap.get(mdmOrgAllVo.getOrgCode());
            if (CollectionUtil.isNotEmpty(listUser)) {
                for (MdmHbytUserDto mdmHbytUserDto : listUser) {
                    //组装mdm User
                    MdmUserDto mdmUser = new MdmUserDto();
                    mdmUser.setOrgId(Long.valueOf(mdmHbytUserDto.getOrgCode()));
                    mdmUser.setOrgName(mdmHbytUserDto.getOrgName());
                    //登录时用这个字段
                    mdmUser.setUserName(mdmHbytUserDto.getStaffCode());
                    mdmUser.setUserCode(mdmHbytUserDto.getStaffCode());
                    //汉字名称
                    mdmUser.setUserNameCh(mdmHbytUserDto.getStaffName());
                    mdmUser.setCardType(0);//默认身份证号
                    if (null != mdmHbytUserDto.getSex()) { //华北0男 1女  平台 1男2女
                        mdmUser.setSex(mdmHbytUserDto.getSex() == 0 ? 1 : 2);
                    }
                    mdmUser.setIdCard(mdmHbytUserDto.getStaffCode());
                    mdmUser.setPhoneNum(null);
                    mdmUser.setOfficePhone(mdmHbytUserDto.getPhonenumber());
                    mdmUser.setPassWord("Sjzx@123456"); //明文Sjzx@123456  现值为AES加密后
                    mdmUser.setEmail(mdmHbytUserDto.getEmail());
                    mdmUser.setEmploymentType(null);
                    mdmUser.setStatus(1); //股份 1在职 2离职；本系统： 1启用 2停用
                    resultList.add(mdmUser);
                }
            }
        }
        log.info("user-- save ---start---------------------------------------------------------------------------");
        log.info("保存的用户集合；{}", resultList.size());
        log.info("user---save ----end---------------------------------------------------------------------------");
        boolean saveResult = mdmUserService.saveList(resultList);
        log.info("保存的用户集合结果：{}", saveResult);
    }


    private List<MdmOrgAllVo> treeList(MdmOrgDto mdmOrgDto) {
        List<MdmOrg> orgList = mdmOrgService.list(searchQuery(mdmOrgDto));
        List<MdmOrgAllVo> mdmOrgAllVos = DozerUtils.mapList(dozerMapper, orgList, MdmOrgAllVo.class);
        return mdmOrgAllVos;
    }

    /**
     * 根据参数构建查询参数
     *
     * @param mdmOrgDto
     * @return
     */
    @SneakyThrows
    public LambdaQueryWrapper<MdmOrg> searchQuery(MdmOrgDto mdmOrgDto) {
        Integer isDefault = ObjectUtil.isEmpty(mdmOrgDto.getIsDefault()) ? 0 : mdmOrgDto.getIsDefault();
        LambdaQueryWrapper<MdmOrg> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.le(ObjectUtil.isNotEmpty(mdmOrgDto.getGrade()), MdmOrg::getGrade, mdmOrgDto.getGrade());
        if (isDefault == 0) {
            queryWrapper.like(StrUtil.isNotEmpty(mdmOrgDto.getOrgCode()), MdmOrg::getOrgCode, mdmOrgDto.getOrgCode())
                    .like(StrUtil.isNotEmpty(mdmOrgDto.getOrgName()), MdmOrg::getOrgName, mdmOrgDto.getOrgName())
                    .like(ObjectUtil.isNotEmpty(mdmOrgDto.getParentId()), MdmOrg::getOrgFullId, mdmOrgDto.getParentId())
                    .eq(ObjectUtil.isNotEmpty(mdmOrgDto.getStatus()), MdmOrg::getStatus, mdmOrgDto.getStatus())
                    .eq(ObjectUtil.isNotEmpty(mdmOrgDto.getOrgType()), MdmOrg::getOrgType, mdmOrgDto.getOrgType())
                    .eq(MdmOrg::getOrgType, ObjectUtil.isEmpty(mdmOrgDto.getOrgType()) || 0 == mdmOrgDto.getOrgType() ? 2 : mdmOrgDto.getOrgType())
                    .or()
                    .eq(MdmOrg::getOrgType, ObjectUtil.isEmpty(mdmOrgDto.getOrgType()) || 0 == mdmOrgDto.getOrgType() ? 1 : mdmOrgDto.getOrgType())
                    .ne(MdmOrg::getId, 0l)//处理root 不查询 root节点
                    .orderByDesc(MdmOrg::getGrade);
        } else {
            queryWrapper.eq(ObjectUtil.isNotEmpty(mdmOrgDto.getStatus()), MdmOrg::getStatus, mdmOrgDto.getStatus());
            queryWrapper.eq(ObjectUtil.isNotEmpty(mdmOrgDto.getOrgType()), MdmOrg::getOrgType, mdmOrgDto.getOrgType());
            queryWrapper.eq(MdmOrg::getOrgType, ObjectUtil.isEmpty(mdmOrgDto.getOrgType()) || 0 == mdmOrgDto.getOrgType() ? 2 : mdmOrgDto.getOrgType());
            //queryWrapper.between(ObjectUtil.isNotNull(mdmOrgDto.getSUpdateTime()) && ObjectUtil.isNotNull(mdmOrgDto.getEUpdateTime()), MdmOrg::getUpdateTime, mdmOrgDto.getSUpdateTime(), mdmOrgDto.getEUpdateTime());
            queryWrapper.eq(MdmOrg::getParentId, ObjectUtil.isNotNull(mdmOrgDto.getParentId()) ? mdmOrgDto.getParentId() : defaultRootId);
        }

        queryWrapper.orderByAsc(MdmOrg::getSort);
        return queryWrapper;
    }
}
