package com.mortals.xhx.module.one.service.impl;

import com.mortals.framework.exception.AppException;
import com.mortals.framework.model.Context;
import com.mortals.framework.model.OrderCol;
import com.mortals.framework.model.PageInfo;
import com.mortals.framework.model.Result;
import com.mortals.xhx.busiz.onethinglist.OneThingReq;
import com.mortals.xhx.common.code.TreeTypeEnum;
import com.mortals.xhx.common.code.YesNoEnum;
import com.mortals.xhx.module.one.model.*;
import com.mortals.xhx.module.one.service.OneClassifyService;
import com.mortals.xhx.module.one.service.OneClassifyTopicalService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import com.mortals.framework.service.impl.AbstractCRUDServiceImpl;
import com.mortals.xhx.module.one.dao.OneTopicalDao;
import com.mortals.xhx.module.one.service.OneTopicalService;
import org.springframework.util.ObjectUtils;

import java.util.*;
import java.util.stream.Collectors;

/**
 * <p>Title: 主题表</p>
 * <p>Description: OneTopicalService service接口 </p>
 * <p>Copyright: Copyright &reg;  </p>
 *
 * @version 1.0.0
 */
@Service("oneTopicalService")
public class OneTopicalServiceImpl extends AbstractCRUDServiceImpl<OneTopicalDao, OneTopicalEntity, Long> implements OneTopicalService {

    @Autowired
    private OneClassifyTopicalService oneClassifyTopicalService;
    @Autowired
    private OneClassifyService oneClassifyService;

    @Override
    public List<Map<String, Object>> getTreeList(Integer type) {


        OneClassifyTopicalQuery oneClassifyTopicalQuery = new OneClassifyTopicalQuery().deleted(YesNoEnum.NO.getValue());
        oneClassifyTopicalQuery.setOrderColList(Arrays.asList(new OrderCol("classifyRank", OrderCol.ASCENDING)));

        List<OneClassifyTopicalEntity> classifyTopicalEntityList = oneClassifyTopicalService.find(oneClassifyTopicalQuery);

        OneTopicalQuery oneTopicalQuery = new OneTopicalQuery().deleted(YesNoEnum.NO.getValue()).topicalType(type);
        oneTopicalQuery.setOrderColList(Arrays.asList(new OrderCol("topicalRank", OrderCol.ASCENDING)));

        List<Map<String, Object>> collect = this.find(oneTopicalQuery).stream().map(item -> {
            Map<String, Object> data = new HashMap<>();

            data.put("name", item.getTopicalName());
            data.put("id", item.getId());
            data.put("type", TreeTypeEnum.TOPIC.getValue());
            data.put("icon", TreeTypeEnum.TOPIC.getDesc());
            data.put("isLeaf", true);

            List<Map<String, Object>> children = classifyTopicalEntityList
                    .stream().filter(f -> f.getTopicalId() == item.getId()).map(classifyTopic -> {
                        OneClassifyEntity oneClassifyEntity = oneClassifyService.getCache(classifyTopic.getClassifyId().toString());
                        Map<String, Object> map = new HashMap<>();
                        map.put("id", classifyTopic.getId());
                        map.put("name", oneClassifyEntity == null ? "" : oneClassifyEntity.getClassifyName());
                        map.put("isLeaf", true);
                        map.put("type", TreeTypeEnum.CLASSIFY.getValue());
                        map.put("classifyId", classifyTopic.getClassifyId());
                        map.put("icon", TreeTypeEnum.CLASSIFY.getDesc());
                        return map;
                    }).collect(Collectors.toList());

            if (children.size() > 0) {
                data.put("isLeaf", false);
                data.put("children", children);
            }
            return data;

        }).collect(Collectors.toList());

        return collect;
    }

    @Override
    public Result<OneClassifyEntity> getList(OneThingReq req) {
        //分页查询
        PageInfo pageInfo = new PageInfo();
        pageInfo.setPrePageResult(req.getLimit());
        pageInfo.setCurrPage(req.getPage());

        return oneClassifyService.find(new OneClassifyQuery().classifyLevel(1L).classifyName("%"+req.getName()+"%").deleted(YesNoEnum.NO.getValue()), pageInfo, null);

    }

    @Override
    public void upOrDownTopicList(Long id, Integer type) {
        OneTopicalQuery query = new OneTopicalQuery().deleted(YesNoEnum.NO.getValue());
        query.setOrderColList(Arrays.asList(new OrderCol("topical_rank")));
        query.setOrderKind(OrderCol.ASCENDING);
        List<OneTopicalEntity> list = this.find(query);
        OneTopicalEntity preEntity = null;
        OneTopicalEntity curEntity = null;
        if (type == YesNoEnum.NO.getValue()) {
            //up
            for (int i = 0; i < list.size(); i++) {
                if (list.get(i).getId() == id && i > 0) {
                    curEntity = list.get(i);
                    preEntity = list.get(i - 1);
                    break;
                }
            }

        } else {
            //down
            for (int i = 0; i < list.size(); i++) {
                if (list.get(i).getId() == id && i + 1 < list.size()) {
                    curEntity = list.get(i);
                    preEntity = list.get(i + 1);
                    break;
                }
            }
        }

        if (preEntity != null && curEntity != null) {
            //交换
            int temp = preEntity.getTopicalRank();
            preEntity.setTopicalRank(curEntity.getTopicalRank());
            curEntity.setTopicalRank(temp);

            this.update(preEntity);
            this.update(curEntity);
        }

    }

    @Override
    protected void saveBefore(OneTopicalEntity entity, Context context) throws AppException {
        //计算排序号，取最大值加1
        int max = this.find(new OneTopicalQuery()).stream().mapToInt(OneTopicalEntity::getTopicalRank).max().orElseGet(() -> 0);
        entity.setTopicalRank(max + 1);
    }

    @Override
    protected void logicDeleteAfter(OneTopicalEntity entity, Context context) throws AppException {
        //级联删除所有

        oneClassifyTopicalService.find(new OneClassifyTopicalQuery().topicalId(entity.getId()).deleted(YesNoEnum.NO.getValue()))
                .stream().peek(item -> oneClassifyTopicalService.logicDelete(item, context)).count();


    }
}