package org.nl.system.service.role.impl;

import cn.hutool.core.date.DateUtil;
import cn.hutool.core.util.IdUtil;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.core.util.StrUtil;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import org.apache.commons.lang3.StringUtils;
import org.nl.common.domain.query.PageQuery;
import org.nl.common.exception.BadRequestException;
import org.nl.common.utils.SecurityUtils;
import org.nl.system.service.menu.dao.mapper.SysMenuMapper;
import org.nl.system.service.role.ISysRoleService;
import org.nl.system.service.role.dao.SysRole;
import org.nl.system.service.role.dao.mapper.SysRoleMapper;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.CollectionUtils;

import java.util.*;

/**
 * <p>
 * 角色表 服务实现类
 * </p>
 *
 * @author generator
 * @since 2022-12-15
 */
@Service
public class SysRoleServiceImpl extends ServiceImpl<SysRoleMapper, SysRole> implements ISysRoleService {

    @Autowired
    private SysRoleMapper roleMapper;
    @Autowired
    private SysMenuMapper sysMenuMapper;

    @Override
    public IPage<SysRole> query(Map param, PageQuery page) {
        String blurry = null;
        if (ObjectUtil.isNotEmpty(param.get("blurry"))) blurry = param.get("blurry").toString();
        LambdaQueryWrapper<SysRole> lam = new LambdaQueryWrapper<>();
        lam.like(ObjectUtil.isNotEmpty(blurry), SysRole::getName, blurry);
        IPage<SysRole> pages = new Page<>(page.getPage() + 1, page.getSize());
        roleMapper.selectPage(pages, lam);
        // 需要吧menus返回去
        pages.getRecords().forEach(sysRole -> sysRole.setMenus(roleMapper.selectMenuIdsByRoles(sysRole.getRole_id())));
        return pages;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void create(JSONObject param) {
        //判断角色名字是否存在
        String name = param.getString("name");
        if (StrUtil.isEmpty(name)) throw new BadRequestException("角色名字不能为空!");
        SysRole sysRole = JSONObject.parseObject(JSONObject.toJSONString(param), SysRole.class);

        //判断角色名字是否存在
        SysRole role = roleMapper.selectOne(new LambdaQueryWrapper<SysRole>().eq(SysRole::getName, sysRole.getName()));
        if (ObjectUtil.isNotEmpty(role)) throw new BadRequestException("角色【" + name + "】已存在!");
        String userId = SecurityUtils.getCurrentUserId();
        String nickName = SecurityUtils.getCurrentNickName();
        String now = DateUtil.now();
        // 插入
        sysRole.setRole_id(IdUtil.getSnowflake(1, 1).nextIdStr());
        sysRole.setCreate_id(userId);
        sysRole.setCreate_name(nickName);
        sysRole.setCreate_time(now);
        sysRole.setUpdate_id(userId);
        sysRole.setUpdate_name(nickName);
        sysRole.setUpdate_time(now);
        roleMapper.insert(sysRole);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void update(JSONObject param) {
        SysRole sysRole = JSONObject.parseObject(JSONObject.toJSONString(param), SysRole.class);
        //判断角色名字是否存在
        String name = sysRole.getName();
        if (StrUtil.isEmpty(name)) throw new BadRequestException("角色名字不能为空!");

        //判断角色名字是否存在
        SysRole role = roleMapper.selectOne(new LambdaQueryWrapper<SysRole>().eq(SysRole::getName, sysRole.getName())
                .ne(SysRole::getRole_id, sysRole.getRole_id()));
        if (ObjectUtil.isNotEmpty(role)) throw new BadRequestException("角色【" + name + "】已存在!");
        String userId = SecurityUtils.getCurrentUserId();
        String nickName = SecurityUtils.getCurrentNickName();
        String now = DateUtil.now();
        sysRole.setUpdate_id(userId);
        sysRole.setUpdate_name(nickName);
        sysRole.setUpdate_time(now);
        roleMapper.updateById(sysRole);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void deleteBatchByIds(Set<String> ids) {
        // 删除角色表
        roleMapper.deleteBatchIds(ids);
        // 删除角色菜单绑定关系
        roleMapper.deleteRoleMenuBatchRoleIds(ids);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void updateMenu(JSONObject form) {
        String roleId = form.getString("role_id");
        JSONArray menus = form.getJSONArray("menus");
        Set<String> menuIds = new HashSet<>();
        for (int i = 0; i < menus.size(); i++) {
            JSONObject object = menus.getJSONObject(i);
            menuIds.add(object.getString("menuId"));
        }
        // 删除当前角色绑定的菜单
        roleMapper.deleteRoleMenuBatchRoleIds(Arrays.asList(roleId));
        // 插入数据
        roleMapper.insertRoleMenu(roleId, menuIds);
    }

    @Override
    public List<String> getPermissionList(JSONObject userDto) {
        List<String> permission = new LinkedList<>();
        // 查看是否为管理员
        permission.add("admin");
        permission.addAll(sysMenuMapper.getPermissionByUserId(userDto.getString("userId")));
        return permission;
    }

    @Override
    public void saveUserRoleRelation(String user, List<String> roles) {
        if (StringUtils.isEmpty(user) || CollectionUtils.isEmpty(roles)){
            return;
        }
        roleMapper.saveRoleRelation(user,roles);
    }

    @Override
    public void delUserRoleRelation(String user) {
        roleMapper.delRoleRelation(user);
    }
}
