package cn.cslg.pas.service.business.es; import cn.cslg.pas.common.core.base.IfConstant; import cn.cslg.pas.common.dto.es.EsCustomFieldValueDTO; import cn.cslg.pas.common.dto.es.EsValueCurveDTO; import cn.cslg.pas.common.dto.es.SelectValueCurveDTO; import cn.cslg.pas.common.model.cronModel.PersonnelVO; import cn.cslg.pas.common.model.cronModel.Records; import cn.cslg.pas.common.model.request.OrderDTO; import cn.cslg.pas.common.utils.CacheUtils; import cn.cslg.pas.common.utils.LoginUtils; import cn.cslg.pas.common.utils.parseQueryToTree.expressManager; import cn.cslg.pas.common.utils.parseQueryToTree.operateNode; import cn.cslg.pas.common.utils.parseQueryToTree.treeNode; import cn.cslg.pas.common.vo.EsConfigVO; import cn.cslg.pas.common.vo.es.EsCustomFieldBatchVO; import cn.cslg.pas.common.vo.es.EsValueCurveVO; import cn.cslg.pas.domain.BaseEntity; import cn.cslg.pas.domain.business.PermissionRecord; import cn.cslg.pas.domain.business.Product; import cn.cslg.pas.domain.business.ProductMarketData; import cn.cslg.pas.domain.es.Patent; import cn.cslg.pas.exception.XiaoShiException; import cn.cslg.pas.mapper.PermissionRecordMapper; import cn.cslg.pas.mapper.ProductMapper; import cn.cslg.pas.mapper.ProductMarketDataMapper; import cn.cslg.pas.service.business.CommonService; import cn.cslg.pas.service.query.FormatQueryService; import co.elastic.clients.elasticsearch.ElasticsearchClient; import co.elastic.clients.elasticsearch._types.SortOrder; import co.elastic.clients.elasticsearch._types.query_dsl.Query; import co.elastic.clients.elasticsearch._types.query_dsl.QueryBuilders; import co.elastic.clients.elasticsearch.core.SearchRequest; import co.elastic.clients.elasticsearch.core.SearchResponse; import co.elastic.clients.elasticsearch.core.search.Hit; import com.alibaba.fastjson.JSON; import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper; import lombok.RequiredArgsConstructor; import org.apache.commons.lang3.StringUtils; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.context.annotation.Lazy; import org.springframework.stereotype.Service; import org.springframework.util.CollectionUtils; import java.io.IOException; import java.math.BigDecimal; import java.text.SimpleDateFormat; import java.util.ArrayList; import java.util.HashMap; import java.util.List; import java.util.Map; import java.util.stream.Collectors; @Service @RequiredArgsConstructor(onConstructor_ = {@Lazy}) public class EsValueCurveService { private final ElasticsearchClient client; @Autowired private CacheUtils cacheUtils; @Autowired private LoginUtils loginUtils; @Autowired private EsService esService; @Autowired private FormatQueryService formatQueryService; @Autowired private ProductMarketDataMapper productMarketDataMapper; @Autowired private PermissionRecordMapper permissionRecordMapper; @Autowired private ProductMapper productMapper; /** * 查询价值曲线 * @param vo * @return * @throws Exception */ public List selectValueCurve(EsValueCurveVO vo) throws Exception { List isAdd = vo.getIsAdd(); List isDel = vo.getIsDelete(); Integer startNum = vo.getStartNumber(); Integer endNum = vo.getEndNumber(); Integer timeType = vo.getTimeType(); //获取登陆人信息 用于设置创建人 PersonnelVO personnelVO = new PersonnelVO(); try { personnelVO = cacheUtils.getLoginUser(loginUtils.getId()); } catch (Exception e) { throw new XiaoShiException("未登录"); } Integer tenantId = personnelVO.getTenantId(); Map> map = new HashMap<>(); if (!CollectionUtils.isEmpty(isAdd) && startNum <= 1 && endNum < 1) { isAdd.removeAll(isDel); map = this.getProductIdByPatentNo(isAdd,tenantId); } else if (startNum >= 1 && endNum > 0) { List patentNos = this.getPatentNos(vo); map = this.getProductIdByPatentNo(patentNos,tenantId); } return this.getValueCurveList(map, timeType,tenantId); } /** * 提取返回数据 * * @param map * @param timeType * @return */ public List getValueCurveList(Map> map, Integer timeType, Integer tenantId) { List curveDTOS = new ArrayList<>(); if (!CollectionUtils.isEmpty(map)) { for (String patentNo : map.keySet()) { List listLicensee = new ArrayList<>(); List listSale = new ArrayList<>(); //获取许可记录 List licenseeList = this.selectLicensee(patentNo, timeType,tenantId); if (!CollectionUtils.isEmpty(licenseeList)) { Map> licenseeMap = licenseeList.stream().collect(Collectors.groupingBy(SelectValueCurveDTO::getLicenseTime)); for (String key : licenseeMap.keySet()) { List licenseeDTOS = licenseeMap.get(key); BigDecimal sum = new BigDecimal(0); for (SelectValueCurveDTO licenseeDTO : licenseeDTOS) { BigDecimal licenseeFee = new BigDecimal(String.valueOf(licenseeDTO.getLicenseFee())); sum = sum.add(licenseeFee); } SelectValueCurveDTO curveDTO = new SelectValueCurveDTO(); if (sum.compareTo(new BigDecimal(0)) > 0) { curveDTO.setLicenseFee(sum.doubleValue()); } curveDTO.setLicenseTime(key); curveDTO.setTimeType(licenseeDTOS.get(0).getTimeType()); listLicensee.add(curveDTO); } } //获取营销数据 List productIds = map.get(patentNo); if (!CollectionUtils.isEmpty(productIds)) { List saleList = this.selectSale(productIds, timeType); if (!CollectionUtils.isEmpty(saleList)) { Map> saleMap = saleList.stream().collect(Collectors.groupingBy(SelectValueCurveDTO::getSaleTime)); for (String key : saleMap.keySet()) { List saleLDTOS = saleMap.get(key); //销售额 BigDecimal count = new BigDecimal(0); //自定义许可费 BigDecimal sum = new BigDecimal(0); for (SelectValueCurveDTO saleLDTO : saleLDTOS) { BigDecimal customLicensee = new BigDecimal(String.valueOf(saleLDTO.getCustomLicense())); sum = sum.add(customLicensee); BigDecimal saleMoney = new BigDecimal(String.valueOf(saleLDTO.getSaleMoney())); count = count.add(saleMoney); } SelectValueCurveDTO curveDTO = new SelectValueCurveDTO(); if (sum.compareTo(new BigDecimal(0)) > 0) { curveDTO.setLicenseFee(sum.doubleValue()); } if (count.compareTo(new BigDecimal(0)) > 0) { curveDTO.setCustomLicense(count.doubleValue()); } curveDTO.setSaleTime(key); curveDTO.setSaleArea(saleLDTOS.get(0).getSaleArea()); curveDTO.setTimeType(saleLDTOS.get(0).getTimeType()); listSale.add(curveDTO); } } } List data = this.mergeData(listLicensee, listSale); curveDTOS.addAll(data); } } return curveDTOS; } /** * 提取合并数据 * @param listLicensee * @param listSale * @return */ public List mergeData(List listLicensee,List listSale) { List list = new ArrayList<>(); if (!CollectionUtils.isEmpty(listLicensee) && !CollectionUtils.isEmpty(listSale)) { for (SelectValueCurveDTO licensee : listLicensee) { String licenseTime = licensee.getLicenseTime(); for (SelectValueCurveDTO sale : listSale) { String saleTime = sale.getSaleTime(); if (licenseTime.equals(saleTime)) { EsValueCurveDTO dto = new EsValueCurveDTO(); dto.setSaleArea(sale.getSaleArea()); dto.setSaleMoney(sale.getSaleMoney()); dto.setCustomLicense(sale.getCustomLicense()); dto.setTime(saleTime); dto.setLicenseFee(licensee.getLicenseFee()); dto.setTimeType(sale.getTimeType()); list.add(dto); } } } } else if (!CollectionUtils.isEmpty(listLicensee) && CollectionUtils.isEmpty(listSale)) { for (SelectValueCurveDTO licensee : listLicensee) { EsValueCurveDTO dto = new EsValueCurveDTO(); dto.setTime(licensee.getLicenseTime()); dto.setLicenseFee(licensee.getLicenseFee()); dto.setTimeType(licensee.getTimeType()); list.add(dto); } } else if (!CollectionUtils.isEmpty(listSale) && CollectionUtils.isEmpty(listLicensee)) { for (SelectValueCurveDTO sale : listSale) { EsValueCurveDTO dto = new EsValueCurveDTO(); dto.setSaleArea(sale.getSaleArea()); dto.setSaleMoney(sale.getSaleMoney()); dto.setCustomLicense(sale.getCustomLicense()); dto.setTime(sale.getSaleTime()); dto.setTimeType(sale.getTimeType()); list.add(dto); } } if (!CollectionUtils.isEmpty(list)) { for (EsValueCurveDTO dto : list) { listLicensee.removeIf(licensee -> licensee.getLicenseTime().equals(dto.getTime())); } for (EsValueCurveDTO dto : list) { listSale.removeIf(sale -> sale.getSaleTime().equals(dto.getTime())); } if (!CollectionUtils.isEmpty(listLicensee)) { for (SelectValueCurveDTO licensee : listLicensee) { EsValueCurveDTO dto = new EsValueCurveDTO(); dto.setTime(licensee.getLicenseTime()); dto.setLicenseFee(licensee.getLicenseFee()); dto.setTimeType(licensee.getTimeType()); list.add(dto); } } if (!CollectionUtils.isEmpty(listSale)) { for (SelectValueCurveDTO sale : listSale) { EsValueCurveDTO dto = new EsValueCurveDTO(); dto.setSaleArea(sale.getSaleArea()); dto.setSaleMoney(sale.getSaleMoney()); dto.setCustomLicense(sale.getCustomLicense()); dto.setTime(sale.getSaleTime()); dto.setTimeType(sale.getTimeType()); list.add(dto); } } } return list; } /** * 查询营销数据 * @param productIds * @param timeType * @return */ public List selectSale(List productIds, Integer timeType) { List curveDTOS = new ArrayList<>(); if (timeType == 0) { curveDTOS = productMarketDataMapper.selectSaleMonthList(productIds); if (!CollectionUtils.isEmpty(curveDTOS)) { curveDTOS.forEach(i -> i.setTimeType(timeType)); } } else if (timeType == 2) { curveDTOS = productMarketDataMapper.selectSaleYearList(productIds); if (!CollectionUtils.isEmpty(curveDTOS)) { curveDTOS.forEach(i -> i.setTimeType(timeType)); } } else { curveDTOS = productMarketDataMapper.selectSaleQuarterList(productIds); if (!CollectionUtils.isEmpty(curveDTOS)) { curveDTOS.forEach(i -> i.setTimeType(timeType)); } } return curveDTOS; } /** * 查询许可记录 * @param patentNo * @param timeType * @return */ public List selectLicensee(String patentNo, Integer timeType,Integer tenantId) { List curveDTOS = new ArrayList<>(); if (timeType == 0) { curveDTOS = permissionRecordMapper.selectLicenseeMonthList(patentNo,tenantId); if (!CollectionUtils.isEmpty(curveDTOS)) { curveDTOS.forEach(i -> i.setTimeType(timeType)); } } else if (timeType == 2) { curveDTOS = permissionRecordMapper.selectLicenseeYearList(patentNo,tenantId); if (!CollectionUtils.isEmpty(curveDTOS)) { curveDTOS.forEach(i -> i.setTimeType(timeType)); } } else { curveDTOS = permissionRecordMapper.selectLicenseeQuarterList(patentNo,tenantId); if (!CollectionUtils.isEmpty(curveDTOS)) { curveDTOS.forEach(i -> i.setTimeType(timeType)); } } return curveDTOS; } /** * 获取专利号列表 * * @param vo * @return * @throws Exception */ public List getPatentNos(EsValueCurveVO vo) throws Exception { Integer taskId = vo.getTaskId(); Integer projectId = vo.getProjectId(); Integer startNum = vo.getStartNumber(); Integer endNum = vo.getEndNumber(); List isAdd = new ArrayList<>(); if (!CollectionUtils.isEmpty(vo.getIsAdd())) { isAdd = vo.getIsAdd(); } List isDel = new ArrayList<>(); if (!CollectionUtils.isEmpty(vo.getIsDelete())) { isDel = vo.getIsDelete(); } String searchCondition = ""; if (StringUtils.isNotEmpty(vo.getSearchQuery())) { searchCondition = vo.getSearchQuery(); } List customFields = vo.getCustomFields(); if (!CollectionUtils.isEmpty(customFields)) { searchCondition = esService.parseCustomField(customFields, projectId, taskId); } if (taskId != null) { if (searchCondition != null && !"".equals(searchCondition.trim())) { searchCondition = "taskId = " + taskId + " AND " + searchCondition; } else { searchCondition = "taskId = " + taskId; } } else { if (projectId != null) { if (searchCondition != null && !"".equals(searchCondition.trim())) { searchCondition = "projectId = " + projectId + " AND " + searchCondition; } else { searchCondition = "projectId = " + projectId; } } } SearchRequest.Builder builder = new SearchRequest.Builder(); //设置查询索引 builder.index("patent"); //1. 解析检索条件 treeNode tree = expressManager.getInstance().Parse(searchCondition, false); //格式化检索式 //3. 从es中检索数据 Query q = formatQueryService.EsQueryToQuery((operateNode) tree, "patent"); builder.query(q); List dtoList = vo.getOrderDTOList(); if (!CollectionUtils.isEmpty(dtoList)) { String json = CommonService.readJsonFile("patent.json"); List esConfigVOS = JSON.parseArray(json, EsConfigVO.class); for (OrderDTO orderDTO : dtoList) { EsConfigVO configVO = esConfigVOS.stream().filter(item -> item.getField().equals(orderDTO.getOrderBy())).findFirst().orElse(null); if (configVO != null) { if (orderDTO.getOrderType().equals(IfConstant.NO)) { builder.sort(sortOptionsBuilder -> sortOptionsBuilder .field(fieldSortBuilder -> fieldSortBuilder .field(configVO.getEsField()).order(SortOrder.Asc))); } else { builder.sort(sortOptionsBuilder -> sortOptionsBuilder .field(fieldSortBuilder -> fieldSortBuilder .field(configVO.getEsField()).order(SortOrder.Desc))); } } } } else { builder.sort(sortOptionsBuilder -> sortOptionsBuilder .field(fieldSortBuilder -> fieldSortBuilder .field("patent_no.keyword").order(SortOrder.Desc))); } int number = endNum - startNum; if (startNum > 0 && endNum > startNum) { builder.from(startNum - 1).size(number); } SearchResponse response = client.search(builder.build(), Patent.class); List> hits = response.hits().hits(); List patentNos = new ArrayList<>(); for (Hit hit : hits) { Patent patent = hit.source(); patentNos.add(patent.getPatentNo()); } patentNos.addAll(isAdd); patentNos.removeAll(isDel); return patentNos.stream().distinct().collect(Collectors.toList()); } /** * 根据专利号获取productId * @param list * @return * @throws IOException */ public Map> getProductIdByPatentNo(List list,Integer tenantId) throws IOException { Map> map = new HashMap<>(); if (!CollectionUtils.isEmpty(list)) { for (String patentNo : list) { List productIds = new ArrayList<>(); SearchRequest.Builder builder = new SearchRequest.Builder(); //设置查询索引 builder.index("patent"); //申请号 Query q1 = QueryBuilders.term(t -> t.field("app_no.keyword").value(patentNo)); //公开号 Query q2 = QueryBuilders.term(t -> t.field("public_no.keyword").value(patentNo)); //授权号 Query q3 = QueryBuilders.term(t -> t.field("grant_no.keyword").value(patentNo)); Query bool = QueryBuilders.bool(i -> i.should(q1, q2, q3)); Query q = QueryBuilders.exists(i -> i.field("product_id")); Query query = QueryBuilders.hasParent(parent -> parent.parentType("patent").query(bool)); Query bool1 = QueryBuilders.bool(i -> i.must(q,query)); builder.query(bool1); SearchResponse response = client.search(builder.build(), Patent.class); List> hits = response.hits().hits(); for (Hit hit : hits) { Patent patent = hit.source(); if (patent.getProductId() != null) { productIds.add(patent.getProductId()); } } List ids = new ArrayList<>(); List collect = productIds.stream().distinct().collect(Collectors.toList()); List products = productMapper.selectBatchIds(collect); if (!CollectionUtils.isEmpty(products)) { ids = products.stream().filter(i -> i.getTenantId().equals(tenantId)).map(BaseEntity::getId).collect(Collectors.toList()); } map.put(patentNo, ids); } } return map; } }