于杰
19 小时以前 8052785b8f8c423b3ba62b2c546d628b801b18dc
新增 动态补片功能
1个文件已添加
5个文件已修改
1113 ■■■■■ 已修改文件
north-glass-erp/src/main/java/com/example/erp/ErpApplication.java 2 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
north-glass-erp/src/main/java/com/example/erp/controller/pp/GlassOptimizeController.java 24 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
north-glass-erp/src/main/java/com/example/erp/dto/pp/MesCalculateDTO.java 247 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
north-glass-erp/src/main/java/com/example/erp/mapper/pp/GlassOptimizeMapper.java 26 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
north-glass-erp/src/main/java/com/example/erp/service/pp/GlassOptimizeService.java 540 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
north-glass-erp/src/main/resources/mapper/pp/GlassOptimize.xml 274 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
north-glass-erp/src/main/java/com/example/erp/ErpApplication.java
@@ -3,6 +3,7 @@
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cache.annotation.EnableCaching;
import org.springframework.scheduling.annotation.EnableAsync;
import org.springframework.scheduling.annotation.EnableScheduling;
import org.springframework.transaction.annotation.EnableTransactionManagement;
@@ -11,6 +12,7 @@
@EnableCaching
@EnableScheduling
@EnableTransactionManagement//事务注解
@EnableAsync  //启用异步任务
//@Transactional//在service里面有多表操作,开启事务注解
public class ErpApplication {
    public static void main(String[] args) {
north-glass-erp/src/main/java/com/example/erp/controller/pp/GlassOptimizeController.java
@@ -1,5 +1,6 @@
package com.example.erp.controller.pp;
import com.example.erp.dto.pp.MesCalculateDTO;
import org.springframework.core.io.InputStreamResource;
import com.example.erp.common.Constants;
import com.example.erp.common.Result;
@@ -26,6 +27,7 @@
import java.sql.Date;
import java.util.HashMap;
import java.util.Map;
import java.util.concurrent.CompletableFuture;
@RestController
@Api(value="优化管理controller",tags={"优化管理操作接口"})
@@ -230,7 +232,7 @@
    @PostMapping("/mesCalculate")
    public ResponseEntity<Map<String, Object>> receiveOptimizeRequest(
            @RequestBody Map<String, Object> requestData) {
            @RequestBody MesCalculateDTO mesCalculateDTO) {
        Map<String, Object> response = new HashMap<>();
@@ -238,17 +240,22 @@
            // 立即返回接收成功的响应
            response.put("code", "200");
            response.put("msg", "success");
            response.put("data", "");
            response.put("data", true);
            // todo 异步处理计算任务
//            glassOptimizeService.processExternalOptimizeRequest(requestData);
            System.out.println(requestData);
            // 使用CompletableFuture 异步处理计算任务
            CompletableFuture.runAsync(() -> {
                try {
                    glassOptimizeService.processExternalOptimizeRequest(mesCalculateDTO);
                } catch (Exception e) {
                    System.err.println("异步处理优化请求时发生错误: " + e.getMessage());
                    e.printStackTrace();
                }
            });
            return ResponseEntity.ok(response);
        } catch (Exception e) {
            response.put("code", 201);
            response.put("msg", "false: " + e.getMessage());
            response.put("data", "");
            response.put("msg", e.getMessage());
            response.put("data", false);
            return ResponseEntity.status(500).body(response);
        }
    }
@@ -256,6 +263,7 @@
    //创建工程查询流程卡明细
    @ApiOperation("创建工程查询流程卡明细")
    @PostMapping  ("/getProcessCardDetail/{processId}/{technologyNumber}")
north-glass-erp/src/main/java/com/example/erp/dto/pp/MesCalculateDTO.java
New file
@@ -0,0 +1,247 @@
package com.example.erp.dto.pp;
import com.fasterxml.jackson.annotation.JsonProperty;
import lombok.Data;
import java.util.List;
/**
 * @author yujie
 * @date 2025/12/23 9:23
 */
@Data
public class MesCalculateDTO {
    @JsonProperty("engineerId")
    private String engineerId;
    //    private String projectNo;
    @JsonProperty("rawQueueList")
    private Object rawQueueList;
    private Double usageRate;
    @JsonProperty("engineeringRawQueueList")
    private List<EngineeringRawQueue> engineeringRawQueueList;
    //    private List<materialDetail> materialDetails;
    @JsonProperty("glassInfoList")
    private List<GlassInfo> glassInfoList;
//    private List<GlassDetail> glassDetails;
    @JsonProperty("damageList")
    private List<DamageList> damageList;
    @Data
    public static class EngineeringRawQueue{
        @JsonProperty("id")
        private String id;
//        private String stockCode;
        @JsonProperty("engineeringId")
        private String engineeringId;
//        private String projectNo;
        @JsonProperty("filmsId")
        private String filmsId;
//        private String glassType;
        @JsonProperty("rawGlassWidth")
        private Double rawGlassWidth;
//        private Double width;
        @JsonProperty("rawGlassHeight")
        private Double rawGlassHeight;
//        private Double height;
        @JsonProperty("rawGlassThickness")
        private String rawGlassThickness;
//        private String glassThickness;
        private Integer quantity = 1;
        private Integer priority = 0;
        private Integer materialType = 1;
        private Integer rawSequence;
        private Integer state;
        private String createTime;
        private String updateTime;
        private Object usageRate;
    }
    @Data
    public static class GlassInfo {
        private Integer id;
        @JsonProperty("flowCardId")
        private String flowCardId;
//        private String processId;
        private String orderNumber;
        private Double width;
        private Double height;
        private Integer thickness;
        private String filmsId;
        private Integer layer;
        private Integer totalLayer;
        @JsonProperty("edgWidth")
        private Double edgWidth;
//        private Double widthGrind;
        @JsonProperty("edgHeight")
        private Double edgHeight;
//        private Double heightGrind;
        private Integer isMultiple;
        private Double maxWidth;
        private Double maxHeight;
        private Object isHorizontal;
        private Integer rawSequence;
        private Integer temperingLayoutId;
        private Integer temperingFeedSequence;
        private Double angle;
        private String engineerId;
        private Object ruleId;
        private String glassId;
        private Integer combine;
        private String markIcon;
        private Integer quantity = 1;
        private Integer patchState = 1;
        private Object filmRemove;
        private String flowCardSequence;
        private String process;
        private Integer rawAngle;
        private Integer hollowCombineDirection;
        private Integer productSortNumber;
        private Object shelfOrder;
        private Object graphNo;
        private Object processParam;
        private Integer ycoordinate;
        private Integer xcoordinate;
        private Integer xaxis;
        private Integer yaxis;
    }
    @Data
    public static class DamageList {
        private Integer id;
        private String flowCardId;
        private String orderNumber;
        private Double width;
        private Double height;
        private Integer thickness;
        private String filmsId;
        private Integer layer;
        private Integer totalLayer;
        private Double edgWidth;
        private Double edgHeight;
        private Integer isMultiple;
        private Double maxWidth;
        private Double maxHeight;
        private Object isHorizontal;
        private Integer rawSequence;
        private Integer temperingLayoutId;
        private Integer temperingFeedSequence;
        private Double angle;
        private String engineerId;
        private Object ruleId;
        private String glassId;
        private Integer combine;
        private String markIcon;
        private Object filmRemove;
        private String flowCardSequence;
        private String process;
        private Integer rawAngle;
        private Integer hollowCombineDirection;
        private Integer productSortNumber;
        private Object shelfOrder;
        private Object graphNo;
        private Object processParam;
        private Integer xcoordinate;
        private Integer ycoordinate;
        private Integer xaxis;
        private Integer yaxis;
    }
}
north-glass-erp/src/main/java/com/example/erp/mapper/pp/GlassOptimizeMapper.java
@@ -243,4 +243,30 @@
    List<Map<String, Object>> optimizeTemp(String projectNo);
    List<Map<String, Object>> selectTempProject(String processId);
    Map<String, Object> getGlassType(String projectNo);
    String getRockNo(Object glassId);
    Map<String, Object> getTrimInfo(String projectNo, Object stockId);
    Map<String, Object> selectOptimizeDynamicProject(String projectNo);
    List<Map<String,Object>> selectOptimizeDynamicLayout(String projectNo);
    List<Map<String,Object>> selectOptimizeDynamicDetail(String projectNo);
    List<Map<String,Object>> selectFlowCardDynamicInfoList(String projectNo);
    void insertDynamicProject(Map<String, Object> dataObj);
    void insertDynamicLayout(Map<String, Object> layout);
    void insertDynamicDetail(List<Map<String, Object>> glassDetails, String projectNo);
    void deleteOptimizeDynamicProject(String projectNo);
    void deleteOptimizeDynamicLayout(String projectNo);
    void deleteOptimizeDynamicDetail(String projectNo);
}
north-glass-erp/src/main/java/com/example/erp/service/pp/GlassOptimizeService.java
@@ -4,17 +4,14 @@
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.dynamic.datasource.annotation.DS;
import com.baomidou.mybatisplus.annotation.IdType;
import com.baomidou.mybatisplus.annotation.TableId;
import com.example.erp.common.RabbitMQUtil;
import com.example.erp.dto.pp.MesCalculateDTO;
import com.example.erp.entity.pp.*;
import com.example.erp.entity.sd.Delivery;
import com.example.erp.entity.sd.OrderDetail;
import com.example.erp.entity.userInfo.Log;
import com.example.erp.entity.userInfo.SysError;
import com.example.erp.mapper.pp.GlassOptimizeMapper;
import com.example.erp.service.userInfo.SysErrorService;
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.DeserializationFeature;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.datatype.jsr310.JavaTimeModule;
import org.springframework.beans.factory.annotation.Autowired;
@@ -24,18 +21,15 @@
import org.springframework.transaction.interceptor.TransactionAspectSupport;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.OutputStream;
import java.lang.reflect.Field;
import java.math.BigDecimal;
import java.net.HttpURLConnection;
import java.net.URL;
import java.nio.charset.StandardCharsets;
import java.sql.Date;
import java.text.DecimalFormat;
import java.time.LocalDate;
import java.util.*;
import java.util.concurrent.TimeoutException;
import java.util.stream.Collectors;
@Service
@@ -1563,5 +1557,533 @@
    }
    public void processExternalOptimizeRequest(MesCalculateDTO mesCalculateDTO){
        // 使用反射将对象转换为 Map,使用 Java 字段名
        List<Map<String, Object>> materialDetailList = new ArrayList<>();
        if (mesCalculateDTO.getEngineeringRawQueueList() != null) {
            for (MesCalculateDTO.EngineeringRawQueue materialDetail : mesCalculateDTO.getEngineeringRawQueueList()) {
                Map<String, Object> materialMap = objectToMapUsingFields(materialDetail);
                materialDetailList.add(materialMap);
            }
        }
        List<Map<String, Object>> glassDetailList = new ArrayList<>();
        if (mesCalculateDTO.getGlassInfoList() != null) {
            for (MesCalculateDTO.GlassInfo glassDetail : mesCalculateDTO.getGlassInfoList()) {
                Map<String, Object> glassMap = objectToMapUsingFields(glassDetail);
                glassDetailList.add(glassMap);
            }
        }
        List<Map<String, Object>> glassDamageList = new ArrayList<>();
        if (mesCalculateDTO.getDamageList() != null) {
            for (MesCalculateDTO.DamageList damageInfo : mesCalculateDTO.getDamageList()) {
                Map<String, Object> damageMap = objectToMapUsingFields(damageInfo);
                glassDamageList.add(damageMap);
            }
        }
        List<Map<String, Object>> glassDamageTempList = new ArrayList<>();
        if (mesCalculateDTO.getDamageList() != null) {
            for (MesCalculateDTO.DamageList damageInfo : mesCalculateDTO.getDamageList()) {
                Map<String, Object> damageMap = objectToMapUsingFields(damageInfo);
                // 创建新的Map只保留glassId字段并添加reportState字段
                Map<String, Object> filteredDamageMap = new HashMap<>();
                if (damageMap.containsKey("glassId")) {
                    filteredDamageMap.put("glassId", damageMap.get("glassId"));
                }
                filteredDamageMap.put("reportState", 10);
                glassDamageTempList.add(filteredDamageMap);
            }
        }
        String projectNo = mesCalculateDTO.getEngineerId();
        System.out.println("projectNo: " + projectNo);
        for (Map<String, Object> materialDetail : materialDetailList) {
            Object stockId = materialDetail.get("rawSequence");
            Map<String, Object> trimInfo = glassOptimizeMapper.getTrimInfo(projectNo, stockId);
            if (trimInfo != null) {
                materialDetail.putAll(trimInfo);
            }
        }
        Map<String, Object> glassOptimaizeMap = new HashMap<>();
        Map<String, Object> optimizeProperty = glassOptimizeMapper.getGlassType(projectNo);
        glassOptimaizeMap.put("requestSource", "ERP");
        glassOptimaizeMap.put("usageRate", mesCalculateDTO.getUsageRate());
        glassOptimaizeMap.put("optimizeProperty", optimizeProperty);
        glassOptimaizeMap.put("engineeringRawQueueList", materialDetailList);
        glassOptimaizeMap.put("glassInfoList", glassDetailList);
        try {
            ObjectMapper objectMapper = new ObjectMapper();
            String glassDamageListJson = objectMapper.writeValueAsString(glassDamageList);
            System.out.println("damageList JSON: " + glassDamageListJson);
            String glassDamageTempListJson = objectMapper.writeValueAsString(glassDamageTempList);
            System.out.println("glassDamageTempListJson: " + glassDamageTempListJson);
            String optimizeJsonString = objectMapper.writeValueAsString(glassOptimaizeMap);
            System.out.println("glassTypeMap JSON: " + optimizeJsonString);
            // 获取并输出动态优化返回结果
            String optimizeResult = callDynamicOptimizeApi(optimizeJsonString);
            System.out.println("动态优化返回结果: " + optimizeResult);
            // 将结果转换为JSON格式
            Object optimaizeResultJson = null;
            try {
                // 尝试解析为JSON对象
                optimaizeResultJson = objectMapper.readValue(optimizeResult, Object.class);
            } catch (Exception e) {
                // 如果不是有效的JSON字符串,创建一个包含原始字符串的Map
                Map<String, String> errorResult = new HashMap<>();
                errorResult.put("result", optimizeResult);
                optimaizeResultJson = errorResult;
            }
            // 输出JSON格式的结果
            String jsonOptimizeResult = objectMapper.writeValueAsString(optimaizeResultJson);
            System.out.println("动态优化返回结果JSON格式: " + jsonOptimizeResult);
            // 调用issuingDamageDynamicProjects接口
            Boolean MESResult = issuingDamageDynamicProjects(projectNo, glassDamageTempList);
            System.out.println("MES返回结果: " + MESResult);
            // 检查issuingDamageDynamicProjects接口调用结果,如果失败则停止后续操作
            if (!MESResult) {
                System.out.println("issuingDamageDynamicProjects接口调用失败,停止后续操作");
                return;
            }
            // 调用cutFiles接口
            Boolean cutFileResult = callCutFilesApi(jsonOptimizeResult);
            System.out.println("调用cutFiles接口返回结果: " + cutFileResult);
            // 检查cutFiles接口调用结果,如果失败则停止后续操作
            if (!cutFileResult) {
                System.out.println("cutFiles接口调用失败,停止后续操作");
                return;
            }
            // 调用issuingDynamicProjects接口
            Boolean MESTwiceResult = issuingDynamicProjects(projectNo);
            System.out.println("MES二次返回结果: " + MESTwiceResult);
            // 检查issuingDynamicProjects接口调用结果,如果失败则停止后续操作
            if (!MESTwiceResult) {
                System.out.println("issuingDynamicProjects接口调用失败,停止后续操作");
            }
        } catch (JsonProcessingException e) {
            System.err.println("转换JSON失败: " + e.getMessage());
        }
    }
    // 使用反射将对象转换为 Map,使用 Java 字段名
    private Map<String, Object> objectToMapUsingFields(Object obj) {
        Map<String, Object> map = new HashMap<>();
        if (obj == null) return map;
        Class<?> clazz = obj.getClass();
        Field[] fields = clazz.getDeclaredFields();
        for (Field field : fields) {
            try {
                field.setAccessible(true);
                Object value = field.get(obj);
                // 使用 Java 字段名作为 key
                map.put(field.getName(), value);
            } catch (IllegalAccessException e) {
                // 记录或处理异常
                System.err.println("访问字段失败: " + field.getName() + ", 错误: " + e.getMessage());
            }
        }
        return map;
    }
    private String callDynamicOptimizeApi(String jsonData) {
        try {
            URL url = new URL("http://" + mesIp + ":8078/api/dynamicOptimize");
            HttpURLConnection conn = (HttpURLConnection) url.openConnection();
            // 设置请求方法
            conn.setRequestMethod("POST");
            // 设置请求头
            conn.setRequestProperty("Content-Type", "application/json; charset=UTF-8");
            conn.setRequestProperty("Accept", "application/json");
            // 允许输出
            conn.setDoOutput(true);
            // 设置超时时间
            conn.setConnectTimeout(10000); // 10秒连接超时
            conn.setReadTimeout(30000);    // 30秒读取超时
            // 发送JSON数据
            try (OutputStream os = conn.getOutputStream()) {
                byte[] input = jsonData.getBytes(StandardCharsets.UTF_8);
                os.write(input, 0, input.length);
            }
            // 读取响应
            StringBuilder response = new StringBuilder();
            try (BufferedReader br = new BufferedReader(
                    new InputStreamReader(conn.getInputStream(), StandardCharsets.UTF_8))) {
                String responseLine;
                while ((responseLine = br.readLine()) != null) {
                    response.append(responseLine.trim());
                }
            }
            String responseResult = response.toString();
            System.out.println("优化软件响应结果: " + responseResult);
            // 断开连接
            conn.disconnect();
            ObjectMapper objectMapper = new ObjectMapper();
            // 启用类型转换功能,允许将浮点数转换为整数
            objectMapper.configure(DeserializationFeature.ACCEPT_FLOAT_AS_INT, true);
            Map<String, Object> responseMap = objectMapper.readValue(responseResult, Map.class);
            // 检查code是否为200
            Object codeObj = responseMap.get("code");
            int code = -1;
            if (codeObj instanceof Integer) {
                code = (Integer) codeObj;
            } else if (codeObj instanceof String) {
                try {
                    code = Integer.parseInt((String) codeObj);
                } catch (NumberFormatException e) {
                    System.err.println("无法解析code字段: " + codeObj);
                }
            }
            if (code == 200) {
                // 设置回滚点,用于事务处理
                Object savePoint = TransactionAspectSupport.currentTransactionStatus().createSavepoint();
                try {
                    // 返回data字段的内容作为JSON字符串
                    Object dataObj = responseMap.get("data");
                    if (dataObj != null) {
                        // 确保 dataObj 是 Map 类型并验证 projectNo 字段
                        if (dataObj instanceof Map) {
                            Map<String, Object> dataMap = (Map<String, Object>) dataObj;
                            // 验证 projectNo 是否存在
                            Object projectNoObj = dataMap.get("projectNo");
                            if (projectNoObj == null) {
                                throw new RuntimeException("projectNo 不能为空");
                            }
                            String projectNo = projectNoObj.toString();
                            dataMap.put("projectNo", projectNo);
                            // 删除已存在的相关数据
                            glassOptimizeMapper.deleteOptimizeDynamicProject(projectNo);
                            glassOptimizeMapper.deleteOptimizeDynamicLayout(projectNo);
                            glassOptimizeMapper.deleteOptimizeDynamicDetail(projectNo);
                            // 插入动态项目
                            glassOptimizeMapper.insertDynamicProject(dataMap);
                            // 处理 layouts 数组并插入
                            Object layoutsObj = dataMap.get("layouts");
                            if (layoutsObj instanceof List) {
                                @SuppressWarnings("unchecked")
                                List<Map<String, Object>> layouts = (List<Map<String, Object>>) layoutsObj;
                                for (Map<String, Object> layout : layouts) {
                                    // 为每个 layout 添加 projectNo
                                    layout.put("projectNo", projectNo);
                                    // 获取当前 layout 的 glassDetails
                                    Object glassDetailsObj = layout.get("glassDetails");
                                    if (glassDetailsObj instanceof List) {
                                        @SuppressWarnings("unchecked")
                                        List<Map<String, Object>> glassDetails = (List<Map<String, Object>>) glassDetailsObj;
                                        // 为每个 glassDetail 添加 projectNo 和处理 glassPoint
                                        for (Map<String, Object> detail : glassDetails) {
                                            detail.put("projectNo", projectNo);
                                            // 处理 isRotate 为 1 时交换 width 和 height 的逻辑
                                            if (detail.containsKey("isRotate")) {
                                                Object isRotateObj = detail.get("isRotate");
                                                int isRotate = 0;
                                                if (isRotateObj instanceof Number) {
                                                    isRotate = ((Number) isRotateObj).intValue();
                                                } else if (isRotateObj instanceof String) {
                                                    isRotate = Integer.parseInt(isRotateObj.toString());
                                                }
                                                if (isRotate == 1) {
                                                    // 交换 width 和 height
                                                    Object widthObj = detail.get("width");
                                                    Object heightObj = detail.get("height");
                                                    detail.put("width", heightObj);
                                                    detail.put("height", widthObj);
                                                }
                                            }
                                            // 处理 glassPoint 字段转换
                                            if (detail.containsKey("glassPoint")) {
                                                Object glassPointObj = detail.get("glassPoint");
                                                if (glassPointObj != null) {
                                                    try {
                                                        // 如果 glassPointObj 已经是字符串,则不需要转换
                                                        if (!(glassPointObj instanceof String)) {
                                                            // 将对象转换为 JSON 字符串
                                                            String glassPointStr = objectMapper.writeValueAsString(glassPointObj);
                                                            detail.put("glassPoint", glassPointStr);
                                                        }
                                                    } catch (Exception e) {
                                                        // 如果转换失败,记录错误并移除该字段
                                                        System.err.println("转换 glassPoint 失败: " + e.getMessage());
                                                        detail.remove("glassPoint");
                                                    }
                                                } else {
                                                    // 如果 glassPointObj 为 null,移除该字段
                                                    detail.remove("glassPoint");
                                                }
                                            }
                                        }
                                        glassOptimizeMapper.insertDynamicDetail(glassDetails, projectNo);
                                    }
                                    // 插入 layout 到 optimize_dynamic_layout 表
                                    glassOptimizeMapper.insertDynamicLayout(layout);
                                }
                            }
                        }
                        return responseResult;
                    } else {
                        return "{}"; // 如果data字段为空,返回空JSON对象
                    }
                } catch (Exception e) {
                    // 发生异常时回滚事务
                    TransactionAspectSupport.currentTransactionStatus().rollbackToSavepoint(savePoint);
                    throw e; // 重新抛出异常
                }
            } else {
                // 当code不是200时,返回错误信息
                Object messageObj = responseMap.get("message");
                String errorMessage = "接口返回错误码: " + code;
                if (messageObj != null) {
                    errorMessage = messageObj.toString();
                }
                return errorMessage;
            }
        } catch (Exception e) {
            System.err.println("调用动态优化接口失败: " + e.getMessage());
            e.printStackTrace();
            return "调用动态优化接口失败: " + e.getMessage();
        }
    }
    public Boolean issuingDamageDynamicProjects(String projectNo, List<Map<String, Object>> glassDamageTempList){
        boolean  saveState=false;
        try {
            System.out.println(mesIp);
            // 1. 创建URL对象
            URL url = new URL("http://" + mesIp + ":88/api/loadGlass/engineering/engineerOptimizeImport");
            // 2. 打开连接
            HttpURLConnection conn = (HttpURLConnection) url.openConnection();
            conn.setRequestMethod("POST");
            conn.setRequestProperty("Content-Type", "application/json");
            conn.setRequestProperty("Accept", "application/json");
            conn.setDoOutput(true);
            // 3. 准备请求体
            // 获取glassInfolList数据
            List<Map<String, Object>> glassInfolList = glassOptimizeMapper.selectOptimizeDynamicDetail(projectNo);
            // 处理damageList,对glassInfolList中存在的glassId设置reportState为10,不存在的设置为1
            List<Map<String, Object>> processedDamageList = new ArrayList<>();
            Set<String> glassIdSet = new HashSet<>();
            // 收集glassInfolList中的所有glassId
            for (Map<String, Object> glassInfo : glassInfolList) {
                if (glassInfo.containsKey("glassId") && glassInfo.get("glassId") != null) {
                    glassIdSet.add(glassInfo.get("glassId").toString());
                }
            }
            // 处理glassDamageTempList,根据glassId是否在glassInfolList中存在来设置reportState
            for (Map<String, Object> damageItem : glassDamageTempList) {
                if (damageItem.containsKey("glassId") && damageItem.get("glassId") != null) {
                    String glassId = damageItem.get("glassId").toString();
                    Map<String, Object> processedItem = new HashMap<>(damageItem);
                    // 如果glassId在glassInfolList中存在,reportState保持为10,否则改为1
                    if (glassIdSet.contains(glassId)) {
                        // glassId存在,保持reportState为10(已在glassDamageTempList中设置)
                        processedItem.put("reportState", 10);
                    } else {
                        // glassId不存在,将reportState改为1
                        processedItem.put("reportState", 6);
                    }
                    processedDamageList.add(processedItem);
                }
            }
            Map<String, Object> optimizeProject=glassOptimizeMapper.selectOptimizeDynamicProject(projectNo);
            optimizeProject.put("engineeringRawQueueList", glassOptimizeMapper.selectOptimizeDynamicLayout(projectNo));
            optimizeProject.put("glassInfolList", glassOptimizeMapper.selectOptimizeDynamicDetail(projectNo));
            optimizeProject.put("flowCardInfoList", glassOptimizeMapper.selectFlowCardDynamicInfoList(projectNo));
            optimizeProject.put("damageList", processedDamageList);
            ObjectMapper mapper = new ObjectMapper();
            mapper.registerModule(new JavaTimeModule());
            String jsonInputString = mapper.writeValueAsString(optimizeProject);
            System.out.println("传给MES的数据"+ jsonInputString);
            //发送请求
            try(OutputStream os = conn.getOutputStream()) {
                byte[] input = jsonInputString.getBytes(StandardCharsets.UTF_8);
                os.write(input, 0, input.length);
            }
            // 获取响应
            try(BufferedReader br = new BufferedReader(
                    new InputStreamReader(conn.getInputStream(), StandardCharsets.UTF_8))) {
                StringBuilder response = new StringBuilder();
                String responseLine;
                while ((responseLine = br.readLine()) != null) {
                    response.append(responseLine.trim());
                }
                System.out.println("MES第一次返回信息: " + response.toString());
                JSONObject obj = JSONObject.parseObject(response.toString());
                if(obj.get("code").equals(200)&&obj.get("data").equals(true)){
                    saveState=true;
                }
            }
            //关闭连接
            conn.disconnect();
        } catch (Exception e) {
            e.printStackTrace();
            saveState= false;
        }
        return saveState;
    }
    public Boolean issuingDynamicProjects(String projectNo){
        boolean  saveState=false;
        try {
            System.out.println(mesIp);
            // 1. 创建URL对象
            URL url = new URL("http://" + mesIp + ":88/api/loadGlass/engineering/importEngineer");
            // 2. 打开连接
            HttpURLConnection conn = (HttpURLConnection) url.openConnection();
            conn.setRequestMethod("POST");
            conn.setRequestProperty("Content-Type", "application/json");
            conn.setRequestProperty("Accept", "application/json");
            conn.setDoOutput(true);
            // 3. 准备请求体
            Map<String, Object> optimizeProject=glassOptimizeMapper.selectOptimizeDynamicProject(projectNo);
            optimizeProject.put("engineeringRawQueueList", glassOptimizeMapper.selectOptimizeDynamicLayout(projectNo));
            optimizeProject.put("glassInfolList", glassOptimizeMapper.selectOptimizeDynamicDetail(projectNo));
            optimizeProject.put("flowCardInfoList", glassOptimizeMapper.selectFlowCardDynamicInfoList(projectNo));
            ObjectMapper mapper = new ObjectMapper();
            mapper.registerModule(new JavaTimeModule());
            String jsonInputString = mapper.writeValueAsString(optimizeProject);
            //发送请求
            try(OutputStream os = conn.getOutputStream()) {
                byte[] input = jsonInputString.getBytes(StandardCharsets.UTF_8);
                os.write(input, 0, input.length);
            }
            // 获取响应
            try(BufferedReader br = new BufferedReader(
                    new InputStreamReader(conn.getInputStream(), StandardCharsets.UTF_8))) {
                StringBuilder response = new StringBuilder();
                String responseLine;
                while ((responseLine = br.readLine()) != null) {
                    response.append(responseLine.trim());
                }
                System.out.println("MES第二次返回信息: " + response.toString());
                JSONObject obj = JSONObject.parseObject(response.toString());
                if(obj.get("code").equals(200)&&obj.get("data").equals(true)){
                    saveState=true;
                }
            }
            //关闭连接
            conn.disconnect();
        } catch (Exception e) {
            e.printStackTrace();
            saveState= false;
        }
        return saveState;
    }
    private Boolean callCutFilesApi(String jsonOptimizeResult) {
        boolean saveState = false;
        try {
            System.out.println(mesIp);
            // 1. 创建URL对象
            URL url = new URL("http://" + mesIp + ":8078/api/resultToCutFiles");
            // 2. 打开连接
            HttpURLConnection conn = (HttpURLConnection) url.openConnection();
            conn.setRequestMethod("POST");
            conn.setRequestProperty("Content-Type", "application/json");
            conn.setRequestProperty("Accept", "application/json");
            conn.setDoOutput(true);
            // 3. 发送请求体
            try(OutputStream os = conn.getOutputStream()) {
                byte[] input = jsonOptimizeResult.getBytes(StandardCharsets.UTF_8);
                os.write(input, 0, input.length);
            }
            // 获取响应
            try(BufferedReader br = new BufferedReader(
                    new InputStreamReader(conn.getInputStream(), StandardCharsets.UTF_8))) {
                StringBuilder response = new StringBuilder();
                String responseLine;
                while ((responseLine = br.readLine()) != null) {
                    response.append(responseLine.trim());
                }
                System.out.println("保存切割文件端口返回数据: " + response.toString());
                JSONObject obj = JSONObject.parseObject(response.toString());
                if(obj.get("code").equals(200)){
                    saveState = true;
                }
            }
            //关闭连接
            conn.disconnect();
        } catch (Exception e) {
            e.printStackTrace();
            saveState = false;
        }
        return saveState;
    }
}
north-glass-erp/src/main/resources/mapper/pp/GlassOptimize.xml
@@ -1558,6 +1558,116 @@
            now()
        )
    </insert>
    <insert id="insertDynamicProject">
        INSERT INTO pp.optimize_dynamic_project (
            project_no,
            optimize_state,
            avg_cut_pct,
            valid_cut_pct,
            last_cut_pct,
            raw_stock_qty,
            raw_stock_area,
            glass_total,
            glass_total_area,
            glass_thickness,
            glass_type
        )VALUES (
                #{projectNo},
                1,
                 #{avgCutRate},
                 #{validCutRate},
                 #{lastCutRate},
                 #{totalQuantity},
                 #{totalArea},
                 #{glassTotal},
                 #{glassTotalArea},
                 #{glassThickness},
                 #{glassType}
        )
    </insert>
    <insert id="insertDynamicLayout" parameterType="java.util.Map">
        INSERT INTO pp.optimize_dynamic_layout (
            project_no,
            stock_id,
            width,
            height,
            realwidth,
            realheight,
            usage_rate,
            stock_code,
            up_trim,
            down_trim,
            left_trim,
            right_trim,
            count,
            glass_count,
            glass_area
        ) VALUES (
                     #{projectNo},
                     #{stockId},
                     #{width},
                     #{height},
                     #{realWidth},
                     #{realHeight},
                     #{usageRate},
                     #{stockCode},
                     #{upTrim},
                     #{downTrim},
                     #{leftTrim},
                     #{rightTrim},
                     #{quantity},
                     #{glassQuantity},
                     #{glassArea}
                 )
    </insert>
    <insert id="insertDynamicDetail" parameterType="map">
        INSERT INTO pp.optimize_dynamic_detail (
        project_no,
        process_id,
        layer,
        total_layer,
        order_sort,
        stock_id,
        polys_id,
        o_width,
        o_height,
        p_width,
        p_height,
        x_axis,
        y_axis,
        patch_state,
        mark_icon,
        isRotate,
        glass_point,
        glass_id,
        rack_no,
        is_remain
        ) VALUES
        <foreach collection="glassDetails" item="detail" separator=",">
            (
            #{projectNo},
            #{detail.processId},
            #{detail.layer},
            #{detail.totalLayer},
            #{detail.orderSort},
            #{detail.stockSort},
            #{detail.polySort},
            #{detail.realWidth},
            #{detail.realHeight},
            #{detail.width},
            #{detail.height},
            #{detail.x},
            #{detail.y},
            #{detail.patchState},
            #{detail.markIcon},
            #{detail.isRotate},
            #{detail.glassPoint},
            #{detail.glassId},
            #{detail.rackNo},
             #{detail.isRemain}
            )
        </foreach>
    </insert>
    <update id="updateFlowCardRack">
        UPDATE pp.flow_card
        SET rack = #{rackValue}
@@ -1794,6 +1904,17 @@
    </delete>
    <delete id="deleteOffcutDetails">
        delete from pp.optimize_offcut where project_no = #{processId}
    </delete>
    <delete id="deleteOptimizeDynamicProject" parameterType="string">
        DELETE FROM pp.optimize_dynamic_project WHERE project_no = #{projectNo}
    </delete>
    <delete id="deleteOptimizeDynamicLayout" parameterType="string">
        DELETE FROM pp.optimize_dynamic_layout WHERE project_no = #{projectNo}
    </delete>
    <delete id="deleteOptimizeDynamicDetail" parameterType="string">
        DELETE FROM pp.optimize_dynamic_detail WHERE project_no = #{projectNo}
    </delete>
@@ -2197,6 +2318,159 @@
            o_width,
            o_height
    </select>
    <select id="getGlassType" resultType="java.util.Map" parameterType="java.lang.String">
        SELECT
            project_no AS projectNo,
            glass_type AS glassType,
            glass_thickness AS glassThickness,
            min_cut_distance AS minCutDistance,
            1 AS optimizeMode,
            'X' AS travType,
            0 AS rackCycleQty
        FROM
            pp.optimize_project
        WHERE
            project_no = #{projectNo}
    </select>
    <select id="getRockNo" resultType="java.lang.String" parameterType="java.lang.Object">
        SELECT
            rack_no AS rackNo
        FROM
            pp.optimize_detail
        WHERE
            glass_id = #{glassId}
    </select>
    <select id="getTrimInfo" resultType="java.util.Map">
        SELECT
            up_trim,
            down_trim,
            left_trim,
            right_trim,
            0 as priority,
            1 as materialType
        FROM
            pp.optimize_layout
        WHERE
            project_no = #{projectNo}
          AND
            stock_id = #{stockId}
    </select>
    <select id="selectOptimizeDynamicProject" resultType="java.util.Map">
        select
            project_no as engineerId,
            project_name as engineerName,
            avg_cut_pct as avgAvailability,
            valid_cut_pct as validAvailability,
            last_cut_pct as lastAvailability,
            glass_total as glassTotal,
            glass_total_area as glassTotalArea,
            raw_stock_qty as planPatternTotal,
            raw_stock_area as planPatternTotalArea,
            glass_thickness as thickness,
            glass_type as filmsId
        from
            pp.optimize_dynamic_project
        where
            project_no = #{projectNo}
    </select>
    <select id="selectOptimizeDynamicLayout" resultType="java.util.Map" parameterType="java.lang.String">
        select
            ol.project_no as engineeringId,
            op.glass_type as filmsId,
            ol.realwidth as rawGlassWidth,
            ol.realheight as rawGlassHeight,
            op.glass_thickness as rawGlassThickness,
            ol.stock_id as rawSequence,
            ol.usage_rate as usageRate
        from
            pp.optimize_dynamic_layout ol
                left join pp.optimize_dynamic_project op on ol.project_no = op.project_no
        where
            ol.project_no = #{projectNo}
        order by
            ol.stock_id
    </select>
    <select id="selectOptimizeDynamicDetail" resultType="java.util.Map" parameterType="java.lang.String">
        select
            opd.glass_id as glassId,
            opd.project_no as engineerId,
            opd.process_id as flowCardId,
            od.order_id as orderNumber,
            opd.order_sort as productSortNumber,
            IF(LOCATE('中空', ogd.process ) > 0 and LOCATE('#', pd.separation ),
               REPLACE(JSON_UNQUOTE(JSON_EXTRACT(pd.separation, "$.lowE")),'#',''),
               0) as hollowCombineDirection,
            opd.o_width as width,
            opd.o_height as height,
            op.glass_thickness as thickness,
            op.glass_type as filmsId,
            opd.total_layer as totalLayer,
            opd.layer,
            opd.stock_id as rawSequence,
            opd.p_width as edgWidth,
            opd.p_height as edgHeight,
            opd.x_axis as xAxis,
            opd.y_axis as yAxis,
            if(opd.o_width!=opd.width,1,0) as rawAngle,
            opd.heat_layout_id as temperingLayoutId,
            opd.heat_layout_sort as temperingFeedSequence,
            ohd.x_axis as xCoordinate,
            ohd.y_axis as yCoordinate,
            ohd.rotate_angle as angle,
            IF(LOCATE('中空', ogd.process ) > 0 or LOCATE('夹层', ogd.process ) > 0, 1, 0) as isMultiple,
            od.width as maxWidth,
            od.height as maxHeight,
            opd.mark_icon as markIcon,
            fc.`merge` as combine,
            concat( opd.process_id, '/', opd.layer ) as flowCardSequence,
            ogd.process,
            if(opd.graph_no=100,0,1) as graphNo
        from
            pp.optimize_dynamic_detail opd
                left join pp.optimize_dynamic_project op on op.project_no = opd.project_no
                left join pp.flow_card fc on opd.process_id = fc.process_id
                and opd.layer = fc.technology_number
                and opd.order_sort = order_number
                left join sd.`order` o on fc.order_id = o.order_id
                left join sd.order_detail od on fc.order_id = od.order_id
                and fc.order_number = od.order_number
                left join sd.order_glass_detail ogd on fc.order_id = ogd.order_id
                and fc.order_number = ogd.order_number
                and ogd.technology_number = fc.technology_number
                left join pp.optimize_heat_detail ohd on ohd.layout_id = opd.heat_layout_id
                and ohd.sort = opd.heat_layout_sort and ohd.project_no=opd.project_no
                left join sd.product_detail pd on od.product_id=pd.prod_id and opd.layer=pd.glass_sort
        where
            opd.project_no = #{projectNo} and opd.is_remain = 0
    </select>
    <select id="selectFlowCardDynamicInfoList" resultType="java.util.Map" parameterType="java.lang.String">
        select
            fc.process_id as flowCardId,
            ogd.child_width as width,
            ogd.child_height as height,
            REPLACE (JSON_UNQUOTE( JSON_EXTRACT( pd.separation, '$.thickness' )), 'mm', '' ) as thickness,
            JSON_UNQUOTE(JSON_EXTRACT( pd.separation, '$.color' )) as filmsId,
            fc.layers_number as totalLayer,
            fc.technology_number as layer,
            fc.quantity as glassTotal,
            od.order_number as orderNumber,
            od.product_name as productName,
            o.customer_name as customerName
        from
            pp.flow_card fc
                left join sd.`order` o on fc.order_id = o.order_id
                left join sd.order_detail od on fc.order_id = od.order_id
                and fc.order_number = od.order_number
                left join sd.order_glass_detail ogd on fc.order_id = ogd.order_id
                and fc.order_number = ogd.order_number
                and ogd.technology_number = fc.technology_number
                left join sd.product p on od.product_id = p.id
                left join sd.product_detail pd on od.product_id = pd.prod_id
                and fc.technology_number = pd.glass_sort
        where
            project_no =#{projectNo}
    </select>
</mapper>