소스 검색

fix(payment): 修复支付金额计算逻辑和数据更新问题

- 修复了锅炉任务订单支付取消和正常缴费的数据库原子操作逻辑
- 修复了管道任务订单支付取消和正常缴费的数据库原子操作逻辑
- 添加了OA流程创建中的报告编号和属性字段设置功能
- 修复了锅炉检验报告接收人手机号码的存储问题
- 优化了控制器中的用户权限验证逻辑
xuzhancheng 3 일 전
부모
커밋
083e5dfb44

+ 6 - 11
tz-module-pressure2/tz-module-pressure2-biz/src/main/java/cn/start/tz/module/pressure2/controller/app/taskorder/BoilerTaskOrderIssueReportAppController.java

@@ -90,17 +90,12 @@ public class BoilerTaskOrderIssueReportAppController {
      @GetMapping("/record-equip/page")
      @PermitAll
      public CommonResult<PageResult<TaskOrderIssueReportItemRespVO>> getTaskOrderIssueReportEquipPageApp(@Valid TaskOrderIssueReportPageReqVO pageReqVO) {
-//         String mobile = getLoginUserMobile();
-//         if(StringUtils.isNotBlank(mobile)){
-//             pageReqVO.setRecipientPhone(mobile);
-//         }else{
-//             return success(PageResult.empty());
-//         }
-
-//         String currentUserUnitId = miniAuthService.getCurrentUserUnitCode();
-//         if(!"-1".equals(currentUserUnitId)){
-//             pageReqVO.setUnitCode(currentUserUnitId);
-//         }
+         String mobile = getLoginUserMobile();
+         if(StringUtils.isNotBlank(mobile)){
+             pageReqVO.setRecipientPhone(mobile);
+         }else{
+             return success(PageResult.empty());
+         }
 
          PageResult<TaskOrderIssueReportItemRespVO> pageResult = boilerTaskOrderIssueReportService.getTaskOrderIssueReportEquipPageApp(pageReqVO);
          return success(pageResult);

+ 6 - 10
tz-module-pressure2/tz-module-pressure2-biz/src/main/java/cn/start/tz/module/pressure2/controller/app/taskorder/PipeTaskOrderIssueReportAppController.java

@@ -108,17 +108,13 @@ public class PipeTaskOrderIssueReportAppController {
     @PermitAll
 
     public CommonResult<PageResult<TaskOrderIssueReportItemRespVO>> getTaskOrderIssueReportEquipPageApp(@Valid TaskOrderIssueReportPageReqVO pageReqVO) {
-//        String mobile = getLoginUserMobile();
-//        if(StringUtils.isNotBlank(mobile)){
-//            pageReqVO.setRecipientPhone(mobile);
-//        }else{
-//            return success(PageResult.empty());
-//        }
+        String mobile = getLoginUserMobile();
+        if(StringUtils.isNotBlank(mobile)){
+            pageReqVO.setRecipientPhone(mobile);
+        }else{
+            return success(PageResult.empty());
+        }
 
-//         String currentUserUnitId = miniAuthService.getCurrentUserUnitCode();
-//         if(!"-1".equals(currentUserUnitId)){
-//             pageReqVO.setUnitCode(currentUserUnitId);
-//         }
 
         PageResult<TaskOrderIssueReportItemRespVO> pageResult = pipeTaskOrderIssueReportService.getTaskOrderIssueReportEquipPageApp(pageReqVO);
         return success(pageResult);

+ 1 - 0
tz-module-pressure2/tz-module-pressure2-biz/src/main/java/cn/start/tz/module/pressure2/service/boilertaskorder/BoilerTaskOrderInspectionServiceImpl.java

@@ -201,6 +201,7 @@ public class BoilerTaskOrderInspectionServiceImpl implements BoilerTaskOrderInsp
                     updateObj.setId(taskOrderItemReportDO.getId());
                     updateObj.setMpSendStatus(4);
                     updateObj.setRecipient(inspectionOpinionSendVo.getRecipient());
+                    updateObj.setRecipientPhone(inspectionOpinionSendVo.getRecipientPhone());
                     taskOrderItemReportMapper.updateById(updateObj);
 
                     //添加业务与平台用户关联

+ 28 - 32
tz-module-pressure2/tz-module-pressure2-biz/src/main/java/cn/start/tz/module/pressure2/service/boilertaskorder/BoilerTaskOrderServiceImpl.java

@@ -3916,11 +3916,17 @@ public class BoilerTaskOrderServiceImpl extends ServiceImpl<BoilerTaskOrderMappe
     private ExternalOACreateFlowRes createExternalOAFlow(BoilerTaskOrderItemReportDO taskOrderItemReportDO, BoilerTaskOrderItemReportDO updateObj) throws Exception {
         BoilerTaskOrderItemDO boilerTaskOrderItemDO = boilerTaskOrderItemMapper.selectById(taskOrderItemReportDO.getOrderItemId());
         BoilerTaskOrderDO boilerTaskOrderDO = boilerTaskOrderMapper.selectById(boilerTaskOrderItemDO.getOrderId());
+        String equipId = boilerTaskOrderItemDO.getEquipId();
+        EquipBoilerDO equipBoilerDO = equipBoilerMapper.selectById(equipId);
         ExternalOACreateFlowReq externalOACreateFlowReq = new ExternalOACreateFlowReq();
         ExternalOACreateFlowBodyDataReq.FormMain formmain_0042 = new ExternalOACreateFlowBodyDataReq.FormMain();
         formmain_0042.setContractno(boilerTaskOrderDO.getUnitName());
         formmain_0042.setUnitname(taskOrderItemReportDO.getReportNo());
         formmain_0042.setDeptName("锅炉");
+        formmain_0042.setReportnum(taskOrderItemReportDO.getReportNo().substring(0, 2));
+        //  设备类型是锅炉,设备小类非电站锅炉,且关联部门是电站锅炉检验部的就传1,否则传0
+        DeptRespDTO data = deptApi.getDept(equipBoilerDO.getRelatedDepartment()).getCheckedData();
+        formmain_0042.setProperty(!equipBoilerDO.getType().equals("1") && data.getName().equals("锅炉检验部") ? "1" : "0");
         formmain_0042.setBeginDate(boilerTaskOrderDO.getRemark());
         ExternalOACreateFlowBodyDataReq externalOACreateFlowBodyDataReq = new ExternalOACreateFlowBodyDataReq();
 
@@ -5835,58 +5841,48 @@ public class BoilerTaskOrderServiceImpl extends ServiceImpl<BoilerTaskOrderMappe
             return false;
         }
 
-        // 取消支付
-        BigDecimal payAmount = boilerTaskOrderDO.getPayAmount();
+        // 取消支付 - 使用数据库原子操作扣减,避免并发丢失更新
         if (payInfo.getIsCancel() != null && payInfo.getIsCancel()) {
             LambdaUpdateWrapper<BoilerTaskOrderDO> wrap = new LambdaUpdateWrapper<>();
             wrap.eq(BoilerTaskOrderDO::getId, boilerTaskOrderDO.getId());
 
-            if (payAmount == null || payAmount.compareTo(BigDecimal.ZERO) == 0 || payAmount.equals(payInfo.getChargeAmount())) {
-                wrap.set(BoilerTaskOrderDO::getPayAmount, 0);
-                wrap.set(BoilerTaskOrderDO::getPaymentStatus, 0);
-            }else{
-                wrap.set(BoilerTaskOrderDO::getPayAmount, payAmount.subtract(payInfo.getChargeAmount()));
-                wrap.set(BoilerTaskOrderDO::getPaymentStatus, 1);
-            }
+            BigDecimal cancelAmount = payInfo.getChargeAmount() != null ? payInfo.getChargeAmount() : BigDecimal.ZERO;
+            String cancelAmountStr = cancelAmount.toPlainString();
+            // 单 setSql 合并两个列更新,所有表达式只依赖旧列值,确保不依赖求值顺序
+            // 旧 pay_amount <= cancelAmount 说明扣减后为 0 → 未支付(0);否则 → 部分结算(2)
+            wrap.setSql("pay_amount = GREATEST(0, COALESCE(pay_amount, 0) - " + cancelAmountStr
+                + "), payment_status = CASE WHEN COALESCE(pay_amount, 0) <= " + cancelAmountStr + " THEN 0 ELSE 2 END");
             wrap.set(BoilerTaskOrderDO::getPayTime, null);
             boilerTaskOrderMapper.update(wrap);
             return true;
         }
 
-        BoilerTaskOrderDO updateOrder = new BoilerTaskOrderDO();
-        updateOrder.setId(boilerTaskOrderDO.getId());
+        // 正常缴费 - 使用数据库原子操作累加,避免并发丢失更新
+        LambdaUpdateWrapper<BoilerTaskOrderDO> wrap = new LambdaUpdateWrapper<>();
+        wrap.eq(BoilerTaskOrderDO::getId, boilerTaskOrderDO.getId());
+
+        BigDecimal chargeAmount = payInfo.getChargeAmount() != null ? payInfo.getChargeAmount() : BigDecimal.ZERO;
+        String chargeAmountStr = chargeAmount.toPlainString();
+        // 单 setSql 合并两个列更新,所有表达式只依赖旧列值,确保不依赖求值顺序
+        // 旧 pay_amount + chargeAmount >= serviceAmount → 已结算(1);否则 → 部分结算(2)
+        wrap.setSql("pay_amount = COALESCE(pay_amount, 0) + " + chargeAmountStr
+            + ", payment_status = CASE WHEN COALESCE(service_amount, 0) <= COALESCE(pay_amount, 0) + " + chargeAmountStr + " THEN 1 ELSE 2 END");
+
         String chargeTime = payInfo.getChargeTime();
         try {
             LocalDateTime localDateTime = DateUtils.parseDateTimeWithMultipleFormats(chargeTime);
-            updateOrder.setPayTime(localDateTime);
+            wrap.set(BoilerTaskOrderDO::getPayTime, localDateTime);
         } catch (Exception e) {
             log.error("日期转换失败", e);
-            updateOrder.setPayTime(LocalDateTime.now());
-        }
-        try {
-//            updateOrder.setPayAmount(payInfo.getChargeAmount());
-//            if (payInfo.getChargeAmount() == null) {
-//                updateOrder.setPayAmount(boilerTaskOrderDO.getActualAmount());
-//            }
-            // 如果全部缴费满了
-            if (boilerTaskOrderDO.getServiceAmount().equals(payAmount.add(payInfo.getChargeAmount()))) {
-                updateOrder.setPayAmount(boilerTaskOrderDO.getServiceAmount());
-                updateOrder.setPaymentStatus(1);
-            }else{
-                updateOrder.setPayAmount(payAmount.add(payInfo.getChargeAmount()));
-                updateOrder.setPaymentStatus(2);
-            }
-
-        } catch (Exception e) {
-            log.error("payAmount 设置错误", e);
+            wrap.set(BoilerTaskOrderDO::getPayTime, LocalDateTime.now());
         }
 
         if (payInfo.getFeeType() != null) {
             log.info("更新收费形式" + payInfo.getOrderNo());
-            updateOrder.setFeeType(payInfo.getFeeType());
+            wrap.set(BoilerTaskOrderDO::getFeeType, payInfo.getFeeType());
         }
 
-        boilerTaskOrderMapper.updateById(updateOrder);
+        boilerTaskOrderMapper.update(wrap);
         //非合同收费并且不属于免征范围时结算回调后自动发放报告
         if (Integer.valueOf(100).equals(boilerTaskOrderDO.getFeeType()) && (Integer.valueOf(200).equals(boilerTaskOrderDO.getFeeNature()) || boilerTaskOrderDO.getFeeNature() == null)) {
             List<BoilerTaskOrderItemDO> taskOrderItemDOList = boilerTaskOrderItemMapper.selectList(new LambdaQueryWrapperX<BoilerTaskOrderItemDO>().

+ 2 - 0
tz-module-pressure2/tz-module-pressure2-biz/src/main/java/cn/start/tz/module/pressure2/service/externalOA/vo/ExternalOACreateFlowBodyDataReq.java

@@ -16,5 +16,7 @@ public class ExternalOACreateFlowBodyDataReq {
         private String beginDate;
         private String totalFee;
         private String discount;
+        private String reportnum;
+        private String property;
     }
 }

+ 36 - 33
tz-module-pressure2/tz-module-pressure2-biz/src/main/java/cn/start/tz/module/pressure2/service/pipetaskorder/PipeTaskOrderServiceImpl.java

@@ -3132,12 +3132,26 @@ public class PipeTaskOrderServiceImpl extends ServiceImpl<PipeTaskOrderMapper, P
      */
     private ExternalOACreateFlowRes createExternalOAFlow(PipeTaskOrderItemReportDO taskOrderItemReportDO, PipeTaskOrderItemReportDO updateObj) throws Exception {
         PipeTaskOrderDO pipeTaskOrderDO = pipeTaskOrderMapper.selectById(taskOrderItemReportDO.getOrderId());
+        List<PipeTaskOrderItemDO> pipeTaskOrderItemDOS = pipeTaskOrderItemMapper.selectList(PipeTaskOrderItemDO::getOrderId, pipeTaskOrderDO.getId());
+        if (pipeTaskOrderItemDOS.isEmpty()){
+            throw new Exception("没有任务单明细");
+        }
+        PipeTaskOrderItemDO pipeTaskOrderItemDO = pipeTaskOrderItemDOS.get(0);
+        List<PipeTaskOrderItemDetailDO> pipeTaskOrderItemDetailDOS = pipeTaskOrderItemDetailMapper.selectList(PipeTaskOrderItemDetailDO::getOrderId, pipeTaskOrderItemDO.getId());
+        if (pipeTaskOrderItemDetailDOS.isEmpty()){
+            throw new Exception("没有任务单明细");
+        }
+        String equipId = pipeTaskOrderItemDetailDOS.get(0).getEquipDetailId();
+        EquipPipeDetailDO equipPipeDetailDO = equipPipeDetailMapper.selectById(equipId);
         ExternalOACreateFlowReq externalOACreateFlowReq = new ExternalOACreateFlowReq();
         ExternalOACreateFlowBodyDataReq.FormMain formmain_0042 = new ExternalOACreateFlowBodyDataReq.FormMain();
         formmain_0042.setContractno(pipeTaskOrderDO.getUnitName());
         formmain_0042.setUnitname(taskOrderItemReportDO.getReportNo());
         formmain_0042.setDeptName("管道");
         formmain_0042.setBeginDate(pipeTaskOrderDO.getRemark());
+        formmain_0042.setReportnum(taskOrderItemReportDO.getReportNo().substring(0, 2));
+        // 如果注册代码是81开头的,就传1,否则传0
+        formmain_0042.setProperty(equipPipeDetailDO.getPipeRegCode().startsWith("81") ? "1" : "0");
         ExternalOACreateFlowBodyDataReq externalOACreateFlowBodyDataReq = new ExternalOACreateFlowBodyDataReq();
 
         // 重新发送
@@ -5670,59 +5684,48 @@ public class PipeTaskOrderServiceImpl extends ServiceImpl<PipeTaskOrderMapper, P
             return false;
         }
 
-        // 取消支付
-        BigDecimal payAmount = pipeTaskOrderDO.getPayAmount();
+        // 取消支付 - 使用数据库原子操作扣减,避免并发丢失更新
         if (payInfo.getIsCancel() != null && payInfo.getIsCancel()) {
             LambdaUpdateWrapper<PipeTaskOrderDO> wrap = new LambdaUpdateWrapper<>();
             wrap.eq(PipeTaskOrderDO::getId, pipeTaskOrderDO.getId());
 
-            if (payAmount == null || payAmount.compareTo(BigDecimal.ZERO) == 0 || payAmount.equals(payInfo.getChargeAmount())) {
-                wrap.set(PipeTaskOrderDO::getPaymentStatus, 0);
-                wrap.set(PipeTaskOrderDO::getPayAmount, 0);
-            }else{
-                wrap.set(PipeTaskOrderDO::getPaymentStatus, 1);
-                wrap.set(PipeTaskOrderDO::getPayAmount, payAmount.subtract(payInfo.getChargeAmount()));
-            }
+            BigDecimal cancelAmount = payInfo.getChargeAmount() != null ? payInfo.getChargeAmount() : BigDecimal.ZERO;
+            String cancelAmountStr = cancelAmount.toPlainString();
+            // 单 setSql 合并两个列更新,所有表达式只依赖旧列值,确保不依赖求值顺序
+            // 旧 pay_amount <= cancelAmount 说明扣减后为 0 → 未支付(0);否则 → 部分结算(2)
+            wrap.setSql("pay_amount = GREATEST(0, COALESCE(pay_amount, 0) - " + cancelAmountStr
+                + "), payment_status = CASE WHEN COALESCE(pay_amount, 0) <= " + cancelAmountStr + " THEN 0 ELSE 2 END");
             wrap.set(PipeTaskOrderDO::getPayTime, null);
             pipeTaskOrderMapper.update(wrap);
             return true;
         }
 
-        PipeTaskOrderDO updateOrder = new PipeTaskOrderDO();
-        updateOrder.setId(pipeTaskOrderDO.getId());
-//        updateOrder.setPaymentStatus(1);
+        // 正常缴费 - 使用数据库原子操作累加,避免并发丢失更新
+        LambdaUpdateWrapper<PipeTaskOrderDO> wrap = new LambdaUpdateWrapper<>();
+        wrap.eq(PipeTaskOrderDO::getId, pipeTaskOrderDO.getId());
+
+        BigDecimal chargeAmount = payInfo.getChargeAmount() != null ? payInfo.getChargeAmount() : BigDecimal.ZERO;
+        String chargeAmountStr = chargeAmount.toPlainString();
+        // 单 setSql 合并两个列更新,所有表达式只依赖旧列值,确保不依赖求值顺序
+        // 旧 pay_amount + chargeAmount >= serviceAmount → 已结算(1);否则 → 部分结算(2)
+        wrap.setSql("pay_amount = COALESCE(pay_amount, 0) + " + chargeAmountStr
+            + ", payment_status = CASE WHEN COALESCE(service_amount, 0) <= COALESCE(pay_amount, 0) + " + chargeAmountStr + " THEN 1 ELSE 2 END");
+
         String chargeTime = payInfo.getChargeTime();
         try {
             LocalDateTime localDateTime = DateUtils.parseDateTimeWithMultipleFormats(chargeTime);
-            updateOrder.setPayTime(localDateTime);
+            wrap.set(PipeTaskOrderDO::getPayTime, localDateTime);
         } catch (Exception e) {
             log.error("日期转换失败", e);
-            updateOrder.setPayTime(LocalDateTime.now());
-        }
-        try {
-//            updateOrder.setPayAmount(payInfo.getChargeAmount());
-//            if (payInfo.getChargeAmount() == null) {
-//                updateOrder.setPayAmount(boilerTaskOrderDO.getActualAmount());
-//            }
-            // 如果全部缴费满了
-            if (pipeTaskOrderDO.getServiceAmount().equals(payAmount.add(payInfo.getChargeAmount()))) {
-                updateOrder.setPayAmount(pipeTaskOrderDO.getServiceAmount());
-                updateOrder.setPaymentStatus(1);
-            }else{
-                updateOrder.setPayAmount(payAmount.add(payInfo.getChargeAmount()));
-                updateOrder.setPaymentStatus(2);
-            }
-
-        } catch (Exception e) {
-            log.error("payAmount 设置错误", e);
+            wrap.set(PipeTaskOrderDO::getPayTime, LocalDateTime.now());
         }
 
         if (payInfo.getFeeType() != null) {
             log.info("更新收费形式" + payInfo.getOrderNo());
-            updateOrder.setFeeType(payInfo.getFeeType());
+            wrap.set(PipeTaskOrderDO::getFeeType, payInfo.getFeeType());
         }
 
-        pipeTaskOrderMapper.updateById(updateOrder);
+        pipeTaskOrderMapper.update(wrap);
         //非合同收费并且不属于免征范围时结算回调后自动发放报告
         if (Integer.valueOf(100).equals(pipeTaskOrderDO.getFeeType()) && (Integer.valueOf(200).equals(pipeTaskOrderDO.getFeeNature()) || pipeTaskOrderDO.getFeeNature() == null)) {
             List<PipeTaskOrderItemDO> taskOrderItemDOList = pipeTaskOrderItemMapper.selectList(new LambdaQueryWrapperX<PipeTaskOrderItemDO>().