feat(测试跟踪): 测试跟踪关联测试用例支持关联UI测试用例

--story=1010475 --user=张大海 【测试跟踪】测试跟踪关联测试用例支持关联UI测试用例 https://www.tapd.cn/55049933/s/1312023
This commit is contained in:
zhangdahai112 2022-12-05 10:26:22 +08:00 committed by zhangdahai112
parent 54278943ff
commit 3a26a32b62
26 changed files with 485 additions and 42 deletions

View File

@ -1,5 +1,5 @@
export default {
sync_add_api_load: 'Synchronously add associated api and load tests',
sync_add_api_load: 'Synchronously add associated test case',
next: 'Next',
total_size: 'Total {0}',
related_requirements: 'Related requirements',

View File

@ -1,5 +1,5 @@
export default {
sync_add_api_load: '同步添加关联的接口和性能测试',
sync_add_api_load: '同步添加关联测试的用例',
next: '下一条',
total_size: '共 {0} 条',
related_requirements: '关联需求',

View File

@ -1,5 +1,5 @@
export default {
sync_add_api_load: '同步添加關聯的接口和性能測試',
sync_add_api_load: '同步添加關聯測試的用例',
next: '下一條',
total_size: '共 {0} 條',
related_requirements: '關聯需求',

View File

@ -2027,7 +2027,8 @@ const message = {
api: "接口用例",
scene: "场景用例",
load: "性能用例",
functional: "功能用例"
functional: "功能用例",
ui: "UI用例",
}
}
},

View File

@ -79,11 +79,11 @@ public interface ExtTestCaseMapper {
List<TrackCountResult> countStatus(@Param("projectId") String projectId);
List<TrackCountResult> countRelevance(@Param("projectId") String projectId);
List<TrackCountResult> countRelevance(@Param("projectId") String projectId, @Param("queryUI") boolean queryUI);
long countRelevanceCreatedThisWeek(@Param("projectId") String projectId, @Param("firstDayTimestamp") long firstDayTimestamp, @Param("lastDayTimestamp") long lastDayTimestamp);
int countCoverage(@Param("projectId") String projectId);
int countCoverage(@Param("projectId") String projectId, @Param("queryUi") boolean queryUi);
List<TrackCountResult> countFuncMaintainer(@Param("projectId") String projectId);

View File

@ -836,7 +836,14 @@
FROM test_case_test
WHERE test_type = 'automation'
and test_id IN (select id FROM api_scenario WHERE `STATUS` != 'Trash')
)
<if test="queryUI">
UNION
SELECT test_case_id, test_id, test_type
FROM test_case_test
WHERE test_type = 'uiAutomation'
and test_id IN (select id FROM ui_scenario WHERE `STATUS` != 'Trash')
</if>
)
test_case_test
ON test_case.id = test_case_test.test_case_id
WHERE
@ -869,6 +876,11 @@
UNION
SELECT test_case_id FROM test_case_test WHERE test_type = 'automation' and test_id IN (select id FROM
api_scenario WHERE `STATUS` != 'Trash')
<if test="queryUi">
UNION
SELECT test_case_id FROM test_case_test WHERE test_type = 'uiAutomation' and test_id IN (select id FROM
ui_scenario WHERE `STATUS` != 'Trash')
</if>
)
</select>
<select id="countFuncMaintainer" resultType="io.metersphere.dto.TrackCountResult">

View File

@ -1,5 +1,5 @@
package io.metersphere.constants;
public enum TestCaseTestType {
testcase, automation, performance
testcase, automation, performance, uiAutomation
}

View File

@ -2,6 +2,7 @@ package io.metersphere.controller;
import io.metersphere.base.domain.TestCase;
import io.metersphere.commons.constants.MicroServiceName;
import io.metersphere.dto.BugStatistics;
import io.metersphere.dto.TrackCountResult;
import io.metersphere.dto.TrackStatisticsDTO;
@ -9,6 +10,7 @@ import io.metersphere.i18n.Translator;
import io.metersphere.plan.dto.ChartsData;
import io.metersphere.service.TestCaseService;
import io.metersphere.service.TrackService;
import io.metersphere.utils.DiscoveryUtil;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
@ -21,7 +23,6 @@ import java.util.List;
@RestController
@RequestMapping("/track")
public class TrackController {
@Resource
private TrackService trackService;
@Resource
@ -61,7 +62,8 @@ public class TrackController {
public TrackStatisticsDTO getRelevanceCount(@PathVariable String projectId) {
TrackStatisticsDTO statistics = new TrackStatisticsDTO();
List<TrackCountResult> relevanceResults = trackService.countRelevance(projectId);
boolean queryUi = DiscoveryUtil.hasService(MicroServiceName.UI_TEST);
List<TrackCountResult> relevanceResults = trackService.countRelevance(projectId, queryUi);
statistics.countRelevance(relevanceResults);
long size = trackService.countRelevanceCreatedThisWeek(projectId);
@ -69,7 +71,7 @@ public class TrackController {
List<TestCase> list = testCaseService.getTestCaseByProjectId(projectId);
long total = list.size();
int coverage = trackService.countCoverage(projectId);
int coverage = trackService.countCoverage(projectId, queryUi);
statistics.setCoverageCount(coverage);
statistics.setUncoverageCount(total - coverage);
@ -82,6 +84,9 @@ public class TrackController {
statistics.setApiCaseCountStr(Translator.get("api_case") + "<br/><br/>" + statistics.getApiCaseCount());
statistics.setPerformanceCaseCountStr(Translator.get("performance_case") + "<br/><br/>" + statistics.getPerformanceCaseCount());
statistics.setScenarioCaseStr(Translator.get("scenario_case") + "<br/><br/>" + statistics.getScenarioCaseCount());
if (queryUi) {
statistics.setUiScenarioCaseStr(Translator.get("ui_scenario_case") + "<br/><br/>" + statistics.getUiScenarioCaseCount());
}
return statistics;
}

View File

@ -11,7 +11,8 @@ import javax.servlet.http.HttpServletRequest;
"/test/plan/uiScenario/case",
"/ui/scenario/module",
"/share/test/plan/uiScenario/case",
"/ui/automation"
"/ui/automation",
"/test/case/relevance/uiScenario"
})
public class TrackUiTestController {
@Resource

View File

@ -1,5 +1,5 @@
package io.metersphere.dto;
public enum TestCaseTestStatus {
performance, api, testcase, automation
performance, api, testcase, automation, uiAutomation
}

View File

@ -69,10 +69,16 @@ public class TrackStatisticsDTO {
*/
private long performanceCaseCount = 0;
/**
* UI场景用例数量统计
*/
private long uiScenarioCaseCount = 0;
private String apiCaseCountStr = StringUtils.EMPTY;
private String scenarioCaseStr = StringUtils.EMPTY;
private String performanceCaseCountStr = StringUtils.EMPTY;
private String uiScenarioCaseStr = StringUtils.EMPTY;
/**
* 本周新增数量
@ -187,6 +193,15 @@ public class TrackStatisticsDTO {
chartData.put(Translator.get("scenario_case"), count);
}
}
if (StringUtils.equalsIgnoreCase(TrackCount.UI_AUTOMATION, countResult.getGroupField())) {
Integer count = chartData.get(Translator.get("ui_scenario_case"));
if (count == null) {
chartData.put(Translator.get("ui_scenario_case"), (int) countResult.getCountNumber());
} else {
count += (int) countResult.getCountNumber();
chartData.put(Translator.get("ui_scenario_case"), count);
}
}
this.allRelevanceCaseCount += countResult.getCountNumber();
}

View File

@ -28,5 +28,8 @@ public class PlanCaseRelevanceRequest {
*/
private List<String> testCaseIds = new ArrayList<>();
/**
* 是否同步关联功能用例下关联的接口场景性能ui用例
*/
private Boolean checked;
}

View File

@ -628,22 +628,30 @@ public class TestPlanService {
List<String> apiCaseIds = new ArrayList<>();
List<String> scenarioIds = new ArrayList<>();
List<String> performanceIds = new ArrayList<>();
buildCaseIdList(list, apiCaseIds, scenarioIds, performanceIds);
startRelevance(request, apiCaseIds, scenarioIds, performanceIds);
List<String> uiScenarioIds = new ArrayList<>();
buildCaseIdList(list, apiCaseIds, scenarioIds, performanceIds, uiScenarioIds);
startRelevance(request, apiCaseIds, scenarioIds, performanceIds, uiScenarioIds);
}
private void startRelevance(PlanCaseRelevanceRequest request, List<String> apiCaseIds, List<String> scenarioIds, List<String> performanceIds) {
private void startRelevance(PlanCaseRelevanceRequest request, List<String> apiCaseIds, List<String> scenarioIds, List<String> performanceIds, List<String> uiScenarioIds) {
Set<String> serviceIdSet = DiscoveryUtil.getServiceIdSet();
if (serviceIdSet.contains(MicroServiceName.API_TEST)) {
planTestPlanApiCaseService.relevanceByTestIds(apiCaseIds, request.getPlanId());
planTestPlanScenarioCaseService.relevanceByTestIds(scenarioIds, request.getPlanId());
if (CollectionUtils.isNotEmpty(apiCaseIds)) {
planTestPlanApiCaseService.relevanceByTestIds(apiCaseIds, request.getPlanId());
}
if (CollectionUtils.isNotEmpty(scenarioIds)) {
planTestPlanScenarioCaseService.relevanceByTestIds(scenarioIds, request.getPlanId());
}
}
if (serviceIdSet.contains(MicroServiceName.PERFORMANCE_TEST)) {
if (serviceIdSet.contains(MicroServiceName.PERFORMANCE_TEST) && CollectionUtils.isNotEmpty(performanceIds)) {
planTestPlanLoadCaseService.relevanceByTestIds(performanceIds, request.getPlanId());
}
if (serviceIdSet.contains(MicroServiceName.UI_TEST) && CollectionUtils.isNotEmpty(uiScenarioIds)) {
planTestPlanUiScenarioCaseService.relevanceByTestIds(uiScenarioIds, request.getPlanId());
}
}
private static void buildCaseIdList(List<TestCaseTest> list, List<String> apiCaseIds, List<String> scenarioIds, List<String> performanceIds) {
private static void buildCaseIdList(List<TestCaseTest> list, List<String> apiCaseIds, List<String> scenarioIds, List<String> performanceIds, List<String> uiScenarioIds) {
for (TestCaseTest l : list) {
if (StringUtils.equals(l.getTestType(), TestCaseTestStatus.performance.name())) {
performanceIds.add(l.getTestId());
@ -654,6 +662,9 @@ public class TestPlanService {
if (StringUtils.equals(l.getTestType(), TestCaseTestStatus.automation.name())) {
scenarioIds.add(l.getTestId());
}
if (StringUtils.equals(l.getTestType(), TestCaseTestStatus.uiAutomation.name())) {
uiScenarioIds.add(l.getTestId());
}
}
}

View File

@ -29,7 +29,7 @@ import java.util.*;
@Service
public class PlanTestPlanUiScenarioCaseService extends UiTestService {
private static final String BASE_UEL = "/test/plan/uiScenario/case";
private static final String BASE_URL = "/test/plan/uiScenario/case";
@Resource
private PlanTestPlanScenarioCaseService planTestPlanScenarioCaseService;
@ -41,11 +41,11 @@ public class PlanTestPlanUiScenarioCaseService extends UiTestService {
TestPlanService testPlanService;
public List<String> getExecResultByPlanId(String planId) {
return (List<String>) microService.getForData(serviceName, BASE_UEL + "/plan/exec/result/" + planId);
return (List<String>) microService.getForData(serviceName, BASE_URL + "/plan/exec/result/" + planId);
}
public UiPlanReportDTO getUiReport(ApiPlanReportRequest request) {
return microService.postForData(serviceName, BASE_UEL + "/plan/report", request, UiPlanReportDTO.class);
return microService.postForData(serviceName, BASE_URL + "/plan/report", request, UiPlanReportDTO.class);
}
public void calculatePlanReport(List<String> reportIds, TestPlanSimpleReportDTO report) {
@ -93,20 +93,20 @@ public class PlanTestPlanUiScenarioCaseService extends UiTestService {
private TestPlanScenarioStepCountSimpleDTO getStepCount(List<PlanReportCaseDTO> planReportCaseDTOS) {
return microService.postForData(serviceName, BASE_UEL + "/step/count", planReportCaseDTOS, TestPlanScenarioStepCountSimpleDTO.class);
return microService.postForData(serviceName, BASE_URL + "/step/count", planReportCaseDTOS, TestPlanScenarioStepCountSimpleDTO.class);
}
public List<PlanReportCaseDTO> selectStatusForPlanReport(String planId) {
return microService.getForDataArray(serviceName, BASE_UEL + "/get/report/status/" + planId, PlanReportCaseDTO.class);
return microService.getForDataArray(serviceName, BASE_URL + "/get/report/status/" + planId, PlanReportCaseDTO.class);
}
public void copyPlan(String sourcePlanId, String targetPlanId) {
microService.getForData(serviceName, BASE_UEL + "/plan/copy/" + sourcePlanId + "/" + targetPlanId);
microService.getForData(serviceName, BASE_URL + "/plan/copy/" + sourcePlanId + "/" + targetPlanId);
}
public boolean haveUiCase(String planId) {
try {
return (boolean) microService.getForData(serviceName, BASE_UEL + "/have/ui/case/" + planId);
return (boolean) microService.getForData(serviceName, BASE_URL + "/have/ui/case/" + planId);
} catch (MSException e) {
LogUtil.error(e);
return false;
@ -114,34 +114,38 @@ public class PlanTestPlanUiScenarioCaseService extends UiTestService {
}
public List<TestPlanUiScenario> list(String planId) {
return microService.getForDataArray(serviceName, BASE_UEL + "/list/" + planId, TestPlanUiScenario.class);
return microService.getForDataArray(serviceName, BASE_URL + "/list/" + planId, TestPlanUiScenario.class);
}
public Boolean isCaseExecuting(String planId) {
return (Boolean) microService.getForData(serviceName, BASE_UEL + "/is/executing/" + planId);
return (Boolean) microService.getForData(serviceName, BASE_URL + "/is/executing/" + planId);
}
public List<TestPlanUiScenarioDTO> getFailureListByIds(Set<String> ids) {
return microService.postForDataArray(serviceName, BASE_UEL + "/failure/list", ids, TestPlanUiScenarioDTO.class);
return microService.postForDataArray(serviceName, BASE_URL + "/failure/list", ids, TestPlanUiScenarioDTO.class);
}
public List<ModuleNodeDTO> getNodeByPlanId(List<String> projectIds, String planId) {
return microService.postForDataArray(serviceName, BASE_UEL + "/list/module/" + planId, projectIds, ModuleNodeDTO.class);
return microService.postForDataArray(serviceName, BASE_URL + "/list/module/" + planId, projectIds, ModuleNodeDTO.class);
}
public List<TestPlanUiScenarioDTO> buildResponse(List<TestPlanUiScenarioDTO> uiCases) {
if (CollectionUtils.isEmpty(uiCases)) {
return null;
}
return microService.postForDataArray(serviceName, BASE_UEL + "/build/response", uiCases, TestPlanUiScenarioDTO.class);
return microService.postForDataArray(serviceName, BASE_URL + "/build/response", uiCases, TestPlanUiScenarioDTO.class);
}
public Object relevanceList(ApiScenarioRequest request, int pageNum, int pageSize) {
request.setAllowedRepeatCase(testPlanService.isAllowedRepeatCase(request.getPlanId()));
return microService.postForData(serviceName, BASE_UEL + String.format("/relevance/list/%s/%s", pageNum, pageSize), request);
return microService.postForData(serviceName, BASE_URL + String.format("/relevance/list/%s/%s", pageNum, pageSize), request);
}
public void orderCase(ResetOrderRequest request) {
microService.postForData(serviceName, BASE_UEL + "/edit/order", request);
microService.postForData(serviceName, BASE_URL + "/edit/order", request);
}
public void relevanceByTestIds(List<String> uiScenarioIds, String planId) {
microService.postForData(serviceName, BASE_URL + "/relevance/" + planId, uiScenarioIds);
}
}

View File

@ -9,4 +9,5 @@ public class TrackCount {
public static final String TESTCASE = "testcase";
public static final String PERFORMANCE = "performance";
public static final String AUTOMATION = "automation";
public static final String UI_AUTOMATION = "uiAutomation";
}

View File

@ -35,6 +35,7 @@ import io.metersphere.plan.service.TestPlanTestCaseService;
import io.metersphere.request.OrderRequest;
import io.metersphere.request.ProjectVersionRequest;
import io.metersphere.request.ResetOrderRequest;
import io.metersphere.service.remote.ui.RelevanceUiCaseService;
import io.metersphere.xpack.track.dto.AttachmentRequest;
import io.metersphere.request.member.QueryMemberRequest;
import io.metersphere.request.testcase.*;
@ -145,6 +146,8 @@ public class TestCaseService {
private RelevanceApiCaseService relevanceApiCaseService;
@Resource
private RelevanceLoadCaseService relevanceLoadCaseService;
@Resource
private RelevanceUiCaseService relevanceUiCaseService;
// @Resource
// @Lazy
// private ApiTestCaseService apiTestCaseService;
@ -2593,6 +2596,7 @@ public class TestCaseService {
List<ApiTestCase> apiCases = new ArrayList<>();
List<ApiScenario> apiScenarios = new ArrayList<>();
List<LoadTest> apiLoadTests = new ArrayList<>();
List<UiScenario> uiScenarios = new ArrayList<>();
if (serviceIdSet.contains(MicroServiceName.API_TEST)) {
apiCases = relevanceApiCaseService.getApiCaseByIds(
@ -2612,6 +2616,13 @@ public class TestCaseService {
versionIds.addAll(apiLoadTests.stream().map(l -> l.getVersionId()).collect(Collectors.toList()));
}
if (serviceIdSet.contains(MicroServiceName.UI_TEST)) {
uiScenarios = relevanceUiCaseService.getUiCaseByIds(
getTestIds(testCaseTests, TestCaseTestType.uiAutomation.name()));
projectIds.addAll(uiScenarios.stream().map(s -> s.getProjectId()).collect(Collectors.toList()));
versionIds.addAll(uiScenarios.stream().map(l -> l.getVersionId()).collect(Collectors.toList()));
}
projectIds = projectIds.stream().distinct().collect(Collectors.toList());
versionIds = versionIds.stream().distinct().collect(Collectors.toList());
@ -2647,6 +2658,10 @@ public class TestCaseService {
getTestCaseTestDaoList(TestCaseTestType.performance.name(), item.getNum(), item.getName(), item.getId(), projectNameMap.get(item.getProjectId()), versionNameMap.get(item.getVersionId()),
testCaseTestList, testCaseTestsMap);
});
uiScenarios.forEach(item -> {
getTestCaseTestDaoList(TestCaseTestType.uiAutomation.name(), item.getNum(), item.getName(), item.getId(), projectNameMap.get(item.getProjectId()), versionNameMap.get(item.getVersionId()),
testCaseTestList, testCaseTestsMap);
});
return testCaseTestList;
}

View File

@ -94,8 +94,8 @@ public class TrackService {
return extTestCaseMapper.countStatus(projectId);
}
public List<TrackCountResult> countRelevance(String projectId) {
return extTestCaseMapper.countRelevance(projectId);
public List<TrackCountResult> countRelevance(String projectId, boolean queryUI) {
return extTestCaseMapper.countRelevance(projectId, queryUI);
}
public long countRelevanceCreatedThisWeek(String projectId) {
@ -111,8 +111,8 @@ public class TrackService {
}
}
public int countCoverage(String projectId) {
return extTestCaseMapper.countCoverage(projectId);
public int countCoverage(String projectId, boolean queryUi) {
return extTestCaseMapper.countCoverage(projectId, queryUi);
}
public List<ChartsData> getCaseMaintenanceBar(String projectId) {

View File

@ -0,0 +1,17 @@
package io.metersphere.service.remote.ui;
import io.metersphere.base.domain.UiScenario;
import io.metersphere.service.remote.project.TrackUiTestService;
import org.springframework.stereotype.Service;
import java.util.List;
@Service
public class RelevanceUiCaseService extends TrackUiTestService {
private static final String BASE_URL = "/test/case";
public List<UiScenario> getUiCaseByIds(List<String> ids) {
return microService.postForDataArray(serviceName, BASE_URL + "/getUiCaseByIds", ids, UiScenario.class);
}
}

View File

@ -188,6 +188,7 @@ message_task_already_exists=Task recipient already exists
api_case=Api
performance_case=Performance
scenario_case=Scenario
ui_scenario_case=UI Scenario
create_user=Create user
test_case_status=Case status
id_not_rightful=ID is not rightful

View File

@ -161,6 +161,7 @@ message_task_already_exists=任务接收人已经存在
api_case=接口用例
performance_case=性能用例
scenario_case=场景用例
ui_scenario_case=UI用例
test_case_status_error=失败
test_case_status_success=成功
test_case_status_trash=废弃

View File

@ -161,6 +161,7 @@ message_task_already_exists=任務接收人已經存在
api_case=接口用例
performance_case=性能用例
scenario_case=場景用例
ui_scenario_case=UI用例
test_case_status_error=失敗
test_case_status_success=成功
test_case_status_trash=廢棄

View File

@ -233,6 +233,10 @@ export function getTestCaseRelevanceScenarioList(pageNum, pageSize, param) {
return post(BASE_URL + "relevance/scenario/list/" + pageNum + "/" + pageSize, param);
}
export function getTestCaseRelevanceUiScenarioList(pageNum, pageSize, param) {
return post(BASE_URL + "relevance/uiScenario/list/" + pageNum + "/" + pageSize, param);
}
export function getTestCaseRelevanceLoadList(pageNum, pageSize, param) {
return post(BASE_URL + "relevance/load/list/" + pageNum + "/" + pageSize, param);
}
@ -245,6 +249,10 @@ export function saveCaseRelevanceScenario(caseId, param) {
return post(BASE_URL + "relate/test/automation/" + caseId, param);
}
export function saveUiCaseRelevanceScenario(caseId, param) {
return post(BASE_URL + "relate/test/uiAutomation/" + caseId, param);
}
export function saveCaseRelevanceLoad(caseId, param) {
return post(BASE_URL + "relate/test/performance/" + caseId, param);
}

View File

@ -0,0 +1,215 @@
<template>
<div>
<div class="right-search">
<version-select v-xpack :project-id="projectId" @changeVersion="changeVersion" margin-right="20"/>
<el-input :placeholder="$t('commons.search_by_name_or_id')" @blur="initTable"
@keyup.enter.native="initTable" class="search-input" size="small" v-model="condition.name"/>
<ms-table-adv-search-bar :condition.sync="condition" class="adv-search-bar"
v-if="condition.components !== undefined && condition.components.length > 0"
@search="initTable"/>
</div>
<ms-table v-loading="result.loading" :data="tableData" :select-node-ids="selectNodeIds" :condition="condition"
:page-size="pageSize"
:total="total"
:showSelectAll="false"
:screenHeight="screenHeight"
@selectCountChange="selectCountChange"
@refresh="initTable"
ref="table">
<ms-table-column
prop="num"
label="ID"
width="100px"
sortable=true>
</ms-table-column>
<ms-table-column
prop="name"
:label="$t('api_test.automation.scenario_name')"/>
<ms-table-column
prop="level"
sortable
min-width="130px"
:label="$t('api_test.automation.case_level')">
<template v-slot:default="scope">
<priority-table-item :value="scope.row.level"/>
</template>
</ms-table-column>
<ms-table-column prop="status"
:label="$t('test_track.plan.plan_status')"
sortable
min-width="120px">
<template v-slot:default="scope">
<plan-status-table-item :value="scope.row.status"/>
</template>
</ms-table-column>
<ms-table-column prop="tags" width="120px" :label="$t('commons.tag')">
<template v-slot:default="scope">
<ms-tag v-for="(itemName,index) in scope.row.tags" :key="index" type="success" effect="plain"
:content="itemName" style="margin-left: 0px; margin-right: 2px"/>
<span></span>
</template>
</ms-table-column>
</ms-table>
<ms-table-pagination :change="initTable" :current-page.sync="currentPage" :page-size.sync="pageSize"
:total="total"/>
</div>
</template>
<script>
import MsTable from "metersphere-frontend/src/components/table/MsTable";
import MsTableColumn from "metersphere-frontend/src/components/table/MsTableColumn";
import PriorityTableItem from "@/business/common/tableItems/planview/PriorityTableItem";
import MsTablePagination from "metersphere-frontend/src/components/pagination/TablePagination";
import PlanStatusTableItem from "@/business/common/tableItems/plan/PlanStatusTableItem";
import MsTableAdvSearchBar from "metersphere-frontend/src/components/search/MsTableAdvSearchBar";
import MsTag from "metersphere-frontend/src/components/MsTag";
import {TEST_CASE_RELEVANCE_API_CASE_CONFIGS} from "metersphere-frontend/src/components/search/search-components";
import {getVersionFilters} from "@/business/utils/sdk-utils";
import MxVersionSelect from "metersphere-frontend/src/components/version/MxVersionSelect";
import {getTestCaseRelevanceScenarioList, getTestCaseRelevanceUiScenarioList} from "@/api/testCase";
export default {
name: "TestCaseRelateUiScenarioList",
components: {
PlanStatusTableItem,
MsTablePagination,
PriorityTableItem,
MsTable,
MsTableColumn,
MsTableAdvSearchBar,
MsTag,
'VersionSelect': MxVersionSelect,
},
data() {
return {
condition: {
components: TEST_CASE_RELEVANCE_API_CASE_CONFIGS
},
result: {},
priorityFilters: [
{text: 'P0', value: 'P0'},
{text: 'P1', value: 'P1'},
{text: 'P2', value: 'P2'},
{text: 'P3', value: 'P3'}
],
screenHeight: 'calc(100vh - 400px)',//
tableData: [],
currentPage: 1,
pageSize: 10,
total: 0,
versionFilters: []
}
},
props: {
selectNodeIds: Array,
projectId: String,
versionEnable: Boolean,
notInIds: {
type: Array,
default: null
},
testCaseId: String
},
created: function () {
this.getVersionOptions();
},
watch: {
selectNodeIds() {
this.initTable();
},
projectId() {
this.condition.versionId = null;
this.initTable();
}
},
computed: {
selectRows() {
if (this.$refs.table) {
return this.$refs.table.getSelectRows();
} else {
return new Set();
}
}
},
methods: {
selectCountChange(data) {
this.$emit("selectCountChange", data);
},
initTable(projectId) {
this.condition.status = "";
this.condition.moduleIds = this.selectNodeIds;
if (projectId != null && typeof projectId === 'string') {
this.condition.projectId = projectId;
} else if (this.projectId != null) {
this.condition.projectId = this.projectId;
}
this.condition.notInIds = this.notInIds;
this.condition.testCaseId = this.testCaseId;
getTestCaseRelevanceUiScenarioList(this.currentPage, this.pageSize, this.condition)
.then(response => {
this.total = response.data.itemCount;
this.tableData = response.data.listObject;
this.tableData.forEach(item => {
if (item.tags && item.tags.length > 0) {
item.tags = JSON.parse(item.tags);
}
});
});
},
clear() {
if (this.$refs.table) {
this.$refs.table.clear();
}
},
buildPagePath(path) {
return path + this.currentPage + "/" + this.pageSize;
},
getSelectIds() {
return this.$refs.table.selectIds;
},
clearSelection() {
if (this.$refs.table) {
this.$refs.table.clearSelectRows();
}
},
getVersionOptions() {
getVersionFilters(this.projectId)
.then(r => this.versionFilters = r.data);
},
changeVersion(currentVersion) {
this.condition.versionId = currentVersion || null;
this.initTable();
}
},
}
</script>
<style scoped>
.right-search {
float: right;
display: inline-block;
}
.search-input {
width: 300px;
margin-right: 20px;
}
.adv-search-bar {
float: right;
margin-top: 5px;
margin-right: 10px;
}
</style>

View File

@ -8,6 +8,7 @@
<el-dropdown-menu slot="dropdown">
<el-dropdown-item command="api">{{ $t('api_test.home_page.failed_case_list.table_value.case_type.api') }}</el-dropdown-item>
<el-dropdown-item command="scenario">{{ $t('api_test.home_page.failed_case_list.table_value.case_type.scene') }}</el-dropdown-item>
<el-dropdown-item command="ui" v-xpack>{{ $t('api_test.home_page.failed_case_list.table_value.case_type.ui') }}</el-dropdown-item>
<el-dropdown-item command="performance">{{$t('api_test.home_page.failed_case_list.table_value.case_type.load')}}</el-dropdown-item>
</el-dropdown-menu>
</el-dropdown>
@ -61,6 +62,13 @@
@refresh="initTable"
ref="apiScenarioRelevance"/>
<test-case-ui-scenario-relate
:case-id="caseId"
:versionEnable="versionEnable"
:not-in-ids="notInIds"
@refresh="initTable"
ref="uiScenarioRelevance"/>
<test-case-load-relate
:case-id="caseId"
:not-in-ids="notInIds"
@ -77,11 +85,15 @@ import MsTableColumn from "metersphere-frontend/src/components/table/MsTableColu
import TestCaseApiRelate from "@/business/case/components/TestCaseApiRelate";
import {deleteRelateTest, getRelateTest} from "@/api/testCase";
import TestCaseScenarioRelate from "@/business/case/components/TestCaseScenarioRelate";
import TestCaseUiScenarioRelate from "@/business/case/components/TestCaseUiScenarioRelate";
import TestCaseLoadRelate from "@/business/case/components/TestCaseLoadRelate";
import i18n from "@/i18n";
import TestCaseUiScenarioRelevance from "@/business/plan/view/comonents/ui/TestCaseUiScenarioRelevance";
export default {
name: "TestCaseTestRelate",
components: {TestCaseLoadRelate, TestCaseScenarioRelate, TestCaseApiRelate, MsTableColumn, MsTable},
components: {
TestCaseUiScenarioRelevance,
TestCaseLoadRelate, TestCaseScenarioRelate, TestCaseApiRelate, MsTableColumn, MsTable, TestCaseUiScenarioRelate},
data() {
return {
data: [],
@ -89,7 +101,8 @@ export default {
typeMap: {
testcase: this.$t('api_test.home_page.failed_case_list.table_value.case_type.api'),
automation: this.$t('api_test.home_page.failed_case_list.table_value.case_type.scene'),
performance: this.$t('api_test.home_page.failed_case_list.table_value.case_type.load')
performance: this.$t('api_test.home_page.failed_case_list.table_value.case_type.load'),
uiAutomation: this.$t('api_test.home_page.failed_case_list.table_value.case_type.ui')
},
operators: [
{
@ -122,6 +135,8 @@ export default {
this.$refs.apiScenarioRelevance.open();
} else if (key === 'performance') {
this.$refs.loadRelevance.open();
} else if (key === 'ui') {
this.$refs.uiScenarioRelevance.open();
}
},
remove(row) {

View File

@ -0,0 +1,117 @@
<template>
<test-case-relevance-base
@setProject="setProject"
@save="saveCaseRelevance"
ref="baseRelevance">
<template v-slot:aside>
<ui-scenario-module
:show-case-num="false"
:relevance-project-id="projectId"
@nodeSelectEvent="nodeChange"
@refreshTable="refresh"
@setModuleOptions="setModuleOptions"
@enableTrash="false"
:is-read-only="true"
ref="nodeTree"/>
</template>
<test-case-relate-ui-scenario-list
:select-node-ids="selectNodeIds"
:project-id="projectId"
:not-in-ids="notInIds"
:versionEnable="versionEnable"
:test-case-id="caseId"
@selectCountChange="setSelectCounts"
ref="apiCaseList"/>
</test-case-relevance-base>
</template>
<script>
import TestCaseRelateApiList from "@/business/case/components/TestCaseRelateApiList";
import TestCaseRelevanceBase from "@/business/plan/view/comonents/base/TestCaseRelevanceBase";
import UiScenarioModule from "@/business/plan/view/comonents/ui/UiScenarioModule";
import TestCaseRelateUiScenarioList from "@/business/case/components/TestCaseRelateUiScenarioList";
import {saveUiCaseRelevanceScenario} from "@/api/testCase";
export default {
name: "TestCaseUiScenarioRelate",
components: {
TestCaseRelateUiScenarioList,
UiScenarioModule,
TestCaseRelevanceBase,
TestCaseRelateApiList,
},
data() {
return {
selectNodeIds: [],
moduleOptions: {},
condition: {},
projectId: ""
};
},
props: {
caseId: {
type: String
},
versionEnable: {
type: Boolean,
default: false
},
notInIds: {
type: Array,
default: null
}
},
methods: {
open() {
this.init();
this.$refs.baseRelevance.open();
if (this.$refs.apiCaseList) {
this.$refs.apiCaseList.clear();
}
},
init() {
if (this.$refs.apiCaseList) {
this.$refs.apiCaseList.initTable();
}
if (this.$refs.nodeTree) {
this.$refs.nodeTree.list();
}
},
setProject(projectId) {
this.projectId = projectId;
},
refresh(data) {
this.$refs.apiCaseList.initTable(data);
},
nodeChange(node, nodeIds, pNodes) {
this.selectNodeIds = nodeIds;
},
setModuleOptions(data) {
this.moduleOptions = data;
},
saveCaseRelevance() {
let ids = this.$refs.apiCaseList.getSelectIds();
saveUiCaseRelevanceScenario(this.caseId, ids)
.then(() => {
this.$success(this.$t('commons.save_success'));
this.$emit('refresh');
this.$refs.baseRelevance.close();
});
},
setSelectCounts(data) {
this.$refs.baseRelevance.selectCounts = data;
}
}
}
</script>
<style scoped>
</style>

View File

@ -1,4 +1,4 @@
<template>
<template>
<div class="dashboard-card">
<el-card shadow="never" class="box-card" style="height: 100%">
<div slot="header" class="clearfix">