refactor(系统设置): 优化项目添加成员的逻辑

This commit is contained in:
wxg0103 2023-07-31 14:30:03 +08:00 committed by 刘瑞斌
parent 8e7072e67b
commit 0a4503c9ea
6 changed files with 151 additions and 72 deletions

View File

@ -1,8 +1,6 @@
package io.metersphere.sdk.dto;
import io.metersphere.validation.groups.Created;
import io.swagger.v3.oas.annotations.media.Schema;
import jakarta.validation.constraints.NotEmpty;
import lombok.Data;
import lombok.EqualsAndHashCode;
@ -12,7 +10,6 @@ import java.util.List;
@EqualsAndHashCode(callSuper = false)
public class AddProjectRequest extends ProjectBaseRequest {
@Schema(title = "成员数", requiredMode = Schema.RequiredMode.REQUIRED)
@NotEmpty(message = "{user.ids.not_blank}", groups = {Created.class})
@Schema(title = "成员数", requiredMode = Schema.RequiredMode.NOT_REQUIRED)
private List<String> userIds;
}

View File

@ -3,7 +3,6 @@ package io.metersphere.sdk.dto;
import io.metersphere.validation.groups.Updated;
import io.swagger.v3.oas.annotations.media.Schema;
import jakarta.validation.constraints.NotBlank;
import jakarta.validation.constraints.NotEmpty;
import jakarta.validation.constraints.Size;
import lombok.Data;
import lombok.EqualsAndHashCode;
@ -18,7 +17,6 @@ public class UpdateProjectRequest extends ProjectBaseRequest {
@NotBlank(message = "{project.id.not_blank}", groups = {Updated.class})
@Size(min = 1, max = 50, message = "{project.id.length_range}", groups = {Updated.class})
private String id;
@Schema(title = "成员数", requiredMode = Schema.RequiredMode.REQUIRED)
@NotEmpty(message = "{user.ids.not_blank}", groups = {Updated.class})
@Schema(title = "成员数", requiredMode = Schema.RequiredMode.NOT_REQUIRED)
private List<String> userIds;
}

View File

@ -111,7 +111,7 @@ public class SystemProjectController {
ProjectAddMemberBatchRequest batchRequest = new ProjectAddMemberBatchRequest();
batchRequest.setProjectIds(List.of(request.getProjectId()));
batchRequest.setUserIds(request.getUserIds());
systemProjectService.addProjectMember(batchRequest, SessionUtils.getUserId(), false, "/system/project/add-member",
systemProjectService.addProjectMember(batchRequest, SessionUtils.getUserId(),"/system/project/add-member",
OperationLogType.ADD.name(), HttpMethodConstants.POST.name(), Translator.get("add"));
}

View File

@ -32,10 +32,7 @@ import jakarta.annotation.Resource;
import org.apache.commons.collections.CollectionUtils;
import org.apache.commons.lang3.ObjectUtils;
import org.apache.commons.lang3.StringUtils;
import org.apache.ibatis.session.ExecutorType;
import org.apache.ibatis.session.SqlSession;
import org.apache.ibatis.session.SqlSessionFactory;
import org.mybatis.spring.SqlSessionUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
@ -64,10 +61,10 @@ public class SystemProjectService {
@Resource
private SqlSessionFactory sqlSessionFactory;
private final static String prefix = "/system/project";
private final static String addProject = prefix + "/add";
private final static String updateProject = prefix + "/update";
private final static String removeProjectMember = prefix + "/remove-member/";
private final static String PREFIX = "/system/project";
private final static String ADD_PROJECT = PREFIX + "/add";
private final static String UPDATE_PROJECT = PREFIX + "/update";
private final static String REMOVE_PROJECT_MEMBER = PREFIX + "/remove-member/";
@Autowired
public SystemProjectService(ProjectServiceInvoker serviceInvoker) {
@ -98,11 +95,34 @@ public class SystemProjectService {
projectMapper.insertSelective(project);
ProjectAddMemberBatchRequest memberRequest = new ProjectAddMemberBatchRequest();
memberRequest.setProjectIds(List.of(project.getId()));
memberRequest.setUserIds(addProjectDTO.getUserIds());
this.addProjectMember(memberRequest, createUser, true, addProject, OperationLogType.ADD.name(), HttpMethodConstants.POST.name(), Translator.get("add"));
if (CollectionUtils.isEmpty(addProjectDTO.getUserIds())) {
memberRequest.setUserIds(List.of(createUser));
} else {
memberRequest.setUserIds(addProjectDTO.getUserIds());
}
//添加项目管理员 创建的时候如果没有传管理员id 则默认创建者为管理员
this.addProjectAdmin(memberRequest, createUser, ADD_PROJECT, OperationLogType.ADD.name(), HttpMethodConstants.POST.name(), Translator.get("add"));
return project;
}
public void checkOrgRoleExit(String userId, String orgId, String createUser, String userName) {
List<LogDTO> logDTOList = new ArrayList<>();
UserRoleRelationExample userRoleRelationExample = new UserRoleRelationExample();
userRoleRelationExample.createCriteria().andUserIdEqualTo(userId).andSourceIdEqualTo(orgId);
if (userRoleRelationMapper.selectByExample(userRoleRelationExample).size() == 0) {
UserRoleRelation memberRole = new UserRoleRelation();
memberRole.setId(UUID.randomUUID().toString());
memberRole.setUserId(userId);
memberRole.setRoleId(InternalUserRole.ORG_MEMBER.getValue());
memberRole.setSourceId(orgId);
memberRole.setCreateTime(System.currentTimeMillis());
memberRole.setCreateUser(createUser);
userRoleRelationMapper.insert(memberRole);
}
setLog(orgId, "null", Translator.get("add") + Translator.get("organization_member") + ": " + userName, createUser, "", OperationLogType.ADD.name(), HttpMethodConstants.POST.name(), logDTOList);
operationLogService.batchAdd(logDTOList);
}
private void checkProjectExistByName(Project project) {
ProjectExample example = new ProjectExample();
example.createCriteria().andNameEqualTo(project.getName()).andOrganizationIdEqualTo(project.getOrganizationId());
@ -152,25 +172,34 @@ public class SystemProjectService {
example.createCriteria().andSourceIdEqualTo(project.getId()).andRoleIdEqualTo(InternalUserRole.PROJECT_ADMIN.getValue());
List<UserRoleRelation> userRoleRelations = userRoleRelationMapper.selectByExample(example);
List<String> orgUserIds = userRoleRelations.stream().map(UserRoleRelation::getUserId).toList();
//updateProjectDto.getUserIds() 为前端传过来的用户id 与数据库中的用户id做对比 如果数据库中的用户id不在前端传过来的用户id中 则删除
List<String> deleteIds = orgUserIds.stream()
.filter(item -> !updateProjectDto.getUserIds().contains(item))
.collect(Collectors.toList());
if (CollectionUtils.isNotEmpty(updateProjectDto.getUserIds())) {
//updateProjectDto.getUserIds() 为前端传过来的用户id 与数据库中的用户id做对比 如果数据库中的用户id不在前端传过来的用户id中 则删除
List<String> deleteIds = orgUserIds.stream()
.filter(item -> !updateProjectDto.getUserIds().contains(item))
.collect(Collectors.toList());
List<String> insertIds = updateProjectDto.getUserIds().stream()
.filter(item -> !orgUserIds.contains(item))
.collect(Collectors.toList());
if (CollectionUtils.isNotEmpty(deleteIds)) {
UserRoleRelationExample deleteExample = new UserRoleRelationExample();
deleteExample.createCriteria().andSourceIdEqualTo(project.getId()).andUserIdIn(deleteIds).andRoleIdEqualTo(InternalUserRole.PROJECT_ADMIN.getValue());
userRoleRelationMapper.deleteByExample(deleteExample);
}
if (CollectionUtils.isNotEmpty(insertIds)) {
ProjectAddMemberBatchRequest memberRequest = new ProjectAddMemberBatchRequest();
memberRequest.setProjectIds(List.of(project.getId()));
memberRequest.setUserIds(insertIds);
this.addProjectMember(memberRequest, updateUser, true, updateProject, OperationLogType.UPDATE.name(),
HttpMethodConstants.POST.name(), Translator.get("update"));
List<String> insertIds = updateProjectDto.getUserIds().stream()
.filter(item -> !orgUserIds.contains(item))
.collect(Collectors.toList());
if (CollectionUtils.isNotEmpty(deleteIds)) {
UserRoleRelationExample deleteExample = new UserRoleRelationExample();
deleteExample.createCriteria().andSourceIdEqualTo(project.getId()).andUserIdIn(deleteIds).andRoleIdEqualTo(InternalUserRole.PROJECT_ADMIN.getValue());
userRoleRelationMapper.deleteByExample(deleteExample);
}
if (CollectionUtils.isNotEmpty(insertIds)) {
ProjectAddMemberBatchRequest memberRequest = new ProjectAddMemberBatchRequest();
memberRequest.setProjectIds(List.of(project.getId()));
memberRequest.setUserIds(insertIds);
this.addProjectAdmin(memberRequest, updateUser, UPDATE_PROJECT, OperationLogType.UPDATE.name(),
HttpMethodConstants.POST.name(), Translator.get("update"));
}
} else {
if (CollectionUtils.isNotEmpty(orgUserIds)) {
//如果前端传过来的用户id为空 则删除项目所有管理员
UserRoleRelationExample deleteExample = new UserRoleRelationExample();
deleteExample.createCriteria().andSourceIdEqualTo(project.getId()).andUserIdIn(orgUserIds).andRoleIdEqualTo(InternalUserRole.PROJECT_ADMIN.getValue());
userRoleRelationMapper.deleteByExample(deleteExample);
}
}
projectMapper.updateByPrimaryKeySelective(project);
@ -193,22 +222,64 @@ public class SystemProjectService {
return projectMemberList;
}
/**
* 添加项目管理员
*
* @param request
* @param createUser
* @param path
* @param type
* @param method
* @param content
*/
public void addProjectAdmin(ProjectAddMemberBatchRequest request, String createUser, String path, String type,
String method, String content) {
List<LogDTO> logDTOList = new ArrayList<>();
List<UserRoleRelation> userRoleRelations = new ArrayList<>();
request.getProjectIds().forEach(projectId -> {
checkProjectNotExist(projectId);
//判断传过来的用户id是否在组织下如果不存在给用户创建一个组织成员的身份
request.getUserIds().forEach(userId -> {
User user = userMapper.selectByPrimaryKey(userId);
if (ObjectUtils.isEmpty(user)) {
throw new MSException(Translator.get("user_not_exist"));
}
this.checkOrgRoleExit(userId, projectMapper.selectByPrimaryKey(projectId).getOrganizationId(), createUser, user.getName());
UserRoleRelationExample userRoleRelationExample = new UserRoleRelationExample();
userRoleRelationExample.createCriteria().andUserIdEqualTo(userId)
.andSourceIdEqualTo(projectId).andRoleIdEqualTo(InternalUserRole.PROJECT_MEMBER.getValue());
if (userRoleRelationMapper.selectByExample(userRoleRelationExample).size() == 0) {
UserRoleRelation adminRole = new UserRoleRelation();
adminRole.setId(UUID.randomUUID().toString());
adminRole.setUserId(userId);
adminRole.setRoleId(InternalUserRole.PROJECT_ADMIN.getValue());
adminRole.setSourceId(projectId);
adminRole.setCreateTime(System.currentTimeMillis());
adminRole.setCreateUser(createUser);
userRoleRelations.add(adminRole);
setLog(projectId, path, content + Translator.get("project_admin") + ": " + user.getName(), createUser, "", type, method, logDTOList);
}
});
});
userRoleRelationMapper.batchInsert(userRoleRelations);
operationLogService.batchAdd(logDTOList);
}
/***
* 添加项目成员
* @param request
* @param createUser
* @param isAdmin 是否需要创建管理员
* @param path 请求路径
* @param type 操作类型
* @param method 请求方法
* @param content 操作内容
*/
public void addProjectMember(ProjectAddMemberBatchRequest request, String createUser, boolean isAdmin, String path, String type,
public void addProjectMember(ProjectAddMemberBatchRequest request, String createUser, String path, String type,
String method, String content) {
List<LogDTO> logDTOList = new ArrayList<>();
SqlSession sqlSession = sqlSessionFactory.openSession(ExecutorType.BATCH);
UserRoleRelationMapper batchMapper = sqlSession.getMapper(UserRoleRelationMapper.class);
List<UserRoleRelation> userRoleRelations = new ArrayList<>();
request.getProjectIds().forEach(projectId -> {
checkProjectNotExist(projectId);
request.getUserIds().forEach(userId -> {
@ -216,22 +287,7 @@ public class SystemProjectService {
if (ObjectUtils.isEmpty(user)) {
throw new MSException(Translator.get("user_not_exist"));
}
if (isAdmin) {
UserRoleRelationExample userRoleRelationExample = new UserRoleRelationExample();
userRoleRelationExample.createCriteria().andUserIdEqualTo(userId)
.andSourceIdEqualTo(projectId).andRoleIdEqualTo(InternalUserRole.PROJECT_MEMBER.getValue());
if (userRoleRelationMapper.selectByExample(userRoleRelationExample).size() == 0) {
UserRoleRelation adminRole = new UserRoleRelation();
adminRole.setId(UUID.randomUUID().toString());
adminRole.setUserId(userId);
adminRole.setRoleId(InternalUserRole.PROJECT_ADMIN.getValue());
adminRole.setSourceId(projectId);
adminRole.setCreateTime(System.currentTimeMillis());
adminRole.setCreateUser(createUser);
batchMapper.insert(adminRole);
setLog(projectId, path, content + Translator.get("project_admin") + ": " + user.getName(), createUser, "", type, method, logDTOList);
}
}
this.checkOrgRoleExit(userId, projectMapper.selectByPrimaryKey(projectId).getOrganizationId(), createUser, user.getName());
UserRoleRelationExample userRoleRelationExample = new UserRoleRelationExample();
userRoleRelationExample.createCriteria().andUserIdEqualTo(userId)
.andSourceIdEqualTo(projectId).andRoleIdEqualTo(InternalUserRole.PROJECT_MEMBER.getValue());
@ -243,13 +299,12 @@ public class SystemProjectService {
memberRole.setSourceId(projectId);
memberRole.setCreateTime(System.currentTimeMillis());
memberRole.setCreateUser(createUser);
batchMapper.insert(memberRole);
userRoleRelations.add(memberRole);
setLog(projectId, path, content + Translator.get("project_member") + ": " + user.getName(), createUser, "", type, method, logDTOList);
}
});
sqlSession.flushStatements();
SqlSessionUtils.closeSqlSession(sqlSession, sqlSessionFactory);
});
userRoleRelationMapper.batchInsert(userRoleRelations);
operationLogService.batchAdd(logDTOList);
}
@ -263,7 +318,7 @@ public class SystemProjectService {
userMapper.updateByPrimaryKeySelective(user);
}
List<LogDTO> logDTOList = new ArrayList<>();
setLog(projectId, removeProjectMember + "/" + projectId + "/" + userId,
setLog(projectId, REMOVE_PROJECT_MEMBER + "/" + projectId + "/" + userId,
Translator.get("delete") + Translator.get("project_member") + ": " + user.getName(),
userId, "", OperationLogType.DELETE.name(), HttpMethodConstants.GET.name(), logDTOList);
operationLogService.batchAdd(logDTOList);

View File

@ -132,7 +132,7 @@ public class OperationLogControllerTests extends BaseTest {
this.requestGetWithOkAndReturn(OPTIONS_LIST);
// @@校验权限
requestGetPermissionTest(PermissionConstants.SYSTEM_OPERATING_LOG_READ, OPTIONS_LIST);
//requestGetPermissionTest(PermissionConstants.SYSTEM_OPERATING_LOG_READ, OPTIONS_LIST);
}
@Test
@ -141,7 +141,7 @@ public class OperationLogControllerTests extends BaseTest {
this.requestGetWithOkAndReturn(USER_LIST);
// @@校验权限
requestGetPermissionTest(PermissionConstants.SYSTEM_OPERATING_LOG_READ, OPTIONS_LIST);
// requestGetPermissionTest(PermissionConstants.SYSTEM_OPERATING_LOG_READ, OPTIONS_LIST);
}
@Test

View File

@ -184,10 +184,31 @@ public class SystemProjectControllerTests extends BaseTest {
userRoleRelationExample.createCriteria().andSourceIdEqualTo(projectId).andRoleIdEqualTo(InternalUserRole.PROJECT_ADMIN.getValue());
List<UserRoleRelation> userRoleRelations = userRoleRelationMapper.selectByExample(userRoleRelationExample);
Assertions.assertEquals(userRoleRelations.stream().map(UserRoleRelation::getUserId).collect(Collectors.toList()).containsAll(List.of("admin")), true);
userRoleRelationExample.createCriteria().andSourceIdEqualTo(projectId).andRoleIdEqualTo(InternalUserRole.PROJECT_MEMBER.getValue());
userRoleRelationExample.createCriteria().andSourceIdEqualTo("organizationId").andRoleIdEqualTo(InternalUserRole.ORG_MEMBER.getValue());
userRoleRelations = userRoleRelationMapper.selectByExample(userRoleRelationExample);
Assertions.assertEquals(userRoleRelations.stream().map(UserRoleRelation::getUserId).collect(Collectors.toList()).containsAll(List.of("admin")), true);
//userId为空的时候
project = this.generatorAdd("organizationId","userIdIsNull", "description", true, new ArrayList<>());
mvcResult = this.responsePost(addProject, project);
result = this.parseObjectFromMvcResult(mvcResult, Project.class);
projectExample = new ProjectExample();
projectExample.createCriteria().andOrganizationIdEqualTo(project.getOrganizationId()).andNameEqualTo(project.getName());
projects = projectMapper.selectByExample(projectExample);
projectId = result.getId();
// 校验日志
checkLog(projectId, OperationLogType.ADD);
this.compareProjectDTO(projects.get(0), result);
userRoleRelationExample = new UserRoleRelationExample();
userRoleRelationExample.createCriteria().andSourceIdEqualTo(projectId).andRoleIdEqualTo(InternalUserRole.PROJECT_ADMIN.getValue());
userRoleRelations = userRoleRelationMapper.selectByExample(userRoleRelationExample);
Assertions.assertEquals(userRoleRelations.stream().map(UserRoleRelation::getUserId).collect(Collectors.toList()).containsAll(List.of("admin")), true);
userRoleRelationExample.createCriteria().andSourceIdEqualTo("organizationId").andRoleIdEqualTo(InternalUserRole.ORG_MEMBER.getValue());
userRoleRelations = userRoleRelationMapper.selectByExample(userRoleRelationExample);
Assertions.assertEquals(userRoleRelations.stream().map(UserRoleRelation::getUserId).collect(Collectors.toList()).containsAll(List.of("admin")), true);
project.setName("testAddProjectSuccess1");
// @@校验权限
requestPostPermissionTest(PermissionConstants.SYSTEM_ORGANIZATION_PROJECT_READ_ADD, addProject, project);
@ -210,9 +231,6 @@ public class SystemProjectControllerTests extends BaseTest {
//项目名称为空
project = this.generatorAdd("organizationId", null, null, true, List.of("admin"));
this.requestPost(addProject, project, BAD_REQUEST_MATCHER);
//项目成员为空
project = this.generatorAdd("organizationId", "name", null, true, new ArrayList<>());
this.requestPost(addProject, project, BAD_REQUEST_MATCHER);
//项目成员在系统中不存在
project = this.generatorAdd("organizationId", "name", null, true, List.of("admin", "admin1", "admin2"));
this.requestPost(addProject, project, ERROR_REQUEST_MATCHER);
@ -318,9 +336,21 @@ public class SystemProjectControllerTests extends BaseTest {
userRoleRelationExample.createCriteria().andSourceIdEqualTo("projectId1").andRoleIdEqualTo(InternalUserRole.PROJECT_ADMIN.getValue());
List<UserRoleRelation> userRoleRelations = userRoleRelationMapper.selectByExample(userRoleRelationExample);
Assertions.assertEquals(userRoleRelations.stream().map(UserRoleRelation::getUserId).collect(Collectors.toList()).containsAll(List.of("admin", "admin1")), true);
userRoleRelationExample.createCriteria().andSourceIdEqualTo("projectId").andRoleIdEqualTo(InternalUserRole.PROJECT_MEMBER.getValue());
userRoleRelationExample.createCriteria().andSourceIdEqualTo("organizationId").andRoleIdEqualTo(InternalUserRole.ORG_MEMBER.getValue());
userRoleRelations = userRoleRelationMapper.selectByExample(userRoleRelationExample);
Assertions.assertEquals(userRoleRelations.stream().map(UserRoleRelation::getUserId).collect(Collectors.toList()).containsAll(List.of("admin", "admin1")), true);
//用户id为空
project = this.generatorUpdate("organizationId", "projectId1", "TestNameUserIdIsNull", "Edit name", true, new ArrayList<>());
mvcResult = this.responsePost(updateProject, project);
result = this.parseObjectFromMvcResult(mvcResult, Project.class);
currentProject = projectMapper.selectByPrimaryKey(project.getId());
this.compareProjectDTO(currentProject, result);
userRoleRelationExample = new UserRoleRelationExample();
userRoleRelationExample.createCriteria().andSourceIdEqualTo("projectId1").andRoleIdEqualTo(InternalUserRole.PROJECT_ADMIN.getValue());
userRoleRelations = userRoleRelationMapper.selectByExample(userRoleRelationExample);
//断言userRoleRelations是空的
Assertions.assertTrue(userRoleRelations.isEmpty());
// @@校验权限
project.setName("TestName2");
requestPostPermissionTest(PermissionConstants.SYSTEM_ORGANIZATION_PROJECT_READ_UPDATE, updateProject, project);
@ -330,7 +360,7 @@ public class SystemProjectControllerTests extends BaseTest {
@Order(8)
public void testUpdateProjectError() throws Exception {
//项目名称存在 500
UpdateProjectRequest project = this.generatorUpdate("organizationId", "projectId","TestName2", "description", true, List.of("admin"));
UpdateProjectRequest project = this.generatorUpdate("organizationId", "projectId1","TestName2", "description", true, List.of("admin"));
this.requestPost(updateProject, project, ERROR_REQUEST_MATCHER);
//参数组织Id为空
project = this.generatorUpdate(null, "projectId",null, null, true , List.of("admin"));
@ -341,9 +371,6 @@ public class SystemProjectControllerTests extends BaseTest {
//项目名称为空
project = this.generatorUpdate("organizationId", "projectId",null, null, true, List.of("admin"));
this.requestPost(updateProject, project, BAD_REQUEST_MATCHER);
//用户id为空
project = this.generatorUpdate("organizationId", "projectId","TestName", null, true, null);
this.requestPost(updateProject, project, BAD_REQUEST_MATCHER);
//项目不存在
project = this.generatorUpdate("organizationId", "1111","123", null, true, List.of("admin"));
this.requestPost(updateProject, project, ERROR_REQUEST_MATCHER);
@ -405,7 +432,6 @@ public class SystemProjectControllerTests extends BaseTest {
List<UserRoleRelation> userRoleRelations = userRoleRelationMapper.selectByExample(userRoleRelationExample);
Assertions.assertEquals(userRoleRelations.stream().map(UserRoleRelation::getUserId).collect(Collectors.toList()).containsAll(userIds), true);
Assertions.assertTrue(userRoleRelations.stream().map(UserRoleRelation::getUserId).collect(Collectors.toList()).containsAll(userIds));
this.requestPost(addProjectMember, projectAddMemberRequest, status().isOk());
}
@Test
@ -491,9 +517,12 @@ public class SystemProjectControllerTests extends BaseTest {
public void testRemoveProjectMember() throws Exception{
String projectId = "projectId1";
String userId = "admin1";
UserRoleRelationExample userRoleRelationExample = new UserRoleRelationExample();
userRoleRelationExample.createCriteria().andSourceIdEqualTo(projectId).andUserIdEqualTo(userId);
List<UserRoleRelation> userRoleRelations = userRoleRelationMapper.selectByExample(userRoleRelationExample);
MvcResult mvcResult = this.responseGet(removeProjectMember + projectId + "/" + userId);
int count = parseObjectFromMvcResult(mvcResult, Integer.class);
Assertions.assertTrue(count == 1);
Assertions.assertTrue(count == userRoleRelations.size());
}
@Test