package com.iformall.service.impl;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONArray;
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;

import com.iformall.common.IdWorker;
import com.iformall.domain.po.WxLogicPermission;
import com.iformall.domain.po.base.BaseEntity;
import com.iformall.domain.po.MallPermission;
import com.iformall.domain.po.MallUserInfo;
import com.iformall.enums.EnumMenuType;
import com.iformall.enums.EnumPermissionType;
import com.iformall.enums.EnumUserAdmin;
import com.iformall.mapper.MallPermissionMapper;
import com.iformall.mapper.MallUserInfoMapper;
import com.iformall.mapper.WxLogicPermissionMapper;
import com.iformall.mapper.WxMallMapper;
import com.iformall.service.MallPermissionService;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.*;

@Service
public class MallPermissionServiceImpl implements MallPermissionService {
    private final Logger logger = LoggerFactory.getLogger(this.getClass());
	
	@Autowired
    private MallPermissionMapper mallPermissionMapper;

	@Autowired
    private MallUserInfoMapper mallUserInfoMapper;

	@Autowired
    private WxMallMapper wxMallMapper;
    @Autowired
    private WxLogicPermissionMapper logicPermissionDao;

    @Override
    public List<MallPermission> queryListParentId(Long parentId, List<Long> menuIdList, boolean boolNav) {
        List<MallPermission> menuList = queryListParentId(parentId);
        if(menuIdList == null){
            return menuList;
        }

        List<MallPermission> userMenuList = new ArrayList<>();
        for(MallPermission menu : menuList){
            if(boolNav) {
                if(menu.getId().longValue() == (long)EnumMenuType.MOBILE_ADMIN.getCode()) {
                    continue;
                }
            }

            if (Objects.equals(menu.getResourceType(), EnumPermissionType.BUTTON.getCode())) {
                continue;
            }
            if(menuIdList.contains(menu.getId())){
                userMenuList.add(menu);
            }
        }
        return userMenuList;
    }

    @Override
    public List<MallPermission> queryListParentId(Long parentId) {
        return mallPermissionMapper.queryListParentId(parentId);
    }

    @Override
    public List<Long> queryAdminMenuList(MallUserInfo userInfo) {
        if(userInfo.isFmSuperAdmin() ||
                userInfo.getIsAdmin().equals(EnumUserAdmin.ADMIN.getCode())) {
            String menus = wxMallMapper.queryMenusByTenantId(userInfo.getTenantId());
            JSONArray menuIdList = JSON.parseArray(menus);
            return menuIdList.toJavaList(Long.class);
        } else {
            List<Long> menuIdList = mallUserInfoMapper.queryAllMenuId(userInfo.getId());
            return menuIdList;
        }
    }

    @Override
    public List<Long> queryUserMenuIds(MallUserInfo userInfo, Long parentId, boolean boolNav) {
        List<Long> mpList = new ArrayList<Long>();
        if(userInfo.isFmSuperAdmin() ||
                userInfo.getIsAdmin().equals(EnumUserAdmin.ADMIN.getCode())) {
            List<MallPermission> mps = getAllMenuListByParentId(parentId, null, boolNav);
            mps.stream().forEach(mp->{
                mpList.add(mp.getId());
            });
            return mpList;
        } else {
            List<Long> menuIdList = mallUserInfoMapper.queryAllMenuId(userInfo.getId());
            List<MallPermission> mps = getAllMenuListByParentId(parentId, menuIdList, boolNav);
            mps.stream().forEach(mp->{
                mpList.add(mp.getId());
            });
            return mpList;
        }
    }

    @Override
    public List<MallPermission> getUserMenuList(MallUserInfo userInfo, Long parentId, boolean boolNav) {
        if(userInfo.isFmSuperAdmin()) {
            // 富茂系统管理员，返回所有菜单
            return getAllMenuListByParentId(parentId, null, boolNav);
        }
        else if(userInfo.getIsAdmin().equals(EnumUserAdmin.ADMIN.getCode())) {
            // 租户超管
            String menus = wxMallMapper.queryMenusByTenantId(userInfo.getTenantId());
            JSONArray menuIdList = JSON.parseArray(menus);
            return getAllMenuListByParentId(0L, menuIdList.toJavaList(Long.class), boolNav);
        } else {
            //用户菜单列表
            List<Long> menuIdList = mallUserInfoMapper.queryAllMenuId(userInfo.getId());
            return getAllMenuListByParentId(0L, menuIdList, boolNav);
        }
    }

    /**
     * 获取所有菜单列表
     */
    private List<MallPermission> getAllMenuListByParentId(Long parentId, List<Long> menuIdList, boolean boolNav){
        //查询根菜单列表
        List<MallPermission> menuList = queryListParentId(parentId, menuIdList, boolNav);
        //递归获取子菜单
        getMenuTreeList(menuList, menuIdList, boolNav);

        return menuList;
    }

    /**
     * 递归
     */
    private List<MallPermission> getMenuTreeList(List<MallPermission> menuList, List<Long> menuIdList, boolean boolNav){
        List<MallPermission> subMenuList = new ArrayList<MallPermission>();

        for(MallPermission entity : menuList){
            //目录
            if(entity.getResourceType().equals(EnumPermissionType.CATALOG.getCode())){
                List<MallPermission> subPermisson = getMenuTreeList(queryListParentId(entity.getId(), menuIdList, boolNav), menuIdList, boolNav);
                List<MallPermission> logicPermisson = getLogicPermisson(entity);
                subPermisson.addAll(logicPermisson);
                entity.setChildren(subPermisson);
            }
            subMenuList.add(entity);
        }

        return subMenuList;
    }

    private List<MallPermission> getLogicPermisson(MallPermission entity) {
        List<MallPermission> mallPermissionList = new ArrayList<>();
        if (entity.getParentId() != 0) {
            return mallPermissionList;
        }
        WxLogicPermission query = new WxLogicPermission();
        query.setParentId(entity.getId());
        List<WxLogicPermission> logicPermissionList = logicPermissionDao.findList(query);
        for (WxLogicPermission logicPermission : logicPermissionList) {
            MallPermission permission = new MallPermission();
            permission.setName(logicPermission.getName());
            List<MallPermission> mallPermissions = mallPermissionMapper.selectBatchIds(JSONArray.parseArray(logicPermission.getPermission(), Long.class));
            permission.setChildren(mallPermissions);
            mallPermissionList.add(permission);
        }
        return mallPermissionList;
    }

    @Override
    public PageInfo<MallPermission> listAsPage(MallPermission record, Integer pageIndex, Integer pageSize) {
        return PageHelper.startPage(pageIndex, pageSize).doSelectPageInfo(() -> mallPermissionMapper.findList(record));
    }

    @Override
    public List<MallPermission> getList(MallPermission record) {
        return mallPermissionMapper.findList(record);
    }

    @Override
    public MallPermission getById(Long id) {
        return mallPermissionMapper.selectById(id);
    }

    @Override
    public List<MallPermission> getByParentId(Long parentId) {
        if(parentId == null) {
            parentId = 0L;
        }
        MallPermission mpQ = new MallPermission();
        mpQ.setParentId(parentId);
        mpQ.setSortColumns(BaseEntity.SortField.Sort_ASC);
        return mallPermissionMapper.findList(mpQ);
    }

    @Override
    public void saveOrUpdate(MallPermission record) {
        if (record.getId() == null) {
            final IdWorker idWorker = IdWorker.get();
            record.setId(idWorker.nextId());
            mallPermissionMapper.insert(record);
        } else {
            mallPermissionMapper.updateById(record);
        }
    }

    @Override
    public void deleteById(Long id) {
        mallPermissionMapper.deleteById(id);
    }
    
}
