From 56085822cfbf2168ab29566a32f0809cddc5b874 Mon Sep 17 00:00:00 2001
From: 云 <2163098428@qq.com>
Date: 星期一, 01 六月 2026 13:02:24 +0800
Subject: [PATCH] feat(quality): 优化批量快速检验功能

---
 src/main/java/com/ruoyi/quality/service/impl/QualityInspectServiceImpl.java |  215 ++++++++++++++++++++++++++++++++++++++++++++++++++++-
 1 files changed, 210 insertions(+), 5 deletions(-)

diff --git a/src/main/java/com/ruoyi/quality/service/impl/QualityInspectServiceImpl.java b/src/main/java/com/ruoyi/quality/service/impl/QualityInspectServiceImpl.java
index 625ff8b..590700d 100644
--- a/src/main/java/com/ruoyi/quality/service/impl/QualityInspectServiceImpl.java
+++ b/src/main/java/com/ruoyi/quality/service/impl/QualityInspectServiceImpl.java
@@ -10,10 +10,14 @@
 import com.deepoove.poi.XWPFTemplate;
 import com.deepoove.poi.config.Configure;
 import com.ruoyi.common.enums.StockInQualifiedRecordTypeEnum;
+import com.ruoyi.common.exception.ServiceException;
+import com.ruoyi.common.utils.DateUtils;
 import com.ruoyi.common.utils.HackLoopTableRenderPolicy;
 import com.ruoyi.common.utils.poi.ExcelUtil;
+import com.ruoyi.framework.web.domain.R;
 import com.ruoyi.procurementrecord.service.ProcurementRecordService;
 import com.ruoyi.procurementrecord.utils.StockUtils;
+import com.ruoyi.quality.dto.BatchQuickInspectRequest;
 import com.ruoyi.quality.dto.QualityInspectDto;
 import com.ruoyi.quality.mapper.QualityInspectMapper;
 import com.ruoyi.quality.mapper.QualityTestStandardMapper;
@@ -32,12 +36,17 @@
 import lombok.AllArgsConstructor;
 import org.springframework.beans.BeanUtils;
 import org.springframework.stereotype.Service;
+import org.springframework.transaction.annotation.Propagation;
 import org.springframework.transaction.annotation.Transactional;
 
 import java.io.InputStream;
 import java.io.OutputStream;
 import java.math.BigDecimal;
 import java.net.URLEncoder;
+import java.sql.Date;
+import java.time.LocalDate;
+import java.time.LocalDateTime;
+import java.util.ArrayList;
 import java.util.Arrays;
 import java.util.HashMap;
 import java.util.List;
@@ -90,16 +99,32 @@
     @Override
     public int submit(QualityInspect inspect) {
         QualityInspect qualityInspect = qualityInspectMapper.selectById(inspect.getId());
+
         //鎻愪氦鍓嶅繀椤诲垽鏂槸鍚﹀悎鏍�
         if (ObjectUtils.isNull(qualityInspect.getCheckResult())) {
-            throw new RuntimeException("璇峰厛鍒ゆ柇鏄惁鍚堟牸");
+            throw new ServiceException("璇峰厛鍒ゆ柇鏄惁鍚堟牸");
         }
 
-        // 鍖哄垎鍚堟牸鏁伴噺浠ュ強涓嶅悎鏍煎鐞嗚繘琛屽搴旂殑澶勭悊
-        Assert.isTrue(qualityInspect.getQuantity().compareTo(qualityInspect.getQualifiedQuantity().add(qualityInspect.getUnqualifiedQuantity())) == 0,"璇锋鏌ュ悎鏍兼暟閲忓拰涓嶅悎鏍兼暟閲忥紝闇�瑕佸悎鏍兼暟閲�+涓嶅悎鏍兼暟閲忎笌鎬绘暟淇濇寔涓�鑷�");
+        if (ObjectUtils.isNull(qualityInspect.getQualifiedQuantity())) {
+            throw new ServiceException("鍚堟牸鏁伴噺涓嶈兘涓虹┖");
+        }
+
+        if (ObjectUtils.isNull(qualityInspect.getUnqualifiedQuantity())) {
+            throw new ServiceException("涓嶅悎鏍兼暟閲忎笉鑳戒负绌�");
+        }
+
+        // 濡傛灉鍚堟牸鏁伴噺涓虹┖锛岃涓�0
+        if (qualityInspect.getQualifiedQuantity() == null) {
+            qualityInspect.setQualifiedQuantity(BigDecimal.ZERO);
+        }
+
+        // 濡傛灉涓嶅悎鏍兼暟閲忎负绌猴紝璁句负0
+        if (qualityInspect.getUnqualifiedQuantity() == null) {
+            qualityInspect.setUnqualifiedQuantity(BigDecimal.ZERO);
+        }
+
+        // 鍚堟牸鐩存帴鍏ュ簱
         if(qualityInspect.getQualifiedQuantity().compareTo(BigDecimal.ZERO) > 0){
-            //鍚堟牸鐩存帴鍏ュ簱
-            // stockUtils.addStock(qualityInspect.getProductModelId(), qualityInspect.getQuantity(), StockInQualifiedRecordTypeEnum.QUALITYINSPECT_STOCK_IN.getCode(), qualityInspect.getId());
             //浠呮坊鍔犲叆搴撹褰�
             StockInventoryDto stockInventoryDto = new StockInventoryDto();
             //濡傛灉鏄噰璐川妫�鍚堟牸鍏ュ簱閫夌敤CUSTOMIZATION_UNSTOCK_OUT,鍏朵綑鍚堟牸鍏ュ簱閫夌敤QUALITYINSPECT_STOCK_IN
@@ -110,17 +135,23 @@
             stockInventoryDto.setRecordId(qualityInspect.getId());
             stockInventoryDto.setProductModelId(qualityInspect.getProductModelId());
             stockInventoryDto.setQualitity(qualityInspect.getQualifiedQuantity());
+            if (qualityInspect.getCheckTime() != null) {
+                LocalDate stockCreateDate = DateUtils.toLocalDate(qualityInspect.getCheckTime()).plusDays(1);
+                stockInventoryDto.setCreateTime(LocalDateTime.of(stockCreateDate, java.time.LocalTime.MIDNIGHT));
+            }
             stockInventoryDto.setBatchNo(resolveProductionBatchNo(
                     qualityInspect.getProductMainId(),
                     qualityInspect.getId(),
                     qualityInspect.getProductModelId()));
             stockInventoryService.addStockInRecordOnly(stockInventoryDto);
         }
+        // 涓嶅悎鏍煎鐞�
         if(qualityInspect.getUnqualifiedQuantity().compareTo(BigDecimal.ZERO) > 0){
             QualityUnqualified qualityUnqualified = new QualityUnqualified();
             BeanUtils.copyProperties(qualityInspect, qualityUnqualified);
             qualityUnqualified.setInspectState(0);//寰呭鐞�
             qualityUnqualified.setQuantity(qualityInspect.getUnqualifiedQuantity());
+            qualityUnqualified.setProductModelId(qualityInspect.getProductModelId());
             List<QualityInspectParam> inspectParams = qualityInspectParamService.list(Wrappers.<QualityInspectParam>lambdaQuery().eq(QualityInspectParam::getInspectId, inspect.getId()));
             String text = inspectParams.stream().map(QualityInspectParam::getParameterItem).collect(Collectors.joining(","));
             qualityUnqualified.setDefectivePhenomena(text + "杩欎簺鎸囨爣涓瓨鍦ㄤ笉鍚堟牸");//涓嶅悎鏍肩幇璞�
@@ -132,6 +163,180 @@
         return qualityInspectMapper.updateById(qualityInspect);
     }
 
+    @Override
+    public R autoSubmit(Long id) {
+        if (id == null) {
+            return R.fail("妫�楠屽崟ID涓嶈兘涓虹┖");
+        }
+        QualityInspect qualityInspect = qualityInspectMapper.selectById(id);
+        if (qualityInspect == null) {
+            return R.fail("妫�楠屽崟涓嶅瓨鍦�");
+        }
+        if (Integer.valueOf(1).equals(qualityInspect.getInspectState())) {
+            return R.ok("妫�楠屽崟宸叉彁浜�");
+        }
+
+        if (ObjectUtils.isNull(qualityInspect.getCheckResult())) {
+            qualityInspect.setCheckResult("鍚堟牸");
+        }
+        if (ObjectUtils.isNull(qualityInspect.getQualifiedQuantity())) {
+            qualityInspect.setQualifiedQuantity(qualityInspect.getQuantity() == null ? BigDecimal.ZERO : qualityInspect.getQuantity());
+        }
+        if (ObjectUtils.isNull(qualityInspect.getUnqualifiedQuantity())) {
+            qualityInspect.setUnqualifiedQuantity(BigDecimal.ZERO);
+        }
+        qualityInspectMapper.updateById(qualityInspect);
+        int rows = submit(qualityInspect);
+        return rows > 0 ? R.ok("妫�楠屽崟鎻愪氦鎴愬姛") : R.fail("妫�楠屽崟鎻愪氦澶辫触");
+    }
+
+    @Override
+    public R batchQuickInspect(BatchQuickInspectRequest request) {
+        // 1. 鏁版嵁鏍¢獙
+        if (request.getIds() == null || request.getIds().isEmpty()) {
+            return R.fail("璇烽�夋嫨鑷冲皯涓�鏉℃楠屽崟");
+        }
+        List<String> validResults = Arrays.asList("鍚堟牸", "涓嶅悎鏍�", "閮ㄥ垎鍚堟牸");
+        if (!validResults.contains(request.getCheckResult())) {
+            return R.fail("妫�娴嬬粨鏋滃繀椤讳负锛氬悎鏍笺�佷笉鍚堟牸銆侀儴鍒嗗悎鏍�");
+        }
+        if (request.getQuantity() == null || request.getQuantity().compareTo(BigDecimal.ZERO) <= 0) {
+            return R.fail("鎬绘暟閲忓繀椤诲ぇ浜�0");
+        }
+        if (request.getTestStandardId() == null) {
+            return R.fail("鎸囨爣鏍囧噯ID涓嶈兘涓虹┖");
+        }
+        // quantity = qualifiedQuantity + unqualifiedQuantity
+        BigDecimal qty = request.getQuantity();
+        BigDecimal qualified = request.getQualifiedQuantity() != null ? request.getQualifiedQuantity() : BigDecimal.ZERO;
+        BigDecimal unqualified = request.getUnqualifiedQuantity() != null ? request.getUnqualifiedQuantity() : BigDecimal.ZERO;
+        if (qty.compareTo(qualified.add(unqualified)) != 0) {
+            return R.fail("鎬绘暟閲忓繀椤荤瓑浜庡悎鏍兼暟閲忓姞涓嶅悎鏍兼暟閲�");
+        }
+        String checkResult = request.getCheckResult();
+        if ("鍚堟牸".equals(checkResult)) {
+            if (qualified.compareTo(qty) != 0 || unqualified.compareTo(BigDecimal.ZERO) != 0) {
+                return R.fail("妫�楠岀粨鏋滀负鍚堟牸鏃讹紝鍚堟牸鏁伴噺搴旂瓑浜庢�绘暟閲忥紝涓嶅悎鏍兼暟閲忓簲涓�0");
+            }
+        } else if ("涓嶅悎鏍�".equals(checkResult)) {
+            if (qualified.compareTo(BigDecimal.ZERO) != 0 || unqualified.compareTo(qty) != 0) {
+                return R.fail("妫�楠岀粨鏋滀负涓嶅悎鏍兼椂锛屽悎鏍兼暟閲忓簲涓�0锛屼笉鍚堟牸鏁伴噺搴旂瓑浜庢�绘暟閲�");
+            }
+        } else {
+            if (qualified.compareTo(BigDecimal.ZERO) <= 0 || unqualified.compareTo(BigDecimal.ZERO) <= 0) {
+                return R.fail("妫�楠岀粨鏋滀负閮ㄥ垎鍚堟牸鏃讹紝鍚堟牸鏁伴噺鍜屼笉鍚堟牸鏁伴噺閮藉繀椤诲ぇ浜�0");
+            }
+        }
+
+        // 瑙f瀽妫�娴嬫棩鏈�
+        Date checkTimeDate = null;
+        if (request.getCheckTime() != null && !request.getCheckTime().isEmpty()) {
+            checkTimeDate = Date.valueOf(LocalDate.parse(request.getCheckTime()));
+        }
+
+        int success = 0;
+        List<String> errors = new ArrayList<>();
+
+        for (Long id : request.getIds()) {
+            try {
+                // 浣跨敤鐙珛浜嬪姟澶勭悊姣忎釜妫�楠屽崟锛岄伩鍏嶅崟涓け璐ュ奖鍝嶆暣浣撲簨鍔�
+                processSingleInspect(id, request, checkResult, qty, qualified, unqualified, checkTimeDate);
+                success++;
+            } catch (Exception e) {
+                errors.add("妫�楠屽崟 " + id + " 澶勭悊澶辫触锛�" + e.getMessage());
+            }
+        }
+
+        if (!errors.isEmpty()) {
+            return R.ok(String.format("蹇�熸楠屽畬鎴愶細鎴愬姛 %d 鏉★紝澶辫触 %d 鏉°�傚け璐ュ師鍥狅細%s",
+                    success, errors.size(), String.join("锛�", errors)));
+        }
+        return R.ok(String.format("蹇�熸楠屽畬鎴愶細鎴愬姛 %d 鏉�", success));
+    }
+
+    /**
+     * 鍦ㄧ嫭绔嬩簨鍔′腑澶勭悊鍗曚釜妫�楠屽崟
+     */
+    @Transactional(rollbackFor = Exception.class, propagation = Propagation.REQUIRES_NEW)
+    public void processSingleInspect(Long id, BatchQuickInspectRequest request,
+                                     String checkResult, BigDecimal qty,
+                                     BigDecimal qualified, BigDecimal unqualified,
+                                     Date checkTimeDate) {
+        QualityInspect qualityInspect = qualityInspectMapper.selectById(id);
+        if (qualityInspect == null) {
+            throw new RuntimeException("妫�楠屽崟涓嶅瓨鍦�");
+        }
+        if (Integer.valueOf(1).equals(qualityInspect.getInspectState())) {
+            throw new RuntimeException("妫�楠屽崟宸叉彁浜�");
+        }
+
+        // 2. 鏇存柊妫�楠屽崟瀛楁
+        qualityInspect.setCheckResult(checkResult);
+        qualityInspect.setTestStandardId(request.getTestStandardId());
+        qualityInspect.setQuantity(qty);
+        qualityInspect.setQualifiedQuantity(qualified);
+        qualityInspect.setUnqualifiedQuantity(unqualified);
+        if (request.getCheckCompany() != null) {
+            qualityInspect.setCheckCompany(request.getCheckCompany());
+        }
+        if (request.getCheckName() != null) {
+            qualityInspect.setCheckName(request.getCheckName());
+        }
+        if (checkTimeDate != null) {
+            qualityInspect.setCheckTime(checkTimeDate);
+        }
+        qualityInspect.setInspectState(1);
+
+        // 3. 淇濆瓨妫�楠屽弬鏁�
+        if (request.getParamList() != null && !request.getParamList().isEmpty()) {
+            qualityInspectParamService.remove(Wrappers.<QualityInspectParam>lambdaQuery()
+                    .eq(QualityInspectParam::getInspectId, id));
+            for (QualityInspectParam param : request.getParamList()) {
+                param.setInspectId(id);
+                param.setId(null);
+            }
+            qualityInspectParamService.saveBatch(request.getParamList());
+        }
+
+        // 4. 鏇存柊妫�楠屽崟
+        qualityInspectMapper.updateById(qualityInspect);
+
+        // 5. 鍚堟牸鍏ュ簱澶勭悊
+        if (qualified.compareTo(BigDecimal.ZERO) > 0) {
+            StockInventoryDto stockInventoryDto = new StockInventoryDto();
+            stockInventoryDto.setRecordType(String.valueOf(StockInQualifiedRecordTypeEnum.QUALITYINSPECT_STOCK_IN.getCode()));
+            if (ObjectUtils.isNotEmpty(qualityInspect.getPurchaseLedgerId())) {
+                stockInventoryDto.setRecordType(String.valueOf(StockInQualifiedRecordTypeEnum.CUSTOMIZATION_UNSTOCK_OUT.getCode()));
+            }
+            stockInventoryDto.setRecordId(qualityInspect.getId());
+            stockInventoryDto.setProductModelId(qualityInspect.getProductModelId());
+            stockInventoryDto.setQualitity(qualified);
+            if (qualityInspect.getCheckTime() != null) {
+                LocalDate stockCreateDate = DateUtils.toLocalDate(qualityInspect.getCheckTime()).plusDays(1);
+                stockInventoryDto.setCreateTime(LocalDateTime.of(stockCreateDate, java.time.LocalTime.MIDNIGHT));
+            }
+            stockInventoryDto.setBatchNo(resolveProductionBatchNo(
+                    qualityInspect.getProductMainId(),
+                    qualityInspect.getId(),
+                    qualityInspect.getProductModelId()));
+            stockInventoryService.addStockInRecordOnly(stockInventoryDto);
+        }
+
+        // 6. 涓嶅悎鏍煎鐞�
+        if (unqualified.compareTo(BigDecimal.ZERO) > 0) {
+            QualityUnqualified qualityUnqualified = new QualityUnqualified();
+            BeanUtils.copyProperties(qualityInspect, qualityUnqualified);
+            qualityUnqualified.setInspectState(0);
+            qualityUnqualified.setQuantity(unqualified);
+            List<QualityInspectParam> inspectParams = qualityInspectParamService.list(
+                    Wrappers.<QualityInspectParam>lambdaQuery().eq(QualityInspectParam::getInspectId, id));
+            String text = inspectParams.stream().map(QualityInspectParam::getParameterItem).collect(Collectors.joining(","));
+            qualityUnqualified.setDefectivePhenomena(text + "杩欎簺鎸囨爣涓瓨鍦ㄤ笉鍚堟牸");
+            qualityUnqualified.setInspectId(id);
+            qualityUnqualifiedMapper.insert(qualityUnqualified);
+        }
+    }
+
     private String resolveProductionBatchNo(Long productionProductMainId,
                                             Long qualityInspectId,
                                             Long productModelId) {

--
Gitblit v1.9.3