From b4a5a008b6c96f470e1cef87a6c03e1f8cfa2a99 Mon Sep 17 00:00:00 2001 From: song-tianyang Date: Tue, 20 Jul 2021 20:36:51 +0800 Subject: [PATCH] =?UTF-8?q?feat(=E6=B5=8B=E8=AF=95=E8=AE=A1=E5=88=92):=20?= =?UTF-8?q?=E4=BF=AE=E5=A4=8D=E6=B5=8B=E8=AF=95=E8=AE=A1=E5=88=92=E5=AE=9A?= =?UTF-8?q?=E6=97=B6=E4=BB=BB=E5=8A=A1=E6=80=BB=E6=98=AFRunning=E7=9A=84?= =?UTF-8?q?=E9=97=AE=E9=A2=98?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --bug=1005249 --user=宋天阳 【定时任务】测试计划定时任务,状态一直是running https://www.tapd.cn/55049933/s/1026590 --- .../automation/TestPlanScenarioRequest.java | 1 + .../api/service/ApiAutomationService.java | 1 - .../ApiDefinitionExecResultService.java | 138 ++-- .../api/service/ApiScenarioReportService.java | 16 +- .../api/service/TestResultService.java | 16 +- .../mapper/ext/ExtTestPlanApiCaseMapper.java | 3 + .../mapper/ext/ExtTestPlanApiCaseMapper.xml | 6 +- .../mapper/ext/ExtTestPlanLoadCaseMapper.xml | 6 + .../ext/ExtTestPlanScenarioCaseMapper.xml | 7 + .../constants/TestPlanApiExecuteStatus.java | 5 + .../track/controller/TestPlanController.java | 2 +- .../dto/TestPlanScheduleReportInfoDTO.java | 21 + .../track/service/TestPlanApiCaseService.java | 4 + .../track/service/TestPlanReportService.java | 640 +++++++++++++++--- .../track/service/TestPlanService.java | 102 +-- .../FailureResultAdvanceComponent.vue | 49 +- .../TestResultAdvanceChartComponent.vue | 34 +- 17 files changed, 765 insertions(+), 286 deletions(-) create mode 100644 backend/src/main/java/io/metersphere/commons/constants/TestPlanApiExecuteStatus.java create mode 100644 backend/src/main/java/io/metersphere/track/dto/TestPlanScheduleReportInfoDTO.java diff --git a/backend/src/main/java/io/metersphere/api/dto/automation/TestPlanScenarioRequest.java b/backend/src/main/java/io/metersphere/api/dto/automation/TestPlanScenarioRequest.java index ca4f25bdfb..789e64e057 100644 --- a/backend/src/main/java/io/metersphere/api/dto/automation/TestPlanScenarioRequest.java +++ b/backend/src/main/java/io/metersphere/api/dto/automation/TestPlanScenarioRequest.java @@ -15,6 +15,7 @@ public class TestPlanScenarioRequest { private String projectId; private String moduleId; private List moduleIds; + private List scenarioIds; private String name; private String status; private String workspaceId; diff --git a/backend/src/main/java/io/metersphere/api/service/ApiAutomationService.java b/backend/src/main/java/io/metersphere/api/service/ApiAutomationService.java index c06f864a26..3fc87894f6 100644 --- a/backend/src/main/java/io/metersphere/api/service/ApiAutomationService.java +++ b/backend/src/main/java/io/metersphere/api/service/ApiAutomationService.java @@ -2342,7 +2342,6 @@ public class ApiAutomationService { } } } -// uploadFiles(request, bodyFiles, scenarioFiles); } public DeleteCheckResult checkBeforeDelete(ApiScenarioBatchRequest request) { diff --git a/backend/src/main/java/io/metersphere/api/service/ApiDefinitionExecResultService.java b/backend/src/main/java/io/metersphere/api/service/ApiDefinitionExecResultService.java index f90d91710f..55f662c0cc 100644 --- a/backend/src/main/java/io/metersphere/api/service/ApiDefinitionExecResultService.java +++ b/backend/src/main/java/io/metersphere/api/service/ApiDefinitionExecResultService.java @@ -9,15 +9,15 @@ import io.metersphere.base.mapper.ApiDefinitionMapper; import io.metersphere.base.mapper.ApiTestCaseMapper; import io.metersphere.base.mapper.TestCaseReviewApiCaseMapper; import io.metersphere.base.mapper.ext.ExtApiDefinitionExecResultMapper; -import io.metersphere.commons.constants.ApiRunMode; -import io.metersphere.commons.constants.DelimiterConstants; -import io.metersphere.commons.constants.TriggerMode; +import io.metersphere.commons.constants.*; +import io.metersphere.commons.utils.CommonBeanFactory; import io.metersphere.commons.utils.DateUtils; import io.metersphere.commons.utils.SessionUtils; import io.metersphere.track.dto.TestPlanDTO; import io.metersphere.track.request.testcase.QueryTestPlanRequest; import io.metersphere.track.service.TestCaseReviewApiCaseService; import io.metersphere.track.service.TestPlanApiCaseService; +import io.metersphere.track.service.TestPlanReportService; import io.metersphere.track.service.TestPlanService; import org.apache.commons.collections4.CollectionUtils; import org.apache.commons.lang3.StringUtils; @@ -157,69 +157,89 @@ public class ApiDefinitionExecResultService { * @param result * @param type */ - public void saveApiResultByScheduleTask(TestResult result, String type) { + public void saveApiResultByScheduleTask(TestResult result,String testPlanReportId, String type,String trigeMode) { String saveResultType = type; if (StringUtils.equalsAny(saveResultType, ApiRunMode.SCHEDULE_API_PLAN.name(), ApiRunMode.JENKINS_API_PLAN.name())) { saveResultType = ApiRunMode.API_PLAN.name(); } String finalSaveResultType = saveResultType; - result.getScenarios().get(0).getRequestResults().forEach(item -> { - ApiDefinitionExecResult saveResult = new ApiDefinitionExecResult(); - saveResult.setId(UUID.randomUUID().toString()); - saveResult.setCreateTime(System.currentTimeMillis()); - saveResult.setName(item.getName()); - ApiDefinitionWithBLOBs apiDefinitionWithBLOBs = apiDefinitionMapper.selectByPrimaryKey(item.getName()); - if (apiDefinitionWithBLOBs != null) { - saveResult.setName(apiDefinitionWithBLOBs.getName()); - } else { - ApiTestCaseWithBLOBs caseWithBLOBs = apiTestCaseMapper.selectByPrimaryKey(item.getName()); - if (caseWithBLOBs != null) { - saveResult.setName(caseWithBLOBs.getName()); + + Map apiIdResultMap = new HashMap<>(); + + if (CollectionUtils.isNotEmpty(result.getScenarios())) { + result.getScenarios().forEach(scenarioResult -> { + if (scenarioResult != null && CollectionUtils.isNotEmpty(scenarioResult.getRequestResults())) { + scenarioResult.getRequestResults().forEach(item -> { + String status = item.isSuccess() ? "success" : "error"; + ApiDefinitionExecResult saveResult = new ApiDefinitionExecResult(); + saveResult.setId(UUID.randomUUID().toString()); + saveResult.setCreateTime(System.currentTimeMillis()); + saveResult.setName(item.getName()); + ApiDefinitionWithBLOBs apiDefinitionWithBLOBs = apiDefinitionMapper.selectByPrimaryKey(item.getName()); + if (apiDefinitionWithBLOBs != null) { + saveResult.setName(apiDefinitionWithBLOBs.getName()); + apiIdResultMap.put(apiDefinitionWithBLOBs.getId(),item.isSuccess()? TestPlanApiExecuteStatus.SUCCESS.name() : TestPlanApiExecuteStatus.FAILD.name()); + } else { + ApiTestCaseWithBLOBs caseWithBLOBs = apiTestCaseMapper.selectByPrimaryKey(item.getName()); + if (caseWithBLOBs != null) { + saveResult.setName(caseWithBLOBs.getName()); + apiIdResultMap.put(caseWithBLOBs.getId(),item.isSuccess()? TestPlanApiExecuteStatus.SUCCESS.name() : TestPlanApiExecuteStatus.FAILD.name()); + }else { + caseWithBLOBs = testPlanApiCaseService.getApiTestCaseById(item.getName()); + if (caseWithBLOBs != null) { + saveResult.setName(caseWithBLOBs.getName()); + apiIdResultMap.put(caseWithBLOBs.getId(), item.isSuccess() ? TestPlanApiExecuteStatus.SUCCESS.name() : TestPlanApiExecuteStatus.FAILD.name()); + } + } + } + if (StringUtils.equals(type, ApiRunMode.JENKINS_API_PLAN.name())) { + saveResult.setTriggerMode(TriggerMode.API.name()); + } else { + saveResult.setTriggerMode(TriggerMode.SCHEDULE.name()); + } + + saveResult.setResourceId(item.getName()); + saveResult.setActuator("LOCAL"); + saveResult.setContent(JSON.toJSONString(item)); + saveResult.setStartTime(item.getStartTime()); + saveResult.setEndTime(item.getResponseResult().getResponseTime()); + saveResult.setType(finalSaveResultType); + saveResult.setStatus(status); + + String userID = null; + if (StringUtils.equals(type, ApiRunMode.SCHEDULE_API_PLAN.name())) { + TestPlanApiCase apiCase = testPlanApiCaseService.getById(item.getName()); + String scheduleCreateUser = testPlanService.findScheduleCreateUserById(apiCase.getTestPlanId()); + userID = scheduleCreateUser; + apiCase.setStatus(status); + apiCase.setUpdateTime(System.currentTimeMillis()); + testPlanApiCaseService.updateByPrimaryKeySelective(apiCase); + } else if (StringUtils.equals(type, ApiRunMode.JENKINS_SCENARIO_PLAN.name())) { + TestPlanApiCase apiCase = testPlanApiCaseService.getById(item.getName()); + userID = Objects.requireNonNull(SessionUtils.getUser()).getId(); + apiCase.setStatus(status); + apiCase.setUpdateTime(System.currentTimeMillis()); + testPlanApiCaseService.updateByPrimaryKeySelective(apiCase); + } else { + userID = Objects.requireNonNull(SessionUtils.getUser()).getId(); + testPlanApiCaseService.setExecResult(item.getName(), status, item.getStartTime()); + testCaseReviewApiCaseService.setExecResult(item.getName(), status, item.getStartTime()); + } + saveResult.setUserId(userID); + // 前一条数据内容清空 + ApiDefinitionExecResult prevResult = extApiDefinitionExecResultMapper.selectMaxResultByResourceIdAndType(item.getName(), finalSaveResultType); + if (prevResult != null) { + prevResult.setContent(null); + apiDefinitionExecResultMapper.updateByPrimaryKeyWithBLOBs(prevResult); + } + apiDefinitionExecResultMapper.insert(saveResult); + }); } - } - if (StringUtils.equals(type, ApiRunMode.JENKINS_API_PLAN.name())) { - saveResult.setTriggerMode(TriggerMode.API.name()); - } else { - saveResult.setTriggerMode(TriggerMode.SCHEDULE.name()); - } + }); + } - saveResult.setResourceId(item.getName()); - saveResult.setActuator("LOCAL"); - saveResult.setContent(JSON.toJSONString(item)); - saveResult.setStartTime(item.getStartTime()); - String status = item.isSuccess() ? "success" : "error"; - saveResult.setEndTime(item.getResponseResult().getResponseTime()); - saveResult.setType(finalSaveResultType); - saveResult.setStatus(status); - - String userID = null; - if (StringUtils.equals(type, ApiRunMode.SCHEDULE_API_PLAN.name())) { - TestPlanApiCase apiCase = testPlanApiCaseService.getById(item.getName()); - String scheduleCreateUser = testPlanService.findScheduleCreateUserById(apiCase.getTestPlanId()); - userID = scheduleCreateUser; - apiCase.setStatus(status); - apiCase.setUpdateTime(System.currentTimeMillis()); - testPlanApiCaseService.updateByPrimaryKeySelective(apiCase); - } else if (StringUtils.equals(type, ApiRunMode.JENKINS_SCENARIO_PLAN.name())) { - TestPlanApiCase apiCase = testPlanApiCaseService.getById(item.getName()); - userID = Objects.requireNonNull(SessionUtils.getUser()).getId(); - apiCase.setStatus(status); - apiCase.setUpdateTime(System.currentTimeMillis()); - testPlanApiCaseService.updateByPrimaryKeySelective(apiCase); - } else { - userID = Objects.requireNonNull(SessionUtils.getUser()).getId(); - testPlanApiCaseService.setExecResult(item.getName(), status, item.getStartTime()); - testCaseReviewApiCaseService.setExecResult(item.getName(), status, item.getStartTime()); - } - saveResult.setUserId(userID); - // 前一条数据内容清空 - ApiDefinitionExecResult prevResult = extApiDefinitionExecResultMapper.selectMaxResultByResourceIdAndType(item.getName(), finalSaveResultType); - if (prevResult != null) { - prevResult.setContent(null); - apiDefinitionExecResultMapper.updateByPrimaryKeyWithBLOBs(prevResult); - } - apiDefinitionExecResultMapper.insert(saveResult); - }); + TestPlanReportService testPlanReportService = CommonBeanFactory.getBean(TestPlanReportService.class); + testPlanReportService.updateExecuteApis(testPlanReportId,apiIdResultMap,null,null); } public void deleteByResourceId(String resourceId) { diff --git a/backend/src/main/java/io/metersphere/api/service/ApiScenarioReportService.java b/backend/src/main/java/io/metersphere/api/service/ApiScenarioReportService.java index d4ad159ec6..e24a8c14f4 100644 --- a/backend/src/main/java/io/metersphere/api/service/ApiScenarioReportService.java +++ b/backend/src/main/java/io/metersphere/api/service/ApiScenarioReportService.java @@ -23,6 +23,7 @@ import io.metersphere.base.mapper.TestPlanApiScenarioMapper; import io.metersphere.base.mapper.ext.ExtApiScenarioReportMapper; import io.metersphere.commons.constants.ApiRunMode; import io.metersphere.commons.constants.ReportTriggerMode; +import io.metersphere.commons.constants.TestPlanApiExecuteStatus; import io.metersphere.commons.constants.TriggerMode; import io.metersphere.commons.exception.MSException; import io.metersphere.commons.utils.*; @@ -252,7 +253,7 @@ public class ApiScenarioReportService { return returnReport; } - public ApiScenarioReport updateSchedulePlanCase(TestResult result, String runMode) { + public ApiScenarioReport updateSchedulePlanCase(TestResult result, String runMode) { ApiScenarioReport lastReport = null; List scenarioResultList = result.getScenarios(); @@ -261,6 +262,7 @@ public class ApiScenarioReportService { List reportIds = new ArrayList<>(); List scenarioIdList = new ArrayList<>(); + Map scenarioAndErrorMap = new HashMap<>(); for (ScenarioResult scenarioResult : scenarioResultList) { // 存储场景报告 @@ -296,9 +298,12 @@ public class ApiScenarioReportService { report.setScenarioId(testPlanApiScenario.getApiScenarioId()); report.setTestPlanScenarioId(planScenarioId); apiScenarioReportMapper.updateByPrimaryKeySelective(report); + if (scenarioResult.getError() > 0) { + scenarioAndErrorMap.put(testPlanApiScenario.getApiScenarioId(), TestPlanApiExecuteStatus.FAILD.name()); testPlanApiScenario.setLastResult(ScenarioStatus.Fail.name()); } else { + scenarioAndErrorMap.put(testPlanApiScenario.getApiScenarioId(), TestPlanApiExecuteStatus.SUCCESS.name()); testPlanApiScenario.setLastResult(ScenarioStatus.Success.name()); } String passRate = new DecimalFormat("0%").format((float) scenarioResult.getSuccess() / (scenarioResult.getSuccess() + scenarioResult.getError())); @@ -317,18 +322,17 @@ public class ApiScenarioReportService { testPlanApiScenario.setReportId(report.getId()); testPlanApiScenario.setUpdateTime(System.currentTimeMillis()); testPlanApiScenarioMapper.updateByPrimaryKeySelective(testPlanApiScenario); -// scenarioIds.append(scenarioResult.getName()).append(","); scenarioIdList.add(testPlanApiScenario.getApiScenarioId()); scenarioNames.append(report.getName()).append(","); lastReport = report; reportIds.add(report.getId()); } - // 合并报告 - // margeReport(result, scenarioIds, scenarioNames, runMode, projectId, userId, reportIds); - TestPlanReportService testPlanReportService = CommonBeanFactory.getBean(TestPlanReportService.class); - testPlanReportService.updateReport(testPlanReportIdList, runMode, lastReport.getTriggerMode(), scenarioIdList); + for (String planId :testPlanReportIdList) { + testPlanReportService.updateExecuteApis(planId,null,scenarioAndErrorMap,null); + } +// testPlanReportService.updateReport(testPlanReportIdList, runMode, lastReport.getTriggerMode(), scenarioIdList); return lastReport; } diff --git a/backend/src/main/java/io/metersphere/api/service/TestResultService.java b/backend/src/main/java/io/metersphere/api/service/TestResultService.java index e9b480d0a8..31424e3728 100644 --- a/backend/src/main/java/io/metersphere/api/service/TestResultService.java +++ b/backend/src/main/java/io/metersphere/api/service/TestResultService.java @@ -90,21 +90,9 @@ public class TestResultService { } else if (StringUtils.equalsAny(runMode, ApiRunMode.API_PLAN.name(), ApiRunMode.SCHEDULE_API_PLAN.name(), ApiRunMode.JENKINS_API_PLAN.name())) { //测试计划定时任务-接口执行逻辑的话,需要同步测试计划的报告数据 if (StringUtils.equals(runMode, ApiRunMode.SCHEDULE_API_PLAN.name())) { - apiDefinitionExecResultService.saveApiResultByScheduleTask(testResult, ApiRunMode.SCHEDULE_API_PLAN.name()); - List testPlanReportIdList = new ArrayList<>(); - testPlanReportIdList.add(debugReportId); - for (String testPlanReportId : testPlanReportIdList) { // 更新每个测试计划的状态 - testPlanReportService.checkTestPlanStatus(testPlanReportId); - } - testPlanReportService.updateReport(testPlanReportIdList, ApiRunMode.SCHEDULE_API_PLAN.name(), ReportTriggerMode.SCHEDULE.name()); + apiDefinitionExecResultService.saveApiResultByScheduleTask(testResult,debugReportId, ApiRunMode.SCHEDULE_API_PLAN.name(),ReportTriggerMode.SCHEDULE.name()); } else if (StringUtils.equals(runMode, ApiRunMode.JENKINS_API_PLAN.name())) { - apiDefinitionExecResultService.saveApiResultByScheduleTask(testResult, ApiRunMode.JENKINS_API_PLAN.name()); - List testPlanReportIdList = new ArrayList<>(); - testPlanReportIdList.add(debugReportId); - for (String testPlanReportId : testPlanReportIdList) { // 更新每个测试计划的状态 - testPlanReportService.checkTestPlanStatus(testPlanReportId); - } - testPlanReportService.updateReport(testPlanReportIdList, ApiRunMode.JENKINS_API_PLAN.name(), ReportTriggerMode.API.name()); + apiDefinitionExecResultService.saveApiResultByScheduleTask(testResult,debugReportId, ApiRunMode.JENKINS_API_PLAN.name(),ReportTriggerMode.API.name()); } else { apiDefinitionExecResultService.saveApiResult(testResult, ApiRunMode.API_PLAN.name(), TriggerMode.MANUAL.name()); } diff --git a/backend/src/main/java/io/metersphere/base/mapper/ext/ExtTestPlanApiCaseMapper.java b/backend/src/main/java/io/metersphere/base/mapper/ext/ExtTestPlanApiCaseMapper.java index 780e92f3b3..224b4b6a47 100644 --- a/backend/src/main/java/io/metersphere/base/mapper/ext/ExtTestPlanApiCaseMapper.java +++ b/backend/src/main/java/io/metersphere/base/mapper/ext/ExtTestPlanApiCaseMapper.java @@ -2,6 +2,7 @@ package io.metersphere.base.mapper.ext; import io.metersphere.api.dto.definition.ApiTestCaseRequest; import io.metersphere.api.dto.definition.TestPlanApiCaseDTO; +import io.metersphere.base.domain.ApiTestCaseWithBLOBs; import io.metersphere.base.domain.TestPlanApiCase; import org.apache.ibatis.annotations.Param; @@ -21,4 +22,6 @@ public interface ExtTestPlanApiCaseMapper { List getStatusByTestPlanId(String id); List selectIds(@Param("request") ApiTestCaseRequest request); + + ApiTestCaseWithBLOBs getApiTestCaseById(String testPlanApiCaseId); } \ No newline at end of file diff --git a/backend/src/main/java/io/metersphere/base/mapper/ext/ExtTestPlanApiCaseMapper.xml b/backend/src/main/java/io/metersphere/base/mapper/ext/ExtTestPlanApiCaseMapper.xml index b3cb3c1b14..ac60c08102 100644 --- a/backend/src/main/java/io/metersphere/base/mapper/ext/ExtTestPlanApiCaseMapper.xml +++ b/backend/src/main/java/io/metersphere/base/mapper/ext/ExtTestPlanApiCaseMapper.xml @@ -13,7 +13,11 @@ WHERE test_plan_id = #{request.testPlanId} and api_case_id = #{request.apiCaseId} ) - +