Merge branch 'v1.1' of https://github.com/metersphere/metersphere into v1.1
This commit is contained in:
commit
e9f7e532c4
|
@ -95,7 +95,7 @@ public class APITestController {
|
|||
|
||||
@PostMapping(value = "/import", consumes = {"multipart/form-data"})
|
||||
@RequiresRoles(value = {RoleConstants.TEST_USER, RoleConstants.TEST_MANAGER}, logical = Logical.OR)
|
||||
public ApiTest testCaseImport(@RequestPart(value = "file") MultipartFile file, @RequestPart("request") ApiTestImportRequest request) {
|
||||
public ApiTest testCaseImport(@RequestPart(value = "file", required = false) MultipartFile file, @RequestPart("request") ApiTestImportRequest request) {
|
||||
return apiTestService.apiTestImport(file, request);
|
||||
}
|
||||
|
||||
|
|
|
@ -35,6 +35,7 @@ import org.springframework.web.multipart.MultipartFile;
|
|||
import javax.annotation.Resource;
|
||||
|
||||
import java.io.ByteArrayInputStream;
|
||||
import java.io.File;
|
||||
import java.io.InputStream;
|
||||
import java.util.*;
|
||||
import java.util.stream.Collectors;
|
||||
|
@ -263,7 +264,7 @@ public class APITestService {
|
|||
ApiImportParser apiImportParser = ApiImportParserFactory.getApiImportParser(request.getPlatform());
|
||||
ApiImport apiImport = null;
|
||||
try {
|
||||
apiImport = apiImportParser.parse(file.getInputStream(), request);
|
||||
apiImport = apiImportParser.parse(file == null ? null : file.getInputStream(), request);
|
||||
} catch (Exception e) {
|
||||
LogUtil.error(e.getMessage(), e);
|
||||
MSException.throwException(Translator.get("parse_data_error"));
|
||||
|
|
|
@ -5,6 +5,7 @@ import io.metersphere.base.domain.ApiTestEnvironmentWithBLOBs;
|
|||
import io.metersphere.base.mapper.ApiTestEnvironmentMapper;
|
||||
import io.metersphere.commons.exception.MSException;
|
||||
import io.metersphere.i18n.Translator;
|
||||
import org.apache.commons.lang3.StringUtils;
|
||||
import org.springframework.stereotype.Service;
|
||||
import org.springframework.transaction.annotation.Transactional;
|
||||
|
||||
|
@ -34,6 +35,7 @@ public class ApiTestEnvironmentService {
|
|||
}
|
||||
|
||||
public void update(ApiTestEnvironmentWithBLOBs apiTestEnvironment) {
|
||||
checkEnvironmentExist(apiTestEnvironment);
|
||||
apiTestEnvironmentMapper.updateByPrimaryKeyWithBLOBs(apiTestEnvironment);
|
||||
}
|
||||
|
||||
|
@ -47,9 +49,12 @@ public class ApiTestEnvironmentService {
|
|||
private void checkEnvironmentExist (ApiTestEnvironmentWithBLOBs environment) {
|
||||
if (environment.getName() != null) {
|
||||
ApiTestEnvironmentExample example = new ApiTestEnvironmentExample();
|
||||
example.createCriteria()
|
||||
.andNameEqualTo(environment.getName())
|
||||
ApiTestEnvironmentExample.Criteria criteria = example.createCriteria();
|
||||
criteria.andNameEqualTo(environment.getName())
|
||||
.andProjectIdEqualTo(environment.getProjectId());
|
||||
if (StringUtils.isNotBlank(environment.getId())) {
|
||||
criteria.andIdNotEqualTo(environment.getId());
|
||||
}
|
||||
if (apiTestEnvironmentMapper.selectByExample(example).size() > 0) {
|
||||
MSException.throwException(Translator.get("api_test_environment_already_exists"));
|
||||
}
|
||||
|
|
|
@ -1,6 +1,100 @@
|
|||
<?xml version="1.0" encoding="UTF-8" ?>
|
||||
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd" >
|
||||
<mapper namespace="io.metersphere.base.mapper.ext.ExtTestPlanTestCaseMapper">
|
||||
<sql id="condition">
|
||||
<choose>
|
||||
<when test='${object}.operator == "like"'>
|
||||
like CONCAT('%', #{${object}.value},'%')
|
||||
</when>
|
||||
<when test='${object}.operator == "not like"'>
|
||||
not like CONCAT('%', #{${object}.value},'%')
|
||||
</when>
|
||||
<when test='${object}.operator == "in"'>
|
||||
in
|
||||
<foreach collection="${object}.value" item="v" separator="," open="(" close=")">
|
||||
#{v}
|
||||
</foreach>
|
||||
</when>
|
||||
<when test='${object}.operator == "not in"'>
|
||||
not in
|
||||
<foreach collection="${object}.value" item="v" separator="," open="(" close=")">
|
||||
#{v}
|
||||
</foreach>
|
||||
</when>
|
||||
<when test='${object}.operator == "between"'>
|
||||
between #{${object}.value[0]} and #{${object}.value[1]}
|
||||
</when>
|
||||
<when test='${object}.operator == "gt"'>
|
||||
> #{${object}.value}
|
||||
</when>
|
||||
<when test='${object}.operator == "lt"'>
|
||||
< #{${object}.value}
|
||||
</when>
|
||||
<when test='${object}.operator == "ge"'>
|
||||
>= #{${object}.value}
|
||||
</when>
|
||||
<when test='${object}.operator == "le"'>
|
||||
<= #{${object}.value}
|
||||
</when>
|
||||
<when test='${object}.operator == "current user"'>
|
||||
= '${@io.metersphere.commons.utils.SessionUtils@getUserId()}'
|
||||
</when>
|
||||
<otherwise>
|
||||
= #{${object}.value}
|
||||
</otherwise>
|
||||
</choose>
|
||||
</sql>
|
||||
|
||||
<sql id="combine">
|
||||
<if test="${condition}.name != null">
|
||||
and test_case.name
|
||||
<include refid="condition">
|
||||
<property name="object" value="${condition}.name"/>
|
||||
</include>
|
||||
</if>
|
||||
<if test="${condition}.module != null">
|
||||
and test_case.node_path
|
||||
<include refid="condition">
|
||||
<property name="object" value="${condition}.module"/>
|
||||
</include>
|
||||
</if>
|
||||
<if test="${condition}.priority != null">
|
||||
and test_case.priority
|
||||
<include refid="condition">
|
||||
<property name="object" value="${condition}.priority"/>
|
||||
</include>
|
||||
</if>
|
||||
<if test="${condition}.createTime != null">
|
||||
and test_case.create_time
|
||||
<include refid="condition">
|
||||
<property name="object" value="${condition}.createTime"/>
|
||||
</include>
|
||||
</if>
|
||||
<if test="${condition}.type != null">
|
||||
and test_case.type
|
||||
<include refid="condition">
|
||||
<property name="object" value="${condition}.type"/>
|
||||
</include>
|
||||
</if>
|
||||
<if test="${condition}.updateTime != null">
|
||||
and test_case.update_time
|
||||
<include refid="condition">
|
||||
<property name="object" value="${condition}.updateTime"/>
|
||||
</include>
|
||||
</if>
|
||||
<if test="${condition}.method != null">
|
||||
and test_case.method
|
||||
<include refid="condition">
|
||||
<property name="object" value="${condition}.method"/>
|
||||
</include>
|
||||
</if>
|
||||
<if test="${condition}.creator != null">
|
||||
and test_case.maintainer
|
||||
<include refid="condition">
|
||||
<property name="object" value="${condition}.creator"/>
|
||||
</include>
|
||||
</if>
|
||||
</sql>
|
||||
|
||||
<select id="getReportMetric" parameterType="java.lang.String"
|
||||
resultType="io.metersphere.track.dto.TestCaseReportStatusResultDTO">
|
||||
|
@ -25,9 +119,20 @@
|
|||
from test_plan_test_case
|
||||
inner join test_case on test_plan_test_case.case_id = test_case.id
|
||||
<where>
|
||||
<if test="request.name != null">
|
||||
and test_case.name like CONCAT('%', #{request.name},'%')
|
||||
</if>
|
||||
<choose>
|
||||
<!--高级-->
|
||||
<when test="request.combine != null">
|
||||
<include refid="combine">
|
||||
<property name="condition" value="request.combine"/>
|
||||
</include>
|
||||
</when>
|
||||
<!--普通-->
|
||||
<otherwise>
|
||||
<if test="request.name != null">
|
||||
and test_case.name like CONCAT('%', #{request.name},'%')
|
||||
</if>
|
||||
</otherwise>
|
||||
</choose>
|
||||
<if test="request.id != null">
|
||||
and test_case.id = #{request.id}
|
||||
</if>
|
||||
|
|
|
@ -33,4 +33,6 @@ public class QueryTestPlanCaseRequest extends TestPlanTestCase {
|
|||
private String node;
|
||||
|
||||
private String method;
|
||||
|
||||
private Map<String, Object> combine;
|
||||
}
|
||||
|
|
|
@ -49,13 +49,16 @@
|
|||
this.projectId = projectId;
|
||||
this.getEnvironments();
|
||||
},
|
||||
deleteEnvironment(environment) {
|
||||
deleteEnvironment(environment, index) {
|
||||
if (environment.id) {
|
||||
this.result = this.$get('/api/environment/delete/' + environment.id, () => {
|
||||
this.$success(this.$t('commons.delete_success'));
|
||||
this.getEnvironments();
|
||||
});
|
||||
}
|
||||
else {
|
||||
this.environments.splice(index, 1);
|
||||
}
|
||||
},
|
||||
copyEnvironment(environment) {
|
||||
if (!environment.id) {
|
||||
|
@ -149,4 +152,5 @@
|
|||
height: 100%;
|
||||
position: absolute;
|
||||
}
|
||||
|
||||
</style>
|
||||
|
|
|
@ -29,7 +29,7 @@
|
|||
</el-select>
|
||||
</el-form-item>
|
||||
<el-form-item v-if="(selectedPlatformValue != 'Postman' && useEnvironment) || selectedPlatformValue == 'Swagger2'" :label="$t('api_test.environment.environment_config')" prop="environmentId">
|
||||
<el-select size="small" v-model="formData.environmentId" class="environment-select" clearable>
|
||||
<el-select v-if="showEnvironmentSelect" size="small" v-model="formData.environmentId" class="environment-select" clearable>
|
||||
<el-option v-for="(environment, index) in environments" :key="index" :label="environment.name + ': ' + environment.protocol + '://' + environment.socket" :value="environment.id"/>
|
||||
<el-button class="environment-button" size="mini" type="primary" @click="openEnvironmentConfig">{{$t('api_test.environment.environment_config')}}</el-button>
|
||||
<template v-slot:empty>
|
||||
|
@ -42,11 +42,23 @@
|
|||
<el-form-item v-if="selectedPlatformValue == 'Metersphere'" prop="useEnvironment">
|
||||
<el-checkbox v-model="useEnvironment">{{$t('api_test.environment.config_environment')}}</el-checkbox>
|
||||
</el-form-item>
|
||||
|
||||
<el-form-item :label="'Swagger URL'" prop="wgerUrl" v-if="selectedPlatformValue == 'Swagger2' && swaggerUrlEable">
|
||||
<el-input size="small" v-model="formData.swaggerUrl" clearable show-word-limit />
|
||||
</el-form-item>
|
||||
|
||||
<el-form-item v-if="selectedPlatformValue == 'Swagger2'">
|
||||
<el-switch
|
||||
v-model="swaggerUrlEable"
|
||||
:active-text="$t('api_test.api_import.swagger_url_import')">
|
||||
</el-switch>
|
||||
</el-form-item>
|
||||
</el-col>
|
||||
<el-col :span="1">
|
||||
|
||||
<el-col :span="1" v-if="selectedPlatformValue != 'Swagger2' || (selectedPlatformValue == 'Swagger2' && !swaggerUrlEable)">
|
||||
<el-divider direction="vertical"/>
|
||||
</el-col>
|
||||
<el-col :span="12">
|
||||
<el-col :span="12" v-if="selectedPlatformValue != 'Swagger2' || (selectedPlatformValue == 'Swagger2' && !swaggerUrlEable)">
|
||||
<el-upload
|
||||
class="api-upload"
|
||||
drag
|
||||
|
@ -89,6 +101,8 @@
|
|||
data() {
|
||||
return {
|
||||
visible: false,
|
||||
swaggerUrlEable: false,
|
||||
showEnvironmentSelect: true,
|
||||
platforms: [
|
||||
{
|
||||
name: 'Metersphere',
|
||||
|
@ -122,7 +136,8 @@
|
|||
name: '',
|
||||
environmentId: '',
|
||||
projectId: '',
|
||||
file: undefined
|
||||
file: undefined,
|
||||
swaggerUrl: ''
|
||||
},
|
||||
rules: {
|
||||
name: [
|
||||
|
@ -202,7 +217,9 @@
|
|||
this.$error(this.$t('api_test.select_project'));
|
||||
return;
|
||||
}
|
||||
this.showEnvironmentSelect = false;
|
||||
this.$refs.environmentConfig.open(this.formData.projectId);
|
||||
this.showEnvironmentSelect = true;
|
||||
},
|
||||
save() {
|
||||
this.$refs.form.validate(valid => {
|
||||
|
@ -211,10 +228,13 @@
|
|||
Object.assign(param, this.formData);
|
||||
param.platform = this.selectedPlatformValue;
|
||||
param.useEnvironment = this.useEnvironment;
|
||||
if (!this.formData.file) {
|
||||
if ((this.selectedPlatformValue != 'Swagger2' || (this.selectedPlatformValue == 'Swagger2' && !this.swaggerUrlEable)) && !this.formData.file) {
|
||||
this.$warning(this.$t('commons.please_upload'));
|
||||
return ;
|
||||
}
|
||||
if (!this.swaggerUrlEable) {
|
||||
param.swaggerUrl = undefined;
|
||||
}
|
||||
this.result = this.$fileUpload('/api/import', param.file, param,response => {
|
||||
let res = response.data;
|
||||
this.$success(this.$t('test_track.case.import.success'));
|
||||
|
@ -231,7 +251,8 @@
|
|||
name: '',
|
||||
environmentId: '',
|
||||
projectId: '',
|
||||
file: undefined
|
||||
file: undefined,
|
||||
swaggerUrl: ''
|
||||
};
|
||||
this.fileList = [];
|
||||
}
|
||||
|
@ -252,6 +273,7 @@
|
|||
|
||||
.api-upload >>> .el-upload {
|
||||
width: 100%;
|
||||
max-width: 350px;
|
||||
}
|
||||
|
||||
.api-upload >>> .el-upload-dragger {
|
||||
|
|
|
@ -13,7 +13,7 @@
|
|||
<div :style="{'height': itemBarHeight + 'px'}" v-for="(item, index) in data" :key="index" class="item-bar" @click="itemSelected(index, item)" :class="{'item-selected' : index == selectIndex}">
|
||||
<input class="item-input" :style="{'height': itemBarHeight - 12 + 'px', 'line-height': itemBarHeight - 12 + 'px', 'width': width - 90 + 'px'}" v-model="item.name" :placeholder="$t('commons.input_content')"/>
|
||||
<span :style="{'line-height': itemBarHeight - 10 + 'px'}" class="item-right">
|
||||
<i v-for="(operator, index) in itemOperators" :key="index" :class="operator.icon" @click.stop="operator.func(item)"/>
|
||||
<i v-for="(operator, operatorIndex) in itemOperators" :key="operatorIndex" :class="operator.icon" @click.stop="operator.func(item, index)"/>
|
||||
</span>
|
||||
</div>
|
||||
</ms-aside-container>
|
||||
|
|
|
@ -2,19 +2,30 @@
|
|||
<div class="card-container">
|
||||
<el-card class="card-content" v-loading="result.loading">
|
||||
<template v-slot:header>
|
||||
<ms-table-header :is-tester-permission="true" :condition.sync="condition" @search="initTableData" :show-create="false">
|
||||
<ms-table-header :is-tester-permission="true" :condition.sync="condition" @search="initTableData"
|
||||
:show-create="false">
|
||||
<template v-slot:title>
|
||||
<node-breadcrumb class="table-title" :nodes="selectParentNodes" @refresh="refresh"/>
|
||||
</template>
|
||||
<template v-slot:button>
|
||||
<ms-table-button :is-tester-permission="true" v-if="!showMyTestCase" icon="el-icon-s-custom" :content="$t('test_track.plan_view.my_case')" @click="searchMyTestCase"/>
|
||||
<ms-table-button :is-tester-permission="true" v-if="showMyTestCase" icon="el-icon-files" :content="$t('test_track.plan_view.all_case')" @click="searchMyTestCase"/>
|
||||
<ms-table-button :is-tester-permission="true" icon="el-icon-connection" :content="$t('test_track.plan_view.relevance_test_case')" @click="$emit('openTestCaseRelevanceDialog')"/>
|
||||
<ms-table-button :is-tester-permission="true" icon="el-icon-unlock" :content="$t('test_track.plan_view.cancel_relevance')" @click="handleBatch('delete')"/>
|
||||
<ms-table-button :is-tester-permission="true" icon="el-icon-edit-outline" :content="$t('test_track.plan_view.change_execution_results')" @click="handleBatch('status')"/>
|
||||
<ms-table-button :is-tester-permission="true" icon="el-icon-user" :content="$t('test_track.plan_view.change_executor')" @click="handleBatch('executor')"/>
|
||||
<ms-table-button :is-tester-permission="true" v-if="!testPlan.reportId" icon="el-icon-document" :content="$t('test_track.plan_view.create_report')" @click="openTestReport"/>
|
||||
<ms-table-button :is-tester-permission="true" v-if="testPlan.reportId" icon="el-icon-document" :content="$t('test_track.plan_view.view_report')" @click="openReport"/>
|
||||
<ms-table-button :is-tester-permission="true" v-if="!showMyTestCase" icon="el-icon-s-custom"
|
||||
:content="$t('test_track.plan_view.my_case')" @click="searchMyTestCase"/>
|
||||
<ms-table-button :is-tester-permission="true" v-if="showMyTestCase" icon="el-icon-files"
|
||||
:content="$t('test_track.plan_view.all_case')" @click="searchMyTestCase"/>
|
||||
<ms-table-button :is-tester-permission="true" icon="el-icon-connection"
|
||||
:content="$t('test_track.plan_view.relevance_test_case')"
|
||||
@click="$emit('openTestCaseRelevanceDialog')"/>
|
||||
<ms-table-button :is-tester-permission="true" icon="el-icon-unlock"
|
||||
:content="$t('test_track.plan_view.cancel_relevance')" @click="handleBatch('delete')"/>
|
||||
<ms-table-button :is-tester-permission="true" icon="el-icon-edit-outline"
|
||||
:content="$t('test_track.plan_view.change_execution_results')"
|
||||
@click="handleBatch('status')"/>
|
||||
<ms-table-button :is-tester-permission="true" icon="el-icon-user"
|
||||
:content="$t('test_track.plan_view.change_executor')" @click="handleBatch('executor')"/>
|
||||
<ms-table-button :is-tester-permission="true" v-if="!testPlan.reportId" icon="el-icon-document"
|
||||
:content="$t('test_track.plan_view.create_report')" @click="openTestReport"/>
|
||||
<ms-table-button :is-tester-permission="true" v-if="testPlan.reportId" icon="el-icon-document"
|
||||
:content="$t('test_track.plan_view.view_report')" @click="openReport"/>
|
||||
</template>
|
||||
</ms-table-header>
|
||||
</template>
|
||||
|
@ -93,7 +104,7 @@
|
|||
:label="$t('test_track.plan_view.execute_result')">
|
||||
<template v-slot:default="scope">
|
||||
<span @click.stop="clickt = 'stop'">
|
||||
<el-dropdown class="test-case-status" @command="statusChange" >
|
||||
<el-dropdown class="test-case-status" @command="statusChange">
|
||||
<span class="el-dropdown-link">
|
||||
<status-table-item :value="scope.row.status"/>
|
||||
</span>
|
||||
|
@ -101,10 +112,12 @@
|
|||
<el-dropdown-item :disabled="!isTestManagerOrTestUser" :command="{id: scope.row.id, status: 'Pass'}">
|
||||
{{$t('test_track.plan_view.pass')}}
|
||||
</el-dropdown-item>
|
||||
<el-dropdown-item :disabled="!isTestManagerOrTestUser" :command="{id: scope.row.id, status: 'Failure'}">
|
||||
<el-dropdown-item :disabled="!isTestManagerOrTestUser"
|
||||
:command="{id: scope.row.id, status: 'Failure'}">
|
||||
{{$t('test_track.plan_view.failure')}}
|
||||
</el-dropdown-item>
|
||||
<el-dropdown-item :disabled="!isTestManagerOrTestUser" :command="{id: scope.row.id, status: 'Blocking'}">
|
||||
<el-dropdown-item :disabled="!isTestManagerOrTestUser"
|
||||
:command="{id: scope.row.id, status: 'Blocking'}">
|
||||
{{$t('test_track.plan_view.blocking')}}
|
||||
</el-dropdown-item>
|
||||
<el-dropdown-item :disabled="!isTestManagerOrTestUser" :command="{id: scope.row.id, status: 'Skip'}">
|
||||
|
@ -128,8 +141,10 @@
|
|||
<el-table-column
|
||||
:label="$t('commons.operating')">
|
||||
<template v-slot:default="scope">
|
||||
<ms-table-operator-button :is-tester-permission="true" :tip="$t('commons.edit')" icon="el-icon-edit" @exec="handleEdit(scope.row)" />
|
||||
<ms-table-operator-button :is-tester-permission="true" :tip="$t('test_track.plan_view.cancel_relevance')" icon="el-icon-unlock" type="danger" @exec="handleDelete(scope.row)"/>
|
||||
<ms-table-operator-button :is-tester-permission="true" :tip="$t('commons.edit')" icon="el-icon-edit"
|
||||
@exec="handleEdit(scope.row)"/>
|
||||
<ms-table-operator-button :is-tester-permission="true" :tip="$t('test_track.plan_view.cancel_relevance')"
|
||||
icon="el-icon-unlock" type="danger" @exec="handleDelete(scope.row)"/>
|
||||
</template>
|
||||
</el-table-column>
|
||||
</el-table>
|
||||
|
@ -162,12 +177,7 @@
|
|||
import NodeBreadcrumb from '../../../common/NodeBreadcrumb';
|
||||
|
||||
import {ROLE_TEST_MANAGER, ROLE_TEST_USER, TokenKey} from '../../../../../../common/js/constants';
|
||||
import {
|
||||
_filter,
|
||||
_sort,
|
||||
checkoutTestManagerOrTestUser,
|
||||
hasRoles
|
||||
} from '../../../../../../common/js/utils';
|
||||
import {_filter, _sort, checkoutTestManagerOrTestUser, hasRoles} from '../../../../../../common/js/utils';
|
||||
import PriorityTableItem from "../../../common/tableItems/planview/PriorityTableItem";
|
||||
import StatusTableItem from "../../../common/tableItems/planview/StatusTableItem";
|
||||
import TypeTableItem from "../../../common/tableItems/planview/TypeTableItem";
|
||||
|
@ -176,239 +186,251 @@
|
|||
import MsTableOperatorButton from "../../../../common/components/MsTableOperatorButton";
|
||||
import TestReportTemplateList from "./TestReportTemplateList";
|
||||
import TestCaseReportView from "./report/TestCaseReportView";
|
||||
import {TEST_CASE_CONFIGS} from "../../../../common/components/search/search-components";
|
||||
|
||||
export default {
|
||||
name: "TestPlanTestCaseList",
|
||||
components: {
|
||||
TestCaseReportView,
|
||||
TestReportTemplateList,
|
||||
MsTableOperatorButton,
|
||||
MsTableOperator,
|
||||
MethodTableItem,
|
||||
TypeTableItem,
|
||||
StatusTableItem,
|
||||
PriorityTableItem, StatusEdit, ExecutorEdit, MsTipButton, MsTablePagination,
|
||||
TestPlanTestCaseEdit, MsTableHeader, NodeBreadcrumb, MsTableButton},
|
||||
data() {
|
||||
return {
|
||||
result: {},
|
||||
deletePath: "/test/case/delete",
|
||||
condition: {},
|
||||
showMyTestCase: false,
|
||||
tableData: [],
|
||||
currentPage: 1,
|
||||
pageSize: 10,
|
||||
total: 0,
|
||||
selectIds: new Set(),
|
||||
testPlan: {},
|
||||
isReadOnly: false,
|
||||
isTestManagerOrTestUser: false,
|
||||
priorityFilters: [
|
||||
{text: 'P0', value: 'P0'},
|
||||
{text: 'P1', value: 'P1'},
|
||||
{text: 'P2', value: 'P2'},
|
||||
{text: 'P3', value: 'P3'}
|
||||
],
|
||||
methodFilters: [
|
||||
{text: this.$t('test_track.case.manual'), value: 'manual'},
|
||||
{text: this.$t('test_track.case.auto'), value: 'auto'}
|
||||
],
|
||||
typeFilters: [
|
||||
{text: this.$t('commons.functional'), value: 'functional'},
|
||||
{text: this.$t('commons.performance'), value: 'performance'},
|
||||
{text: this.$t('commons.api'), value: 'api'}
|
||||
],
|
||||
statusFilters: [
|
||||
{text: this.$t('test_track.plan.plan_status_prepare'), value: 'Prepare'},
|
||||
{text: this.$t('test_track.plan_view.pass'), value: 'Pass'},
|
||||
{text: this.$t('test_track.plan_view.failure'), value: 'Failure'},
|
||||
{text: this.$t('test_track.plan_view.blocking'), value: 'Blocking'},
|
||||
{text: this.$t('test_track.plan_view.skip'), value: 'Skip'},
|
||||
{text: this.$t('test_track.plan.plan_status_running'), value: 'Underway'},
|
||||
]
|
||||
}
|
||||
},
|
||||
props:{
|
||||
planId: {
|
||||
type: String
|
||||
name: "TestPlanTestCaseList",
|
||||
components: {
|
||||
TestCaseReportView,
|
||||
TestReportTemplateList,
|
||||
MsTableOperatorButton,
|
||||
MsTableOperator,
|
||||
MethodTableItem,
|
||||
TypeTableItem,
|
||||
StatusTableItem,
|
||||
PriorityTableItem, StatusEdit, ExecutorEdit, MsTipButton, MsTablePagination,
|
||||
TestPlanTestCaseEdit, MsTableHeader, NodeBreadcrumb, MsTableButton
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
result: {},
|
||||
deletePath: "/test/case/delete",
|
||||
condition: {
|
||||
components: TEST_CASE_CONFIGS
|
||||
},
|
||||
selectNodeIds: {
|
||||
type: Array
|
||||
},
|
||||
selectParentNodes: {
|
||||
type: Array
|
||||
}
|
||||
showMyTestCase: false,
|
||||
tableData: [],
|
||||
currentPage: 1,
|
||||
pageSize: 10,
|
||||
total: 0,
|
||||
selectIds: new Set(),
|
||||
testPlan: {},
|
||||
isReadOnly: false,
|
||||
isTestManagerOrTestUser: false,
|
||||
priorityFilters: [
|
||||
{text: 'P0', value: 'P0'},
|
||||
{text: 'P1', value: 'P1'},
|
||||
{text: 'P2', value: 'P2'},
|
||||
{text: 'P3', value: 'P3'}
|
||||
],
|
||||
methodFilters: [
|
||||
{text: this.$t('test_track.case.manual'), value: 'manual'},
|
||||
{text: this.$t('test_track.case.auto'), value: 'auto'}
|
||||
],
|
||||
typeFilters: [
|
||||
{text: this.$t('commons.functional'), value: 'functional'},
|
||||
{text: this.$t('commons.performance'), value: 'performance'},
|
||||
{text: this.$t('commons.api'), value: 'api'}
|
||||
],
|
||||
statusFilters: [
|
||||
{text: this.$t('test_track.plan.plan_status_prepare'), value: 'Prepare'},
|
||||
{text: this.$t('test_track.plan_view.pass'), value: 'Pass'},
|
||||
{text: this.$t('test_track.plan_view.failure'), value: 'Failure'},
|
||||
{text: this.$t('test_track.plan_view.blocking'), value: 'Blocking'},
|
||||
{text: this.$t('test_track.plan_view.skip'), value: 'Skip'},
|
||||
{text: this.$t('test_track.plan.plan_status_running'), value: 'Underway'},
|
||||
]
|
||||
}
|
||||
},
|
||||
props: {
|
||||
planId: {
|
||||
type: String
|
||||
},
|
||||
watch: {
|
||||
planId() {
|
||||
this.refreshTableAndPlan();
|
||||
},
|
||||
selectNodeIds() {
|
||||
this.search();
|
||||
}
|
||||
selectNodeIds: {
|
||||
type: Array
|
||||
},
|
||||
mounted() {
|
||||
selectParentNodes: {
|
||||
type: Array
|
||||
}
|
||||
},
|
||||
watch: {
|
||||
planId() {
|
||||
this.refreshTableAndPlan();
|
||||
this.isTestManagerOrTestUser = checkoutTestManagerOrTestUser();
|
||||
},
|
||||
methods: {
|
||||
initTableData() {
|
||||
if (this.planId) {
|
||||
this.condition.planId = this.planId;
|
||||
this.condition.nodeIds = this.selectNodeIds;
|
||||
this.result = this.$post(this.buildPagePath('/test/plan/case/list'), this.condition, response => {
|
||||
let data = response.data;
|
||||
this.total = data.itemCount;
|
||||
this.tableData = data.listObject;
|
||||
this.selectIds.clear();
|
||||
});
|
||||
}
|
||||
},
|
||||
showDetail(row, event, column) {
|
||||
this.isReadOnly = true;
|
||||
this.$refs.testPlanTestCaseEdit.openTestCaseEdit(row);
|
||||
},
|
||||
refresh() {
|
||||
this.condition = {};
|
||||
this.selectIds.clear();
|
||||
this.$emit('refresh');
|
||||
},
|
||||
refreshTableAndPlan() {
|
||||
this.getTestPlanById();
|
||||
this.initTableData();
|
||||
},
|
||||
refreshTestPlanRecent() {
|
||||
if (hasRoles(ROLE_TEST_USER, ROLE_TEST_MANAGER)) {
|
||||
let param = {};
|
||||
param.id = this.planId;
|
||||
param.updateTime = Date.now();
|
||||
this.$post('/test/plan/edit', param);
|
||||
}
|
||||
},
|
||||
search() {
|
||||
this.initTableData();
|
||||
},
|
||||
buildPagePath(path) {
|
||||
return path + "/" + this.currentPage + "/" + this.pageSize;
|
||||
},
|
||||
handleEdit(testCase, index) {
|
||||
this.isReadOnly = false;
|
||||
if (!checkoutTestManagerOrTestUser()) {
|
||||
this.isReadOnly = true;
|
||||
}
|
||||
this.$refs.testPlanTestCaseEdit.openTestCaseEdit(testCase);
|
||||
},
|
||||
handleDelete(testCase) {
|
||||
this.$alert(this.$t('test_track.plan_view.confirm_cancel_relevance') + ' ' + testCase.name + " ?", '', {
|
||||
confirmButtonText: this.$t('commons.confirm'),
|
||||
callback: (action) => {
|
||||
if (action === 'confirm') {
|
||||
this._handleDelete(testCase);
|
||||
}
|
||||
}
|
||||
});
|
||||
},
|
||||
handleDeleteBatch() {
|
||||
this.$alert(this.$t('test_track.plan_view.confirm_cancel_relevance') + " ?", '', {
|
||||
confirmButtonText: this.$t('commons.confirm'),
|
||||
callback: (action) => {
|
||||
if (action === 'confirm') {
|
||||
this.$post('/test/plan/case/batch/delete', {ids: [...this.selectIds]}, () => {
|
||||
this.selectIds.clear();
|
||||
this.$emit("refresh");
|
||||
this.$success(this.$t('commons.delete_success'));
|
||||
});
|
||||
}
|
||||
}
|
||||
});
|
||||
},
|
||||
_handleDelete(testCase) {
|
||||
let testCaseId = testCase.id;
|
||||
this.$post('/test/plan/case/delete/' + testCaseId, {}, () => {
|
||||
this.$emit("refresh");
|
||||
this.$success(this.$t('commons.delete_success'));
|
||||
});
|
||||
},
|
||||
handleSelectAll(selection) {
|
||||
if(selection.length > 0) {
|
||||
this.tableData.forEach(item => {
|
||||
this.selectIds.add(item.id);
|
||||
});
|
||||
} else {
|
||||
this.selectIds.clear();
|
||||
}
|
||||
},
|
||||
handleSelectionChange(selection, row) {
|
||||
if(this.selectIds.has(row.id)){
|
||||
this.selectIds.delete(row.id);
|
||||
} else {
|
||||
this.selectIds.add(row.id);
|
||||
}
|
||||
},
|
||||
handleBatch(type){
|
||||
if (this.selectIds.size < 1) {
|
||||
this.$warning(this.$t('test_track.plan_view.select_manipulate'));
|
||||
return;
|
||||
}
|
||||
if (type === 'executor'){
|
||||
this.$refs.executorEdit.openExecutorEdit();
|
||||
} else if (type === 'status'){
|
||||
this.$refs.statusEdit.openStatusEdit();
|
||||
} else if (type === 'delete') {
|
||||
this.handleDeleteBatch();
|
||||
}
|
||||
},
|
||||
searchMyTestCase() {
|
||||
this.showMyTestCase = !this.showMyTestCase;
|
||||
if (this.showMyTestCase) {
|
||||
let user = JSON.parse(localStorage.getItem(TokenKey));
|
||||
this.condition.executor = user.id;
|
||||
} else {
|
||||
this.condition.executor = null;
|
||||
}
|
||||
this.initTableData();
|
||||
},
|
||||
openTestReport() {
|
||||
this.$refs.testReporTtemplateList.open(this.planId);
|
||||
},
|
||||
statusChange(param) {
|
||||
this.$post('/test/plan/case/edit' , param, () => {
|
||||
for (let i = 0; i < this.tableData.length; i++) {
|
||||
if (this.tableData[i].id == param.id) {
|
||||
this.tableData[i].status = param.status;
|
||||
break;
|
||||
}
|
||||
}
|
||||
});
|
||||
},
|
||||
getTestPlanById() {
|
||||
if (this.planId) {
|
||||
this.$post('/test/plan/get/' + this.planId, {}, response => {
|
||||
this.testPlan = response.data;
|
||||
this.refreshTestPlanRecent();
|
||||
});
|
||||
}
|
||||
},
|
||||
openReport(planId, id) {
|
||||
this.getTestPlanById();
|
||||
if (!id) {
|
||||
id = this.testPlan.reportId;
|
||||
}
|
||||
if (!planId) {
|
||||
planId = this.planId;
|
||||
}
|
||||
this.$refs.testCaseReportView.open(planId, id);
|
||||
},
|
||||
filter(filters) {
|
||||
_filter(filters, this.condition);
|
||||
this.initTableData();
|
||||
},
|
||||
sort(column) {
|
||||
_sort(column, this.condition);
|
||||
this.initTableData();
|
||||
selectNodeIds() {
|
||||
this.search();
|
||||
}
|
||||
},
|
||||
mounted() {
|
||||
this.refreshTableAndPlan();
|
||||
this.isTestManagerOrTestUser = checkoutTestManagerOrTestUser();
|
||||
},
|
||||
methods: {
|
||||
initTableData(combine) {
|
||||
// 只有在点击高级搜索的查询按钮时combine才有值
|
||||
let condition = combine ? {combine: combine} : this.condition;
|
||||
if (this.planId) {
|
||||
// param.planId = this.planId;
|
||||
condition.planId = this.planId;
|
||||
}
|
||||
if (this.selectNodeIds && this.selectNodeIds.length > 0) {
|
||||
// param.nodeIds = this.selectNodeIds;
|
||||
condition.nodeIds = this.selectNodeIds;
|
||||
}
|
||||
if (this.planId) {
|
||||
this.result = this.$post(this.buildPagePath('/test/plan/case/list'), condition, response => {
|
||||
let data = response.data;
|
||||
this.total = data.itemCount;
|
||||
this.tableData = data.listObject;
|
||||
this.selectIds.clear();
|
||||
});
|
||||
}
|
||||
},
|
||||
showDetail(row, event, column) {
|
||||
this.isReadOnly = true;
|
||||
this.$refs.testPlanTestCaseEdit.openTestCaseEdit(row);
|
||||
},
|
||||
refresh() {
|
||||
this.condition = {components: TEST_CASE_CONFIGS};
|
||||
this.selectIds.clear();
|
||||
this.$emit('refresh');
|
||||
},
|
||||
refreshTableAndPlan() {
|
||||
this.getTestPlanById();
|
||||
this.initTableData();
|
||||
},
|
||||
refreshTestPlanRecent() {
|
||||
if (hasRoles(ROLE_TEST_USER, ROLE_TEST_MANAGER)) {
|
||||
let param = {};
|
||||
param.id = this.planId;
|
||||
param.updateTime = Date.now();
|
||||
this.$post('/test/plan/edit', param);
|
||||
}
|
||||
},
|
||||
search() {
|
||||
this.initTableData();
|
||||
},
|
||||
buildPagePath(path) {
|
||||
return path + "/" + this.currentPage + "/" + this.pageSize;
|
||||
},
|
||||
handleEdit(testCase, index) {
|
||||
this.isReadOnly = false;
|
||||
if (!checkoutTestManagerOrTestUser()) {
|
||||
this.isReadOnly = true;
|
||||
}
|
||||
this.$refs.testPlanTestCaseEdit.openTestCaseEdit(testCase);
|
||||
},
|
||||
handleDelete(testCase) {
|
||||
this.$alert(this.$t('test_track.plan_view.confirm_cancel_relevance') + ' ' + testCase.name + " ?", '', {
|
||||
confirmButtonText: this.$t('commons.confirm'),
|
||||
callback: (action) => {
|
||||
if (action === 'confirm') {
|
||||
this._handleDelete(testCase);
|
||||
}
|
||||
}
|
||||
});
|
||||
},
|
||||
handleDeleteBatch() {
|
||||
this.$alert(this.$t('test_track.plan_view.confirm_cancel_relevance') + " ?", '', {
|
||||
confirmButtonText: this.$t('commons.confirm'),
|
||||
callback: (action) => {
|
||||
if (action === 'confirm') {
|
||||
this.$post('/test/plan/case/batch/delete', {ids: [...this.selectIds]}, () => {
|
||||
this.selectIds.clear();
|
||||
this.$emit("refresh");
|
||||
this.$success(this.$t('commons.delete_success'));
|
||||
});
|
||||
}
|
||||
}
|
||||
});
|
||||
},
|
||||
_handleDelete(testCase) {
|
||||
let testCaseId = testCase.id;
|
||||
this.$post('/test/plan/case/delete/' + testCaseId, {}, () => {
|
||||
this.$emit("refresh");
|
||||
this.$success(this.$t('commons.delete_success'));
|
||||
});
|
||||
},
|
||||
handleSelectAll(selection) {
|
||||
if (selection.length > 0) {
|
||||
this.tableData.forEach(item => {
|
||||
this.selectIds.add(item.id);
|
||||
});
|
||||
} else {
|
||||
this.selectIds.clear();
|
||||
}
|
||||
},
|
||||
handleSelectionChange(selection, row) {
|
||||
if (this.selectIds.has(row.id)) {
|
||||
this.selectIds.delete(row.id);
|
||||
} else {
|
||||
this.selectIds.add(row.id);
|
||||
}
|
||||
},
|
||||
handleBatch(type) {
|
||||
if (this.selectIds.size < 1) {
|
||||
this.$warning(this.$t('test_track.plan_view.select_manipulate'));
|
||||
return;
|
||||
}
|
||||
if (type === 'executor') {
|
||||
this.$refs.executorEdit.openExecutorEdit();
|
||||
} else if (type === 'status') {
|
||||
this.$refs.statusEdit.openStatusEdit();
|
||||
} else if (type === 'delete') {
|
||||
this.handleDeleteBatch();
|
||||
}
|
||||
},
|
||||
searchMyTestCase() {
|
||||
this.showMyTestCase = !this.showMyTestCase;
|
||||
if (this.showMyTestCase) {
|
||||
let user = JSON.parse(localStorage.getItem(TokenKey));
|
||||
this.condition.executor = user.id;
|
||||
} else {
|
||||
this.condition.executor = null;
|
||||
}
|
||||
this.initTableData();
|
||||
},
|
||||
openTestReport() {
|
||||
this.$refs.testReporTtemplateList.open(this.planId);
|
||||
},
|
||||
statusChange(param) {
|
||||
this.$post('/test/plan/case/edit', param, () => {
|
||||
for (let i = 0; i < this.tableData.length; i++) {
|
||||
if (this.tableData[i].id == param.id) {
|
||||
this.tableData[i].status = param.status;
|
||||
break;
|
||||
}
|
||||
}
|
||||
});
|
||||
},
|
||||
getTestPlanById() {
|
||||
if (this.planId) {
|
||||
this.$post('/test/plan/get/' + this.planId, {}, response => {
|
||||
this.testPlan = response.data;
|
||||
this.refreshTestPlanRecent();
|
||||
});
|
||||
}
|
||||
},
|
||||
openReport(planId, id) {
|
||||
this.getTestPlanById();
|
||||
if (!id) {
|
||||
id = this.testPlan.reportId;
|
||||
}
|
||||
if (!planId) {
|
||||
planId = this.planId;
|
||||
}
|
||||
this.$refs.testCaseReportView.open(planId, id);
|
||||
},
|
||||
filter(filters) {
|
||||
_filter(filters, this.condition);
|
||||
this.initTableData();
|
||||
},
|
||||
sort(column) {
|
||||
_sort(column, this.condition);
|
||||
this.initTableData();
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped>
|
||||
|
@ -418,8 +440,8 @@
|
|||
width: 240px;
|
||||
}
|
||||
|
||||
.test-case-status,.el-table {
|
||||
cursor:pointer;
|
||||
.test-case-status, .el-table {
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
</style>
|
||||
|
|
|
@ -436,6 +436,7 @@ export default {
|
|||
postman_export_tip: "Export the test collection by Postman",
|
||||
swagger_export_tip: "Export jSON-formatted files via Swagger website",
|
||||
suffixFormatErr: "The file format does not meet the requirements",
|
||||
swagger_url_import: "Import using URL",
|
||||
}
|
||||
},
|
||||
api_report: {
|
||||
|
|
|
@ -436,6 +436,7 @@ export default {
|
|||
post_export_tip: "通过 Postman 导出测试集合",
|
||||
swagger_export_tip: "通过 Swagger 页面导出",
|
||||
suffixFormatErr: "文件格式不符合要求",
|
||||
swagger_url_import: "使用URL导入",
|
||||
}
|
||||
},
|
||||
api_report: {
|
||||
|
|
|
@ -435,6 +435,7 @@ export default {
|
|||
post_export_tip: "通過 Postman 導出測試集合",
|
||||
swagger_export_tip: "通過 Swagger 頁面導出",
|
||||
suffixFormatErr: "文件格式不符合要求",
|
||||
swagger_url_import: "使用URL導入",
|
||||
}
|
||||
},
|
||||
api_report: {
|
||||
|
|
Loading…
Reference in New Issue