实现项目归档功能
This commit is contained in:
@@ -14,6 +14,7 @@ import com.ruoyi.ccdi.project.service.ICcdiProjectService;
|
||||
import io.swagger.v3.oas.annotations.Operation;
|
||||
import io.swagger.v3.oas.annotations.tags.Tag;
|
||||
import jakarta.annotation.Resource;
|
||||
import com.ruoyi.common.utils.SecurityUtils;
|
||||
import org.springframework.security.access.prepost.PreAuthorize;
|
||||
import org.springframework.validation.annotation.Validated;
|
||||
import org.springframework.web.bind.annotation.*;
|
||||
@@ -53,6 +54,17 @@ public class CcdiProjectController extends BaseController {
|
||||
return AjaxResult.success("项目更新成功", vo);
|
||||
}
|
||||
|
||||
/**
|
||||
* 归档项目
|
||||
*/
|
||||
@PostMapping("/{projectId}/archive")
|
||||
@Operation(summary = "归档项目")
|
||||
@PreAuthorize("@ss.hasPermi('ccdi:project:edit')")
|
||||
public AjaxResult archiveProject(@PathVariable Long projectId) {
|
||||
projectService.archiveProject(projectId, SecurityUtils.getUsername());
|
||||
return AjaxResult.success("项目归档成功");
|
||||
}
|
||||
|
||||
/**
|
||||
* 删除项目
|
||||
*/
|
||||
|
||||
@@ -60,6 +60,14 @@ public interface ICcdiProjectService {
|
||||
*/
|
||||
CcdiProjectStatusCountsVO getStatusCounts();
|
||||
|
||||
/**
|
||||
* 归档项目
|
||||
*
|
||||
* @param projectId 项目ID
|
||||
* @param operator 操作人
|
||||
*/
|
||||
void archiveProject(Long projectId, String operator);
|
||||
|
||||
/**
|
||||
* 更新项目状态
|
||||
*
|
||||
@@ -76,6 +84,14 @@ public interface ICcdiProjectService {
|
||||
*/
|
||||
void ensureProjectCanStartTagging(Long projectId);
|
||||
|
||||
/**
|
||||
* 校验项目是否未归档
|
||||
*
|
||||
* @param projectId 项目ID
|
||||
* @param message 拒绝文案
|
||||
*/
|
||||
void ensureProjectNotArchived(Long projectId, String message);
|
||||
|
||||
/**
|
||||
* 校验项目是否允许写入
|
||||
*
|
||||
|
||||
@@ -169,6 +169,7 @@ public class CcdiFileUploadServiceImpl implements ICcdiFileUploadService {
|
||||
throw new IllegalArgumentException("开始日期不能晚于结束日期");
|
||||
}
|
||||
|
||||
projectService.ensureProjectNotArchived(projectId, "已归档项目暂不允许上传或拉取数据");
|
||||
projectService.ensureProjectWritable(projectId, "当前项目正在进行银行流水打标,暂不允许上传或拉取数据");
|
||||
|
||||
CcdiProject project = projectMapper.selectById(projectId);
|
||||
@@ -323,6 +324,7 @@ public class CcdiFileUploadServiceImpl implements ICcdiFileUploadService {
|
||||
log.info("【文件上传】开始批量上传: projectId={}, 文件数量={}, username={}",
|
||||
projectId, files.length, username);
|
||||
|
||||
projectService.ensureProjectNotArchived(projectId, "已归档项目暂不允许上传或拉取数据");
|
||||
projectService.ensureProjectWritable(projectId, "当前项目正在进行银行流水打标,暂不允许上传或拉取数据");
|
||||
|
||||
// 1. 生成批次ID
|
||||
|
||||
@@ -111,6 +111,7 @@ public class CcdiModelParamServiceImpl implements ICcdiModelParamService {
|
||||
Long projectId = saveDTO.getProjectId();
|
||||
|
||||
if (projectId > 0) {
|
||||
projectService.ensureProjectNotArchived(projectId, "已归档项目暂不允许修改参数");
|
||||
projectService.ensureProjectWritable(projectId, "当前项目正在进行银行流水打标,暂不允许修改参数");
|
||||
switchToCustomConfigIfNeeded(getRequiredProject(projectId));
|
||||
}
|
||||
@@ -192,6 +193,7 @@ public class CcdiModelParamServiceImpl implements ICcdiModelParamService {
|
||||
Long projectId = saveAllDTO.getProjectId();
|
||||
|
||||
if (projectId > 0) {
|
||||
projectService.ensureProjectNotArchived(projectId, "已归档项目暂不允许修改参数");
|
||||
projectService.ensureProjectWritable(projectId, "当前项目正在进行银行流水打标,暂不允许修改参数");
|
||||
switchToCustomConfigIfNeeded(getRequiredProject(projectId));
|
||||
}
|
||||
|
||||
@@ -152,6 +152,26 @@ public class CcdiProjectServiceImpl implements ICcdiProjectService {
|
||||
return vo;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void archiveProject(Long projectId, String operator) {
|
||||
CcdiProject project = getRequiredProject(projectId);
|
||||
if (CcdiProjectStatusConstants.ARCHIVED.equals(project.getStatus())) {
|
||||
throw new ServiceException("项目已归档,无需重复操作");
|
||||
}
|
||||
if (!CcdiProjectStatusConstants.COMPLETED.equals(project.getStatus())) {
|
||||
throw new ServiceException("仅已完成项目允许归档");
|
||||
}
|
||||
project.setStatus(CcdiProjectStatusConstants.ARCHIVED);
|
||||
project.setIsArchived(1);
|
||||
project.setUpdateBy(operator);
|
||||
project.setUpdateTime(new Date());
|
||||
projectMapper.updateById(project);
|
||||
log.info("【项目】项目状态变更: projectId={}, projectName={}, oldStatus={}, oldStatusLabel={}, newStatus={}, newStatusLabel={}, operator={}",
|
||||
project.getProjectId(), project.getProjectName(), CcdiProjectStatusConstants.COMPLETED,
|
||||
resolveStatusLabel(CcdiProjectStatusConstants.COMPLETED), CcdiProjectStatusConstants.ARCHIVED,
|
||||
resolveStatusLabel(CcdiProjectStatusConstants.ARCHIVED), resolveOperator(operator));
|
||||
}
|
||||
|
||||
@Override
|
||||
public void updateProjectStatus(Long projectId, String status, String operator) {
|
||||
CcdiProject project = getRequiredProject(projectId);
|
||||
@@ -179,6 +199,14 @@ public class CcdiProjectServiceImpl implements ICcdiProjectService {
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void ensureProjectNotArchived(Long projectId, String message) {
|
||||
CcdiProject project = getRequiredProject(projectId);
|
||||
if (CcdiProjectStatusConstants.ARCHIVED.equals(project.getStatus())) {
|
||||
throw new ServiceException(message);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void ensureProjectWritable(Long projectId, String message) {
|
||||
CcdiProject project = getRequiredProject(projectId);
|
||||
|
||||
@@ -0,0 +1,33 @@
|
||||
package com.ruoyi.ccdi.project.controller;
|
||||
|
||||
import io.swagger.v3.oas.annotations.Operation;
|
||||
import org.junit.jupiter.api.Test;
|
||||
import org.springframework.security.access.prepost.PreAuthorize;
|
||||
import org.springframework.web.bind.annotation.PostMapping;
|
||||
import org.springframework.web.bind.annotation.RequestMapping;
|
||||
|
||||
import java.lang.reflect.Method;
|
||||
|
||||
import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||
import static org.junit.jupiter.api.Assertions.assertNotNull;
|
||||
|
||||
class CcdiProjectControllerContractTest {
|
||||
|
||||
@Test
|
||||
void shouldExposeArchiveProjectEndpointContract() throws Exception {
|
||||
RequestMapping requestMapping = CcdiProjectController.class.getAnnotation(RequestMapping.class);
|
||||
Method method = CcdiProjectController.class.getMethod("archiveProject", Long.class);
|
||||
PostMapping postMapping = method.getAnnotation(PostMapping.class);
|
||||
PreAuthorize preAuthorize = method.getAnnotation(PreAuthorize.class);
|
||||
Operation operation = method.getAnnotation(Operation.class);
|
||||
|
||||
assertNotNull(requestMapping);
|
||||
assertEquals("/ccdi/project", requestMapping.value()[0]);
|
||||
assertNotNull(postMapping);
|
||||
assertEquals("/{projectId}/archive", postMapping.value()[0]);
|
||||
assertNotNull(preAuthorize);
|
||||
assertEquals("@ss.hasPermi('ccdi:project:edit')", preAuthorize.value());
|
||||
assertNotNull(operation);
|
||||
assertEquals("归档项目", operation.summary());
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,55 @@
|
||||
package com.ruoyi.ccdi.project.controller;
|
||||
|
||||
import com.ruoyi.ccdi.project.service.ICcdiProjectService;
|
||||
import com.ruoyi.common.core.domain.AjaxResult;
|
||||
import io.swagger.v3.oas.annotations.Operation;
|
||||
import org.junit.jupiter.api.Test;
|
||||
import org.junit.jupiter.api.extension.ExtendWith;
|
||||
import org.mockito.InjectMocks;
|
||||
import org.mockito.Mock;
|
||||
import org.mockito.MockedStatic;
|
||||
import org.mockito.junit.jupiter.MockitoExtension;
|
||||
import org.springframework.security.access.prepost.PreAuthorize;
|
||||
import org.springframework.web.bind.annotation.PostMapping;
|
||||
|
||||
import java.lang.reflect.Method;
|
||||
|
||||
import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||
import static org.junit.jupiter.api.Assertions.assertNotNull;
|
||||
import static org.mockito.Mockito.mockStatic;
|
||||
import static org.mockito.Mockito.verify;
|
||||
|
||||
@ExtendWith(MockitoExtension.class)
|
||||
class CcdiProjectControllerTest {
|
||||
|
||||
@InjectMocks
|
||||
private CcdiProjectController controller;
|
||||
|
||||
@Mock
|
||||
private ICcdiProjectService projectService;
|
||||
|
||||
@Test
|
||||
void shouldArchiveProject() throws Exception {
|
||||
try (MockedStatic<com.ruoyi.common.utils.SecurityUtils> mocked = mockStatic(com.ruoyi.common.utils.SecurityUtils.class)) {
|
||||
mocked.when(com.ruoyi.common.utils.SecurityUtils::getUsername).thenReturn("tester");
|
||||
|
||||
AjaxResult result = controller.archiveProject(40L);
|
||||
|
||||
assertEquals(200, result.get("code"));
|
||||
assertEquals("项目归档成功", result.get("msg"));
|
||||
verify(projectService).archiveProject(40L, "tester");
|
||||
}
|
||||
|
||||
Method method = CcdiProjectController.class.getMethod("archiveProject", Long.class);
|
||||
PostMapping postMapping = method.getAnnotation(PostMapping.class);
|
||||
PreAuthorize preAuthorize = method.getAnnotation(PreAuthorize.class);
|
||||
Operation operation = method.getAnnotation(Operation.class);
|
||||
|
||||
assertNotNull(postMapping);
|
||||
assertEquals("/{projectId}/archive", postMapping.value()[0]);
|
||||
assertNotNull(preAuthorize);
|
||||
assertEquals("@ss.hasPermi('ccdi:project:edit')", preAuthorize.value());
|
||||
assertNotNull(operation);
|
||||
assertEquals("归档项目", operation.summary());
|
||||
}
|
||||
}
|
||||
@@ -154,6 +154,8 @@ class CcdiFileUploadServiceImplTest {
|
||||
assertEquals("admin", inserted.get().get(0).getUploadUser());
|
||||
assertEquals("uploading", inserted.get().get(0).getFileStatus());
|
||||
assertEquals(1, TransactionSynchronizationManager.getSynchronizations().size());
|
||||
verify(projectService).ensureProjectNotArchived(PROJECT_ID, "已归档项目暂不允许上传或拉取数据");
|
||||
verify(projectService).ensureProjectWritable(PROJECT_ID, "当前项目正在进行银行流水打标,暂不允许上传或拉取数据");
|
||||
} finally {
|
||||
TransactionSynchronizationManager.clearSynchronization();
|
||||
}
|
||||
|
||||
@@ -152,6 +152,7 @@ class CcdiModelParamServiceImplTest {
|
||||
service.saveAllParams(buildSaveAllDto());
|
||||
}
|
||||
|
||||
verify(projectService).ensureProjectNotArchived(40L, "已归档项目暂不允许修改参数");
|
||||
verify(bankTagService).submitAutoRebuild(40L, TriggerType.AUTO_PARAM_CHANGE);
|
||||
}
|
||||
|
||||
@@ -178,6 +179,7 @@ class CcdiModelParamServiceImplTest {
|
||||
service.saveParams(saveDTO);
|
||||
}
|
||||
|
||||
verify(projectService).ensureProjectNotArchived(40L, "已归档项目暂不允许修改参数");
|
||||
verify(bankTagService).submitAutoRebuild(40L, TriggerType.AUTO_PARAM_CHANGE);
|
||||
}
|
||||
|
||||
|
||||
@@ -23,6 +23,7 @@ import static org.junit.jupiter.api.Assertions.assertThrows;
|
||||
import static org.junit.jupiter.api.Assertions.assertTrue;
|
||||
import static org.mockito.ArgumentMatchers.any;
|
||||
import static org.mockito.Mockito.doAnswer;
|
||||
import static org.mockito.Mockito.verify;
|
||||
import static org.mockito.Mockito.when;
|
||||
|
||||
@ExtendWith(MockitoExtension.class)
|
||||
@@ -68,6 +69,43 @@ class CcdiProjectServiceImplTest {
|
||||
() -> service.ensureProjectWritable(40L, "当前项目正在进行银行流水打标,暂不允许修改参数"));
|
||||
}
|
||||
|
||||
@Test
|
||||
void shouldArchiveCompletedProject() {
|
||||
CcdiProject project = new CcdiProject();
|
||||
project.setProjectId(40L);
|
||||
project.setProjectName("专案A");
|
||||
project.setStatus("1");
|
||||
project.setIsArchived(0);
|
||||
when(projectMapper.selectById(40L)).thenReturn(project);
|
||||
|
||||
service.archiveProject(40L, "tester");
|
||||
|
||||
assertEquals("2", project.getStatus());
|
||||
assertEquals(1, project.getIsArchived());
|
||||
verify(projectMapper).updateById(project);
|
||||
}
|
||||
|
||||
@Test
|
||||
void shouldRejectArchivingProjectWhenStatusIsNotCompleted() {
|
||||
CcdiProject project = new CcdiProject();
|
||||
project.setProjectId(41L);
|
||||
project.setStatus("0");
|
||||
when(projectMapper.selectById(41L)).thenReturn(project);
|
||||
|
||||
assertThrows(ServiceException.class, () -> service.archiveProject(41L, "tester"));
|
||||
}
|
||||
|
||||
@Test
|
||||
void shouldRejectWritingWhenProjectIsArchived() {
|
||||
CcdiProject archived = new CcdiProject();
|
||||
archived.setProjectId(42L);
|
||||
archived.setStatus("2");
|
||||
when(projectMapper.selectById(42L)).thenReturn(archived);
|
||||
|
||||
assertThrows(ServiceException.class,
|
||||
() -> service.ensureProjectNotArchived(42L, "已归档项目暂不允许修改参数"));
|
||||
}
|
||||
|
||||
@Test
|
||||
void shouldLogProjectInitialStatusWhenProjectIsCreated() {
|
||||
CcdiProjectSaveDTO dto = new CcdiProjectSaveDTO();
|
||||
|
||||
Reference in New Issue
Block a user