package com.yd.api.metadata.service.impl;

import java.util.ArrayList;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import org.apache.commons.beanutils.BeanPropertyValueEqualsPredicate;
import org.apache.commons.collections.CollectionUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import com.github.pagehelper.PageHelper;
import com.yd.api.metadata.service.MetadataService;
import com.yd.api.metadata.vo.TagQueryBYIDRequestVO;
import com.yd.api.metadata.vo.TagQueryInfo;
import com.yd.api.metadata.vo.TagQueryRequestVO;
import com.yd.api.metadata.vo.TagQueryResponseVO;
import com.yd.api.metadata.vo.TagViewQueryInfo;
import com.yd.api.metadata.vo.TagViewQueryRequestVO;
import com.yd.api.metadata.vo.TagViewQueryResponseVO;
import com.yd.api.result.CommonResult;
import com.yd.dal.entity.meta.MdTagNew;
import com.yd.dal.entity.meta.MdTagView;
import com.yd.dal.entity.user.AclUser;
import com.yd.dal.service.meta.MdTagNewDALService;
import com.yd.dal.service.meta.MdTagViewDALService;
import com.yd.dal.service.metadata.MetadataDALService;
import com.yd.dal.service.user.AclUserDALService;
import com.yd.util.CommonUtil;
import com.yd.util.config.ZHBErrorConfig;

/**
 * @author xxy
 * @date 2021年06月21日 17:33
 */
@Service("metadataService")
public class MetadataServiceImpl implements MetadataService {

    @Autowired
    public MetadataDALService metadataDalService;

    @Autowired
    public MdTagNewDALService mdTagNewDalService;
    
    @Autowired
    public MdTagViewDALService mdTagViewDALService;
    
    @Autowired
    public AclUserDALService aclUserService;

    @Override
    @SuppressWarnings("unchecked")
    public TagQueryResponseVO tagQuery(TagQueryRequestVO requestVO) {
        TagQueryResponseVO responseVO = new TagQueryResponseVO();
        CommonResult commonResult = new CommonResult();
        tagQueryCheck(requestVO, commonResult);
        if (!commonResult.isSuccess()){
            responseVO.setCommonResult(commonResult);
            return responseVO;
        }

        Long isActive = null, configLevel = null, upperTagId = null,tagType = null;
        String tagName = null;
        if(requestVO.getIsActive() != null){
        	isActive = requestVO.getIsActive().longValue();
        }
        if(requestVO.getConfigLevel() != null){
        	configLevel = requestVO.getConfigLevel();
        }
        if(requestVO.getUpperTagId() != null){
        	upperTagId = requestVO.getUpperTagId();
        }
        if(requestVO.getTagType() != null){
        	tagType = requestVO.getTagType();
        }
        if(!CommonUtil.isNullOrBlank(requestVO.getTagName())){
        	if(requestVO.getConfigLevel() == null){
                commonResult.setSuccess(false);
                commonResult.setMessage(ZHBErrorConfig.getErrorInfo("830036"));
                responseVO.setCommonResult(commonResult);
                return responseVO;
        	}
        	tagName = requestVO.getTagName()+"%";
        }
        
        PageHelper.clearPage();//偶然遇到了这个问题，同一个查询结果一会是10个（预期），一会是真实个数（刷新/重启应用就又变成真实个数）  查看日志，发现了问题：结果为10个时查询SQL自动加上了Limit 10
        List<MdTagNew> mdTagNewList = mdTagNewDalService.selectByIsActive(isActive,configLevel,upperTagId,tagName,tagType);
        List<TagQueryInfo> tagQueryInfos = new ArrayList<>(16);
        if(configLevel == null){
        	if((requestVO.getUpperTagId() != null || !CommonUtil.isNullOrBlank(requestVO.getTagName()))){
            	if(mdTagNewList != null && mdTagNewList.size() >0 && mdTagNewList.get(0) != null)  
            		configLevel = ((MdTagNew)mdTagNewList.get(0)).getConfigLevel();
        	}else{
            	configLevel = 1L;
        	}
        }
        Map<Long,String> userMap = getUserMap();
        if(isActive == null || isActive == 1L || (configLevel != null || upperTagId != null || !CommonUtil.isNullOrBlank(requestVO.getTagName()))){
            List<MdTagNew> mdTagNewAddList = new ArrayList<>(16);
	        BeanPropertyValueEqualsPredicate predicateClause = new BeanPropertyValueEqualsPredicate( "configLevel", configLevel);
	        List<MdTagNew> objectListSelect= (List<MdTagNew>) CollectionUtils.select(mdTagNewList, predicateClause);
	        mdTagNewAddList.addAll(objectListSelect);
	        classificationBuildUpMdTag(mdTagNewList,mdTagNewAddList,objectListSelect,tagQueryInfos,userMap);
	        
	        mdTagNewList.removeAll(mdTagNewAddList);
//	        uncategorizedMdTag(mdTagNewList,tagQueryInfos);
        }else{
	        for (MdTagNew mdTagNew : mdTagNewList) {
	            TagQueryInfo tagQueryInfo = new TagQueryInfo();
	            BeanUtils.copyProperties(mdTagNew,tagQueryInfo);
	            tagQueryInfo.setCreatedAt(CommonUtil.dateParseString(mdTagNew.getCreatedAt(),"yyyy-MM-dd HH:mm:ss"));
	            tagQueryInfo.setCreatedBy(userMap.get(mdTagNew.getCreatedBy()));
                if(mdTagNew.getCreatedBy() != null){
                	tagQueryInfo.setUpdatedBy(userMap.get(mdTagNew.getCreatedBy()));
                	tagQueryInfo.setUpdatedAt(CommonUtil.dateParseString(mdTagNew.getUpdatedAt(),"yyyy-MM-dd HH:mm:ss"));
                }
	            tagQueryInfos.add(tagQueryInfo);
	        }
        }

        responseVO.setTagQueryInfos(tagQueryInfos);
        responseVO.setCommonResult(new CommonResult(true, ZHBErrorConfig.getErrorInfo("800000")));
        return responseVO;
    }
    
    private void tagQueryCheck(TagQueryRequestVO requestVO, CommonResult commonResult) {
//        if (requestVO.getIsActive() == null){
//            commonResult.setSuccess(false);
//            commonResult.setMessage(ZHBErrorConfig.getErrorInfo("830031"));
//            return;
//        }
        commonResult.setSuccess(true);
        commonResult.setMessage(ZHBErrorConfig.getErrorInfo("800000"));
    }

    @SuppressWarnings("unchecked")
    private void classificationBuildUpMdTag(List<MdTagNew> mdTagNewList,
                                            List<MdTagNew> mdTagNewAddList,
                                            List<MdTagNew> objectListSelect,
                                            List<TagQueryInfo> tagQueryInfos,Map<Long,String> userMap) {
        for (MdTagNew mdTagNew : objectListSelect) {
            Long id = mdTagNew.getId();
            TagQueryInfo tagQueryInfo = new TagQueryInfo();
            BeanUtils.copyProperties(mdTagNew,tagQueryInfo);
            tagQueryInfo.setCreatedAt(CommonUtil.dateParseString(mdTagNew.getCreatedAt(),"yyyy-MM-dd HH:mm:ss"));
            tagQueryInfo.setCreatedBy(userMap.get(mdTagNew.getCreatedBy()));
            if(mdTagNew.getCreatedBy() != null){
            	tagQueryInfo.setUpdatedBy(userMap.get(mdTagNew.getCreatedBy()));
            	tagQueryInfo.setUpdatedAt(CommonUtil.dateParseString(mdTagNew.getUpdatedAt(),"yyyy-MM-dd HH:mm:ss"));
            }
            BeanPropertyValueEqualsPredicate predicateClause = new BeanPropertyValueEqualsPredicate( "upperTagId", id);
            List<MdTagNew> mdTagNewListSelect= (List<MdTagNew>) CollectionUtils.select(mdTagNewList, predicateClause);
            if (mdTagNewListSelect.isEmpty()){
                tagQueryInfos.add(tagQueryInfo);
                continue;
            }
            mdTagNewAddList.addAll(mdTagNewListSelect);
            List<TagQueryInfo> tagQueryInfoList = new ArrayList<>(16);
            classificationBuildUpMdTag(mdTagNewList,mdTagNewAddList,mdTagNewListSelect,tagQueryInfoList,userMap);
            tagQueryInfoList.sort((o1, o2) -> o2.getId().compareTo(o1.getId()));
            tagQueryInfo.setTagQueryInfos(tagQueryInfoList);
            tagQueryInfos.add(tagQueryInfo);
        }
    }


//    private void uncategorizedMdTag(List<MdTagNew> mdTagNewList, List<TagQueryInfo> tagQueryInfos) {
//        TagQueryInfo tagQueryInfo = new TagQueryInfo();
//        tagQueryInfo.setTagName("未分类");
//        tagQueryInfo.setIsActive(1);
//        tagQueryInfo.setCreatedAt(CommonUtil.dateParseString(new Date(),"yyyy-MM-dd HH:mm:ss"));
//        tagQueryInfo.setCreatedBy(-1L);
//        tagQueryInfo.setUpdatedAt(CommonUtil.dateParseString(new Date(),"yyyy-MM-dd HH:mm:ss"));
//        tagQueryInfo.setUpdatedBy(-1L);
//        List<TagQueryInfo> tagQueryInfoList = new ArrayList<>(16);
//        mdTagNewList.forEach(m->{
//            TagQueryInfo tagInfo = new TagQueryInfo();
//            BeanUtils.copyProperties(m,tagInfo);
//            tagInfo.setCreatedAt(CommonUtil.dateParseString(m.getCreatedAt(),"yyyy-MM-dd HH:mm:ss"));
//            tagInfo.setUpdatedAt(CommonUtil.dateParseString(m.getUpdatedAt(),"yyyy-MM-dd HH:mm:ss"));
//            tagQueryInfoList.add(tagInfo);
//        });
//        tagQueryInfoList.sort((o1, o2) -> o2.getId().compareTo(o1.getId()));
//        tagQueryInfo.setTagQueryInfos(tagQueryInfoList);
//        tagQueryInfos.add(tagQueryInfo);
//    }
//    
    

    /**
     * 根据标签ID查询标签信息
     * @param requestVO
     * @return TagQueryBYIDRequestVO
     */
    @Override
    public TagQueryResponseVO tagQueryBYIDRequestVO(TagQueryBYIDRequestVO requestVO){
    	TagQueryResponseVO responseVO = new TagQueryResponseVO();
        CommonResult commonResult = new CommonResult();
    	if(CommonUtil.isNullOrZero(requestVO.getId())){
            String[] params = {"id"};
            commonResult.setSuccess(false);
            commonResult.setMessage(ZHBErrorConfig.getErrorInfo("610001", params));
            responseVO.setCommonResult(commonResult);
            return responseVO;
    	}
        PageHelper.clearPage();//偶然遇到了这个问题，同一个查询结果一会是10个（预期），一会是真实个数（刷新/重启应用就又变成真实个数）  查看日志，发现了问题：结果为10个时查询SQL自动加上了Limit 10
        List<TagQueryInfo> tagQueryInfos = new ArrayList<>(16);
        classificationBuildUpMdTagById(requestVO.getId(), tagQueryInfos);
        responseVO.setTagQueryInfos(tagQueryInfos);
        responseVO.setCommonResult(new CommonResult(true, ZHBErrorConfig.getErrorInfo("800000")));
        return responseVO;
    }
    
    /**
     * 通过标签ID，递归获取上级标签,值到上级标签为空
     * @param id 标签ID
     * @param tagQueryInfos
     */
    private void classificationBuildUpMdTagById(Long id, List<TagQueryInfo> tagQueryInfos) {
        MdTagNew mdTagNew = mdTagNewDalService.selectByPrimaryKey(id);
        if(mdTagNew != null){
        	 TagQueryInfo tagQueryInfo = new TagQueryInfo();
             BeanUtils.copyProperties(mdTagNew,tagQueryInfo);
             tagQueryInfo.setCreatedAt(CommonUtil.dateParseString(mdTagNew.getCreatedAt(),"yyyy-MM-dd HH:mm:ss"));
             tagQueryInfo.setUpdatedAt(CommonUtil.dateParseString(mdTagNew.getUpdatedAt(),"yyyy-MM-dd HH:mm:ss"));
             if(mdTagNew.getUpperTagId() != null && !"".equals(mdTagNew.getUpperTagId().toString())){
            	 List<TagQueryInfo> tagQueryInfoList = new ArrayList<>(16);
            	 classificationBuildUpMdTagById(mdTagNew.getUpperTagId(), tagQueryInfoList);
                 tagQueryInfo.setTagQueryInfos(tagQueryInfoList);
             }
             tagQueryInfos.add(tagQueryInfo);
        }
    }
    
    /**
     * 前端显示标签合集查询
     * @param TagViewQueryRequestVO requestVO
     * @return TagViewQueryResponseVO
     * @date 2021年06月21日 17:14
     */
    @Override
    @SuppressWarnings("unchecked")
    public TagViewQueryResponseVO tagViewQuery(TagViewQueryRequestVO requestVO) {
        TagViewQueryResponseVO responseVO = new TagViewQueryResponseVO();
        CommonResult commonResult = new CommonResult();
        tagViewQueryCheck(requestVO, commonResult);
        if (!commonResult.isSuccess()){
            responseVO.setCommonResult(commonResult);
            return responseVO;
        }
        
        Long isActive = null,upperTagViewId = null;
        String taglevel = null,tagName = null,tagViewType = null;
        if(requestVO.getIsActive() != null){
        	isActive = requestVO.getIsActive().longValue();
        }
        if(requestVO.getTagLevel() != null){
        	taglevel = requestVO.getTagLevel();
        }
        if(requestVO.getUpperTagViewId() != null){
        	upperTagViewId = requestVO.getUpperTagViewId();
        }
        if(requestVO.getTagViewType() != null){
        	tagViewType = requestVO.getTagViewType();
        }
        if(!CommonUtil.isNullOrBlank(requestVO.getTagName())){
        	if(requestVO.getTagLevel() == null){
                commonResult.setSuccess(false);
                commonResult.setMessage(ZHBErrorConfig.getErrorInfo("830036"));
                responseVO.setCommonResult(commonResult);
                return responseVO;
        	}
        	tagName = requestVO.getTagName()+"%";
        }

        PageHelper.clearPage();//偶然遇到了这个问题，同一个查询结果一会是10个（预期），一会是真实个数（刷新/重启应用就又变成真实个数）  查看日志，发现了问题：结果为10个时查询SQL自动加上了Limit 10
        List<MdTagView> mdTagViewList = mdTagViewDALService.selectByIsActive(isActive,upperTagViewId,taglevel,tagViewType,tagName);
        if(taglevel == null){
        	if((requestVO.getUpperTagViewId() != null || !CommonUtil.isNullOrBlank(requestVO.getTagName()))){
            	if(mdTagViewList != null && mdTagViewList.size() >0 && mdTagViewList.get(0) != null)  
            		taglevel = ((MdTagView)mdTagViewList.get(0)).getTagLevel();
        	}else{
        		taglevel = "1";
        	}
        }

        Map<Long,String> userMap = getUserMap();
        List<TagViewQueryInfo> tagViewQueryInfos = new ArrayList<>(16);
        if(isActive == null || isActive == 1L || (taglevel != null || upperTagViewId != null || !CommonUtil.isNullOrBlank(requestVO.getTagName()))){
            List<MdTagView> mdTagViewAddList = new ArrayList<>(16);
            BeanPropertyValueEqualsPredicate predicateClause = new BeanPropertyValueEqualsPredicate("tagLevel", taglevel);
            List<MdTagView> objectListSelect = (List<MdTagView>) CollectionUtils.select(mdTagViewList, predicateClause);
            
            mdTagViewAddList.addAll(objectListSelect);
            classificationBuildUpMdTagView(mdTagViewList,mdTagViewAddList,objectListSelect,tagViewQueryInfos,userMap);

            mdTagViewList.removeAll(mdTagViewAddList);
        }else{
	        for (MdTagView mdTagView : mdTagViewList) {
	            TagViewQueryInfo tagViewQueryInfo = new TagViewQueryInfo();
	            BeanUtils.copyProperties(mdTagView,tagViewQueryInfo);
	            tagViewQueryInfo.setCreatedAt(CommonUtil.dateParseString(mdTagView.getCreatedAt(),"yyyy-MM-dd HH:mm:ss"));
	            tagViewQueryInfo.setCreatedBy(userMap.get(mdTagView.getCreatedBy()));
                if(mdTagView.getCreatedBy() != null){
                	tagViewQueryInfo.setUpdatedBy(userMap.get(mdTagView.getCreatedBy()));
    	            tagViewQueryInfo.setUpdatedAt(CommonUtil.dateParseString(mdTagView.getUpdatedAt(),"yyyy-MM-dd HH:mm:ss"));
                }
	            tagViewQueryInfos.add(tagViewQueryInfo);
	        }
        }

        responseVO.setTagViewQueryInfos(tagViewQueryInfos);
        responseVO.setCommonResult(new CommonResult(true, ZHBErrorConfig.getErrorInfo("800000")));
        return responseVO;
    }
    
    @SuppressWarnings("unchecked")
    private void classificationBuildUpMdTagView(List<MdTagView> mdTagViewList,
                                            List<MdTagView> mdTagViewAddList,
                                            List<MdTagView> objectListSelect,
                                            List<TagViewQueryInfo> tagViewQueryInfos,Map<Long,String> userMap) {
        for (MdTagView mdTagView : objectListSelect) {
            Long id = mdTagView.getId();
            TagViewQueryInfo tagViewQueryInfo = new TagViewQueryInfo();
            BeanUtils.copyProperties(mdTagView,tagViewQueryInfo);
            tagViewQueryInfo.setCreatedAt(CommonUtil.dateParseString(mdTagView.getCreatedAt(),"yyyy-MM-dd HH:mm:ss"));
            tagViewQueryInfo.setCreatedBy(userMap.get(mdTagView.getCreatedBy()));
            if(mdTagView.getCreatedBy() != null){
            	tagViewQueryInfo.setUpdatedBy(userMap.get(mdTagView.getCreatedBy()));
	            tagViewQueryInfo.setUpdatedAt(CommonUtil.dateParseString(mdTagView.getUpdatedAt(),"yyyy-MM-dd HH:mm:ss"));
            }
            BeanPropertyValueEqualsPredicate predicateClause = new BeanPropertyValueEqualsPredicate( "upperTagViewId", id);
            List<MdTagView> mdTagNewListSelect = (List<MdTagView>) CollectionUtils.select(mdTagViewList, predicateClause);
            if (mdTagNewListSelect.isEmpty()){
            	tagViewQueryInfos.add(tagViewQueryInfo);
                continue;
            }
            mdTagViewAddList.addAll(mdTagNewListSelect);
            List<TagViewQueryInfo> tagViewQueryInfoList = new ArrayList<>(16);
            classificationBuildUpMdTagView(mdTagViewList,mdTagViewAddList,mdTagNewListSelect,tagViewQueryInfoList,userMap);
            tagViewQueryInfoList.sort((o1, o2) -> o2.getId().compareTo(o1.getId()));
            tagViewQueryInfo.setTagViewQueryInfos(tagViewQueryInfoList);
            tagViewQueryInfos.add(tagViewQueryInfo);
        }
    }
    

    private void tagViewQueryCheck(TagViewQueryRequestVO requestVO, CommonResult commonResult) {
//        if (CommonUtil.isNullOrZero(requestVO.getIsActive())){
//            commonResult.setSuccess(false);
//            commonResult.setMessage(ZHBErrorConfig.getErrorInfo("830031"));
//            return;
//        }
        commonResult.setSuccess(true);
        commonResult.setMessage(ZHBErrorConfig.getErrorInfo("800000"));
    }
    
    /**
     * 获取所有的用户信息
     * @return 返回所有的用户信息
     */
    private Map<Long, String> getUserMap() {
        Map<Long,String> userMap = new HashMap<>();
        List<AclUser> users = aclUserService.findAll();
        for(AclUser item : users){
            userMap.put(item.getId(),item.getLogin());
        }
        return userMap;
    }
    
}
