package com.yeejoin.amos.boot.module.statistcs.biz.service.impl;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.yeejoin.amos.boot.biz.common.annotation.TechnicalParameter;
import com.yeejoin.amos.boot.biz.common.entity.BaseEntity;
import com.yeejoin.amos.boot.biz.common.entity.DataDictionary;
import com.yeejoin.amos.boot.biz.common.excel.ExcelUtil;
import com.yeejoin.amos.boot.biz.common.service.impl.DataDictionaryServiceImpl;
import com.yeejoin.amos.boot.biz.common.utils.DateUtils;
import com.yeejoin.amos.boot.module.common.api.dto.TechParamItem;
import com.yeejoin.amos.boot.module.common.biz.utils.TechParamUtil;
import com.yeejoin.amos.boot.module.jg.api.enums.DPMapStatisticsItemEnum;
import com.yeejoin.amos.boot.module.statistcs.biz.utils.JsonUtils;
import com.yeejoin.amos.boot.module.statistcs.biz.utils.MinioUtils;
import com.yeejoin.amos.boot.module.statistcs.factory.DynamicQueryBuilder;
import com.yeejoin.amos.boot.module.statistcs.factory.EnhancedDynamicQueryBuilder;
import com.yeejoin.amos.boot.module.statistics.api.enums.*;
import com.yeejoin.amos.boot.module.statistics.api.mapper.TzsCustomFilterMapper;
import com.yeejoin.amos.boot.module.statistics.api.vo.EquipInfoVo;
import com.yeejoin.amos.boot.module.ymt.api.dto.EquipmentCategoryDto;
import com.yeejoin.amos.boot.module.ymt.api.enums.EquipmentClassifityEnum;
import com.yeejoin.amos.boot.module.ymt.api.mapper.EquipmentCategoryMapper;
import com.yeejoin.amos.feign.systemctl.Systemctl;
import com.yeejoin.amos.feign.systemctl.model.DictionarieValueModel;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.apache.lucene.queryparser.classic.QueryParser;
import org.apache.lucene.search.join.ScoreMode;
import org.elasticsearch.action.search.SearchRequest;
import org.elasticsearch.action.search.SearchResponse;
import org.elasticsearch.client.RequestOptions;
import org.elasticsearch.client.RestHighLevelClient;
import org.elasticsearch.index.query.*;
import org.elasticsearch.search.SearchHit;
import org.elasticsearch.search.builder.SearchSourceBuilder;
import org.elasticsearch.search.sort.FieldSortBuilder;
import org.elasticsearch.search.sort.SortBuilders;
import org.elasticsearch.search.sort.SortOrder;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.core.io.Resource;
import org.springframework.stereotype.Service;
import org.springframework.util.ObjectUtils;
import org.springframework.web.multipart.MultipartFile;
import org.typroject.tyboot.component.emq.EmqKeeper;
import org.typroject.tyboot.core.foundation.context.RequestContext;
import org.typroject.tyboot.core.foundation.utils.ValidationUtil;
import org.typroject.tyboot.core.restful.exception.instance.BadRequest;

import java.io.IOException;
import java.nio.charset.StandardCharsets;
import java.time.LocalDate;
import java.time.format.DateTimeFormatter;
import java.util.*;

import static org.elasticsearch.index.query.QueryBuilders.existsQuery;

/**
 * 综合统计分析服务实现类
 *
 * @author system_generator
 * @date 2025-06-24
 */
@Service
@Slf4j
@RequiredArgsConstructor
public class ComprehensiveStatisticalAnalysisServiceImpl {

    final static String EQU_LIST = "EQU_LIST";

    @Value("classpath:/json/equipCategory.json")
    private Resource equipCategory;
    private final TzsCustomFilterMapper tzsCustomFilterMapper;
    private final DataDictionaryServiceImpl dataDictionaryService;
    private final EmqKeeper emqKeeper;

    private final StCommonServiceImpl stCommonService;

    private final RestHighLevelClient restHighLevelClient;
    private final String DOWN_LOAD_START_TEMP = "{\"id\":\"%s\",\"status\":\"starting\",\"fileName\":\"%s\",\"time\":\"%s\"}";
    private final String DOWNLOAD_TOPIC = "/topic/download/excel/%s";
    private final String BUCKET_NAME = "upload";
    private final String UPLOAD_PATH = "/tzs/excelTempFile";

    private final List<String> equipHandleOtherFields = Arrays.asList("techParam", "paramRange", "NEXT_INSPECT_DATE", "IS_SUPERVISORY_CODE", "USC_DATE", "createDate");
    private final List<String> companyHandleOtherFields = Arrays.asList("itemCode", "subItemCode", "permitStatus", "equipCategory", "regulatoryLabels", "unitType");
    private final List<String> personHandleOtherFields = Arrays.asList("newPost", "subPost", "certNo", "expiryDate", "certType", "permissionLevel", "jobItem", "permissionItem", "issueDate", "equipType", "unitType");

    private final String or = "or";
    private final String and = "and";


    @Autowired
    EquipmentCategoryMapper equipmentCategoryMapper;

    DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd");

    public List<Map<String, Object>> queryEquipmentCategory(String key) {
        List<Map<String, Object>> list;
        Map<String, List<Map<String, Object>>> resourceJson = JsonUtils.getResourceJson(equipCategory);
        if (key == null) {
            list = resourceJson.get(EquipmentClassifityEnum.ZHTJFX.getCode());
        } else {
            list = tzsCustomFilterMapper.selectEquipmentCategoryByParentId(key);
        }

        return list;
    }

    public JSONArray queryEquipmentSearchData(String value) {
        List<TechParamItem> paramMetaList = TechParamUtil.getParamMetaList(value);
        JSONArray list = new JSONArray();
        for (int i = 0; i < paramMetaList.size(); i++) {
            JSONObject object = new JSONObject();
            object.put("key", paramMetaList.get(i).getParamKey());
            object.put("value", paramMetaList.get(i).getParamKey());
            object.put("label", paramMetaList.get(i).getParamLabel());
            object.put("unit", paramMetaList.get(i).getUnit());
            JSONObject skillConfig = new JSONObject();
            skillConfig.put("conditions", getConditionList(paramMetaList.get(i).getParamType(), paramMetaList.get(i).getDictCode()));
            if (!ValidationUtil.isEmpty(paramMetaList.get(i).getDictCode())) {
                skillConfig.put("type", "select");
                skillConfig.put("data", getData(paramMetaList.get(i).getDictCode()));
            } else if (TechnicalParameter.ParamType.BIG_DECIMAL.equals(paramMetaList.get(i).getParamType())) {
                skillConfig.put("type", "inputNumber");
            } else if (TechnicalParameter.ParamType.STRING.equals(paramMetaList.get(i).getParamType())) {
                skillConfig.put("type", "input");
            } else if (TechnicalParameter.ParamType.DATE.equals(paramMetaList.get(i).getParamType())) {
                skillConfig.put("type", "date");
            }
            skillConfig.put("fieldType", paramMetaList.get(i).getParamType());
            skillConfig.put("isMulti", false);
            object.put("skillConfig", skillConfig);
            list.add(object);
        }
        return list;
    }

    public JSONArray getData(String dictCode) {
        JSONArray jsonArray = new JSONArray();
        //根据dictCode查询数据字典
        List<DataDictionary> dictionaries = dataDictionaryService.getByType(dictCode);
        for (DataDictionary dictionary : dictionaries) {
            JSONObject object = new JSONObject();
            object.put("label", dictionary.getName());
            object.put("value", dictionary.getCode());
            object.put("key", dictionary.getCode());
            jsonArray.add(object);
        }
        return jsonArray;
    }

    public JSONArray queryDicDataNew(String dictCode) {
        JSONArray jsonArray = new JSONArray();
        //根据dictCode查询数据字典
        List<DataDictionary> dictionaries = dataDictionaryService.getByType(dictCode);
        for (DataDictionary dictionary : dictionaries) {
            JSONObject object = new JSONObject();
            object.put("label", dictionary.getName());
            object.put("value", dictionary.getName());
            object.put("key", dictionary.getCode());
            jsonArray.add(object);
        }
        return jsonArray;
    }

    private JSONArray getConditionList(TechnicalParameter.ParamType value, String dictCode) {
        return ConditionEnum.getByCode(ValidationUtil.isEmpty(dictCode) ? value : null);
    }

    public JSONArray queryAdvancedSearch(String type) {
        JSONArray all = new JSONArray();
        if ("equip".equals(type)) {
            all = EquipAdvanceSearchEnum.getAll();
        } else if ("company".equals(type)) {
            all = CompanyAdvanceSearchEnum.getAll();
        } else if ("person".equals(type)) {
            all = PersonAdvanceSearchEnum.getAll();
        }
        return all;
    }

    public JSONObject queryForPage(JSONObject filter) {
        JSONObject result = new JSONObject();
        Integer current = ObjectUtils.isEmpty(filter.getInteger("current")) ? 1 : filter.getInteger("current");
        Integer size = ObjectUtils.isEmpty(filter.getInteger("size")) ? 20 : filter.getInteger("size");

        Page<JSONObject> page = new Page<>(current, size);
        String businessType = filter.getString("businessType");
        if (ObjectUtils.isEmpty(businessType)) {
            JSONObject statics = new JSONObject();
            statics.put("totalCount", null);
            result.put("statics", statics);
            page.setRecords(new ArrayList<>());
            page.setTotal(0);
            result.put("pageData", page);
            result.put("businessType", businessType);
            return result;
        }
        if (StatisticalAnalysisEnum.equip.getCode().equals(businessType)) {
            result = queryEquipmentPage(filter, page, current, size);
        } else if (StatisticalAnalysisEnum.company.getCode().equals(businessType)) {
            result = queryCompanyPage(filter, page, current, size);
        } else {
            result = queryPersonPage(filter, page, current, size);
        }
        result.put("businessType", businessType);
        return result;
    }

    private JSONObject queryPersonPage(JSONObject filter, Page<JSONObject> page, Integer current, Integer size) {

        JSONObject result = new JSONObject();

        SearchRequest request = new SearchRequest();
        request.indices(StatisticalAnalysisEnum.person.getKey());
        SearchSourceBuilder builder = new SearchSourceBuilder();
        builder.trackTotalHits(true);
        BoolQueryBuilder boolMust = QueryBuilders.boolQuery();

        String orgCode = filter.getString("orgCode");
        boolMust.must(QueryBuilders.prefixQuery("superviseOrgCode", orgCode));

        JSONObject filterParams = null;
        if (!ObjectUtils.isEmpty(filter.get("filterParams"))) {
            filterParams = JSONObject.parseObject(JSONObject.toJSONString(filter.get("filterParams")));
            String filterType = filter.getString("filterType");
            //快捷筛选和自定义筛选解析筛选规则不一致
            if (filterType.equals("advanced")) {
                filterParams.forEach((k, v) -> {
                    if (v instanceof JSONArray) {
                        if (!((JSONArray) v).contains("all")) {
                            String field = k;
                            if (k.equals("equipType") || k.equals("unitType") || k.equals("newPost") || k.equals("subPost")) {
                                boolMust.must(existsQuery(field));
                                ((JSONArray) v).forEach(item -> boolMust.must(QueryBuilders.wildcardQuery(k.equals("equipType") ? field : field + ".keyword", "*" + item + "*")));
                            } else if (k.equals("education")) {
                                boolMust.must(existsQuery(field));
                                TermsQueryBuilder termsQuery = QueryBuilders.termsQuery(field, (JSONArray) v);
                                boolMust.must(termsQuery);
                            } else if (k.equals("certNo") || k.equals("expiryDate") || k.equals("permissionLevel") || k.equals("certType") || k.equals("jobItem") || k.equals("permissionItem")) {
                                String path = "licenses";

                                ((JSONArray) v).forEach(item -> {
                                    String nestedField = path + "." + k;
                                    // 根据证书编号判断有无资质

                                    if (k.equals("certNo")) {
                                        NestedQueryBuilder nestedQuery = QueryBuilders.nestedQuery(
                                                path,
                                                existsQuery(nestedField),
                                                ScoreMode.Avg
                                        );
                                        // 以下人员类型有资质要求
                                        // 人员类型(newPost)：检验人员：66151、检测人员：66152
                                        // 人员子类型(subPost)： 持证人员:6712、持证人员(P):6764、持证人员(R2):6765
                                        if (item.equals("1")) {
                                            boolMust.must(nestedQuery);
                                        } else if (item.equals("0")) {
                                            // 无资质
                                            BoolQueryBuilder queryBuilder = QueryBuilders.boolQuery()
                                                    .should(QueryBuilders.wildcardQuery("newPost.keyword", "*66151*"))
                                                    .should(QueryBuilders.wildcardQuery("newPost.keyword", "*66152*"))
                                                    .should(QueryBuilders.wildcardQuery("subPost.keyword", "*6712*"))
                                                    .should(QueryBuilders.wildcardQuery("subPost.keyword", "*6764*"))
                                                    .should(QueryBuilders.wildcardQuery("subPost.keyword", "*6765*"))
                                                    .minimumShouldMatch(1);
                                            boolMust.must(queryBuilder);
                                            boolMust.mustNot(nestedQuery);
                                        } else {
                                            // 无资质要求
                                            BoolQueryBuilder queryBuilder = QueryBuilders.boolQuery()
                                                    .mustNot(QueryBuilders.wildcardQuery("newPost.keyword", "*66151*"))
                                                    .mustNot(QueryBuilders.wildcardQuery("newPost.keyword", "*66152*"))
                                                    .mustNot(QueryBuilders.wildcardQuery("subPost.keyword", "*6712*"))
                                                    .mustNot(QueryBuilders.wildcardQuery("subPost.keyword", "*6764*"))
                                                    .mustNot(QueryBuilders.wildcardQuery("subPost.keyword", "*6765*"));
                                            boolMust.must(queryBuilder);
                                        }
                                    } else if (k.equals("expiryDate")) {
                                        boolMust.must(existsQuery(nestedField));
                                        if (item.equals("overdue")) {
                                            // 超期：小于当前日期
                                            NestedQueryBuilder nestedQuery = QueryBuilders.nestedQuery(
                                                    path,
                                                    QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(nestedField).lt(LocalDate.now().format(formatter))),
                                                    ScoreMode.Avg
                                            );
                                            boolMust.must(nestedQuery);
                                        } else if (item.equals("near")) {
                                            // 临期：小于等于当前日期加上30天
                                            NestedQueryBuilder nestedQuery = QueryBuilders.nestedQuery(
                                                    path,
                                                    QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(nestedField).lte(LocalDate.now().plusDays(30).format(formatter)).gte(LocalDate.now().format(formatter))),
                                                    ScoreMode.Avg
                                            );
                                            boolMust.must(nestedQuery);
                                        } else if (item.equals("normal")) {
                                            // 正常：大于当前日期加上30天
                                            NestedQueryBuilder nestedQuery = QueryBuilders.nestedQuery(
                                                    path,
                                                    QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(nestedField).gt(LocalDate.now().plusDays(30).format(formatter))),
                                                    ScoreMode.Avg
                                            );
                                            boolMust.must(nestedQuery);
                                        }
                                    } else if (k.equals("certType") || k.equals("permissionLevel")) {
                                        NestedQueryBuilder nestedQuery = QueryBuilders.nestedQuery(
                                                path,
                                                QueryBuilders.boolQuery().must(QueryBuilders.termsQuery(nestedField, (JSONArray) v)),
                                                ScoreMode.Avg
                                        );
                                        boolMust.must(nestedQuery);
                                    } else {
                                        NestedQueryBuilder nestedQuery = QueryBuilders.nestedQuery(
                                                path,
                                                QueryBuilders.boolQuery().must(QueryBuilders.wildcardQuery(nestedField, "*" + item + "*")),
                                                ScoreMode.Avg
                                        );
                                        boolMust.should(nestedQuery);
                                    }
                                });
                            } else if (k.equals("issueDate")) {
                                JSONArray issueDates = (JSONArray) v;
                                String startDate = DateUtils.convertDateToString(issueDates.getDate(0), DateUtils.DATE_PATTERN);
                                String endDate = DateUtils.convertDateToString(issueDates.getDate(1), DateUtils.DATE_PATTERN);
                                NestedQueryBuilder nestedQuery = QueryBuilders.nestedQuery(
                                        "licenses",
                                        QueryBuilders.rangeQuery("licenses." + k).gte(startDate).lte(endDate),
                                        ScoreMode.Avg
                                );
                                boolMust.filter(nestedQuery);
                            }
                        }
                    }
                });
            } else {
                JSONArray leftGroup = filterParams.getJSONArray("group1");
                JSONArray rightGroup = filterParams.getJSONArray("group2");
                Boolean isOrGroup = or.equals(filterParams.getString("groupAndOr")) ? Boolean.TRUE : Boolean.FALSE;
                handleAdvancedFilter(boolMust, leftGroup, rightGroup, isOrGroup);
            }
        }
        // 排序
        if (!ObjectUtils.isEmpty(filter.get("sort"))) {
            JSONObject sort = JSONObject.parseObject(JSONObject.toJSONString(filter.get("sort")));
            String field = sort.getString("field");
            if (field.equals("subPostName")) {
                field = "subPost";
            } else if (field.equals("postName")) {
                field = "newPost";
            } else if (field.equals("superviseOrgName")) {
                field = "superviseOrgCode";
            }
            builder.sort(field, sort.getString("order").equals("desc") ? SortOrder.DESC : SortOrder.ASC);
        }
        builder.query(boolMust);
        builder.from((current - 1) * size);
        builder.size(size);
        request.source(builder);

        List<JSONObject> list = new LinkedList<>();
        long totle = 0;
        try {
            SearchResponse response = restHighLevelClient.search(request, RequestOptions.DEFAULT);
            for (SearchHit hit : response.getHits().getHits()) {
                JSONObject jsonObject = (JSONObject) JSONObject.toJSON(hit);
                JSONObject dto = jsonObject.getJSONObject("sourceAsMap");
                if (dto.containsKey("identification") && !ObjectUtils.isEmpty(dto.get("identification"))) {
                    JSONArray jsonArray = JSONObject.parseArray(dto.get("identification").toString());
                    if (!ObjectUtils.isEmpty(jsonArray)) {
                        dto.put("identification", JSONObject.parseObject(JSONObject.parseArray(dto.get("identification").toString()).get(0).toString()).get("url"));
                    }
                }
                if (dto.containsKey("equipType")) {
                    String[] equipCodes = dto.get("equipType").toString().split(",");
                    StringBuilder equipTypes = new StringBuilder();
                    for (String equipType : equipCodes) {
                        equipTypes.append(EquipmentClassifityEnum.getNameByCode(equipType) + ",");
                    }
                    dto.put("equipType", equipTypes.substring(0, equipTypes.length() - 1));
                }
                list.add(dto);
            }
            totle = Objects.requireNonNull(response.getInternalResponse().hits().getTotalHits()).value;
            page.setRecords(list);
            page.setTotal(totle);
            result.put("pageData", page);
        } catch (IOException e) {
            throw new RuntimeException(e);
        }

        List<Map<String, Object>> statics = new ArrayList<>();
        Map<String, Object> sum = new HashMap<>();
        sum.put("name", "人员总数（人）");
        sum.put("value", totle);
        statics.add(sum);
        result.put("statics", statics);

        return result;
    }

    private JSONObject queryCompanyPage(JSONObject filter, Page<JSONObject> page, Integer current, Integer size) {

        JSONObject result = new JSONObject();

        SearchRequest request = new SearchRequest();
        request.indices(StatisticalAnalysisEnum.company.getKey());
        SearchSourceBuilder builder = new SearchSourceBuilder();
        builder.trackTotalHits(true);
        BoolQueryBuilder boolMust = QueryBuilders.boolQuery();

        String orgCode = filter.getString("orgCode");
        boolMust.must(QueryBuilders.prefixQuery("superviseOrgCode.keyword", orgCode));
        JSONObject filterParams = null;
        if (!ObjectUtils.isEmpty(filter.get("filterParams"))) {
            filterParams = JSONObject.parseObject(JSONObject.toJSONString(filter.get("filterParams")));
            String filterType = filter.getString("filterType");
            //快捷筛选和自定义筛选解析筛选规则不一致
            if (filterType.equals("advanced")) {
                filterParams.forEach((k, v) -> {
                    if (v instanceof JSONArray) {
                        if (!((JSONArray) v).contains("all")) {
                            String field = k;
                            if (k.equals("regulatoryLabels") || k.equals("equipCategory") || k.equals("unitType")) {
                                boolMust.must(existsQuery(field));
                                ((JSONArray) v).forEach(item -> boolMust.should(QueryBuilders.wildcardQuery(field + ".keyword", "*" + item + "*")));
                                boolMust.minimumShouldMatch(1);
                            } else if (k.equals("industrySupervisor") || k.equals("operatingStatus")) {
                                boolMust.must(existsQuery(field));
                                TermsQueryBuilder termsQuery = QueryBuilders.termsQuery(field + ".keyword", ((JSONArray) v).get(0));
                                boolMust.must(termsQuery);
                            } else if (k.equals("itemCode") || k.equals("subItemCode") || k.equals("permitStatus")) {
                                String path = "licenses";
                                ((JSONArray) v).forEach(item -> {
                                    String nestedField = path + "." + (k.equals("permitStatus") ? "expiryDate" : k + ".keyword");
                                    if (k.equals("permitStatus")) {
                                        if (item.equals("overdue")) {
                                            // 超期：小于当前日期
                                            NestedQueryBuilder nestedQuery = QueryBuilders.nestedQuery(
                                                    path,
                                                    QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(nestedField).lt(LocalDate.now().format(formatter))),
                                                    ScoreMode.Avg
                                            );
                                            boolMust.must(nestedQuery);
                                        } else if (item.equals("near")) {
                                            // 临期：小于等于当前日期加上30天
                                            NestedQueryBuilder nestedQuery = QueryBuilders.nestedQuery(
                                                    path,
                                                    QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(nestedField).lte(LocalDate.now().plusDays(30).format(formatter)).gte(LocalDate.now().format(formatter))),
                                                    ScoreMode.Avg
                                            );
                                            boolMust.must(nestedQuery);
                                        } else if (item.equals("normal")) {
                                            // 正常：大于当前日期加上30天
                                            NestedQueryBuilder nestedQuery = QueryBuilders.nestedQuery(
                                                    path,
                                                    QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(nestedField).gt(LocalDate.now().plusDays(30).format(formatter))),
                                                    ScoreMode.Avg
                                            );
                                            boolMust.must(nestedQuery);
                                        }
                                    } else {
                                        // 创建嵌套查询
                                        NestedQueryBuilder nestedQuery = QueryBuilders.nestedQuery(
                                                path,
                                                QueryBuilders.termsQuery(nestedField, item),
                                                ScoreMode.Avg
                                        );
                                        boolMust.must(nestedQuery);
                                    }
                                });
                            }
                        }
                    }
                });
            } else {
                JSONArray leftGroup = filterParams.getJSONArray("group1");
                JSONArray rightGroup = filterParams.getJSONArray("group2");
                Boolean isOrGroup = or.equals(filterParams.getString("groupAndOr")) ? Boolean.TRUE : Boolean.FALSE;
                handleAdvancedFilter(boolMust, leftGroup, rightGroup, isOrGroup);
            }
        }


        // 排序
        if (!ObjectUtils.isEmpty(filter.get("sort"))) {
            JSONObject sort = JSONObject.parseObject(JSONObject.toJSONString(filter.get("sort")));
            String field = sort.getString("field").equals("permissionStatus") ? "licenses.expiryDate" : sort.getString("field") + ".keyword";
            SortOrder sortOrder = sort.getString("order").equals("desc") ? SortOrder.DESC : SortOrder.ASC;
            FieldSortBuilder sortBuilder = SortBuilders.fieldSort(field).order(sortOrder);
            builder.sort(sortBuilder);
        }

        builder.query(boolMust);
        builder.from((current - 1) * size);
        builder.size(size);
        request.source(builder);

        List<JSONObject> list = new LinkedList<>();
        long totle = 0;

        try {
            SearchResponse response = restHighLevelClient.search(request, RequestOptions.DEFAULT);
            for (SearchHit hit : response.getHits().getHits()) {
                JSONObject jsonObject = (JSONObject) JSONObject.toJSON(hit);
                JSONObject dto = jsonObject.getJSONObject("sourceAsMap");
                list.add(dto);
            }
            totle = Objects.requireNonNull(response.getInternalResponse().hits().getTotalHits()).value;
            page.setRecords(list);
            page.setTotal(totle);
            result.put("pageData", page);
        } catch (IOException e) {
            throw new RuntimeException(e);
        }


        List<Map<String, Object>> statics = new ArrayList<>();
        Map<String, Object> sum = new HashMap<>();
        sum.put("name", "企业总数（个）");
        sum.put("value", totle);
        statics.add(sum);
        result.put("statics", statics);

        return result;
    }

    private JSONObject queryEquipmentPage(JSONObject filter, Page<JSONObject> page, Integer current, Integer size) {

        JSONObject result = new JSONObject();

        SearchRequest request = new SearchRequest();
        request.indices(StatisticalAnalysisEnum.equip.getKey());
        SearchSourceBuilder builder = new SearchSourceBuilder();
        builder.trackTotalHits(true);
        BoolQueryBuilder boolMust = QueryBuilders.boolQuery();

        String orgCode = filter.getString("orgCode");
        boolMust.must(QueryBuilders.prefixQuery("ORG_BRANCH_CODE", orgCode));
        JSONObject filterParams;
        // 筛选
        if (!ObjectUtils.isEmpty(filter.get("filterParams"))) {
            filterParams = JSONObject.parseObject(JSONObject.toJSONString(filter.get("filterParams")));
            String filterType = filter.getString("filterType");
            //快捷筛选和自定义筛选解析筛选规则不一致
            if (filterType.equals("advanced")) {
                JSONObject finalFilterParams = filterParams;
                filterParams.forEach((k, v) -> {
                    if (k.equals("techParam")) {
                        JSONArray techParams = (JSONArray) v;
                        if (!techParams.contains("all") && techParams.size() == 1) {
                            JSONObject paramRangeJson = JSONObject.parseObject(JSONObject.toJSONString(finalFilterParams.get("paramRange")));
                            String paramKey = techParams.getString(0);
                            String condition = paramRangeJson.getString("condition");
                            Object value = paramRangeJson.getString("value");
                            String fieldType = paramRangeJson.getString("fieldType");
                            getParamQuery(paramKey, condition, value, fieldType, false, boolMust, null, null);
                        }
                    } else if (!k.equals("paramRange")) {
                        if (v instanceof JSONArray) {
                            // 判断是否需要解析参数
                            Boolean parseParam = getParamAnalysis(v);
                            if (parseParam) {
                                String field = k;
                                if (k.equals("unitType")) {
                                    String finalField = field;
                                    EnhancedDynamicQueryBuilder queryBuilder = new EnhancedDynamicQueryBuilder();
                                    ((JSONArray) v).forEach(item -> {
                                        queryBuilder.add(QueryBuilders.wildcardQuery(finalField, "*" + item + "*"), or);
                                    });
                                    boolMust.must(queryBuilder.build());
                                } else if (k.equals("NEXT_INSPECT_DATE")) {
                                    String finalField = field;
                                    boolMust.must(existsQuery(finalField));
                                    EnhancedDynamicQueryBuilder queryBuilder = new EnhancedDynamicQueryBuilder();
                                    ((JSONArray) v).forEach(item -> {
                                        if (item.equals("overdue")) {
                                            // 超期：小于当前日期
                                            queryBuilder.add(QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(finalField).lt(LocalDate.now().format(formatter))), or);
                                        } else if (item.equals("near")) {
                                            // 临期：小于等于当前日期加上30天
                                            queryBuilder.add(QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(finalField).gte(LocalDate.now().format(formatter)).lte(LocalDate.now().plusDays(30).format(formatter))), or);
                                        } else {
                                            // 正常：大于当前日期加上30天
                                            queryBuilder.add(QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(finalField).gt(LocalDate.now().plusDays(30).format(formatter))), or);
                                        }
                                    });
                                    boolMust.must(queryBuilder.build());
                                } else if (k.equals("USC_DATE")) {
                                    String finalField = field;
                                    boolMust.must(existsQuery(finalField));
                                    EnhancedDynamicQueryBuilder queryBuilder = new EnhancedDynamicQueryBuilder();
                                    ((JSONArray) v).forEach(item -> {
                                        if (item.equals("15")) {
                                            // 15年以上：大于当前日期减去15年
                                            queryBuilder.add(QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(finalField).gt(LocalDate.now().minusYears(15).format(formatter))), or);
                                        } else if (item.equals("10-15")) {
                                            // 10-15年：小于当前日期减去15年，大于等于当前日期减去10年
                                            queryBuilder.add(QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(finalField).lt(LocalDate.now().minusYears(15).format(formatter)).gte(LocalDate.now().minusYears(10).format(formatter))), or);
                                        } else if (item.equals("5-10")) {
                                            // 5-10年：小于当前日期减去10年，大于等于当前日期减去5年
                                            queryBuilder.add(QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(finalField).lt(LocalDate.now().minusYears(10).format(formatter)).gte(LocalDate.now().minusYears(5).format(formatter))), or);
                                        } else if (item.equals("0-5")) {
                                            // 0-5年：小于当前日期减去5年
                                            queryBuilder.add(QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(finalField).lt(LocalDate.now().minusYears(5).format(formatter))), or);
                                        }
                                    });
                                    boolMust.must(queryBuilder.build());
                                } else if (k.equals("IS_SUPERVISORY_CODE")) {
                                    String finalField = k;
                                    ((JSONArray) v).forEach(item -> {
                                        if (item.equals("1")) {
                                            boolMust.must(existsQuery(finalField));
                                            boolMust.mustNot(QueryBuilders.termQuery(finalField, "null"));
                                        } else {
                                            boolMust.mustNot(existsQuery(finalField));
                                        }
                                    });
                                } else if (k.equals("createDate")) {
                                    JSONArray createDates = (JSONArray) v;
                                    String startDate = DateUtils.convertDateToString(createDates.getDate(0), DateUtils.DATE_TIME_PATTERN);
                                    String endDate = DateUtils.convertDateToString(createDates.getDate(1), DateUtils.DATE_TIME_PATTERN);
                                    boolMust.filter(QueryBuilders.rangeQuery("createDate").gte(startDate.replace(" ", "T")).lte(endDate.replace(" ", "T")));
                                } else if (k.equals("EQU_LIST") || k.equals("EQU_CATEGORY") || k.equals("EQU_DEFINE") || k.equals("EQU_STATE") || k.equals("DATA_QUALITY_SCORE") || k.equals("DATA_SOURCE")) {
                                    if (k.equals("EQU_LIST")) {
                                        field = "EQU_LIST_CODE";
                                    } else if (k.equals("EQU_CATEGORY")) {
                                        field = "EQU_CATEGORY_CODE";
                                    } else if (k.equals("EQU_DEFINE")) {
                                        field = "EQU_DEFINE_CODE";
                                    }
                                    boolMust.must(existsQuery(field));
                                    TermsQueryBuilder termsQuery = QueryBuilders.termsQuery(field, (JSONArray) v);
                                    boolMust.must(termsQuery);
                                }
                            }
                        }
                    }
                });
            } else {
                JSONArray leftGroup = filterParams.getJSONArray("group1");
                JSONArray rightGroup = filterParams.getJSONArray("group2");
                Boolean isOrGroup = or.equals(filterParams.getString("groupAndOr")) ? Boolean.TRUE : Boolean.FALSE;
                handleAdvancedFilter(boolMust, leftGroup, rightGroup, isOrGroup);
            }
        } else {
            filterParams = null;
        }

        //  排序
        if (!ObjectUtils.isEmpty(filter.get("sort"))) {
            JSONObject sort = JSONObject.parseObject(JSONObject.toJSONString(filter.get("sort")));
            String field = sort.getString("field");
            if (field.equals("EQU_LIST")) {
                field = "EQU_LIST_CODE";
            } else if (field.equals("EQU_CATEGORY")) {
                field = "EQU_CATEGORY_CODE";
            } else if (field.equals("EQU_DEFINE")) {
                field = "EQU_DEFINE_CODE";
            } else if (field.equals("ORG_BRANCH_NAME")) {
                field = "ORG_BRANCH_CODE";
            } else if (field.equals("USE_UNIT_NAME")) {
                field = "USE_UNIT_CREDIT_CODE";
            }
            builder.sort(field, sort.getString("order").equals("desc") ? SortOrder.DESC : SortOrder.ASC);
        }

        builder.query(boolMust);

        builder.from((current - 1) * size);
        builder.size(size);
        request.source(builder);

        List<JSONObject> list = new LinkedList<>();
        long totle = 0;
//        double pipeLong = 0;
        try {
            SearchResponse response = restHighLevelClient.search(request, RequestOptions.DEFAULT);
            for (SearchHit hit : response.getHits().getHits()) {
                JSONObject jsonObject = (JSONObject) JSONObject.toJSON(hit);
                JSONObject dto = jsonObject.getJSONObject("sourceAsMap");
                dto.put("record", dto.get("SEQUENCE_NBR"));
                dto.put("equipAddress", dto.get("USE_PLACE") + "/" + dto.get("ADDRESS"));
                String dataQualityScore = ObjectUtils.isEmpty(dto.get("DATA_QUALITY_SCORE")) ? null : DataQualityScoreEnum.getNameByCode(dto.get("DATA_QUALITY_SCORE").toString());
                dto.put("DATA_QUALITY_SCORE", dataQualityScore);
//                if (dto.get("EQU_LIST_CODE").equals("8000")) {
//                    JSONArray techParams = (JSONArray) dto.get("techParams");
//                    if (!ObjectUtils.isEmpty(techParams)) {
//                        Object obj = techParams.stream().filter(item -> JSONObject.parseObject(JSONObject.toJSONString(item)).get("paramKey").equals("pipeLength")).findFirst().get();
//                        JSONObject jsonParam = JSONObject.parseObject(JSONObject.toJSONString(obj));
//                        if (jsonParam.containsKey("doubleValue")) {
//                            String pipeLength = JSONObject.parseObject(JSONObject.toJSONString(obj)).get("doubleValue").toString();
//                            pipeLong += Double.parseDouble(pipeLength);
//                        }
//                    }
//                }
                list.add(dto);
            }
            totle = Objects.requireNonNull(response.getInternalResponse().hits().getTotalHits()).value;
            page.setRecords(list);
            page.setTotal(totle);
            result.put("pageData", page);
        } catch (IOException e) {
            throw new RuntimeException(e);
        }

        List<Map<String, Object>> statics = new ArrayList<>();
        Map<String, Object> sum = new HashMap<>();
        sum.put("name", "设备总数（台套）");
        sum.put("value", totle);
        statics.add(sum);

        if (ObjectUtils.isEmpty(filterParams) || !filterParams.containsKey("EQU_LIST")) {
            filterParams = new JSONObject();
            JSONArray jsonArray = new JSONArray();
            jsonArray.add("all");
            filterParams.put("EQU_LIST", jsonArray);
        }

        JSONArray equList = (JSONArray) filterParams.get("EQU_LIST");
        if (equList.contains("8000") || equList.contains("all") || ObjectUtils.isEmpty(equList)) {
            // 压力管道长度
            Map<String, Object> pipeMaps = new HashMap<>();
            stCommonService.staticsCenterMapCountDataForPipeline(pipeMaps, orgCode, true, false);
            // 获取压力管道长度
//            getPipeLength(pipeMaps, boolMust, builder, filterParams);
            Map<String, Object> pipeMap = new HashMap<>();
            pipeMap.put("name", "压力管道（千米）");
            pipeMap.put("value", pipeMaps.get("pressurePipelines"));
            statics.add(pipeMap);
        }
        if (equList.contains("2000") || equList.contains("all") || ObjectUtils.isEmpty(equList)) {
            // 气瓶数量
            Map<String, Object> gasMap = new HashMap<>();
            gasMap.put("name", "气瓶（个）");
            Map<String, Object> gas = new HashMap<>();
            gas.put(DPMapStatisticsItemEnum.GAS.getCode(), 0);
            long cylinderNum = stCommonService.staticsCenterMapCountDataForCylinder(gas, orgCode, true, true, false);
            // 1. 8大类设备数量统计,压力容器里包括气瓶所以需要特殊处理，在统计压力容器时去掉气瓶的数量
            stCommonService.staticsCenterMapCountDataForEquip(gas, cylinderNum, orgCode, true, true, false);
            gasMap.put("value", gas.get(DPMapStatisticsItemEnum.GAS.getCode()));
            statics.add(gasMap);
        }
        result.put("statics", statics);
        return result;
    }

    private Boolean getParamAnalysis(Object v) {
        Boolean result = false;
        if (v instanceof JSONArray) {
            JSONArray jsonArray = (JSONArray) v;
            result = jsonArray.size() != 0 && !jsonArray.get(0).equals("all");
        } else if (v instanceof String) {
            if ("null".equals(v) || "".equals(v) || null == v) {
                result = true;
            }
        }
        return result;
    }

    private void getParamQuery(String paramKey, String condition, Object value, String fieldType, Boolean isCustom, BoolQueryBuilder boolMust, EnhancedDynamicQueryBuilder builder, String andOr) {
        String path = "techParams";
        String nestedFieldKey = path + ".paramKey";
        String tail = "BIG_DECIMAL".equals(fieldType) ? ".doubleValue" : ".strValue";
        NestedQueryBuilder keyNestedQuery = QueryBuilders.nestedQuery(
                path,
                QueryBuilders.boolQuery().must(QueryBuilders.termsQuery(nestedFieldKey, paramKey)),
                ScoreMode.Avg
        );
        if (isCustom) {
            builder.add(keyNestedQuery, andOr);
        } else {
            boolMust.must(keyNestedQuery);
        }
        switch (condition) {
            case "eq":
                NestedQueryBuilder eqQuery = QueryBuilders.nestedQuery(
                        path,
                        QueryBuilders.boolQuery().must(QueryBuilders.termsQuery(path + tail, value)),
                        ScoreMode.Avg
                );
                if (isCustom) {
                    builder.add(eqQuery, andOr);
                } else {
                    boolMust.must(eqQuery);
                }
                break;
            case "neq":
                boolMust.must(keyNestedQuery);
                NestedQueryBuilder neqQuery = QueryBuilders.nestedQuery(
                        path,
                        QueryBuilders.boolQuery().mustNot(QueryBuilders.termsQuery(path + tail, value)),
                        ScoreMode.Avg
                );
                if (isCustom) {
                    builder.add(neqQuery, andOr);
                } else {
                    boolMust.mustNot(neqQuery);
                }
                break;
            case "like":
                NestedQueryBuilder likeQuery = QueryBuilders.nestedQuery(
                        path,
                        QueryBuilders.boolQuery().must(QueryBuilders.wildcardQuery(path + tail, "*" + value + "*")),
                        ScoreMode.Avg
                );
                if (isCustom) {
                    builder.add(likeQuery, andOr);
                } else {
                    boolMust.must(likeQuery);
                }
                break;
            case "notLike":
                NestedQueryBuilder notLikeQuery = QueryBuilders.nestedQuery(
                        path,
                        QueryBuilders.boolQuery().must(QueryBuilders.wildcardQuery(path + tail, "*" + value + "*")),
                        ScoreMode.Avg
                );
                if (isCustom) {
                    builder.add(QueryBuilders.boolQuery().mustNot(notLikeQuery), andOr);
                } else {
                    boolMust.mustNot(notLikeQuery);
                }
                break;
            case "gt":
                NestedQueryBuilder gtQuery = QueryBuilders.nestedQuery(
                        path,
                        QueryBuilders.rangeQuery(path + tail).gt(value.toString()),
                        ScoreMode.Avg
                );
                if (isCustom) {
                    builder.add(gtQuery, andOr);
                } else {
                    boolMust.must(gtQuery);
                }
                break;
            case "gte":
                NestedQueryBuilder gteQuery = QueryBuilders.nestedQuery(
                        path,
                        QueryBuilders.boolQuery().must(QueryBuilders.rangeQuery(path + tail).gte(value.toString())),
                        ScoreMode.Avg
                );
                if (isCustom) {
                    builder.add(gteQuery, andOr);
                } else {
                    boolMust.must(gteQuery);
                }
                break;
            case "lt":
                NestedQueryBuilder ltQuery = QueryBuilders.nestedQuery(
                        path,
                        QueryBuilders.boolQuery().must(QueryBuilders.rangeQuery(path + tail).lt(value.toString())),
                        ScoreMode.Avg
                );
                if (isCustom) {
                    builder.add(ltQuery, andOr);
                } else {
                    boolMust.must(ltQuery);
                }
                break;
            case "lte":
                NestedQueryBuilder lteQuery = QueryBuilders.nestedQuery(
                        path,
                        QueryBuilders.boolQuery().must(QueryBuilders.rangeQuery(path + tail).lte(value.toString())),
                        ScoreMode.Avg
                );
                if (isCustom) {
                    builder.add(lteQuery, andOr);
                } else {
                    boolMust.must(lteQuery);
                }
                break;
            case "between":
                JSONArray btValues = (JSONArray) value;
                NestedQueryBuilder betweenQuery = QueryBuilders.nestedQuery(
                        path,
                        QueryBuilders.boolQuery().must(QueryBuilders.rangeQuery(path + tail).gte(Double.parseDouble(btValues.get(0).toString())).lte(Double.parseDouble(btValues.get(1).toString()))),
                        ScoreMode.Avg
                );
                if (isCustom) {
                    builder.add(betweenQuery, andOr);
                } else {
                    boolMust.must(betweenQuery);
                }
                break;
            case "in":
                JSONArray inValues = (JSONArray) value;
                NestedQueryBuilder inQuery = QueryBuilders.nestedQuery(
                        path,
                        QueryBuilders.boolQuery().must(QueryBuilders.termsQuery(path + tail, inValues)),
                        ScoreMode.Avg
                );
                if (isCustom) {
                    builder.add(inQuery, andOr);
                } else {
                    boolMust.must(inQuery);
                }
                break;
            case "notIn":
                JSONArray notInValues = (JSONArray) value;
                NestedQueryBuilder notInQuery = QueryBuilders.nestedQuery(
                        path,
                        QueryBuilders.boolQuery().must(QueryBuilders.termsQuery(path + tail, notInValues)),
                        ScoreMode.Avg
                );
                if (isCustom) {
                    builder.add(QueryBuilders.boolQuery().mustNot(notInQuery), andOr);
                } else {
                    boolMust.mustNot(notInQuery);
                }
                break;
        }
    }

    // 处理高级筛选条件
    private void handleAdvancedFilter(BoolQueryBuilder boolMust, JSONArray leftGroup, JSONArray rightGroup, Boolean isOrGroup) {
        DynamicQueryBuilder mainBuilder = new DynamicQueryBuilder();
        EnhancedDynamicQueryBuilder leftBuilder = new EnhancedDynamicQueryBuilder();
        if (!ObjectUtils.isEmpty(leftGroup)) {
            // 处理左侧分组
            JSONObject leftTechParam = new JSONObject();
            JSONObject leftParamRange = new JSONObject();
            JSONArray leftGroupList = new JSONArray();
            // 剥离计数参数
            getTechParam(leftGroup, leftGroupList, leftTechParam, leftParamRange);
            // 如果技术参数和分组不为空，添加技术参数筛选条件到左侧筛选条件中
            if (!ObjectUtils.isEmpty(leftTechParam) && !ObjectUtils.isEmpty(leftParamRange)) {
                addTechParam(leftTechParam, leftParamRange, leftBuilder);
            }
            // 非计数参数处理
            groupHandler(leftGroupList, leftBuilder);
            // 添加左侧筛选条件到最终筛选条件中
            mainBuilder.and(leftBuilder.build());
        }

        if (!ObjectUtils.isEmpty(rightGroup)) {
            // 处理右侧分组
            EnhancedDynamicQueryBuilder rightBuilder = new EnhancedDynamicQueryBuilder();
            JSONObject rightTechParam = new JSONObject();
            JSONObject rightParamRange = new JSONObject();
            JSONArray rightGroupList = new JSONArray();
            // 剥离计数参数
            getTechParam(rightGroup, rightGroupList, rightTechParam, rightParamRange);
            // 如果技术参数和分组不为空，添加技术参数筛选条件到右侧筛选条件中
            if (!ObjectUtils.isEmpty(rightTechParam) && !ObjectUtils.isEmpty(rightParamRange)) {
                addTechParam(rightTechParam, rightParamRange, rightBuilder);
            }
            // 非计数参数处理
            groupHandler(rightGroupList, rightBuilder);

            // 添加右侧筛选条件到最终筛选条件中
            if (isOrGroup) {
                mainBuilder.or(rightBuilder.build());
            } else {
                mainBuilder.and(rightBuilder.build());
            }
        }

        // 组装最终筛选条件
        boolMust.must(mainBuilder.build());
    }

    private void addTechParam(JSONObject techParam, JSONObject paramRange, EnhancedDynamicQueryBuilder builder) {
        JSONObject jsonObject = JSONObject.parseObject(JSONObject.toJSONString(techParam));
        String field = jsonObject.getString("value");
        String fieldType = jsonObject.getString("fieldType");
        String itemCondition = paramRange.getString("itemCondition");
        Object value = paramRange.get("value");
        String andOr = paramRange.getString("andOr");
        getParamQuery(field, itemCondition, value, fieldType, true, null, builder, andOr);
    }

    private void groupHandler(JSONArray group, EnhancedDynamicQueryBuilder builder) {
        for (Object object : group) {
            JSONObject itemObj = JSONObject.parseObject(JSONObject.toJSONString(object));
            String field = itemObj.getString("field");
            String itemCondition = itemObj.getString("itemCondition");
            Object value = itemObj.get("value");
            String andOr = itemObj.getString("andOr");
            // 组装查询条件
            getItemQuery(field, itemCondition, value, andOr, builder);
        }
    }

    private void getTechParam(JSONArray group, JSONArray resultGroup, JSONObject techParam, JSONObject paramRange) {
        // 剥离技术参数分组
        group.forEach(item -> {
            JSONObject itemObj = JSONObject.parseObject(JSONObject.toJSONString(item));
            if (itemObj.containsKey("field") && itemObj.containsKey("value")) {
                if (itemObj.getString("field").equals("techParam")) {
                    techParam.putAll(itemObj);
                } else if (itemObj.getString("field").equals("paramRange")) {
                    paramRange.putAll(itemObj);
                } else {
                    resultGroup.add(itemObj);
                }
            }
        });
    }

    private void getItemQuery(String field, String itemCondition, Object value, String isOr, EnhancedDynamicQueryBuilder builder) {
        // 如果包含需要特殊处理的字段，则调用对应的处理方法，否则调用通用处理方法
        if (equipHandleOtherFields.contains(field) || companyHandleOtherFields.contains(field) || personHandleOtherFields.contains(field)) {
            handleOtherField(field, itemCondition, value, isOr, builder);
        } else {
            switch (itemCondition) {
                case "eq":
                    builder.add(QueryBuilders.termQuery(field, value), isOr);
                    break;
                case "neq":
                    builder.add(QueryBuilders.boolQuery().mustNot(QueryBuilders.termQuery(field, value)), isOr);
                    break;
                case "like":
                    builder.add(QueryBuilders.boolQuery().must(QueryBuilders.wildcardQuery(field, "*" + value + "*")), isOr);
                    break;
                case "notLike":
                    builder.add(QueryBuilders.boolQuery().mustNot(QueryBuilders.wildcardQuery(field, "*" + value + "*")), isOr);
                    break;
                case "gt":
                    builder.add(QueryBuilders.rangeQuery(field).gt(value.toString()), isOr);
                    break;
                case "gte":
                    builder.add(QueryBuilders.rangeQuery(field).gte(value.toString()), isOr);
                    break;
                case "lt":
                    builder.add(QueryBuilders.rangeQuery(field).lt(value.toString()), isOr);
                    break;
                case "lte":
                    builder.add(QueryBuilders.rangeQuery(field).lte(value.toString()), isOr);
                    break;
                case "between":
                    JSONArray btValues = (JSONArray) value;
                    builder.add(QueryBuilders.rangeQuery(field).gte(Double.parseDouble(btValues.get(0).toString())).lte(Double.parseDouble(btValues.get(1).toString())), isOr);
                    break;
                case "in":
                    builder.add(QueryBuilders.termsQuery(field, value), isOr);
                    break;
                case "notIn":
                    builder.add(QueryBuilders.boolQuery().mustNot(QueryBuilders.termsQuery(field, value)), isOr);
                    break;
            }
        }
    }

    // 特殊处理字段
    private void handleOtherField(String field, String itemCondition, Object value, String isOr, EnhancedDynamicQueryBuilder builder) {
        if (equipHandleOtherFields.contains(field)) {
            equipFieldHandle(field, itemCondition, value, isOr, builder);
        } else if (companyHandleOtherFields.contains(field)) {
            companyFieldHandle(field, itemCondition, value, isOr, builder);
        } else if (personHandleOtherFields.contains(field)) {
            personFieldHandle(field, itemCondition, value, isOr, builder);
        }
    }

    private void personFieldHandle(String field, String itemCondition, Object value, String isOr, EnhancedDynamicQueryBuilder builder) {
        if (field.equals("newPost") || field.equals("subPost") || field.equals("equipType") || field.equals("unitType")) {
            if (itemCondition.equals("eq")) {
                builder.add(QueryBuilders.termQuery(field + ".keyword", value), isOr);
            } else if (itemCondition.equals("in")) {
                builder.add(QueryBuilders.wildcardQuery(field + ".keyword", "*" + value + "*"), isOr);
            } else {
                builder.add(QueryBuilders.boolQuery().mustNot(QueryBuilders.wildcardQuery(field + ".keyword", "*" + value + "*")), isOr);
            }
        } else {
            String path = "licenses";
            String nestedField = path + "." + field;
            // 根据证书编号判断有无资质
            if (field.equals("certNo")) {
                NestedQueryBuilder nestedQuery = QueryBuilders.nestedQuery(
                        path,
                        existsQuery(nestedField),
                        ScoreMode.Avg
                );
                // 无资质查询
                BoolQueryBuilder noCertQuery = QueryBuilders.boolQuery()
                        .should(QueryBuilders.wildcardQuery("newPost.keyword", "*66151*"))
                        .should(QueryBuilders.wildcardQuery("newPost.keyword", "*66152*"))
                        .should(QueryBuilders.wildcardQuery("subPost.keyword", "*6712*"))
                        .should(QueryBuilders.wildcardQuery("subPost.keyword", "*6764*"))
                        .should(QueryBuilders.wildcardQuery("subPost.keyword", "*6765*"))
                        .minimumShouldMatch(1);
                // 无资质要求查询
                BoolQueryBuilder noCertRequestQuery = QueryBuilders.boolQuery()
                        .mustNot(QueryBuilders.wildcardQuery("newPost.keyword", "*66151*"))
                        .mustNot(QueryBuilders.wildcardQuery("newPost.keyword", "*66152*"))
                        .mustNot(QueryBuilders.wildcardQuery("subPost.keyword", "*6712*"))
                        .mustNot(QueryBuilders.wildcardQuery("subPost.keyword", "*6764*"))
                        .mustNot(QueryBuilders.wildcardQuery("subPost.keyword", "*6765*"));

                if (value.equals("1")) {
                    if (itemCondition.equals("eq") || itemCondition.equals("in")) {
                        builder.add(nestedQuery, isOr);
                    } else {
                        builder.add(QueryBuilders.boolQuery().mustNot(nestedQuery), isOr);
                    }
                } else if (value.equals("0")) {
                    if (itemCondition.equals("eq") || itemCondition.equals("in")) {
                        builder.add(noCertQuery, isOr);
                    } else {
                        EnhancedDynamicQueryBuilder builders = new EnhancedDynamicQueryBuilder();
                        builders.add(nestedQuery, and);
                        builders.add(noCertRequestQuery, and);
                        builder.add(builders.build(), isOr);
                    }
                } else {
                    if (itemCondition.equals("eq") || itemCondition.equals("in")) {
                        builder.add(noCertRequestQuery, isOr);
                    } else {
                        EnhancedDynamicQueryBuilder builders = new EnhancedDynamicQueryBuilder();
                        builders.add(nestedQuery, and);
                        builders.add(noCertQuery, and);
                        builder.add(builders.build(), isOr);
                    }
                }
            } else if (field.equals("expiryDate")) {
                if (value.equals("overdue")) {
                    if (itemCondition.equals("eq") || itemCondition.equals("in")) {
                        NestedQueryBuilder nestedQuery = QueryBuilders.nestedQuery(
                                path,
                                QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(nestedField).lt(LocalDate.now().format(formatter))),
                                ScoreMode.Avg
                        );
                        builder.add(nestedQuery, isOr);
                    } else {
                        NestedQueryBuilder nestedQuery = QueryBuilders.nestedQuery(
                                path,
                                QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(nestedField).gte(LocalDate.now().format(formatter))),
                                ScoreMode.Avg
                        );
                        builder.add(nestedQuery, isOr);
                    }
                } else if (value.equals("near")) {
                    if (itemCondition.equals("eq") || itemCondition.equals("in")) {
                        NestedQueryBuilder nestedQuery = QueryBuilders.nestedQuery(
                                path,
                                QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(nestedField).lte(LocalDate.now().plusDays(30).format(formatter)).gte(LocalDate.now().format(formatter))),
                                ScoreMode.Avg
                        );
                        builder.add(nestedQuery, isOr);
                    } else {
                        NestedQueryBuilder overdueNestedQuery = QueryBuilders.nestedQuery(
                                path,
                                QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(nestedField).lt(LocalDate.now().format(formatter))),
                                ScoreMode.Avg
                        );
                        NestedQueryBuilder normalNestedQuery = QueryBuilders.nestedQuery(
                                path,
                                QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(nestedField).gt(LocalDate.now().plusDays(30).format(formatter))),
                                ScoreMode.Avg
                        );
                        builder.add(overdueNestedQuery, or);
                        builder.add(normalNestedQuery, or);
                    }
                } else if (value.equals("normal")) {
                    if (itemCondition.equals("eq") || itemCondition.equals("in")) {
                        NestedQueryBuilder nestedQuery = QueryBuilders.nestedQuery(
                                path,
                                QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(nestedField).gt(LocalDate.now().plusDays(30).format(formatter))),
                                ScoreMode.Avg
                        );
                        builder.add(nestedQuery, isOr);
                    } else {
                        NestedQueryBuilder elseNestedQuery = QueryBuilders.nestedQuery(
                                path,
                                QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(nestedField).lte(LocalDate.now().plusDays(30).format(formatter))),
                                ScoreMode.Avg
                        );
                        NestedQueryBuilder noLicensesNestedQuery = QueryBuilders.nestedQuery(
                                path,
                                existsQuery(nestedField),
                                ScoreMode.Avg
                        );
                        builder.add(elseNestedQuery, or);
                    }
                }
            } else {
                NestedQueryBuilder nestedQuery = QueryBuilders.nestedQuery(
                        path,
                        QueryBuilders.wildcardQuery(nestedField, "*" + value + "*"),
                        ScoreMode.Avg
                );
                if (itemCondition.equals("eq")) {
                    NestedQueryBuilder eqNestedQuery = QueryBuilders.nestedQuery(
                            path,
                            QueryBuilders.termQuery(nestedField, value),
                            ScoreMode.Avg
                    );
                    builder.add(eqNestedQuery, isOr);
                } else if (itemCondition.equals("in")) {
                    builder.add(nestedQuery, isOr);
                } else {
                    builder.add(QueryBuilders.boolQuery().mustNot(nestedQuery), isOr);
                }
            }
        }
    }

    private void companyFieldHandle(String field, String itemCondition, Object value, String isOr, EnhancedDynamicQueryBuilder builder) {
        if (field.equals("itemCode") || field.equals("subItemCode") || field.equals("permitStatus")) {
            String path = "licenses";
            String nestedField = path + "." + (field.equals("permitStatus") ? "expiryDate" : field + ".keyword");
            if (field.equals("permitStatus")) {
                if (value.equals("overdue")) {
                    if (itemCondition.equals("eq") || itemCondition.equals("in")) {
                        NestedQueryBuilder nestedQuery = QueryBuilders.nestedQuery(
                                path,
                                QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(nestedField).lt(LocalDate.now().format(formatter))),
                                ScoreMode.Avg
                        );
                        builder.add(QueryBuilders.boolQuery().must(nestedQuery), isOr);
                    } else {
                        NestedQueryBuilder nestedQuery = QueryBuilders.nestedQuery(
                                path,
                                QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(nestedField).gte(LocalDate.now().format(formatter))),
                                ScoreMode.Avg
                        );
                        builder.add(QueryBuilders.boolQuery().must(nestedQuery), isOr);
                    }

                } else if (value.equals("near")) {
                    if (itemCondition.equals("eq") || itemCondition.equals("in")) {
                        NestedQueryBuilder nestedQuery = QueryBuilders.nestedQuery(
                                path,
                                QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(nestedField).lte(LocalDate.now().plusDays(30).format(formatter)).gte(LocalDate.now().format(formatter))),
                                ScoreMode.Avg
                        );
                        builder.add(QueryBuilders.boolQuery().must(nestedQuery), isOr);
                    } else {
                        NestedQueryBuilder overdueNestedQuery = QueryBuilders.nestedQuery(
                                path,
                                QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(nestedField).lt(LocalDate.now().format(formatter))),
                                ScoreMode.Avg
                        );
                        builder.add(QueryBuilders.boolQuery().must(overdueNestedQuery), or);
                        NestedQueryBuilder normalNestedQuery = QueryBuilders.nestedQuery(
                                path,
                                QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(nestedField).gt(LocalDate.now().plusDays(30).format(formatter))),
                                ScoreMode.Avg
                        );
                        builder.add(QueryBuilders.boolQuery().must(normalNestedQuery), or);
                    }
                } else if (value.equals("normal")) {
                    if (itemCondition.equals("eq") || itemCondition.equals("in")) {
                        NestedQueryBuilder nestedQuery = QueryBuilders.nestedQuery(
                                path,
                                QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(nestedField).gt(LocalDate.now().plusDays(30).format(formatter))),
                                ScoreMode.Avg
                        );
                        builder.add(QueryBuilders.boolQuery().must(nestedQuery), isOr);
                    } else {
                        NestedQueryBuilder nestedQuery = QueryBuilders.nestedQuery(
                                path,
                                QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(nestedField).lte(LocalDate.now().plusDays(30).format(formatter))),
                                ScoreMode.Avg
                        );
                        builder.add(QueryBuilders.boolQuery().must(nestedQuery), isOr);
                    }
                }
            } else {
                if (itemCondition.equals("eq") || itemCondition.equals("in")) {
                    // 创建嵌套查询
                    NestedQueryBuilder nestedQuery = QueryBuilders.nestedQuery(
                            path,
                            QueryBuilders.termsQuery(nestedField, value),
                            ScoreMode.Avg
                    );
                    builder.add(QueryBuilders.boolQuery().must(nestedQuery), isOr);
                } else {
                    NestedQueryBuilder nestedQuery = QueryBuilders.nestedQuery(
                            path,
                            QueryBuilders.termsQuery(nestedField, value),
                            ScoreMode.Avg
                    );
                    builder.add(QueryBuilders.boolQuery().mustNot(nestedQuery), isOr);
                }
            }
        } else {
            if (itemCondition.equals("eq")) {
                builder.add(QueryBuilders.termQuery(field + ".keyword", value), isOr);
            } else if (itemCondition.equals("in")) {
                builder.add(QueryBuilders.wildcardQuery(field + ".keyword", "*" + value + "*"), isOr);
            } else {
                builder.add(QueryBuilders.boolQuery().mustNot(QueryBuilders.wildcardQuery(field + ".keyword", "*" + value + "*")), isOr);
            }
        }
    }

    private void equipFieldHandle(String field, String itemCondition, Object value, String isOr, EnhancedDynamicQueryBuilder builder) {
        if (field.equals("NEXT_INSPECT_DATE")) {
            if (value.equals("overdue")) {
                // 超期：小于当前日期
                if (itemCondition.equals("eq") || itemCondition.equals("in")) {
                    builder.add(QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(field).lt(LocalDate.now().format(formatter))), isOr);
                } else {
                    builder.add(QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(field).gt(LocalDate.now().format(formatter))), isOr);
                }
            } else if (value.equals("near")) {
                // 临期：小于等于当前日期加上30天
                if (itemCondition.equals("eq") || itemCondition.equals("in")) {
                    builder.add(QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(field).gte(LocalDate.now().format(formatter)).lte(LocalDate.now().plusDays(30).format(formatter))), isOr);
                } else {
                    builder.add(QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(field).lt(LocalDate.now().format(formatter))), or);
                    builder.add(QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(field).gt(LocalDate.now().plusDays(30).format(formatter))), or);
                }
            } else {
                // 正常：大于当前日期加上30天
                if (itemCondition.equals("eq") || itemCondition.equals("in")) {
                    builder.add(QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(field).gt(LocalDate.now().plusDays(30).format(formatter))), isOr);
                } else {
                    builder.add(QueryBuilders.boolQuery().filter(QueryBuilders.rangeQuery(field).lt(LocalDate.now().plusDays(30).format(formatter))), isOr);
                }
            }
        } else if (field.equals("IS_SUPERVISORY_CODE")) {
            String finalField = "SUPERVISORY_CODE";
            if (value.equals("1")) {
                builder.add(QueryBuilders.boolQuery().must(existsQuery(finalField)).mustNot(QueryBuilders.termsQuery(finalField, "null")), isOr);
            } else {
                builder.add(QueryBuilders.boolQuery().mustNot(existsQuery(finalField)), isOr);
            }
        } else if (field.equals("USC_DATE")) {
            if (value.equals("15")) {
                // 15年以上：大于当前日期减去15年
                if (itemCondition.equals("eq") || itemCondition.equals("in")) {
                    builder.add(QueryBuilders.rangeQuery(field).gt(LocalDate.now().minusYears(15).format(formatter)), isOr);
                } else {
                    builder.add(QueryBuilders.rangeQuery(field).lte(LocalDate.now().minusYears(15).format(formatter)), isOr);
                }
            } else if (value.equals("10-15")) {
                // 10-15年：小于当前日期减去15年，大于等于当前日期减去10年
                if (itemCondition.equals("eq") || itemCondition.equals("in")) {
                    builder.add(QueryBuilders.rangeQuery(field).lt(LocalDate.now().minusYears(15).format(formatter)).gte(LocalDate.now().minusYears(10).format(formatter)), isOr);
                } else {
                    builder.add(QueryBuilders.rangeQuery(field).gte(LocalDate.now().minusYears(15).format(formatter)), or);
                    builder.add(QueryBuilders.rangeQuery(field).lte(LocalDate.now().minusYears(10).format(formatter)), or);
                }
            } else if (value.equals("5-10")) {
                // 5-10年：小于当前日期减去10年，大于等于当前日期减去5年
                if (itemCondition.equals("eq") || itemCondition.equals("in")) {
                    builder.add(QueryBuilders.rangeQuery(field).lt(LocalDate.now().minusYears(10).format(formatter)).gte(LocalDate.now().minusYears(5).format(formatter)), isOr);
                } else {
                    builder.add(QueryBuilders.rangeQuery(field).gte(LocalDate.now().minusYears(10).format(formatter)), or);
                    builder.add(QueryBuilders.rangeQuery(field).lte(LocalDate.now().minusYears(5).format(formatter)), or);
                }
            } else if (value.equals("0-5")) {
                // 0-5年：小于当前日期减去5年
                if (itemCondition.equals("eq") || itemCondition.equals("in")) {
                    builder.add(QueryBuilders.rangeQuery(field).lt(LocalDate.now().minusYears(5).format(formatter)), isOr);
                } else {
                    builder.add(QueryBuilders.rangeQuery(field).gte(LocalDate.now().minusYears(5).format(formatter)), isOr);
                }
            }
        } else if (field.equals("createDate")) {
            JSONArray createDates = (JSONArray) value;
            String startDate = DateUtils.convertDateToString(createDates.getDate(0), DateUtils.DATE_TIME_PATTERN);
            String endDate = DateUtils.convertDateToString(createDates.getDate(1), DateUtils.DATE_TIME_PATTERN);
            builder.add(QueryBuilders.rangeQuery("createDate").gte(startDate.replace(" ", "T")).lte(endDate.replace(" ", "T")), isOr);
        }
    }


    public JSONArray queryUnitType() {
        return UnitTypeEnum.getAll();
    }

    public JSONObject queryCompanySearchData() {
        JSONObject result = new JSONObject();
        //获取企业类型
        result.put("unitType", UnitTypeEnum.getAll());

        //获取企业等级
        result.put("regulatoryLabels", deployDictionary(dataDictionaryService.getByType("QYBQ")));

        //行业主管部门
        result.put("industrySupervisor", deployDictionary(dataDictionaryService.getByType("HYZGBM")));
        //经营状态
        result.put("operatingStatus", deployDictionaryNew(dataDictionaryService.getByType("jyzt")));

        //许可状态
        JSONArray permitStatusData = new JSONArray();
        for (int i = 0; i < 3; i++) {
            JSONObject object = new JSONObject();
            if (0 == i) {
                object.put("key", "overdue");
                object.put("value", "overdue");
                object.put("label", "超期");
            } else if (1 == i) {
                object.put("key", "near");
                object.put("value", "near");
                object.put("label", "临期");
            } else {
                object.put("key", "normal");
                object.put("value", "normal");
                object.put("label", "正常");
            }
            permitStatusData.add(object);
        }
        result.put("permitStatus", permitStatusData);

        //监管设备类型
        List<EquipmentCategoryDto> equipmentCategoryDtos = equipmentCategoryMapper.selectClassify();
        JSONArray equipCategoryData = new JSONArray();
        for (int i = 0; i < equipmentCategoryDtos.size(); i++) {
            JSONObject object = new JSONObject();
            object.put("key", equipmentCategoryDtos.get(i).getCode());
            object.put("value", equipmentCategoryDtos.get(i).getCode());
            object.put("label", equipmentCategoryDtos.get(i).getName());
            equipCategoryData.add(object);
        }
        result.put("equipCategory", equipCategoryData);

        return result;
    }

    public JSONObject queryPersonSearchData() {
        JSONObject result = new JSONObject();
        //有无资质
        JSONArray certNoData = new JSONArray();
        for (int i = 0; i < 2; i++) {
            JSONObject object = new JSONObject();
            if (0 == i) {
                object.put("key", "2");
                object.put("value", "2");
                object.put("label", "无资质要求");
            } else if (1 == i) {
                object.put("key", "1");
                object.put("value", "1");
                object.put("label", "有资质");
            } else if (2 == i) {
                object.put("key", "0");
                object.put("value", "0");
                object.put("label", "无资质");
            }
            certNoData.add(object);
        }
        result.put("certNo", certNoData);
        //资质状态
        JSONArray permissionStatus = new JSONArray();
        for (int i = 0; i < 2; i++) {
            JSONObject object = new JSONObject();
            if (0 == i) {
                object.put("key", "overdue");
                object.put("value", "overdue");
                object.put("label", "资质超期");
            } else if (1 == i) {
                object.put("key", "near");
                object.put("value", "near");
                object.put("label", "资质临期");
            } else {
                object.put("key", "normal");
                object.put("value", "normal");
                object.put("label", "正常");
            }
            permissionStatus.add(object);
        }
        result.put("expiryDate", permissionStatus);
        //证书类型
        List<DictionarieValueModel> certType = Systemctl.dictionarieClient.dictValues("CERT_TYPE").getResult();
        JSONArray certTypeArray = new JSONArray();
        for (int i = 0; i < certType.size(); i++) {
            JSONObject object = new JSONObject();
            object.put("key", certType.get(i).getDictDataKey());
            object.put("value", certType.get(i).getDictDataKey());
            object.put("label", certType.get(i).getDictDataValue());
            certTypeArray.add(object);
        }
        result.put("certType", certTypeArray);
        //证书级别
        List<DictionarieValueModel> RYJB_JC = Systemctl.dictionarieClient.dictValues("RYJB_JC").getResult();
        List<DictionarieValueModel> RYJB_JY = Systemctl.dictionarieClient.dictValues("RYJB_JY").getResult();
        JSONArray permissionLevelArray = new JSONArray();
        for (int i = 0; i < RYJB_JC.size(); i++) {
            JSONObject object = new JSONObject();
            object.put("key", RYJB_JC.get(i).getDictDataKey());
            object.put("value", RYJB_JC.get(i).getDictDataKey());
            object.put("label", RYJB_JC.get(i).getDictDataValue());
            permissionLevelArray.add(object);
        }
        for (int i = 0; i < RYJB_JY.size(); i++) {
            JSONObject object = new JSONObject();
            object.put("key", RYJB_JY.get(i).getDictDataKey());
            object.put("value", RYJB_JY.get(i).getDictDataKey());
            object.put("label", RYJB_JY.get(i).getDictDataValue());
            permissionLevelArray.add(object);
        }
        result.put("permissionLevel", permissionLevelArray);
        //学历
        result.put("education", deployDictionary(dataDictionaryService.getByType("QYRYXL")));
        //监管设备类型
        List<EquipmentCategoryDto> equipmentCategoryDtos = equipmentCategoryMapper.selectClassify();
        JSONArray equipCategoryData = new JSONArray();
        for (int i = 0; i < equipmentCategoryDtos.size(); i++) {
            JSONObject object = new JSONObject();
            object.put("key", equipmentCategoryDtos.get(i).getCode());
            object.put("value", equipmentCategoryDtos.get(i).getCode());
            object.put("label", equipmentCategoryDtos.get(i).getName());
            equipCategoryData.add(object);
        }
        result.put("equipType", equipCategoryData);
        //获取企业类型
        result.put("unitType", UnitTypeEnum.getAll());
        return result;
    }

    public JSONArray deployDictionary(List<DataDictionary> list) {
        JSONArray result = new JSONArray();
        for (int i = 0; i < list.size(); i++) {
            JSONObject object = new JSONObject();
            object.put("key", list.get(i).getCode());
            object.put("value", list.get(i).getCode());
            object.put("label", list.get(i).getName());
            result.add(object);
        }

        return result;
    }

    /**
     * 特殊处理字典，value为name
     *
     * @param list
     * @return
     */
    public JSONArray deployDictionaryNew(List<DataDictionary> list) {
        JSONArray result = new JSONArray();
        for (int i = 0; i < list.size(); i++) {
            JSONObject object = new JSONObject();
            object.put("key", list.get(i).getCode());
            object.put("value", list.get(i).getName());
            object.put("label", list.get(i).getName());
            result.add(object);
        }

        return result;
    }

    public JSONArray queryXK(String type) {
        JSONArray result = new JSONArray();
        if (ValidationUtil.isEmpty(type)) {
            List<DataDictionary> xkxm = dataDictionaryService.lambdaQuery().like(DataDictionary::getType, "XKXM").eq(BaseEntity::getIsDelete, false).list();
            result = deployDictionary(xkxm);
        } else {
            List<DataDictionary> childrenxkxm = dataDictionaryService.lambdaQuery().eq(DataDictionary::getTypeDesc, type).eq(BaseEntity::getIsDelete, false).list();
            result = deployDictionary(childrenxkxm);
        }
        return result;
    }


    public JSONArray queryRYLX(String type) {
        JSONArray result = new JSONArray();
        if (ValidationUtil.isEmpty(type)) {
            List<String> typeList = new ArrayList<>(Arrays.asList(
                    "QYRYGW",
                    "QYRYGW-SYDW",
                    "QYRYGW-SCDW",
                    "QYRYGW-INSTALL",
                    "QYRYGW-INSPECTION"
            ));
            result = deployDictionary(dataDictionaryService.lambdaQuery()
                    .select(DataDictionary::getName, DataDictionary::getCode)
                    .eq(DataDictionary::getIsDelete, false)
                    .isNull(DataDictionary::getParent)
                    .in(DataDictionary::getType, typeList)
                    .list());
        } else {
            List<DataDictionary> childrenrylx = dataDictionaryService.lambdaQuery()
                    .in(DataDictionary::getParent, type)
                    .like(DataDictionary::getType, "QYRYGW")
                    .orderByAsc(DataDictionary::getSortNum)
                    .list();
            ;
            result = deployDictionary(childrenrylx);
        }
        return result;
    }

    /**
     * 开始下载 发送消息
     */
    public void startDownLoadMsg(String fileName, String uuid) {
        try {
            emqKeeper.getMqttClient().publish(String.format(DOWNLOAD_TOPIC, RequestContext.getToken()),
                    String.format(DOWN_LOAD_START_TEMP, uuid, fileName, new Date().getTime()).getBytes(StandardCharsets.UTF_8),
                    2, false);
        } catch (Exception e) {
            log.error(e.getMessage());
        }
    }

    /**
     * 发送主题消息，给企业推送excel 结束下载提醒
     *
     * @param topic      主体格式为： /download/excel/${token}
     * @param jsonObject 文件名称 + excel文件路径（minio）
     */
    public void sendDownLoadExcelMsg(String topic, JSONObject jsonObject) {
        try {
            emqKeeper.getMqttClient().publish(topic, JSONObject.toJSONString(jsonObject).getBytes(StandardCharsets.UTF_8), 2, false);
        } catch (Exception e) {
            log.error(e.getMessage());
        }
    }

    /**
     * 综合统计分析接口-导出
     *
     * @param uuid   uuid
     * @param filter 过滤条件
     */
    public void export(String uuid, JSONObject filter) {
        // 查询数据
        JSONObject jsonData = this.queryForPage(filter);
        // 类型转化
        List<EquipInfoVo> exportData = JSONArray.parseArray(JSON.toJSONString(jsonData.get("pageData")), EquipInfoVo.class);
        // 转化附件
        MultipartFile templateExcelFile = ExcelUtil.createTemplateExcelFile("综合统计分析设备列表数据",
                "综合统计分析设备列表", exportData, EquipInfoVo.class, null, false);
        // 上传minio服务器
        String urlString = MinioUtils.uploadExcelFile(templateExcelFile, BUCKET_NAME, UPLOAD_PATH);
        // 提醒下载
        this.sendDownLoadExcelMsg(String.format(DOWNLOAD_TOPIC, RequestContext.getToken()), new JSONObject()
                .fluentPut("id", uuid)
                .fluentPut("status", "done")
                .fluentPut("fileName", "综合统计分析设备列表")
                .fluentPut("url", urlString)
                .fluentPut("time", new Date().getTime()));
    }

    public JSONArray queryZYXM(String type) {
        JSONArray result = new JSONArray();
        if ("特种设备安全管理和作业人员证".equals(type)) {
            List<DictionarieValueModel> certType = Systemctl.dictionarieClient.dictValues("JOB_ITEM").getResult();
            for (DictionarieValueModel certTypeModel : certType) {
                JSONObject jsonObject = new JSONObject();
                jsonObject.put("key", certTypeModel.getDictDataKey());
                jsonObject.put("value", certTypeModel.getDictDataKey());
                jsonObject.put("label", certTypeModel.getDictDataValue());
                result.add(jsonObject);
            }
        } else {
            List<DictionarieValueModel> certType = Systemctl.dictionarieClient.dictValues("ZZXM_" + type).getResult();
            for (DictionarieValueModel certTypeModel : certType) {
                JSONObject jsonObject = new JSONObject();
                jsonObject.put("key", certTypeModel.getDictDataKey());
                jsonObject.put("value", certTypeModel.getDictDataKey());
                jsonObject.put("label", certTypeModel.getDictDataValue());
                result.add(jsonObject);
            }
        }
        return result;
    }

    public JSONArray queryUnitByOrgCode(String orgCode) {
        SearchRequest searchRequest = new SearchRequest("idx_biz_enterprise_info");
        SearchSourceBuilder searchSourceBuilder = new SearchSourceBuilder();
        BoolQueryBuilder boolQueryBuilder = QueryBuilders.boolQuery();
        boolQueryBuilder.must(QueryBuilders.wildcardQuery("superviseOrgCode.keyword", QueryParser.escape(orgCode) + "*"));
        searchSourceBuilder.query(boolQueryBuilder);
        searchRequest.source(searchSourceBuilder);

        JSONArray result = new JSONArray();
        try {
            SearchResponse searchResponse = restHighLevelClient.search(searchRequest, RequestOptions.DEFAULT);
            for (SearchHit hit : searchResponse.getHits().getHits()) {
                JSONObject jsonObject = ((JSONObject) JSONObject.toJSON(hit)).getJSONObject("sourceAsMap");
                JSONObject dto = new JSONObject();
                dto.put("key", jsonObject.getString("useCode"));
                dto.put("value", jsonObject.getString("useCode"));
                dto.put("label", jsonObject.getString("useUnit"));
                result.add(dto);
            }
        } catch (IOException e) {
            throw new RuntimeException(e);
        }

        return result;
    }

    public JSONArray queryEquipList() {
        List<EquipmentCategoryDto> equipmentCategoryDtos = equipmentCategoryMapper.selectClassify();
        JSONArray equipCategoryData = new JSONArray();
        for (int i = 0; i < equipmentCategoryDtos.size(); i++) {
            JSONObject object = new JSONObject();
            object.put("key", equipmentCategoryDtos.get(i).getCode());
            object.put("value", equipmentCategoryDtos.get(i).getCode());
            object.put("label", equipmentCategoryDtos.get(i).getName());
            equipCategoryData.add(object);
        }
        return equipCategoryData;
    }

    public JSONArray queryEquCategory(String type) {
        JSONArray result = tzsCustomFilterMapper.queryEquCategory(type, "EQU_CATEGORY");
        return result;
    }

    public JSONArray queryEquDefine(String type) {
        JSONArray result = tzsCustomFilterMapper.queryEquCategory(type, "EQU_DEFINE");
        return result;
    }

    public JSONArray queryEquState() {
        return EquipStateEnum.getAll();
    }

    public JSONArray queryIsSupervisoryCode() {
        return IsSupervisoryCodeEnum.getAll();
    }

    public JSONArray queryDataQualityScore() {
        return DataQualityScoreEnum.getAll();
    }

    public JSONArray queryUscDate() {
        return UscDateEnum.getAll();
    }

    public JSONArray queryTechParam(String type) {
        if(ValidationUtil.isEmpty(type)){
            throw new BadRequest("需要先选择设备品种，才能选择技术参数");
        }
        List<TechParamItem> paramMetaList = TechParamUtil.getParamMetaList(type);
        JSONArray list = new JSONArray();
        for (int i = 0; i < paramMetaList.size(); i++) {
            JSONObject object = new JSONObject();
            object.put("key", paramMetaList.get(i).getParamKey());
            object.put("value", paramMetaList.get(i).getParamKey());
            object.put("label", paramMetaList.get(i).getParamLabel());
            object.put("fieldType", paramMetaList.get(i).getParamType());
            list.add(object);
        }
        return list;
    }

    public JSONArray queryCertType() {
        //证书类型
        List<DictionarieValueModel> certType = Systemctl.dictionarieClient.dictValues("CERT_TYPE").getResult();
        JSONArray certTypeArray = new JSONArray();
        for (int i = 0; i < certType.size(); i++) {
            JSONObject object = new JSONObject();
            object.put("key", certType.get(i).getDictDataKey());
            object.put("value", certType.get(i).getDictDataKey());
            object.put("label", certType.get(i).getDictDataValue());
            certTypeArray.add(object);
        }
        return certTypeArray;
    }

    public JSONArray queryPermissionLevel() {
        //证书级别
        List<DictionarieValueModel> RYJB_JC = Systemctl.dictionarieClient.dictValues("RYJB_JC").getResult();
        List<DictionarieValueModel> RYJB_JY = Systemctl.dictionarieClient.dictValues("RYJB_JY").getResult();
        JSONArray permissionLevelArray = new JSONArray();
        for (int i = 0; i < RYJB_JC.size(); i++) {
            JSONObject object = new JSONObject();
            object.put("key", RYJB_JC.get(i).getDictDataKey());
            object.put("value", RYJB_JC.get(i).getDictDataKey());
            object.put("label", RYJB_JC.get(i).getDictDataValue());
            permissionLevelArray.add(object);
        }
        for (int i = 0; i < RYJB_JY.size(); i++) {
            JSONObject object = new JSONObject();
            object.put("key", RYJB_JY.get(i).getDictDataKey());
            object.put("value", RYJB_JY.get(i).getDictDataKey());
            object.put("label", RYJB_JY.get(i).getDictDataValue());
            permissionLevelArray.add(object);
        }
        return permissionLevelArray;
    }

    public JSONArray queryCertNo() {
        JSONArray certNoData = new JSONArray();
        for (int i = 0; i < 3; i++) {
            JSONObject object = new JSONObject();
            if (0 == i) {
                object.put("key", "2");
                object.put("value", "2");
                object.put("label", "无资质要求");
            } else if (1 == i) {
                object.put("key", "1");
                object.put("value", "1");
                object.put("label", "有资质");
            } else if (2 == i) {
                object.put("key", "0");
                object.put("value", "0");
                object.put("label", "无资质");
            }
            certNoData.add(object);
        }
        return certNoData;
    }

    public JSONArray queryExpiryDate() {
        //资质状态
        JSONArray permissionStatus = new JSONArray();
        for (int i = 0; i < 3; i++) {
            JSONObject object = new JSONObject();
            if (0 == i) {
                object.put("key", "overdue");
                object.put("value", "overdue");
                object.put("label", "资质超期");
            } else if (1 == i) {
                object.put("key", "near");
                object.put("value", "near");
                object.put("label", "资质临期");
            } else {
                object.put("key", "normal");
                object.put("value", "normal");
                object.put("label", "正常");
            }
            permissionStatus.add(object);
        }
        return permissionStatus;
    }
}