Просмотр исходного кода

新增‘修改驳回准入’接口;优化合同状态动态调整

fuyuchuan 5 дней назад
Родитель
Сommit
90f4f26080

+ 3 - 0
service-vpp/service-vpp-biz/src/main/java/com/usky/vpp/controller/web/ContractController.java

@@ -86,6 +86,7 @@ public class ContractController {
 
     /**
      * 新增合同
+     * <p>合同状态根据生效/到期日期自动计算,无需手动传入生命周期状态。</p>
      */
     @PostMapping
     public ApiResult<Boolean> create(@RequestBody VppContractRequestVO vo) {
@@ -94,6 +95,8 @@ public class ContractController {
 
     /**
      * 修改合同
+     * <p>合同状态根据生效/到期日期自动计算:未到生效时间为待生效,已过生效时间为已生效,已过到期时间为已到期;
+     * 草稿、审核中、已驳回、已终止状态不受日期影响。</p>
      */
     @PutMapping
     public ApiResult<Boolean> update(@RequestBody VppContractRequestVO vo) {

+ 10 - 0
service-vpp/service-vpp-biz/src/main/java/com/usky/vpp/controller/web/CustomerController.java

@@ -81,6 +81,16 @@ public class CustomerController {
         return ApiResult.success();
     }
 
+    /**
+     * 修改准入申请(仅已驳回状态可修改,修改后重新进入待审核)
+     */
+    @PutMapping("/access")
+    public ApiResult<Boolean> updateAccess(@RequestBody CustomerAccessRequestVO vo) {
+        return vppCustomerService.updateAccess(vo)
+                ? ApiResult.success(true)
+                : ApiResult.error("修改准入申请失败,请重试!");
+    }
+
     /**
      * 删除准入申请(软删除)
      */

+ 5 - 0
service-vpp/service-vpp-biz/src/main/java/com/usky/vpp/service/VppCustomerService.java

@@ -40,6 +40,11 @@ public interface VppCustomerService {
      */
     void auditAccess(CustomerAccessAuditRequest request);
 
+    /**
+     * 修改已驳回的准入申请(修改后重新进入待审核)
+     */
+    Boolean updateAccess(CustomerAccessRequestVO request);
+
     /**
      * 删除准入申请(软删除)
      */

+ 13 - 8
service-vpp/service-vpp-biz/src/main/java/com/usky/vpp/service/impl/VppContractServiceImpl.java

@@ -15,6 +15,7 @@ import com.usky.vpp.service.VppContractService;
 import com.usky.vpp.service.vo.VppContractRequestVO;
 import com.usky.vpp.service.vo.VppContractResponseVO;
 import com.usky.vpp.util.VppAuditHelper;
+import com.usky.vpp.util.VppContractStatusHelper;
 import com.usky.vpp.util.VppFieldValidator;
 import org.apache.commons.lang3.StringUtils;
 import org.springframework.beans.factory.annotation.Autowired;
@@ -73,7 +74,8 @@ public class VppContractServiceImpl implements VppContractService {
         contract.setTemplateId(vo.getTemplateId());
         contract.setContractType(vo.getContractType());
         contract.setContractName(vo.getContractName());
-        contract.setContractStatus(vo.getContractStatus());
+        contract.setContractStatus(VppContractStatusHelper.resolveForPersist(
+                vo.getContractStatus(), vo.getEffectiveDate(), vo.getExpireDate()));
         contract.setSignDate(vo.getSignDate());
         contract.setEffectiveDate(vo.getEffectiveDate());
         contract.setExpireDate(vo.getExpireDate());
@@ -117,9 +119,6 @@ public class VppContractServiceImpl implements VppContractService {
         if (StringUtils.isNotBlank(vo.getContractName())) {
             existingRecord.setContractName(vo.getContractName());
         }
-        if (vo.getContractStatus() != null) {
-            existingRecord.setContractStatus(vo.getContractStatus());
-        }
         if (vo.getSignDate() != null) {
             existingRecord.setSignDate(vo.getSignDate());
         }
@@ -145,6 +144,11 @@ public class VppContractServiceImpl implements VppContractService {
             existingRecord.setRemark(vo.getRemark());
         }
 
+        Integer requestedStatus = vo.getContractStatus() != null
+                ? vo.getContractStatus() : existingRecord.getContractStatus();
+        existingRecord.setContractStatus(VppContractStatusHelper.resolveForPersist(
+                requestedStatus, existingRecord.getEffectiveDate(), existingRecord.getExpireDate()));
+
         VppAuditHelper.fillUpdate(existingRecord);
 
         int result = vppContractMapper.updateById(existingRecord);
@@ -164,9 +168,9 @@ public class VppContractServiceImpl implements VppContractService {
                 .le(signDateEnd != null, VppContract::getSignDate, signDateEnd)
                 .eq(templateId != null, VppContract::getTemplateId, templateId)
                 .eq(contractType != null, VppContract::getContractType, contractType)
-                .eq(customerId != null, VppContract::getCustomerId, customerId)
-                .eq(contractStatus != null, VppContract::getContractStatus, contractStatus)
-                .orderByDesc(VppContract::getCreateTime);
+                .eq(customerId != null, VppContract::getCustomerId, customerId);
+        VppContractStatusHelper.applyStatusFilter(queryWrapper, contractStatus);
+        queryWrapper.orderByDesc(VppContract::getCreateTime);
         page = vppContractMapper.selectPage(page, queryWrapper);
 
         List<VppContract> records = page.getRecords();
@@ -197,7 +201,8 @@ public class VppContractServiceImpl implements VppContractService {
             vo.setTemplateName(templateNameMap.get(entity.getTemplateId()));
             vo.setContractType(entity.getContractType());
             vo.setContractName(entity.getContractName());
-            vo.setContractStatus(entity.getContractStatus());
+            vo.setContractStatus(VppContractStatusHelper.resolve(
+                    entity.getContractStatus(), entity.getEffectiveDate(), entity.getExpireDate()));
             vo.setSignDate(entity.getSignDate());
             vo.setEffectiveDate(entity.getEffectiveDate());
             vo.setExpireDate(entity.getExpireDate());

+ 45 - 1
service-vpp/service-vpp-biz/src/main/java/com/usky/vpp/service/impl/VppCustomerServiceImpl.java

@@ -23,6 +23,7 @@ import com.usky.vpp.service.vo.CustomerContactRequest;
 import com.usky.vpp.service.vo.CustomerRequestVO;
 import com.usky.vpp.service.vo.CustomerResponseVO;
 import com.usky.vpp.util.VppAuditHelper;
+import com.usky.vpp.util.VppContractStatusHelper;
 import com.usky.vpp.util.VppFieldValidator;
 import lombok.extern.slf4j.Slf4j;
 import org.apache.commons.lang3.StringUtils;
@@ -201,6 +202,48 @@ public class VppCustomerServiceImpl implements VppCustomerService {
         accessMapper.updateById(access);
     }
 
+    @Override
+    @Transactional(rollbackFor = Exception.class)
+    public Boolean updateAccess(CustomerAccessRequestVO request) {
+        if (request.getId() == null) {
+            throw new BusinessException("准入申请ID不能为空!");
+        }
+        validateAccessRequest(request);
+
+        VppCustomerAccess access = findAccessById(request.getId());
+        if (access.getAccessStatus() != ACCESS_REJECTED) {
+            throw new BusinessException("仅已驳回的准入申请允许修改!");
+        }
+
+        LambdaQueryWrapper<VppCustomerAccess> dupWrapper = new LambdaQueryWrapper<>();
+        dupWrapper.eq(VppCustomerAccess::getAccountNo, request.getAccountNo())
+                .eq(VppCustomerAccess::getTenantId, SecurityUtils.getTenantId())
+                .eq(VppCustomerAccess::getDeleteFlag, VppAuditHelper.NOT_DELETED)
+                .ne(VppCustomerAccess::getId, request.getId());
+        Integer accessCount = accessMapper.selectCount(dupWrapper);
+        if (accessCount != null && accessCount > 0) {
+            throw new BusinessException("该电力户号已存在准入申请,请勿重复提交!");
+        }
+
+        access.setAccountNo(request.getAccountNo());
+        access.setCustomerName(request.getCustomerName());
+        access.setCustomerType(request.getCustomerType());
+        access.setPowerCompany(request.getPowerCompany());
+        access.setContractCapacity(request.getContractCapacity());
+        access.setBusinessLicenseUrl(request.getBusinessLicenseUrl());
+        access.setCreditStatus(request.getCreditStatus());
+        access.setContactName(request.getContactName());
+        access.setContactPhone(request.getContactPhone());
+        access.setContactEmail(request.getContactEmail());
+        access.setAccessStatus(ACCESS_PENDING);
+        access.setAuditOpinion(null);
+        access.setAuditAt(null);
+        access.setApplyAt(LocalDateTime.now());
+
+        VppAuditHelper.fillUpdate(access);
+        return accessMapper.updateById(access) > 0;
+    }
+
     @Override
     @Transactional(rollbackFor = Exception.class)
     public Boolean deleteAccess(Long id) {
@@ -953,7 +996,8 @@ public class VppCustomerServiceImpl implements VppCustomerService {
         brief.setContractNo(contract.getContractNo());
         brief.setContractName(contract.getContractName());
         brief.setContractType(contract.getContractType());
-        brief.setContractStatus(contract.getContractStatus());
+        brief.setContractStatus(VppContractStatusHelper.resolve(
+                contract.getContractStatus(), contract.getEffectiveDate(), contract.getExpireDate()));
         brief.setSignDate(contract.getSignDate());
         brief.setEffectiveDate(contract.getEffectiveDate());
         brief.setExpireDate(contract.getExpireDate());

+ 5 - 0
service-vpp/service-vpp-biz/src/main/java/com/usky/vpp/service/vo/CustomerAccessRequestVO.java

@@ -16,6 +16,11 @@ import java.time.LocalDateTime;
 @Data
 public class CustomerAccessRequestVO {
 
+    /**
+     * 主键(修改已驳回准入申请时必传)
+     */
+    private Long id;
+
     /**
      * 电力户号
      */

+ 92 - 0
service-vpp/service-vpp-biz/src/main/java/com/usky/vpp/util/VppContractStatusHelper.java

@@ -0,0 +1,92 @@
+package com.usky.vpp.util;
+
+import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
+import com.usky.vpp.domain.VppContract;
+
+import java.time.LocalDate;
+import java.util.Arrays;
+import java.util.HashSet;
+import java.util.Set;
+
+/**
+ * 合同状态工具:根据生效/到期日期自动解析生命周期状态
+ */
+public final class VppContractStatusHelper {
+
+    public static final int DRAFT = 0;
+    public static final int AUDITING = 1;
+    public static final int PENDING = 2;
+    public static final int EFFECTIVE = 3;
+    public static final int REJECTED = 4;
+    public static final int EXPIRED = 5;
+    public static final int TERMINATED = 6;
+
+    private static final Set<Integer> MANUAL_STATUSES = new HashSet<>(Arrays.asList(
+            DRAFT, AUDITING, REJECTED, TERMINATED
+    ));
+
+    private VppContractStatusHelper() {
+    }
+
+    /**
+     * 根据生效/到期日期解析合同状态;草稿、审核中、已驳回、已终止保持原状态不变。
+     */
+    public static Integer resolve(Integer storedStatus, LocalDate effectiveDate, LocalDate expireDate) {
+        if (storedStatus != null && MANUAL_STATUSES.contains(storedStatus)) {
+            return storedStatus;
+        }
+        return resolveByDates(effectiveDate, expireDate, storedStatus);
+    }
+
+    /**
+     * 创建/更新时根据日期计算应写入的状态;未提供日期时回退为待生效。
+     */
+    public static Integer resolveForPersist(Integer requestedStatus, LocalDate effectiveDate, LocalDate expireDate) {
+        if (requestedStatus != null && MANUAL_STATUSES.contains(requestedStatus)) {
+            return requestedStatus;
+        }
+        Integer resolved = resolveByDates(effectiveDate, expireDate, requestedStatus);
+        return resolved != null ? resolved : PENDING;
+    }
+
+    private static Integer resolveByDates(LocalDate effectiveDate, LocalDate expireDate, Integer fallback) {
+        LocalDate today = LocalDate.now();
+        if (expireDate != null && today.isAfter(expireDate)) {
+            return EXPIRED;
+        }
+        if (effectiveDate != null) {
+            return today.isBefore(effectiveDate) ? PENDING : EFFECTIVE;
+        }
+        return fallback;
+    }
+
+    /**
+     * 分页筛选:将生命周期状态(待生效/已生效/已到期)转换为日期条件。
+     */
+    public static void applyStatusFilter(LambdaQueryWrapper<VppContract> wrapper, Integer contractStatus) {
+        if (contractStatus == null) {
+            return;
+        }
+        LocalDate today = LocalDate.now();
+        if (contractStatus == PENDING) {
+            wrapper.and(w -> w.in(VppContract::getContractStatus, PENDING, EFFECTIVE, EXPIRED)
+                    .gt(VppContract::getEffectiveDate, today)
+                    .and(inner -> inner.isNull(VppContract::getExpireDate)
+                            .or().ge(VppContract::getExpireDate, today)));
+            return;
+        }
+        if (contractStatus == EFFECTIVE) {
+            wrapper.and(w -> w.in(VppContract::getContractStatus, PENDING, EFFECTIVE, EXPIRED)
+                    .le(VppContract::getEffectiveDate, today)
+                    .and(inner -> inner.isNull(VppContract::getExpireDate)
+                            .or().ge(VppContract::getExpireDate, today)));
+            return;
+        }
+        if (contractStatus == EXPIRED) {
+            wrapper.and(w -> w.in(VppContract::getContractStatus, PENDING, EFFECTIVE, EXPIRED)
+                    .lt(VppContract::getExpireDate, today));
+            return;
+        }
+        wrapper.eq(VppContract::getContractStatus, contractStatus);
+    }
+}