From 5ccc4cc889309ea2ae949b09cc7ecbb1d941ec67 Mon Sep 17 00:00:00 2001 From: amao <56795615+amaoisnb@users.noreply.github.com> Date: Wed, 26 Jul 2023 11:52:57 +0800 Subject: [PATCH] [Improvement-4375][api] cannot delete yarn queue (#13046) * [Bug-12833][api] delete api * [Bug-12833][api] delete yarn queue * [Bug-12833][api] add Unit Test * Repair the failed CI * Repair the failed UT * Repair the failed Docs * Repair the failed Doc --------- Co-authored-by: amao Co-authored-by: xiangzihao <460888207@qq.com> --- .../api/controller/QueueController.java | 25 +++++ .../dolphinscheduler/api/enums/Status.java | 7 +- .../api/service/QueueService.java | 12 +++ .../api/service/impl/QueueServiceImpl.java | 56 ++++++++++ .../api/controller/QueueControllerTest.java | 18 ++++ .../dao/mapper/TenantMapper.java | 7 ++ .../dao/mapper/TenantMapper.xml | 7 ++ .../src/locales/en_US/security.ts | 2 + .../src/locales/zh_CN/security.ts | 2 + .../src/service/modules/queues/index.ts | 7 ++ .../security/yarn-queue-manage/use-table.ts | 102 +++++++++++++----- 11 files changed, 220 insertions(+), 25 deletions(-) diff --git a/dolphinscheduler-api/src/main/java/org/apache/dolphinscheduler/api/controller/QueueController.java b/dolphinscheduler-api/src/main/java/org/apache/dolphinscheduler/api/controller/QueueController.java index e13e23a1df..0527ce77ae 100644 --- a/dolphinscheduler-api/src/main/java/org/apache/dolphinscheduler/api/controller/QueueController.java +++ b/dolphinscheduler-api/src/main/java/org/apache/dolphinscheduler/api/controller/QueueController.java @@ -18,6 +18,7 @@ package org.apache.dolphinscheduler.api.controller; import static org.apache.dolphinscheduler.api.enums.Status.CREATE_QUEUE_ERROR; +import static org.apache.dolphinscheduler.api.enums.Status.DELETE_QUEUE_BY_ID_ERROR; import static org.apache.dolphinscheduler.api.enums.Status.QUERY_QUEUE_LIST_ERROR; import static org.apache.dolphinscheduler.api.enums.Status.UPDATE_QUEUE_ERROR; import static org.apache.dolphinscheduler.api.enums.Status.VERIFY_QUEUE_ERROR; @@ -30,8 +31,11 @@ import org.apache.dolphinscheduler.common.constants.Constants; import org.apache.dolphinscheduler.dao.entity.User; import org.apache.dolphinscheduler.plugin.task.api.utils.ParameterUtils; +import java.util.Map; + import org.springframework.beans.factory.annotation.Autowired; import org.springframework.http.HttpStatus; +import org.springframework.web.bind.annotation.DeleteMapping; import org.springframework.web.bind.annotation.GetMapping; import org.springframework.web.bind.annotation.PathVariable; import org.springframework.web.bind.annotation.PostMapping; @@ -156,6 +160,27 @@ public class QueueController extends BaseController { return queueService.updateQueue(loginUser, id, queue, queueName); } + /** + * delete queue by id + * + * @param loginUser login user + * @param id queue id + * @return update result code + */ + @Operation(summary = "deleteQueueById", description = "DELETE_QUEUE_NOTES") + @Parameters({ + @Parameter(name = "id", description = "QUEUE_ID", required = true, schema = @Schema(implementation = int.class, example = "100")) + }) + @DeleteMapping(value = "/{id}") + @ResponseStatus(HttpStatus.OK) + @ApiException(DELETE_QUEUE_BY_ID_ERROR) + @AccessLogAnnotation(ignoreRequestArgs = "loginUser") + public Result deleteQueueById(@Parameter(hidden = true) @RequestAttribute(value = Constants.SESSION_USER) User loginUser, + @PathVariable(value = "id") int id) throws Exception { + Map result = queueService.deleteQueueById(loginUser, id); + return returnDataList(result); + } + /** * verify queue and queue name * diff --git a/dolphinscheduler-api/src/main/java/org/apache/dolphinscheduler/api/enums/Status.java b/dolphinscheduler-api/src/main/java/org/apache/dolphinscheduler/api/enums/Status.java index 8176a2ff89..f4622b5c9f 100644 --- a/dolphinscheduler-api/src/main/java/org/apache/dolphinscheduler/api/enums/Status.java +++ b/dolphinscheduler-api/src/main/java/org/apache/dolphinscheduler/api/enums/Status.java @@ -263,6 +263,12 @@ public enum Status { QUERY_TASK_INSTANCE_ERROR(10205, "query task instance error", "查询任务实例错误"), EXECUTE_NOT_DEFINE_TASK(10206, "please save and try again", "请先保存后再执行"), + + DELETE_QUEUE_BY_ID_ERROR(10307, "delete queue by id error", "删除队列错误"), + DELETE_QUEUE_BY_ID_FAIL_USERS(10308, "delete queue by id fail, for there are {0} users using it", + "删除队列失败,有[{0}]个用户正在使用"), + DELETE_TENANT_BY_ID_FAIL_TENANTS(10309, "delete queue by id fail, for there are {0} tenants using it", + "删除队列失败,有[{0}]个租户正在使用"), START_NODE_NOT_EXIST_IN_LAST_PROCESS(10207, "this node {0} does not exist in the latest process definition", "该节点 {0} 不存在于最新的流程定义中"), LIST_AZURE_DATA_FACTORY_ERROR(10208, "list azure data factory error", "查询AZURE数据工厂列表错误"), @@ -286,7 +292,6 @@ public enum Status { PROJECT_PARAMETER_NOT_EXISTS(10219, "project parameter {0} not exists", "项目参数[{0}]不存在"), PROJECT_PARAMETER_CODE_EMPTY(10220, "project parameter code empty", "项目参数code为空"), - CREATE_PROJECT_PREFERENCE_ERROR(10300, "create project preference error", "创建项目偏好设置错误"), UPDATE_PROJECT_PREFERENCE_ERROR(10301, "update project preference error", "更新项目偏好设置错误"), diff --git a/dolphinscheduler-api/src/main/java/org/apache/dolphinscheduler/api/service/QueueService.java b/dolphinscheduler-api/src/main/java/org/apache/dolphinscheduler/api/service/QueueService.java index 0f62ea9028..69ed518445 100644 --- a/dolphinscheduler-api/src/main/java/org/apache/dolphinscheduler/api/service/QueueService.java +++ b/dolphinscheduler-api/src/main/java/org/apache/dolphinscheduler/api/service/QueueService.java @@ -21,6 +21,8 @@ import org.apache.dolphinscheduler.api.utils.Result; import org.apache.dolphinscheduler.dao.entity.Queue; import org.apache.dolphinscheduler.dao.entity.User; +import java.util.Map; + /** * queue service */ @@ -66,6 +68,16 @@ public interface QueueService { */ Result updateQueue(User loginUser, int id, String queue, String queueName); + /** + * delete queue + * + * @param loginUser login user + * @param id queue id + * @return delete result code + * @throws Exception exception + */ + Map deleteQueueById(User loginUser, int id) throws Exception; + /** * verify queue and queueName * diff --git a/dolphinscheduler-api/src/main/java/org/apache/dolphinscheduler/api/service/impl/QueueServiceImpl.java b/dolphinscheduler-api/src/main/java/org/apache/dolphinscheduler/api/service/impl/QueueServiceImpl.java index ecdb3773ed..723c3010c5 100644 --- a/dolphinscheduler-api/src/main/java/org/apache/dolphinscheduler/api/service/impl/QueueServiceImpl.java +++ b/dolphinscheduler-api/src/main/java/org/apache/dolphinscheduler/api/service/impl/QueueServiceImpl.java @@ -17,6 +17,7 @@ package org.apache.dolphinscheduler.api.service.impl; +import static org.apache.dolphinscheduler.api.constants.ApiFuncIdentificationConstant.TENANT_DELETE; import static org.apache.dolphinscheduler.api.constants.ApiFuncIdentificationConstant.YARN_QUEUE_CREATE; import static org.apache.dolphinscheduler.api.constants.ApiFuncIdentificationConstant.YARN_QUEUE_UPDATE; @@ -29,16 +30,21 @@ import org.apache.dolphinscheduler.common.constants.Constants; import org.apache.dolphinscheduler.common.enums.AuthorizationType; import org.apache.dolphinscheduler.common.enums.UserType; import org.apache.dolphinscheduler.dao.entity.Queue; +import org.apache.dolphinscheduler.dao.entity.Tenant; import org.apache.dolphinscheduler.dao.entity.User; import org.apache.dolphinscheduler.dao.mapper.QueueMapper; +import org.apache.dolphinscheduler.dao.mapper.TenantMapper; import org.apache.dolphinscheduler.dao.mapper.UserMapper; +import org.apache.commons.collections.CollectionUtils; import org.apache.commons.lang3.StringUtils; import java.util.ArrayList; import java.util.Collections; +import java.util.HashMap; import java.util.HashSet; import java.util.List; +import java.util.Map; import java.util.Objects; import java.util.Set; @@ -64,6 +70,9 @@ public class QueueServiceImpl extends BaseServiceImpl implements QueueService { @Autowired private UserMapper userMapper; + @Autowired + private TenantMapper tenantMapper; + /** * Check the queue new object valid or not * @@ -223,6 +232,53 @@ public class QueueServiceImpl extends BaseServiceImpl implements QueueService { return result; } + /** + * delete queue + * + * @param loginUser login user + * @param id queue id + * @return delete result code + * @throws Exception exception + */ + @Override + @Transactional(rollbackFor = Exception.class) + public Map deleteQueueById(User loginUser, int id) throws Exception { + Map result = new HashMap<>(); + + if (!canOperatorPermissions(loginUser, null, AuthorizationType.TENANT, TENANT_DELETE)) { + throw new ServiceException(Status.USER_NO_OPERATION_PERM); + } + + Queue queue = queueMapper.selectById(id); + if (Objects.isNull(queue)) { + log.error("Queue does not exist"); + throw new ServiceException(Status.QUEUE_NOT_EXIST); + } + + List tenantList = tenantMapper.queryTenantListByQueueId(queue.getId()); + if (CollectionUtils.isNotEmpty(tenantList)) { + log.warn("Delete queue failed, because there are {} tenants using it.", tenantList.size()); + throw new ServiceException(Status.DELETE_TENANT_BY_ID_FAIL_TENANTS, tenantList.size()); + } + + List userList = userMapper.queryUserListByQueue(queue.getQueueName()); + if (CollectionUtils.isNotEmpty(userList)) { + log.warn("Delete queue failed, because there are {} users using it.", userList.size()); + throw new ServiceException(Status.DELETE_QUEUE_BY_ID_FAIL_USERS, userList.size()); + } + + int delete = queueMapper.deleteById(id); + if (delete > 0) { + log.info("Queue is deleted and id is {}.", id); + putMsg(result, Status.SUCCESS); + } else { + log.error("Queue delete failed, queueId:{}.", id); + putMsg(result, Status.DELETE_QUEUE_BY_ID_ERROR); + } + + return result; + } + /** * verify queue and queueName * diff --git a/dolphinscheduler-api/src/test/java/org/apache/dolphinscheduler/api/controller/QueueControllerTest.java b/dolphinscheduler-api/src/test/java/org/apache/dolphinscheduler/api/controller/QueueControllerTest.java index e2311a25ae..0ddd7ad84b 100644 --- a/dolphinscheduler-api/src/test/java/org/apache/dolphinscheduler/api/controller/QueueControllerTest.java +++ b/dolphinscheduler-api/src/test/java/org/apache/dolphinscheduler/api/controller/QueueControllerTest.java @@ -17,6 +17,7 @@ package org.apache.dolphinscheduler.api.controller; +import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.delete; import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.get; import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.post; import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.put; @@ -177,4 +178,21 @@ public class QueueControllerTest extends AbstractControllerTest { logger.info(mvcResult.getResponse().getContentAsString()); logger.info("verify queue return result:{}", mvcResult.getResponse().getContentAsString()); } + @Test + public void testDeleteQueueById() throws Exception { + MultiValueMap paramsMap = new LinkedMultiValueMap<>(); + paramsMap.add("id", "64"); + + MvcResult mvcResult = mockMvc.perform(delete("/queues/{id}", 64) + .header(SESSION_ID, sessionId) + .params(paramsMap)) + .andExpect(status().isOk()) + .andExpect(content().contentType(MediaType.APPLICATION_JSON)) + .andReturn(); + Result result = JSONUtils.parseObject(mvcResult.getResponse().getContentAsString(), Result.class); + + Assertions.assertNotNull(result); + Assertions.assertEquals(Status.QUEUE_NOT_EXIST.getCode(), result.getCode().intValue()); + logger.info("delete queue return result:{}", mvcResult.getResponse().getContentAsString()); + } } diff --git a/dolphinscheduler-dao/src/main/java/org/apache/dolphinscheduler/dao/mapper/TenantMapper.java b/dolphinscheduler-dao/src/main/java/org/apache/dolphinscheduler/dao/mapper/TenantMapper.java index 623c1f8a8d..90fee2ef5a 100644 --- a/dolphinscheduler-dao/src/main/java/org/apache/dolphinscheduler/dao/mapper/TenantMapper.java +++ b/dolphinscheduler-dao/src/main/java/org/apache/dolphinscheduler/dao/mapper/TenantMapper.java @@ -66,6 +66,13 @@ public interface TenantMapper extends BaseMapper { */ Tenant queryByTenantCode(@Param("tenantCode") String tenantCode); + /** + * query tenants by queue id + * + * @param queueId queue id + * @return tenant list + */ + List queryTenantListByQueueId(@Param("queueId") Integer queueId); /** * tenant page * diff --git a/dolphinscheduler-dao/src/main/resources/org/apache/dolphinscheduler/dao/mapper/TenantMapper.xml b/dolphinscheduler-dao/src/main/resources/org/apache/dolphinscheduler/dao/mapper/TenantMapper.xml index 60fe3a45ef..a941db420b 100644 --- a/dolphinscheduler-dao/src/main/resources/org/apache/dolphinscheduler/dao/mapper/TenantMapper.xml +++ b/dolphinscheduler-dao/src/main/resources/org/apache/dolphinscheduler/dao/mapper/TenantMapper.xml @@ -42,6 +42,13 @@ where tenant_code = #{tenantCode} + +