diff --git a/cf-module-prod-executor/cf-module-prod-executor-biz/src/main/java/com/cf/imes/module/executor/dal/dataobject/ordermodel/OrderModelDO.java b/cf-module-prod-executor/cf-module-prod-executor-biz/src/main/java/com/cf/imes/module/executor/dal/dataobject/ordermodel/OrderModelDO.java index 246dd253a..cace4ab22 100644 --- a/cf-module-prod-executor/cf-module-prod-executor-biz/src/main/java/com/cf/imes/module/executor/dal/dataobject/ordermodel/OrderModelDO.java +++ b/cf-module-prod-executor/cf-module-prod-executor-biz/src/main/java/com/cf/imes/module/executor/dal/dataobject/ordermodel/OrderModelDO.java @@ -3,6 +3,7 @@ package com.cf.imes.module.executor.dal.dataobject.ordermodel; import com.alibaba.fastjson.JSONObject; import com.cf.imes.framework.es.core.dal.ESDocument; import com.cf.imes.module.executor.util.deviseData.structure.*; +import com.fasterxml.jackson.annotation.JsonInclude; import io.swagger.v3.oas.annotations.media.Schema; import lombok.AllArgsConstructor; import lombok.Builder; @@ -21,6 +22,7 @@ import java.util.Map; @Builder @AllArgsConstructor @NoArgsConstructor +@JsonInclude(JsonInclude.Include.NON_NULL) public class OrderModelDO extends ESDocument { @Schema(description = "生产单id") @@ -116,6 +118,4 @@ public class OrderModelDO extends ESDocument { private String remarkJson; // 普通备注(板材数据中) @Schema(description = "特殊备注(板材数据中)") private String specialRemark; // 特殊备注(板材数据中) - - private Long sortId; } \ No newline at end of file diff --git a/cf-module-prod-plan/cf-module-prod-plan-biz/src/main/java/com/cf/imes/module/plan/dal/dataobject/ordermodel/OrderModelDO.java b/cf-module-prod-plan/cf-module-prod-plan-biz/src/main/java/com/cf/imes/module/plan/dal/dataobject/ordermodel/OrderModelDO.java index d9148f24e..0da75a0b7 100644 --- a/cf-module-prod-plan/cf-module-prod-plan-biz/src/main/java/com/cf/imes/module/plan/dal/dataobject/ordermodel/OrderModelDO.java +++ b/cf-module-prod-plan/cf-module-prod-plan-biz/src/main/java/com/cf/imes/module/plan/dal/dataobject/ordermodel/OrderModelDO.java @@ -121,6 +121,4 @@ public class OrderModelDO extends ESDocument { private String remarkJson; // 普通备注(板材数据中) @Schema(description = "特殊备注(板材数据中)") private String specialRemark; // 特殊备注(板材数据中) - - private Long sortId; } \ No newline at end of file diff --git a/cf-module-prod-plan/cf-module-prod-plan-biz/src/main/java/com/cf/imes/module/plan/service/order/OrderInputProcessor.java b/cf-module-prod-plan/cf-module-prod-plan-biz/src/main/java/com/cf/imes/module/plan/service/order/OrderInputProcessor.java index 31cb867c5..8b2eda8cf 100644 --- a/cf-module-prod-plan/cf-module-prod-plan-biz/src/main/java/com/cf/imes/module/plan/service/order/OrderInputProcessor.java +++ b/cf-module-prod-plan/cf-module-prod-plan-biz/src/main/java/com/cf/imes/module/plan/service/order/OrderInputProcessor.java @@ -14,6 +14,10 @@ import com.cf.imes.framework.common.exception.ServiceException; import com.cf.imes.framework.es.core.dal.ESDocument; import com.cf.imes.module.plan.dal.dataobject.ordermodel.OrderModelDO; import com.cf.imes.module.plan.dal.elasticsearch.OrderPartsRemark; +import com.fasterxml.jackson.annotation.JsonInclude; +import com.fasterxml.jackson.core.type.TypeReference; +import com.fasterxml.jackson.databind.DeserializationFeature; +import com.fasterxml.jackson.databind.ObjectMapper; import lombok.extern.slf4j.Slf4j; import org.springframework.stereotype.Component; @@ -51,6 +55,15 @@ public class OrderInputProcessor { private static final String FIELD_BATCH_ID = "batchId"; + private static ObjectMapper objectMapper = new ObjectMapper(); + + static { + objectMapper.setSerializationInclusion(JsonInclude.Include.NON_NULL); // 跳过 null 字段 + objectMapper.configure(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES, false); + objectMapper.configure(DeserializationFeature.ACCEPT_EMPTY_STRING_AS_NULL_OBJECT, true); + objectMapper.configure(DeserializationFeature.FAIL_ON_NULL_FOR_PRIMITIVES, false); + } + /** * 保存生产单造型数据 * @@ -80,26 +93,12 @@ public class OrderInputProcessor { try { bulkAsyncCreate(ORDER_PLATE_MODEL, orderModelDOs); } catch (IOException | ElasticsearchException e) { - log.error(e.getMessage()); + log.error(e.getMessage(), e); throw new RuntimeException(e); } } - public void deleteByOrderId(Long orderId, String index) { - DeleteByQueryRequest.Builder builder = new DeleteByQueryRequest.Builder(); - builder.index(index); - builder.query(q -> q.term(t -> t.field(FIELD_ORDER_ID).value(orderId))); - - try { - DeleteByQueryResponse response = elasticsearchClient.deleteByQuery(builder.build()); - log.info("Deleted {} documents with planId {}", response.deleted(), orderId); - } catch (IOException | ElasticsearchException e) { - log.error("Error deleting documents with planId {}: {}", orderId, e.getMessage()); - throw new ServiceException(INTERNAL_SERVER_ERROR); - } - } - /** * 按批次删除生产单OrderModels * @@ -179,10 +178,17 @@ public class OrderInputProcessor { return elasticsearchClient.bulk(br.build()); } - public void bulkAsyncCreate(String idxName, List documents) throws IOException, ElasticsearchException { + public void bulkAsyncCreate(String idxName, List documents) throws IOException, ElasticsearchException { BulkRequest.Builder br = new BulkRequest.Builder(); Date date = new Date(); - documents.forEach(esDocument -> { + // 深拷贝documents + List deepCopy = objectMapper.readValue( + objectMapper.writeValueAsString(documents), + new TypeReference<>() { + } + ); + + deepCopy.forEach(esDocument -> { if (CharSequenceUtil.isBlank(esDocument.getId())) { esDocument.setId(snowflake.nextIdStr()); } @@ -194,6 +200,21 @@ public class OrderInputProcessor { .id(esDocument.getId()) .document(esDocument))); }); - elasticsearchAsyncClient.bulk(br.build()); + + elasticsearchAsyncClient.bulk(br.build()) + .whenComplete((response, exception) -> { + deepCopy.clear(); + + if (exception != null) { + log.error("ES bulk async failed for index: {}, size: {}, error: {}", + idxName, documents.size(), exception.getMessage(), exception); + } else if (response.errors()) { + log.warn("ES bulk async partially failed for index: {}, size: {}", + idxName, documents.size()); + } else { + log.debug("ES bulk async success for index: {}, size: {}", + idxName, documents.size()); + } + }); } } diff --git a/cf-module-prod-plan/cf-module-prod-plan-biz/src/main/java/com/cf/imes/module/plan/service/orderImport/factory/WebCadOrderImportAsyncFactory.java b/cf-module-prod-plan/cf-module-prod-plan-biz/src/main/java/com/cf/imes/module/plan/service/orderImport/factory/WebCadOrderImportAsyncFactory.java index 6b35c0ecc..e61f33044 100644 --- a/cf-module-prod-plan/cf-module-prod-plan-biz/src/main/java/com/cf/imes/module/plan/service/orderImport/factory/WebCadOrderImportAsyncFactory.java +++ b/cf-module-prod-plan/cf-module-prod-plan-biz/src/main/java/com/cf/imes/module/plan/service/orderImport/factory/WebCadOrderImportAsyncFactory.java @@ -192,8 +192,6 @@ public class WebCadOrderImportAsyncFactory { private String tempFilePath; - private long sortId; - public WebCadOrderImportAsyncFactory(Long organId, OrderMapper orderMapper, SnowFlakeGenerator snowFlakeGenerator, @@ -229,7 +227,6 @@ public class WebCadOrderImportAsyncFactory { sealEdgeConfigList = new ArrayList<>(); this.cadImportPlateNumThreshold = cadImportPlateNumThreshold; this.jdbcTemplate = jdbcTemplate; - this.sortId = 1; } public void analyzeTempData(Long taskId, String webcadJsonCachePath) throws FileNotFoundException { @@ -884,7 +881,6 @@ public class WebCadOrderImportAsyncFactory { .orderId(orderId) .plateId(plateDO.getId()) .batchId(batchId) - .sortId(sortId++) .texture(block.getTexture()) .typographicFace(block.getHoleArrange()) .openDoorType(block.getOpenDoorType()) @@ -1819,11 +1815,15 @@ public class WebCadOrderImportAsyncFactory { if (!isLast) { // 存储完成清理 list - list.clear(); + clearPlate(); } } } + private void clearPlate(){ + plateDOS = ListUtils.newArrayListWithExpectedSize(BATCH_THRESHOLD_NUMBER); + } + private void orderItemBatchInsertWithinThreshold(List list, boolean isLast) { // 达到批量的阈值就做一次插入 if (CollUtil.isNotEmpty(list) && (list.size() >= BATCH_THRESHOLD_NUMBER || isLast)) { @@ -1855,11 +1855,15 @@ public class WebCadOrderImportAsyncFactory { if (!isLast) { // 存储完成清理 list - list.clear(); + clearItem(); } } } + private void clearItem(){ + orderItemDOS = ListUtils.newArrayListWithExpectedSize(BATCH_THRESHOLD_NUMBER); + } + private void orderPartBatchInsertWithinThreshold(List list, boolean isLast) { // 达到批量的阈值就做一次插入 if (CollUtil.isNotEmpty(list) && (list.size() >= BATCH_THRESHOLD_NUMBER || isLast)) { @@ -1906,11 +1910,15 @@ public class WebCadOrderImportAsyncFactory { if (!isLast) { // 存储完成清理 list - list.clear(); + clearPart(); } } } + private void clearPart(){ + orderPartsDOS = ListUtils.newArrayListWithExpectedSize(BATCH_THRESHOLD_NUMBER); + } + /** * 每达到阈值就批量插入一次生产单造型数据和压缩数据 * @@ -1923,7 +1931,7 @@ public class WebCadOrderImportAsyncFactory { orderInputProcessor.batchAsyncSaveModel(orderModelDOS); if (!isLast) { // 存储完成清理 list - orderModelDOS.clear(); + orderModelDOS = ListUtils.newArrayListWithExpectedSize(BATCH_THRESHOLD_NUMBER); } } } @@ -2052,21 +2060,21 @@ public class WebCadOrderImportAsyncFactory { * 清空所有列表 */ private void clearAll() { - roomBodyMap.clear(); - bodyMap.clear(); - orderGroupMap.clear(); - materialMap.clear(); - processGroupMap.clear(); - existRoomIdMap.clear(); - orderPartMap.clear(); + roomBodyMap = null; + bodyMap = null; + orderGroupMap = null; + materialMap = null; + processGroupMap = null; + existRoomIdMap = null; + orderPartMap = null; - plateDOS.clear(); - orderItemDOS.clear(); - orderPartsDOS.clear(); - orderModelDOS.clear(); - rawGoodsDOS.clear(); - goodsDOS.clear(); - sealEdgeConfigList.clear(); + plateDOS = null; + orderItemDOS = null; + orderPartsDOS = null; + orderModelDOS = null; + rawGoodsDOS = null; + goodsDOS = null; + sealEdgeConfigList = null; } /** diff --git a/cf-module-prod-plan/cf-module-prod-plan-biz/src/main/java/com/cf/imes/module/plan/service/orderImport/factory/WebCadOrderImportFactory.java b/cf-module-prod-plan/cf-module-prod-plan-biz/src/main/java/com/cf/imes/module/plan/service/orderImport/factory/WebCadOrderImportFactory.java index 4968fc5e2..2d1abd956 100644 --- a/cf-module-prod-plan/cf-module-prod-plan-biz/src/main/java/com/cf/imes/module/plan/service/orderImport/factory/WebCadOrderImportFactory.java +++ b/cf-module-prod-plan/cf-module-prod-plan-biz/src/main/java/com/cf/imes/module/plan/service/orderImport/factory/WebCadOrderImportFactory.java @@ -175,8 +175,6 @@ public class WebCadOrderImportFactory { // 板件数量是否已达到阈值 private boolean plateNumReachThreshold = false; - private long sortId; - public WebCadOrderImportFactory(Long organId, OrderDO orderDO, SnowFlakeGenerator snowFlakeGenerator, @@ -208,7 +206,6 @@ public class WebCadOrderImportFactory { sealEdgeConfigList = new ArrayList<>(); this.cadImportPlateNumThreshold = cadImportPlateNumThreshold; this.jdbcTemplate = jdbcTemplate; - this.sortId = 1; } public void analyzeTempData(WebCadDataReqVO webCadDataReqVO) { @@ -695,7 +692,6 @@ public class WebCadOrderImportFactory { .orderId(orderId) .plateId(plateDO.getId()) .batchId(batchId) - .sortId(sortId++) .texture(block.getTexture()) .typographicFace(block.getHoleArrange()) .openDoorType(block.getOpenDoorType()) @@ -1708,11 +1704,15 @@ public class WebCadOrderImportFactory { if (!isLast) { // 存储完成清理 list - list.clear(); + clearPlate(); } } } + private void clearPlate(){ + plateDOS = ListUtils.newArrayListWithExpectedSize(BATCH_THRESHOLD_NUMBER); + } + private void orderItemBatchInsertWithinThreshold(List list, boolean isLast) { // 达到批量的阈值就做一次插入 if (CollUtil.isNotEmpty(list) && (list.size() >= BATCH_THRESHOLD_NUMBER || isLast)) { @@ -1744,11 +1744,15 @@ public class WebCadOrderImportFactory { if (!isLast) { // 存储完成清理 list - list.clear(); + clearItem(); } } } + private void clearItem(){ + orderItemDOS = ListUtils.newArrayListWithExpectedSize(BATCH_THRESHOLD_NUMBER); + } + private void orderPartBatchInsertWithinThreshold(List list, boolean isLast) { // 达到批量的阈值就做一次插入 if (CollUtil.isNotEmpty(list) && (list.size() >= BATCH_THRESHOLD_NUMBER || isLast)) { @@ -1795,11 +1799,15 @@ public class WebCadOrderImportFactory { if (!isLast) { // 存储完成清理 list - list.clear(); + clearPart(); } } } + private void clearPart(){ + orderPartsDOS = ListUtils.newArrayListWithExpectedSize(BATCH_THRESHOLD_NUMBER); + } + /** * 每达到阈值就批量插入一次生产单造型数据和压缩数据 * @@ -1812,7 +1820,7 @@ public class WebCadOrderImportFactory { orderInputProcessor.batchAsyncSaveModel(orderModelDOS); if (!isLast) { // 存储完成清理 list - orderModelDOS.clear(); + orderModelDOS = ListUtils.newArrayListWithExpectedSize(BATCH_THRESHOLD_NUMBER); } } } @@ -1941,20 +1949,20 @@ public class WebCadOrderImportFactory { * 清空所有列表 */ private void clearAll() { - roomBodyMap.clear(); - bodyMap.clear(); - orderGroupMap.clear(); - materialMap.clear(); - processGroupMap.clear(); - existRoomIdMap.clear(); - orderPartMap.clear(); + roomBodyMap = null; + bodyMap = null; + orderGroupMap = null; + materialMap = null; + processGroupMap = null; + existRoomIdMap = null; + orderPartMap = null; - plateDOS.clear(); - orderItemDOS.clear(); - orderPartsDOS.clear(); - orderModelDOS.clear(); - rawGoodsDOS.clear(); - goodsDOS.clear(); - sealEdgeConfigList.clear(); + plateDOS = null; + orderItemDOS = null; + orderPartsDOS = null; + orderModelDOS = null; + rawGoodsDOS = null; + goodsDOS = null; + sealEdgeConfigList = null; } }