package ink.wgink.mongo.module.dictionary.service.impl;

import ink.wgink.common.base.DefaultBaseService;
import ink.wgink.module.dictionary.pojo.dtos.DataDTO;
import ink.wgink.module.dictionary.service.IDataService;
import ink.wgink.mongo.module.dictionary.enums.MongoDictionaryCollectionEnum;
import ink.wgink.mongo.module.dictionary.service.IMongoDataService;
import ink.wgink.pojo.ListPage;
import ink.wgink.pojo.dtos.ZTreeDTO;
import ink.wgink.pojo.result.SuccessResultList;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Pageable;
import org.springframework.data.mongodb.core.MongoTemplate;
import org.springframework.data.mongodb.core.query.Criteria;
import org.springframework.data.mongodb.core.query.Query;
import org.springframework.stereotype.Service;

import java.util.ArrayList;
import java.util.List;
import java.util.regex.Pattern;

/**
 * @ClassName: DictionaryServiceImpl
 * @Description: 字典
 * @Author: WangGeng
 * @Date: 2019/11/18 14:09
 * @Version: 1.0
 **/
@Service
public class MongoDataServiceImpl extends DefaultBaseService implements IMongoDataService {

    @Autowired
    private IDataService dataService;
    @Autowired
    private MongoTemplate mongoTemplate;

    @Override
    public void updateMongo() {
        List<DataDTO> dataDTOs = dataService.list();
        mongoTemplate.remove(new Query(), MongoDictionaryCollectionEnum.DATA.getValue());
        mongoTemplate.insert(dataDTOs, MongoDictionaryCollectionEnum.DATA.getValue());
    }

    @Override
    public DataDTO get(String dataId) {
        return mongoTemplate.findOne(Query.query(Criteria.where("dataId").is(dataId)), DataDTO.class, MongoDictionaryCollectionEnum.DATA.getValue());
    }

    @Override
    public List<DataDTO> listByParentId(String dataParentId) {
        return mongoTemplate.find(Query.query(Criteria.where("dataParentId").is(dataParentId)), DataDTO.class, MongoDictionaryCollectionEnum.DATA.getValue());
    }

    @Override
    public List<DataDTO> listAllByParentId(String dataParentId) {
        List<DataDTO> dataDTOs = listByParentId(dataParentId);
        listSub(dataDTOs);
        return dataDTOs;
    }

    @Override
    public SuccessResultList<List<DataDTO>> listPage(ListPage page) {
        Query query = new Query(Criteria.where("dataParentId").is(page.getParams().get("dataParentId").toString()));
        String keywords = getKeywords(page.getParams());
        if (!StringUtils.isBlank(keywords)) {
            Pattern pattern = Pattern.compile("^.*" + keywords + ".*$", Pattern.CASE_INSENSITIVE);
            query.addCriteria(Criteria.where("dataName").regex(pattern));
        }
        long total = mongoTemplate.count(query, MongoDictionaryCollectionEnum.DATA.getValue());
        query.with(Pageable.ofSize(page.getRows()).withPage(page.getPage() - 1));
        List<DataDTO> dataDTOs = mongoTemplate.find(query, DataDTO.class, MongoDictionaryCollectionEnum.DATA.getValue());
        return new SuccessResultList<>(dataDTOs, page.getPage(), total);
    }

    @Override
    public List<ZTreeDTO> listZTree(String dataParentId) {
        List<DataDTO> dataDTOs = listByParentId(dataParentId);
        List<ZTreeDTO> zTreeDTOs = new ArrayList<>();
        for (DataDTO dataDTO : dataDTOs) {
            ZTreeDTO zTreeDTO = new ZTreeDTO();
            zTreeDTO.setId(dataDTO.getDataId());
            zTreeDTO.setpId(dataDTO.getDataParentId());
            zTreeDTO.setName(dataDTO.getDataName());
            long subCount = mongoTemplate.count(Query.query(Criteria.where("dataParentId").is(dataDTO.getDataId())), MongoDictionaryCollectionEnum.DATA.getValue());
            setZTreeInfo(zTreeDTO, subCount);
            zTreeDTOs.add(zTreeDTO);
        }
        return zTreeDTOs;
    }

    @Override
    public List<DataDTO> listByCode(String dataCode) {
        Pattern pattern = Pattern.compile("^" + dataCode + ".*$", Pattern.CASE_INSENSITIVE);
        return mongoTemplate.find(Query.query(Criteria.where("dataCode").regex(pattern)), DataDTO.class, MongoDictionaryCollectionEnum.DATA.getValue());
    }

    /**
     * 递归查询子组
     *
     * @param dataDTOs
     */
    private void listSub(List<DataDTO> dataDTOs) {
        for (DataDTO dataDTO : dataDTOs) {
            List<DataDTO> subDataDTOs = listByParentId(dataDTO.getDataId());
            dataDTO.setSubData(subDataDTOs);
            listSub(subDataDTOs);
        }
    }

}