package org.jeecg.modules.system.service.impl;

import cn.dev33.satoken.oauth2.model.AccessTokenModel;
import cn.dev33.satoken.oauth2.model.CodeModel;
import cn.dev33.satoken.oauth2.model.RequestAuthModel;
import cn.hutool.core.util.RandomUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang.StringUtils;
import org.apache.shiro.SecurityUtils;
import org.jeecg.common.api.vo.Result;
import org.jeecg.common.constant.CacheConstant;
import org.jeecg.common.constant.CommonConstant;
import org.jeecg.common.system.api.ISysBaseAPI;
import org.jeecg.common.system.vo.LoginUser;
import org.jeecg.common.system.vo.SysUserCacheInfo;
import org.jeecg.common.util.PasswordUtil;
import org.jeecg.common.util.RedisUtil;
import org.jeecg.common.util.UUIDGenerator;
import org.jeecg.common.util.encryption.EncryptedString;
import org.jeecg.common.util.oConvertUtils;
import org.jeecg.modules.base.service.BaseCommonService;
import org.jeecg.modules.oauth2_server.util.AesUtil;
import org.jeecg.modules.oauth2_server.util.SaOAuth2Utils;
import org.jeecg.modules.system.constant.UserConstant;
import org.jeecg.modules.system.entity.*;
import org.jeecg.modules.system.enums.RoleEnum;
import org.jeecg.modules.system.mapper.*;
import org.jeecg.modules.system.model.SysUserSysDepartModel;
import org.jeecg.modules.system.service.*;
import org.jeecg.modules.system.vo.SysUserDepVo;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.cache.annotation.CacheEvict;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import java.util.*;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import java.util.stream.Collectors;

/**
 * <p>
 * 用户表 服务实现类
 * </p>
 *
 * @Author: scott
 * @Date: 2018-12-20
 */
@Service
@Slf4j
public class SysUserServiceImpl extends ServiceImpl<SysUserMapper, SysUser> implements ISysUserService {

	@Resource
	private ISysUserDepartService sysUserDepartService;
	@Resource
	private AsyncService asyncService;
	@Autowired
	private SysUserMapper userMapper;
	@Autowired
	private ISysUserService sysUserService;
	@Resource
	private SysPermissionMapper sysPermissionMapper;
	@Resource
	private SysUserRoleMapper sysUserRoleMapper;
	@Resource
	private SysUserDepartMapper sysUserDepartMapper;
	@Autowired
	private ISysBaseAPI sysBaseAPI;
	@Resource
	private SysDepartMapper sysDepartMapper;
	@Resource
	private SysRoleMapper sysRoleMapper;
	@Resource
	private SysDepartRoleUserMapper departRoleUserMapper;
	@Resource
	private SysDepartRoleMapper sysDepartRoleMapper;
	@Resource
	private BaseCommonService baseCommonService;
	@Autowired
    private ISysDepartService sysDepartService;
    @Autowired
    private ISysAreaService sysAreaService;
    @Autowired
    private ISysRoleService sysRoleService;
	@Autowired
    private ISysUserRoleService sysUserRoleService;
	@Autowired
	private RedisUtil redisUtil;

	@Override
    @CacheEvict(value = {CacheConstant.SYS_USERS_CACHE}, allEntries = true)
    public Result<?> changePassword(String username, String newpassword, String confirmpassword) {
    	SysUser user = userMapper.getUserByName(username);
        //String passwordEncode = PasswordUtil.encrypt(username, oldpassword, user.getSalt());
//        if (!user.getPassword().equals(passwordEncode)) {
//            return Result.error("旧密码输入错误!");
//        }
		Pattern pattern = Pattern.compile("^.*(?=.{8,})(?=.*\\d)(?=.*[A-Z])(?=.*[a-z])(?=.*[!@#$%^&*? _.]).*$");
		Matcher matcher = pattern.matcher(newpassword);
		boolean matches = matcher.matches();
		if (!matches){
			return Result.error("密码必须包含大写字母、小写字母、数字、非字母数字字符以及八位以上");
		}
        if (oConvertUtils.isEmpty(newpassword)) {
            return Result.error("新密码不允许为空!");
        }
        if (!newpassword.equals(confirmpassword)) {
            return Result.error("两次输入密码不一致!");
        }
        String password = PasswordUtil.encrypt(username, newpassword, user.getSalt());
        user.setPassword(password);
        this.userMapper.update(user, new LambdaQueryWrapper<SysUser>().eq(SysUser::getId, user.getId()));
        return Result.ok("密码修改成功!");
    }

    @Override
    //@CacheEvict(value = {CacheConstant.SYS_USERS_CACHE}, allEntries = true)
    public Result<?> resetPassword(SysUser sysUser) {
        String salt = oConvertUtils.randomGen(8);
        sysUser.setSalt(salt);
		String password = UserConstant.INITIALIZING_PASSWORD;
        String passwordEncode = PasswordUtil.encrypt(sysUser.getUsername(), password, salt);
        sysUser.setPassword(passwordEncode);
        this.userMapper.updateById(sysUser);
        return Result.OK(password);
    }

    @Override
    @CacheEvict(value={CacheConstant.SYS_USERS_CACHE}, allEntries=true)
	@Transactional(rollbackFor = Exception.class)
	public boolean deleteUser(String userId) {
		//1.删除用户
		this.removeById(userId);
		return false;
	}

	@Override
    @CacheEvict(value={CacheConstant.SYS_USERS_CACHE}, allEntries=true)
	@Transactional(rollbackFor = Exception.class)
	public boolean deleteBatchUsers(String userIds) {
		//1.删除用户
		this.removeByIds(Arrays.asList(userIds.split(",")));
		return false;
	}

	@Override
	public SysUser getUserByName(String username) {
		return userMapper.getUserByName(username);
	}
	
	
	@Override
	public void addUserWithRole(SysUser user, String roles) {
		this.save(user);
		if(oConvertUtils.isNotEmpty(roles)) {
			String[] arr = roles.split(",");
			for (String roleId : arr) {
				SysUserRole userRole = new SysUserRole(user.getId(), roleId);
				sysUserRoleMapper.insert(userRole);
			}
		}
	}

	@Override
	@CacheEvict(value= {CacheConstant.SYS_USERS_CACHE}, allEntries=true)
	public void editUserWithRole(SysUser user, String roles) {
		this.updateById(user);
		//先删后加
		sysUserRoleMapper.delete(new QueryWrapper<SysUserRole>().lambda().eq(SysUserRole::getUserId, user.getId()));
		if(oConvertUtils.isNotEmpty(roles)) {
			String[] arr = roles.split(",");
			for (String roleId : arr) {
				SysUserRole userRole = new SysUserRole(user.getId(), roleId);
				sysUserRoleMapper.insert(userRole);
			}
		}
	}


	@Override
	public List<String> getRole(String username) {
		return sysUserRoleMapper.getRoleByUserName(username);
	}
	
	/**
	 * 通过用户名获取用户角色集合
	 * @param username 用户名
     * @return 角色集合
	 */
	@Override
	public Set<String> getUserRolesSet(String username) {
		// 查询用户拥有的角色集合
		List<String> roles = sysUserRoleMapper.getRoleByUserName(username);
		log.info("-------通过数据库读取用户拥有的角色Rules------username： " + username + ",Roles size: " + (roles == null ? 0 : roles.size()));
		return new HashSet<>(roles);
	}

	/**
	 * 通过用户名获取用户权限集合
	 *
	 * @param username 用户名
	 * @return 权限集合
	 */
	@Override
	public Set<String> getUserPermissionsSet(String username) {
		Set<String> permissionSet = new HashSet<>();
		List<SysPermission> permissionList = sysPermissionMapper.queryByUser(username);
		for (SysPermission po : permissionList) {
//			// TODO URL规则有问题？
//			if (oConvertUtils.isNotEmpty(po.getUrl())) {
//				permissionSet.add(po.getUrl());
//			}
			if (oConvertUtils.isNotEmpty(po.getPerms())) {
				permissionSet.add(po.getPerms());
			}
		}
		log.info("-------通过数据库读取用户拥有的权限Perms------username： "+ username+",Perms size: "+ (permissionSet==null?0:permissionSet.size()) );
		return permissionSet;
	}

	@Override
	public SysUserCacheInfo getCacheUser(String username) {
		SysUserCacheInfo info = new SysUserCacheInfo();
		info.setOneDepart(true);
//		SysUser user = userMapper.getUserByName(username);
//		info.setSysUserCode(user.getUsername());
//		info.setSysUserName(user.getRealname());
		

		LoginUser user = sysBaseAPI.getUserByName(username);
		if(user!=null) {
			info.setSysUserCode(user.getUsername());
			info.setSysUserName(user.getRealname());
			info.setSysOrgCode(user.getOrgCode());
		}
		
		//多部门支持in查询
		List<SysDepart> list = sysDepartMapper.queryUserDeparts(user.getId());
		List<String> sysMultiOrgCode = new ArrayList<String>();
		if(list==null || list.size()==0) {
			//当前用户无部门
			//sysMultiOrgCode.add("0");
		}else if(list.size()==1) {
			sysMultiOrgCode.add(list.get(0).getOrgCode());
		}else {
			info.setOneDepart(false);
			for (SysDepart dpt : list) {
				sysMultiOrgCode.add(dpt.getOrgCode());
			}
		}
		info.setSysMultiOrgCode(sysMultiOrgCode);
		
		return info;
	}

	// 根据部门Id查询
	@Override
	public IPage<SysUser> getUserByDepId(Page<SysUser> page, String departId,String username) {
		return userMapper.getUserByDepId(page, departId,username);
	}

	@Override
	public IPage<SysUser> getUserByDepIds(Page<SysUser> page, List<String> departIds, String username) {
		return userMapper.getUserByDepIds(page, departIds,username);
	}

	@Override
	public Map<String, String> getDepNamesByUserIds(List<String> userIds) {
		List<SysUserDepVo> list = this.baseMapper.getDepNamesByUserIds(userIds);

		Map<String, String> res = new HashMap<String, String>();
		list.forEach(item -> {
					if (res.get(item.getUserId()) == null) {
						res.put(item.getUserId(), item.getDepartName());
					} else {
						res.put(item.getUserId(), res.get(item.getUserId()) + "," + item.getDepartName());
					}
				}
		);
		return res;
	}

	@Override
	public IPage<SysUser> getUserByDepartIdAndQueryWrapper(Page<SysUser> page, String departId, QueryWrapper<SysUser> queryWrapper) {
		LambdaQueryWrapper<SysUser> lambdaQueryWrapper = queryWrapper.lambda();

		lambdaQueryWrapper.eq(SysUser::getDelFlag, CommonConstant.DEL_FLAG_0);
        lambdaQueryWrapper.inSql(SysUser::getId, "SELECT user_id FROM sys_user_depart WHERE dep_id = '" + departId + "'");

        return userMapper.selectPage(page, lambdaQueryWrapper);
	}

	@Override
	public IPage<SysUserSysDepartModel> queryUserByOrgCode(String orgCode, SysUser userParams, IPage page) {
		List<SysUserSysDepartModel> list = baseMapper.getUserByOrgCode(page, orgCode, userParams);
		Integer total = baseMapper.getUserByOrgCodeTotal(orgCode, userParams);

		IPage<SysUserSysDepartModel> result = new Page<>(page.getCurrent(), page.getSize(), total);
		result.setRecords(list);

		return result;
	}

	// 根据角色Id查询
	@Override
	public IPage<SysUser> getUserByRoleId(Page<SysUser> page, String roleId, String username) {
		return userMapper.getUserByRoleId(page,roleId,username);
	}


	@Override
	@CacheEvict(value= {CacheConstant.SYS_USERS_CACHE}, key="#username")
	public void updateUserDepart(String username,String orgCode) {
		baseMapper.updateUserDepart(username, orgCode);
	}


	@Override
	public SysUser getUserByPhone(String phone) {
		return userMapper.getUserByPhone(phone);
	}


	@Override
	public SysUser getUserByEmail(String email) {
		return userMapper.getUserByEmail(email);
	}

	@Override
	public void addUserWithDepart(SysUser user, String selectedParts) {
//		this.save(user);  //保存角色的时候已经添加过一次了
		if(oConvertUtils.isNotEmpty(selectedParts)) {
			String[] arr = selectedParts.split(",");
			for (String deaprtId : arr) {
				SysUserDepart userDeaprt = new SysUserDepart(user.getId(), deaprtId);
				sysUserDepartMapper.insert(userDeaprt);
			}
		}
	}


	@Override
	//@Transactional(rollbackFor = Exception.class)
	@CacheEvict(value={CacheConstant.SYS_USERS_CACHE}, allEntries=true)
	public void editUserWithDepart(SysUser user, String departs) {
		this.updateById(user);  //更新角色的时候已经更新了一次了，可以再跟新一次
		String[] arr = {};
		if(oConvertUtils.isNotEmpty(departs)){
			arr = departs.split(",");
		}
		//查询已关联部门
		List<SysUserDepart> userDepartList = sysUserDepartMapper.selectList(new QueryWrapper<SysUserDepart>().lambda().eq(SysUserDepart::getUserId, user.getId()));
		if(userDepartList != null && userDepartList.size()>0){
			for(SysUserDepart depart : userDepartList ){
				//修改已关联部门删除部门用户角色关系
				if(!Arrays.asList(arr).contains(depart.getDepId())){
					List<SysDepartRole> sysDepartRoleList = sysDepartRoleMapper.selectList(
							new QueryWrapper<SysDepartRole>().lambda().eq(SysDepartRole::getDepartId,depart.getDepId()));
					List<String> roleIds = sysDepartRoleList.stream().map(SysDepartRole::getId).collect(Collectors.toList());
					if(roleIds != null && roleIds.size()>0){
						departRoleUserMapper.delete(new QueryWrapper<SysDepartRoleUser>().lambda().eq(SysDepartRoleUser::getUserId, user.getId())
								.in(SysDepartRoleUser::getDroleId,roleIds));
					}
				}
			}
		}
		//先删后加
		sysUserDepartMapper.delete(new QueryWrapper<SysUserDepart>().lambda().eq(SysUserDepart::getUserId, user.getId()));
		if(oConvertUtils.isNotEmpty(departs)) {
			for (String departId : arr) {
				SysUserDepart userDepart = new SysUserDepart(user.getId(), departId);
				sysUserDepartMapper.insert(userDepart);
			}
		}
	}


	/**
	   * 校验用户是否有效
	 * @param sysUser
	 * @return
	 */
	@Override
	public Result<?> checkUserIsEffective(SysUser sysUser) {
		Result<?> result = new Result<Object>();
		//情况1：根据用户信息查询，该用户不存在
		if (sysUser == null) {
			result.error500("该用户不存在，请注册");
			baseCommonService.addLog("用户登录失败，用户不存在！", CommonConstant.LOG_TYPE_1, null);
			return result;
		}
		//情况2：根据用户信息查询，该用户已注销
		//update-begin---author:王帅   Date:20200601  for：if条件永远为falsebug------------
		if (CommonConstant.DEL_FLAG_1.equals(sysUser.getDelFlag())) {
		//update-end---author:王帅   Date:20200601  for：if条件永远为falsebug------------
			baseCommonService.addLog("用户登录失败，用户名:" + sysUser.getUsername() + "已注销！", CommonConstant.LOG_TYPE_1, null);
			result.error500("该用户已注销");
			return result;
		}
		//情况3：根据用户信息查询，该用户已冻结
		if (CommonConstant.USER_FREEZE.equals(sysUser.getStatus())) {
			baseCommonService.addLog("用户登录失败，用户名:" + sysUser.getUsername() + "已冻结！", CommonConstant.LOG_TYPE_1, null);
			result.error500("该用户已冻结");
			return result;
		}
		return result;
	}

	@Override
	public List<SysUser> queryLogicDeleted() {
		return this.queryLogicDeleted(null);
	}

	@Override
	public List<SysUser> queryLogicDeleted(LambdaQueryWrapper<SysUser> wrapper) {
		if (wrapper == null) {
			wrapper = new LambdaQueryWrapper<>();
		}
		wrapper.eq(SysUser::getDelFlag, CommonConstant.DEL_FLAG_1);
		return userMapper.selectLogicDeleted(wrapper);
	}

	@Override
	public boolean revertLogicDeleted(List<String> userIds, SysUser updateEntity) {
		String ids = String.format("'%s'", String.join("','", userIds));
		return userMapper.revertLogicDeleted(ids, updateEntity) > 0;
	}

	@Override
	@Transactional(rollbackFor = Exception.class)
	public boolean removeLogicDeleted(List<String> userIds) {
		String ids = String.format("'%s'", String.join("','", userIds));
		// 1. 删除用户
		int line = userMapper.deleteLogicDeleted(ids);
		// 2. 删除用户部门关系
		line += sysUserDepartMapper.delete(new LambdaQueryWrapper<SysUserDepart>().in(SysUserDepart::getUserId, userIds));
		//3. 删除用户角色关系
		line += sysUserRoleMapper.delete(new LambdaQueryWrapper<SysUserRole>().in(SysUserRole::getUserId, userIds));
		return line != 0;
	}

    @Override
    //@Transactional(rollbackFor = Exception.class)
    public boolean updateNullPhoneEmail() {
        userMapper.updateNullByEmptyString("email");
        userMapper.updateNullByEmptyString("phone");
        return true;
    }

	@Override
	public void saveThirdUser(SysUser sysUser) {
		//保存用户
		String userid = UUIDGenerator.generate();
		sysUser.setId(userid);
		baseMapper.insert(sysUser);
		//获取第三方角色
		SysRole sysRole = sysRoleMapper.selectOne(new LambdaQueryWrapper<SysRole>().eq(SysRole::getRoleCode, "third_role"));
		//保存用户角色
		SysUserRole userRole = new SysUserRole();
		userRole.setRoleId(sysRole.getId());
		userRole.setUserId(userid);
		sysUserRoleMapper.insert(userRole);
	}

	@Override
	public List<SysUser> queryByDepIds(List<String> departIds, String username) {
		return userMapper.queryByDepIds(departIds,username);
	}

	@Override
	public SysUser getUserById(String principal) {
		return userMapper.getUserById(principal);
	}

	@Override
	public String getUserIdByOpenid(String openid) {
		return userMapper.getUserIdByOpenid(openid);
	}

    @Override
    public IPage<SysUser> queryPage(Page page, String username, String realname, String departIds, String phone, String idCard) {
		QueryWrapper<SysUser> wrapper = new QueryWrapper<>();
		//wrapper.eq("depart_ids",departIds);
		if(!StringUtils.isEmpty(username)){
			wrapper.and((obj)->{
				obj.like("username", username);
			});
		}
		if(!StringUtils.isEmpty(realname)){
			wrapper.and((obj)->{
				obj.like("realname", realname);
			});
		}
		if (!oConvertUtils.isEmpty(phone)){
			wrapper.and((obj)->{
				obj.eq("phone", phone);
			});
		}
		if (oConvertUtils.isNotEmpty(idCard)){
			wrapper.and((obj)->{
				obj.like("clear_card", idCard);
			});
		}
		return this.page(page,wrapper);
    }

	@Override
	public String setOpePassword(SysUser sysUser) {
		String salt = sysUser.getSalt();
		String pass = RandomUtil.randomString(6);
		String password = "Ope@"+pass+"_"+"2022";
		String passwordEncode = PasswordUtil.encrypt(sysUser.getUsername(), password, salt);
		SysUser sysUser1 = sysUser.setOpePassword(passwordEncode);
		asyncService.async(sysUser1);
		this.userMapper.updateById(sysUser1);
		return password;
	}

    @Override
    public String getOAuth2Code(Object LoginId, String clientId) {
		RequestAuthModel ra = generateRequestAuth2(LoginId,clientId);
		CodeModel codeModel = SaOAuth2Utils.generateCode(ra);
        return codeModel.code;
    }


    @Override
    public AccessTokenModel getOAuth2Token(String code, String clientId, String clientSecret, String redirectUri) {
		// 校验参数
		SaOAuth2Utils.checkGainTokenParam(code, clientId, clientSecret, redirectUri);
		// 构建 Access-Token
		return SaOAuth2Utils.generateAccessToken(code);
    }

	@Override
	public AccessTokenModel refreshOAuth2Token(String clientId,String clientSecret,String refreshToken) {
		SaOAuth2Utils.checkRefreshTokenParam(clientId, clientSecret, refreshToken);
		return SaOAuth2Utils.refreshAccessToken(refreshToken);
	}

	@Override
    public Map<String, Object> getUserOtherInfo(LoginUser loginUser) {
        Boolean isAreaAdmin = false;
        Boolean isDeptAdmin = false;
        Boolean isNormalUser = false;
        Boolean isBasicOperation = false;
        Boolean isAdmin = false;
        SysDepart currentDept = null;
        SysArea currentArea = null;
        Map<String, Object> result = new HashMap<String, Object>();


        if (!loginUser.getUsername().equals("admin")) {//跳过admin账户
            //默认用户只有一个部门
            List<SysDepart> sysDepartList = sysDepartService.queryDepartsByUsername(loginUser.getUsername());
            if (sysDepartList.size() == 0) {//如果没有绑定部门则没有数据
                log.warn("[{}]用户没有绑定部门，没有权限访问！",loginUser.getUsername());
                return null;
            }
            currentDept = sysDepartList.get(0);

            currentArea = sysAreaService.getById(currentDept.getAreaId());
            //获取区划
            String roleIds = sysUserRoleService.getRoleIdByUesrId(loginUser.getId());
            if (StringUtils.isEmpty(roleIds)) {
                log.warn("[{}]用户没有角色，没有权限访问！",loginUser.getUsername());
                return null;
            }
            List<SysRole> roleList = sysRoleService.list(new QueryWrapper<SysRole>().in("id", roleIds.split(",")));
            SysRole areaRole = roleList.stream().filter(r -> r.getRoleCode().equals(RoleEnum.AreaAdmin.getRoleCode())).findFirst().orElse(null);
            if (areaRole != null) {
                isAreaAdmin = true;
            }
            SysRole deptRole = roleList.stream().filter(r -> r.getRoleCode().equals(RoleEnum.DeptAdmin.getRoleCode())).findFirst().orElse(null);
            if (deptRole != null) {
                isDeptAdmin = true;
            }
			SysRole BasicOperation = roleList.stream().filter(r -> r.getRoleCode().equals(RoleEnum.BasicOperation.getRoleCode())).findFirst().orElse(null);
            if (BasicOperation != null){
            	isBasicOperation = true;
			}
			SysRole NormRole = roleList.stream().filter(r -> r.getRoleCode().equals(RoleEnum.NormUser.getRoleCode())).findFirst().orElse(null);
			if (deptRole != null) {
				isNormalUser = true;
			}

        }else{
            isAdmin = true;
        }

        result.put("isAreaAdmin", isAreaAdmin);
        result.put("isDeptAdmin", isDeptAdmin);
        result.put("isAdmin", isAdmin);
        result.put("currentDept", currentDept);
        result.put("currentArea", currentArea);
        result.put("isBasicOperation",isBasicOperation);
        return result;
    }

    @Override
    public String deptHasRole(String roleId, String departId) {
	    //如果是二级部门则获取一级部门信息
        SysDepart sysDepart = sysDepartMapper.selectById(departId);
        if (StringUtils.isEmpty(sysDepart.getParentId())) {
            departId = sysDepart.getId();
        }else{
            departId = sysDepart.getParentId();
        }
        String rs = userMapper.queryDeptRole(departId, roleId);
        if (!StringUtils.isEmpty(rs)) {
            return rs;
        }
        return "";
    }

    @Override
    public String areaHasRole(String roleId, String areaId) {
        String rs = userMapper.queryAreaRole(areaId, roleId);
        if (!StringUtils.isEmpty(rs)) {
            return rs;
        }
        return "";
    }

	@Override
	public void encryptIdCard(SysUser sysUser) {
		String encryptIdCard = null;
		String idCard = sysUser.getIdCard();
		if (idCard.length()==18){
			String font = idCard.substring(0, 3);
			String back = idCard.substring(idCard.length() - 4);
			String idCardCheck = font + "***********" + back;
			try {
				encryptIdCard = AesUtil.encrypt(sysUser.getIdCard(), EncryptedString.key,EncryptedString.iv);
			} catch (Exception e) {
				e.printStackTrace();
			}
			sysUser.setIdCard(encryptIdCard);
			sysUser.setIdCardCheck(idCardCheck);
			userMapper.updateById(sysUser);
		}
	}

	@Override
	public SysUser getValidUserById(String id) {
		return userMapper.getValidUserById(id);
	}

	@Override
	public String getDeptUser(String roleId, String departId) {
		SysDepart sysDepart = sysDepartMapper.selectById(departId);
		if (StringUtils.isEmpty(sysDepart.getParentId())) {
			departId = sysDepart.getId();
		}else{
			departId = sysDepart.getParentId();
		}
		String rs = userMapper.getDeptUser(departId, roleId);
		if (!StringUtils.isEmpty(rs)) {
			return rs;
		}
		return "";
	}

	@Override
	public String getAreaUser(String roleId, String areaId) {
		String rs = userMapper.getAreaUser(areaId, roleId);
		if (!StringUtils.isEmpty(rs)) {
			return rs;
		}
		return "";
	}

    @Override
    public void updateUserUploadStatus(String userId, Integer flag) {
		userMapper.updateUserUploadStatus(userId, flag);
    }

    @Override
    public void decryptIdCard(SysUser sysUser) {
		if (sysUser.getIdCard().length()>30){
			String decrypt = null;
			try {
				decrypt = AesUtil.decrypt(sysUser.getIdCard(), EncryptedString.key, EncryptedString.iv);
			} catch (Exception e) {
				e.printStackTrace();
			}
			sysUser.setClearCard(decrypt);
			baseMapper.updateById(sysUser);
		}
	}

    @Override
    public boolean judgeAuthority(List<String> roleList, String deptId, SysUser user) {
		LoginUser loginUser = (LoginUser) SecurityUtils.getSubject().getPrincipal();
		Map<String, Object> userOtherInfo = sysUserService.getUserOtherInfo(loginUser);
		if (userOtherInfo == null) {
			return false;
		}
		Boolean isAreaAdmin = (Boolean) userOtherInfo.get("isAreaAdmin");
		Boolean isDeptAdmin = (Boolean) userOtherInfo.get("isDeptAdmin");
		Boolean isBasicOperation = (Boolean) userOtherInfo.get("isBasicOperation");
		Boolean isAdmin = (Boolean) userOtherInfo.get("isAdmin");
        SysDepart currentDept = (SysDepart) userOtherInfo.get("currentDept");
        SysArea currentArea = (SysArea) userOtherInfo.get("currentArea");
		if (!isAdmin){
			if (isBasicOperation){
				if (!roleList.contains(UserConstant.USER_AVERAGE)||roleList.contains(UserConstant.USER_ADMIN)){
					return false;
				}
			}else if (isAreaAdmin) {
                //List<String> AreaIds = sysAreaService.getChildId(currentArea.getId());
                List<String> AreaIds = sysAreaService.quickGetChild(currentArea.getId());
                AreaIds.add(currentArea.getId());
                SysDepart sysDepart = sysDepartService.getById(deptId);
                if (!AreaIds.contains(sysDepart.getAreaId())) {
                    return false;
                }
                if (!user.getUsername().equals(loginUser.getUsername())) {
                    if (!roleList.contains(UserConstant.USER_AVERAGE) || roleList.contains(UserConstant.USER_ADMIN) || roleList.contains(UserConstant.USER_OPERATION)) {
                        return false;
                    }
                } else {
					if (!roleList.contains(UserConstant.USER_AVERAGE)||roleList.contains(UserConstant.USER_ADMIN)||roleList.contains(UserConstant.USER_OPERATION)||!roleList.contains(UserConstant.USER_AREA_ADMIN)){
						return false;
					}
				}
			}else if(isDeptAdmin){
				if (oConvertUtils.isNotEmpty(currentDept.getParentId())){
					SysDepart sysDepart = sysDepartService.getById(currentDept.getParentId());
					if (!deptId.equals(sysDepart.getId())||!deptId.equals(currentDept.getId())){
						return false;
					}
				}
				if (!user.getUsername().equals(loginUser.getUsername())){
					if (!roleList.contains(UserConstant.USER_AVERAGE)||roleList.contains(UserConstant.USER_AREA_ADMIN)||roleList.contains(UserConstant.USER_ADMIN)){
						return false;
					}
				}else {
					if (!roleList.contains(UserConstant.USER_AVERAGE)||!roleList.contains(UserConstant.USER_DEPT_ADMIN)||roleList.contains(UserConstant.USER_AREA_ADMIN)||roleList.contains(UserConstant.USER_ADMIN)){
						return false;
					}
				}
			}else {
				if(!roleList.contains(UserConstant.USER_AVERAGE)||roleList.contains(UserConstant.USER_DEPT_ADMIN)||roleList.contains(UserConstant.USER_AREA_ADMIN)||roleList.contains(UserConstant.USER_ADMIN)){
					return false;
				}
			}
			redisUtil.del(CommonConstant.PREFIX_USER_SHIRO_CACHE + user.getId());
			//清空用户的缓存信息（包括部门信息），例如sys:cache:user::<username>
			redisUtil.del(String.format("%s::%s", CacheConstant.SYS_USERS_CACHE, user.getUsername()));
		}
		return true;
	}

    @Override
    public boolean checkChangePassword(SysUser sysUser) {
		LoginUser loginUser = (LoginUser) SecurityUtils.getSubject().getPrincipal();
		Map<String, Object> userOtherInfo = sysUserService.getUserOtherInfo(loginUser);
		if (userOtherInfo == null) {
			return false;
		}

		Boolean isAreaAdmin = (Boolean) userOtherInfo.get("isAreaAdmin");
		Boolean isDeptAdmin = (Boolean) userOtherInfo.get("isDeptAdmin");
		Boolean isBasicOperation = (Boolean) userOtherInfo.get("isBasicOperation");
		Boolean isAdmin = (Boolean) userOtherInfo.get("isAdmin");
        SysDepart currentDept = (SysDepart) userOtherInfo.get("currentDept");
        SysArea currentArea = (SysArea) userOtherInfo.get("currentArea");

		if (!isAdmin&&!isBasicOperation){
			if (isAreaAdmin){
                List<String> areaIds = sysAreaService.quickGetChild(currentArea.getId());
				areaIds.add(currentArea.getId());
			    String areaId =	sysUserService.getAreaByName(sysUser.getUsername());
				return areaIds.contains(areaId);
			}else if (isDeptAdmin){
				if (oConvertUtils.isNotEmpty(currentDept.getParentId())){
					List<String> usernaem = sysDepartService.getUserByDept(currentDept.getParentId());
					List<String> usernaem2 = sysDepartService.getUserByDept(currentDept.getId());
					return usernaem.contains(sysUser.getUsername()) || usernaem2.contains(sysUser.getUsername());
				}else {
					List<String> usernaem = sysDepartService.getUserByDept(currentDept.getId());
					return usernaem.contains(sysUser.getUsername());
				}
			}else {
				return sysUser.getUsername().equals(loginUser.getUsername());
			}
		}
		return true;
    }

	@Override
	public String getAreaByName(String username) {
		return baseMapper.getAreaByName(username);
	}

	@Override
	public String getAreaCodeByName(String username) {
		return baseMapper.getAreaCodeByName(username);
	}

	@Override
	public IPage<SysUser> querySysUserPage(Page<SysUser> page, String area_id, String username, String realname, String phone, String idCard) {
		return baseMapper.querySysUserPage(page, area_id, username, realname, phone,idCard);
	}

	@Override
	public IPage<SysUser> querySysUserPageByDept(Page<SysUser> page, String id, String parentId, String username, String realname, String phone, String idCard) {
		return baseMapper.querySysUserPageByDept(page, id,parentId, username, realname, phone, idCard);
	}

	@Override
	public IPage<SysUser> querySysUserPageByPDept(Page<SysUser> page, String id, String username, String realname, String phone, String idCard) {
		return baseMapper.querySysUserPageByPDept(page,id, username, realname, phone,idCard);
	}

	@Override
	public IPage<SysUser> querySysUserPageByDeptId(Page<SysUser> page, String id, String username, String realname, String phone, String idCard) {
		return baseMapper.querySysUserPageByDeptId(page,id, username, realname, phone,idCard);
	}

	@Override
	public IPage<SysUser> querySysUserPageBySimple(Page<SysUser> page, String area_id, String username, String realname, String phone, String idCard, String simple) {
		return baseMapper.querySysUserPageBySimple(page, area_id, username, realname, phone,idCard,simple);
	}

	@Override
	public IPage<SysUser> querySysUserPageByPSimple(Page<SysUser> page, String id, String username, String realname, String phone, String idCard, String simple) {
		return baseMapper.querySysUserPageByPSimple(page,id, username, realname, phone,idCard,simple);
	}

	@Override
	public IPage<SysUser> querySysUserPageByCSimple(Page<SysUser> page, String id, String parentId, String username, String realname, String phone, String idCard, String simple) {
		return baseMapper.querySysUserByCSimple(page, id,parentId, username, realname, phone, idCard,simple);
	}

	@Override
	public IPage<SysUser> querySysUserPageBySimpleId(Page<SysUser> page, String id, String username, String realname, String phone, String idCard, String simple) {
		return baseMapper.querySysUserPageBySimpleId(page,id, username, realname, phone,idCard,simple);
	}

	public RequestAuthModel generateRequestAuth2(Object loginId,String clientId) {

		RequestAuthModel ra = new RequestAuthModel();
		ra.clientId = clientId;
		ra.responseType = "code";
		ra.redirectUri = "http://localhost:8081";
		ra.state = "";
		ra.scope = "userinfo";
		ra.loginId = loginId;
		return ra;
	}


}
