Merge branch 'master' of github.com:fit2cloudrd/metersphere-server into master
This commit is contained in:
commit
4f4cef3feb
|
@ -312,7 +312,7 @@
|
|||
<resource>
|
||||
<directory>src/main/resources</directory>
|
||||
<includes>
|
||||
<include>**/*.*</include>
|
||||
<include>**/*</include>
|
||||
</includes>
|
||||
<filtering>false</filtering>
|
||||
</resource>
|
||||
|
|
|
@ -14,6 +14,7 @@ import io.metersphere.track.dto.TestPlanDTOWithMetric;
|
|||
import io.metersphere.track.request.testcase.PlanCaseRelevanceRequest;
|
||||
import io.metersphere.track.request.testcase.QueryTestPlanRequest;
|
||||
import io.metersphere.track.request.testplan.AddTestPlanRequest;
|
||||
import io.metersphere.track.request.testplancase.TestCaseRelevanceRequest;
|
||||
import io.metersphere.track.service.TestPlanProjectService;
|
||||
import io.metersphere.track.service.TestPlanService;
|
||||
import org.apache.shiro.authz.annotation.Logical;
|
||||
|
@ -111,8 +112,18 @@ public class TestPlanController {
|
|||
return testPlanService.getProjectNameByPlanId(planId);
|
||||
}
|
||||
|
||||
@GetMapping("/project/{planId}")
|
||||
public List<Project> getProjectByPlanId(@PathVariable String planId) {
|
||||
return testPlanProjectService.getProjectByPlanId(planId);
|
||||
@PostMapping("/project")
|
||||
public List<Project> getProjectByPlanId(@RequestBody TestCaseRelevanceRequest request) {
|
||||
List<String> projectIds = testPlanProjectService.getProjectIdsByPlanId(request.getPlanId());
|
||||
request.setProjectIds(projectIds);
|
||||
return testPlanProjectService.getProjectByPlanId(request);
|
||||
}
|
||||
|
||||
@PostMapping("/project/{goPage}/{pageSize}")
|
||||
public Pager<List<Project>> getProjectByPlanId(@PathVariable int goPage, @PathVariable int pageSize, @RequestBody TestCaseRelevanceRequest request) {
|
||||
List<String> projectIds = testPlanProjectService.getProjectIdsByPlanId(request.getPlanId());
|
||||
request.setProjectIds(projectIds);
|
||||
Page<Object> page = PageHelper.startPage(goPage, pageSize, true);
|
||||
return PageUtils.setPageInfo(page, testPlanProjectService.getProjectByPlanId(request));
|
||||
}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,14 @@
|
|||
package io.metersphere.track.request.testplancase;
|
||||
|
||||
import lombok.Getter;
|
||||
import lombok.Setter;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
@Getter
|
||||
@Setter
|
||||
public class TestCaseRelevanceRequest {
|
||||
private String planId;
|
||||
private String name;
|
||||
private List<String> projectIds;
|
||||
}
|
|
@ -6,26 +6,25 @@ import io.metersphere.base.domain.TestPlanProject;
|
|||
import io.metersphere.base.domain.TestPlanProjectExample;
|
||||
import io.metersphere.base.mapper.ProjectMapper;
|
||||
import io.metersphere.base.mapper.TestPlanProjectMapper;
|
||||
import org.python.antlr.ast.Str;
|
||||
import io.metersphere.track.request.testplancase.TestCaseRelevanceRequest;
|
||||
import org.apache.commons.lang3.StringUtils;
|
||||
import org.springframework.stereotype.Service;
|
||||
import org.springframework.transaction.annotation.Transactional;
|
||||
import org.springframework.util.CollectionUtils;
|
||||
|
||||
import javax.annotation.Resource;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import java.util.Optional;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
@Service
|
||||
@Transactional(rollbackFor = Exception.class)
|
||||
public class TestPlanProjectService {
|
||||
|
||||
|
||||
@Resource
|
||||
TestPlanProjectMapper testPlanProjectMapper;
|
||||
@Resource
|
||||
ProjectMapper projectMapper;
|
||||
|
||||
|
||||
public List<String> getProjectIdsByPlanId(String planId) {
|
||||
TestPlanProjectExample example = new TestPlanProjectExample();
|
||||
example.createCriteria().andTestPlanIdEqualTo(planId);
|
||||
|
@ -41,12 +40,14 @@ public class TestPlanProjectService {
|
|||
return projectIds;
|
||||
}
|
||||
|
||||
public List<Project> getProjectByPlanId(String planId) {
|
||||
List<String> projectIds = getProjectIdsByPlanId(planId);
|
||||
public List<Project> getProjectByPlanId(TestCaseRelevanceRequest request) {
|
||||
ProjectExample projectExample = new ProjectExample();
|
||||
projectExample.createCriteria().andIdIn(projectIds);
|
||||
List<Project> projects = projectMapper.selectByExample(projectExample);
|
||||
return Optional.ofNullable(projects).orElse(new ArrayList<>());
|
||||
ProjectExample.Criteria criteria = projectExample.createCriteria();
|
||||
criteria.andIdIn(request.getProjectIds());
|
||||
if (StringUtils.isNotBlank(request.getName())) {
|
||||
criteria.andNameLike(StringUtils.wrapIfMissing(request.getName(), "%"));
|
||||
}
|
||||
return projectMapper.selectByExample(projectExample);
|
||||
}
|
||||
|
||||
public void deleteTestPlanProjectByPlanId(String planId) {
|
||||
|
|
|
@ -0,0 +1,13 @@
|
|||
CREATE TABLE `license` (
|
||||
`id` varchar(50) NOT NULL COMMENT 'ID',
|
||||
`create_time` bigint(13) NOT NULL COMMENT 'Create timestamp',
|
||||
`update_time` bigint(13) NOT NULL COMMENT 'Update timestamp',
|
||||
`corporation` varchar(500) NOT NULL COMMENT 'corporation ',
|
||||
`expired` varchar(255) NOT NULL COMMENT 'expired ',
|
||||
`product` varchar(500) DEFAULT NULL COMMENT 'product name',
|
||||
`edition` varchar(255) COMMENT 'edition ',
|
||||
`license_version` varchar(255) NOT NULL COMMENT 'licenseVersion',
|
||||
`license_count` INT COMMENT 'license_count',
|
||||
`license_code` longtext DEFAULT NULL COMMENT 'license_code',
|
||||
PRIMARY KEY (`id`)
|
||||
) ENGINE = InnoDB DEFAULT CHARSET = utf8mb4;
|
|
@ -150,4 +150,6 @@ quota_performance_excess_organization=The number of performance tests exceeds th
|
|||
quota_max_threads_excess_workspace=The maximum number of concurrent threads exceeds the workspace quota
|
||||
quota_max_threads_excess_organization=The maximum number of concurrent threads exceeds the organization quota
|
||||
quota_duration_excess_workspace=The stress test duration exceeds the work space quota
|
||||
quota_duration_excess_organization=The stress test duration exceeds the organization quota
|
||||
quota_duration_excess_organization=The stress test duration exceeds the organization quota
|
||||
license_valid_license_error=valid license error
|
||||
license_valid_license_code=The authorization code already exists
|
||||
|
|
|
@ -151,6 +151,7 @@ quota_max_threads_excess_workspace=最大并发数超过工作空间限额
|
|||
quota_max_threads_excess_organization=最大并发数超过组织限额
|
||||
quota_duration_excess_workspace=压测时长超过工作空间限额
|
||||
quota_duration_excess_organization=压测时长超过组织限额
|
||||
|
||||
license_valid_license_error=授权验证失败
|
||||
license_valid_license_code=授权码已经存在
|
||||
|
||||
|
||||
|
|
|
@ -150,4 +150,7 @@ quota_performance_excess_organization=性能測試數量超過組織限額
|
|||
quota_max_threads_excess_workspace=最大並發數超過工作空間限額
|
||||
quota_max_threads_excess_organization=最大並發數超過組織限額
|
||||
quota_duration_excess_workspace=壓測時長超過工作空間限額
|
||||
quota_duration_excess_organization=壓測時長超過組織限額
|
||||
quota_duration_excess_organization=壓測時長超過組織限額
|
||||
license_valid_license_error=授權驗證失敗
|
||||
license_valid_license_code=授權碼已經存在
|
||||
|
||||
|
|
Binary file not shown.
Binary file not shown.
Binary file not shown.
|
@ -37,6 +37,9 @@
|
|||
:environment="scenario.environment"
|
||||
:description="$t('api_test.scenario.kv_description')"/>
|
||||
</el-tab-pane>
|
||||
<el-tab-pane :label="'数据库配置'" name="database">
|
||||
<ms-database-config :configs="scenario.databaseConfigs"/>
|
||||
</el-tab-pane>
|
||||
<el-tab-pane :label="$t('api_test.scenario.dubbo')" name="dubbo">
|
||||
<div class="dubbo-config-title">Config Center</div>
|
||||
<ms-dubbo-config-center :config="scenario.dubboConfig.configCenter" :is-read-only="isReadOnly"/>
|
||||
|
@ -62,10 +65,12 @@ import {REQUEST_HEADERS} from "@/common/js/constants";
|
|||
import MsDubboRegistryCenter from "@/business/components/api/test/components/request/dubbo/RegistryCenter";
|
||||
import MsDubboConfigCenter from "@/business/components/api/test/components/request/dubbo/ConfigCenter";
|
||||
import MsDubboConsumerService from "@/business/components/api/test/components/request/dubbo/ConsumerAndService";
|
||||
import MsDatabaseConfig from "./request/database/DatabaseConfig";
|
||||
|
||||
export default {
|
||||
name: "MsApiScenarioForm",
|
||||
components: {
|
||||
MsDatabaseConfig,
|
||||
MsDubboConsumerService,
|
||||
MsDubboConfigCenter, MsDubboRegistryCenter, ApiEnvironmentConfig, MsApiScenarioVariables, MsApiKeyValue
|
||||
},
|
||||
|
|
|
@ -0,0 +1,59 @@
|
|||
<template>
|
||||
<div>
|
||||
<ms-database-from :config="currentConfig" @save="addConfig" ref="databaseFrom"/>
|
||||
<ms-database-config-list v-if="configs.length > 0" :table-data="configs"/>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import MsDatabaseConfigList from "./DatabaseConfigList";
|
||||
import {DatabaseConfig} from "../../../model/ScenarioModel";
|
||||
import MsDatabaseFrom from "./DatabaseFrom";
|
||||
import {getUUID} from "../../../../../../../common/js/utils";
|
||||
|
||||
export default {
|
||||
name: "MsDatabaseConfig",
|
||||
components: {MsDatabaseFrom, MsDatabaseConfigList},
|
||||
props: {
|
||||
configs: Array,
|
||||
isReadOnly: {
|
||||
type: Boolean,
|
||||
default: false
|
||||
},
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
drivers: DatabaseConfig.DRIVER_CLASS,
|
||||
currentConfig: new DatabaseConfig()
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
addConfig(config) {
|
||||
for (let item of this.configs) {
|
||||
if (item.name === config.name) {
|
||||
this.$warning("名称重复");
|
||||
return;
|
||||
}
|
||||
}
|
||||
config.id = getUUID();
|
||||
this.configs.push(config);
|
||||
this.currentConfig = new DatabaseConfig();
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped>
|
||||
|
||||
.addButton {
|
||||
float: right;
|
||||
}
|
||||
|
||||
.database-from {
|
||||
padding: 10px;
|
||||
border: #DCDFE6 solid 1px;
|
||||
margin: 5px 0;
|
||||
border-radius: 5px;
|
||||
}
|
||||
|
||||
</style>
|
|
@ -0,0 +1,58 @@
|
|||
<template>
|
||||
<el-dialog :title="'数据库配置'" :visible.sync="visible">
|
||||
<ms-database-from :config="config" @save="editConfig"/>
|
||||
</el-dialog>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import MsDatabaseConfigList from "./DatabaseConfigList";
|
||||
import MsDatabaseFrom from "./DatabaseFrom";
|
||||
import {DatabaseConfig} from "../../../model/ScenarioModel";
|
||||
|
||||
export default {
|
||||
name: "MsDatabaseConfigDialog",
|
||||
components: {MsDatabaseFrom, MsDatabaseConfigList},
|
||||
props: {
|
||||
configs: Array,
|
||||
isReadOnly: {
|
||||
type: Boolean,
|
||||
default: false
|
||||
},
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
visible: false,
|
||||
config: new DatabaseConfig(),
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
open(config) {
|
||||
this.visible = true;
|
||||
Object.assign(this.config, config);
|
||||
},
|
||||
editConfig(config) {
|
||||
let currentConfig = undefined;
|
||||
for (let item of this.configs) {
|
||||
if (item.name === config.name && item.id != config.id) {
|
||||
this.$warning("名称重复");
|
||||
return;
|
||||
}
|
||||
if (item.id === config.id) {
|
||||
currentConfig = item;
|
||||
}
|
||||
}
|
||||
if (currentConfig) {
|
||||
Object.assign(currentConfig, config)
|
||||
} else {
|
||||
//copy
|
||||
this.configs.push(config);
|
||||
}
|
||||
this.visible = false;
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped>
|
||||
|
||||
</style>
|
|
@ -0,0 +1,92 @@
|
|||
<template>
|
||||
<ms-main-container>
|
||||
|
||||
<el-table border :data="tableData" class="adjust-table table-content"
|
||||
@row-click="handleView">
|
||||
|
||||
<el-table-column prop="name" :label="'连接池名称'" show-overflow-tooltip/>
|
||||
<el-table-column prop="driver" :label="'数据库驱动'" show-overflow-tooltip/>
|
||||
<el-table-column prop="dbUrl" :label="'数据库连接URL'" show-overflow-tooltip/>
|
||||
<el-table-column prop="username" :label="'用户名'" show-overflow-tooltip/>
|
||||
<el-table-column prop="poolMax" :label="'最大连接数'" show-overflow-tooltip/>
|
||||
<el-table-column prop="timeout" :label="'最大等待时间'" show-overflow-tooltip/>
|
||||
|
||||
<el-table-column
|
||||
:label="$t('commons.operating')" min-width="100">
|
||||
<template v-slot:default="scope">
|
||||
<ms-table-operator :is-tester-permission="true" @editClick="handleEdit(scope.row)"
|
||||
@deleteClick="handleDelete(scope.$index)">
|
||||
<template v-slot:middle>
|
||||
<ms-table-operator-button :is-tester-permission="true" :tip="$t('commons.copy')"
|
||||
icon="el-icon-document-copy"
|
||||
type="success" @exec="handleCopy(scope.row)"/>
|
||||
</template>
|
||||
</ms-table-operator>
|
||||
</template>
|
||||
</el-table-column>
|
||||
|
||||
</el-table>
|
||||
|
||||
<ms-database-config-dialog :configs="tableData" ref="databaseConfigEdit"/>
|
||||
|
||||
</ms-main-container>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
|
||||
import {DatabaseConfig} from "../../../model/ScenarioModel";
|
||||
import MsMainContainer from "../../../../../common/components/MsMainContainer";
|
||||
import MsTableOperator from "../../../../../common/components/MsTableOperator";
|
||||
import MsTableOperatorButton from "../../../../../common/components/MsTableOperatorButton";
|
||||
import MsDatabaseConfigDialog from "./DatabaseConfigDialog";
|
||||
import {getUUID} from "../../../../../../../common/js/utils";
|
||||
|
||||
export default {
|
||||
name: "MsDatabaseConfigList",
|
||||
components: {MsDatabaseConfigDialog, MsTableOperatorButton, MsTableOperator, MsMainContainer},
|
||||
props: {
|
||||
tableData: Array,
|
||||
isReadOnly: {
|
||||
type: Boolean,
|
||||
default: false
|
||||
}
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
drivers: DatabaseConfig.DRIVER_CLASS,
|
||||
result: {},
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
handleView() {
|
||||
},
|
||||
handleEdit(config) {
|
||||
this.$refs.databaseConfigEdit.open(config);
|
||||
},
|
||||
handleDelete(index) {
|
||||
this.tableData.splice(index, 1);
|
||||
},
|
||||
handleCopy(config) {
|
||||
let copy = {};
|
||||
Object.assign(copy, config);
|
||||
copy.id = getUUID();
|
||||
this.$refs.databaseConfigEdit.open(copy);
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped>
|
||||
|
||||
.addButton {
|
||||
float: right;
|
||||
}
|
||||
|
||||
.database-from {
|
||||
padding: 10px;
|
||||
border: #DCDFE6 solid 1px;
|
||||
margin: 5px 0;
|
||||
border-radius: 5px;
|
||||
}
|
||||
|
||||
</style>
|
|
@ -0,0 +1,121 @@
|
|||
<template>
|
||||
<div>
|
||||
<el-form :model="config" :rules="rules" label-width="150px" size="small" :disabled="isReadOnly" class="database-from" ref="databaseFrom">
|
||||
|
||||
<el-form-item :label="'连接池名称'" prop="name">
|
||||
<el-input v-model="config.name" maxlength="300" show-word-limit
|
||||
:placeholder="$t('commons.input_content')"/>
|
||||
</el-form-item>
|
||||
|
||||
<el-form-item :label="'数据库连接URL'" prop="dbUrl">
|
||||
<el-input v-model="config.dbUrl" maxlength="300" show-word-limit
|
||||
:placeholder="$t('commons.input_content')"/>
|
||||
</el-form-item>
|
||||
|
||||
<el-form-item :label="'数据库驱动'" prop="driver">
|
||||
<el-select v-model="config.driver" class="select-100" clearable>
|
||||
<el-option v-for="p in drivers" :key="p" :label="p" :value="p"/>
|
||||
</el-select>
|
||||
</el-form-item>
|
||||
|
||||
<el-form-item :label="'用户名'" prop="username">
|
||||
<el-input v-model="config.username" maxlength="300" show-word-limit
|
||||
:placeholder="$t('commons.input_content')"/>
|
||||
</el-form-item>
|
||||
|
||||
<el-form-item :label="'密码'" prop="password">
|
||||
<el-input v-model="config.password" maxlength="300" show-word-limit
|
||||
:placeholder="$t('commons.input_content')"/>
|
||||
</el-form-item>
|
||||
|
||||
<el-form-item :label="'最大连接数'" prop="poolMax">
|
||||
<el-input-number size="small" :disabled="isReadOnly" v-model="config.poolMax" :placeholder="$t('commons.millisecond')" :max="1000*10000000" :min="0"/>
|
||||
</el-form-item>
|
||||
|
||||
|
||||
<el-form-item :label="'最大等待时间(ms)'" prop="timeout">
|
||||
<el-input-number size="small" :disabled="isReadOnly" v-model="config.timeout" :placeholder="$t('commons.millisecond')" :max="1000*10000000" :min="0"/>
|
||||
</el-form-item>
|
||||
|
||||
<el-form-item>
|
||||
<el-button type="primary" size="small" class="addButton" @click="save">添加</el-button>
|
||||
</el-form-item>
|
||||
|
||||
</el-form>
|
||||
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import {DatabaseConfig} from "../../../model/ScenarioModel";
|
||||
|
||||
export default {
|
||||
name: "MsDatabaseFrom",
|
||||
components: {},
|
||||
props: {
|
||||
isReadOnly: {
|
||||
type: Boolean,
|
||||
default: false
|
||||
},
|
||||
config: {
|
||||
type: Object,
|
||||
default() {
|
||||
return new DatabaseConfig();
|
||||
}
|
||||
},
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
drivers: DatabaseConfig.DRIVER_CLASS,
|
||||
// config: new DatabaseConfig(),
|
||||
rules: {
|
||||
name: [
|
||||
{required: true, message: this.$t('commons.input_name'), trigger: 'blur'},
|
||||
{max: 300, message: this.$t('commons.input_limit', [0, 300]), trigger: 'blur'}
|
||||
],
|
||||
driver: [
|
||||
{required: true, message: this.$t('commons.input_name'), trigger: 'blur'},
|
||||
],
|
||||
password: [
|
||||
{max: 200, message: this.$t('commons.input_limit', [0, 200]), trigger: 'blur'}
|
||||
],
|
||||
dbUrl: [
|
||||
{required: true, message: this.$t('commons.input_name'), trigger: 'blur'},
|
||||
{max: 500, message: this.$t('commons.input_limit', [0, 500]), trigger: 'blur'}
|
||||
],
|
||||
username: [
|
||||
{required: true, message: this.$t('commons.input_name'), trigger: 'blur'},
|
||||
{max: 200, message: this.$t('commons.input_limit', [0, 200]), trigger: 'blur'}
|
||||
]
|
||||
}
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
save() {
|
||||
this.$refs['databaseFrom'].validate((valid) => {
|
||||
if (valid) {
|
||||
this.$emit('save', this.config);
|
||||
// this.config = new DatabaseConfig();
|
||||
} else {
|
||||
return false;
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped>
|
||||
|
||||
.addButton {
|
||||
float: right;
|
||||
}
|
||||
|
||||
.database-from {
|
||||
padding: 10px;
|
||||
border: #DCDFE6 solid 1px;
|
||||
margin: 5px 0;
|
||||
border-radius: 5px;
|
||||
}
|
||||
|
||||
</style>
|
|
@ -211,14 +211,16 @@ export class Scenario extends BaseConfig {
|
|||
this.environment = undefined;
|
||||
this.enableCookieShare = false;
|
||||
this.enable = true;
|
||||
this.databaseConfigs = undefined;
|
||||
|
||||
this.set(options);
|
||||
this.sets({variables: KeyValue, headers: KeyValue, requests: RequestFactory}, options);
|
||||
this.sets({variables: KeyValue, headers: KeyValue, requests: RequestFactory, databaseConfigs: DatabaseConfig}, options);
|
||||
}
|
||||
|
||||
initOptions(options = {}) {
|
||||
options.id = options.id || uuid();
|
||||
options.requests = options.requests || [new RequestFactory()];
|
||||
options.databaseConfigs = options.databaseConfigs || [];
|
||||
options.dubboConfig = new DubboConfig(options.dubboConfig);
|
||||
return options;
|
||||
}
|
||||
|
@ -479,6 +481,51 @@ export class ConfigCenter extends BaseConfig {
|
|||
}
|
||||
}
|
||||
|
||||
export class DatabaseConfig extends BaseConfig {
|
||||
static DRIVER_CLASS = ["com.mysql.jdbc.Driver"];
|
||||
|
||||
constructor(options) {
|
||||
super();
|
||||
this.id = undefined;
|
||||
this.name = undefined;
|
||||
this.poolMax = undefined;
|
||||
this.timeout = undefined;
|
||||
this.driver = undefined;
|
||||
this.dbUrl = undefined;
|
||||
this.username = undefined;
|
||||
this.password = undefined;
|
||||
|
||||
this.set(options);
|
||||
}
|
||||
|
||||
initOptions(options = {}) {
|
||||
// options.id = options.id || uuid();
|
||||
return options;
|
||||
}
|
||||
// <JDBCDataSource guiclass="TestBeanGUI" testclass="JDBCDataSource" testname="JDBC Connection Configurationqqq" enabled="true">
|
||||
// <boolProp name="autocommit">true</boolProp>
|
||||
// <stringProp name="checkQuery"></stringProp>
|
||||
// <stringProp name="connectionAge">5000</stringProp>
|
||||
// <stringProp name="connectionProperties"></stringProp>
|
||||
// <stringProp name="dataSource">test</stringProp>
|
||||
// <stringProp name="dbUrl">jdbc:mysql://localhost:3306/metersphere?autoReconnect=false&useUnicode=true&characterEncoding=UTF-8&characterSetResults=UTF-8&zeroDateTimeBehavior=convertToNull&allowMultiQueries=true</stringProp>
|
||||
// <stringProp name="driver">com.mysql.jdbc.Driver</stringProp>
|
||||
// <stringProp name="initQuery"></stringProp>
|
||||
// <boolProp name="keepAlive">true</boolProp>
|
||||
// <stringProp name="password">root</stringProp>
|
||||
// <stringProp name="poolMax">10</stringProp>
|
||||
// <boolProp name="preinit">false</boolProp>
|
||||
// <stringProp name="timeout">10000</stringProp>
|
||||
// <stringProp name="transactionIsolation">DEFAULT</stringProp>
|
||||
// <stringProp name="trimInterval">60000</stringProp>
|
||||
// <stringProp name="username">root</stringProp>
|
||||
// </JDBCDataSource>
|
||||
|
||||
isValid() {
|
||||
return !!this.name || !!this.poolMax || !!this.timeout || !!this.driver || !!this.dbUrl || !!this.username || !!this.password;
|
||||
}
|
||||
}
|
||||
|
||||
export class RegistryCenter extends BaseConfig {
|
||||
static PROTOCOLS = ["none", "zookeeper", "nacos", "apollo", "multicast", "redis", "simple"];
|
||||
|
||||
|
|
|
@ -45,64 +45,99 @@
|
|||
</template>
|
||||
|
||||
<script>
|
||||
import {checkoutCurrentOrganization, checkoutCurrentWorkspace} from "@/common/js/utils";
|
||||
import Setting from "@/business/components/settings/router";
|
||||
import {checkoutCurrentOrganization, checkoutCurrentWorkspace} from "@/common/js/utils";
|
||||
import Setting from "@/business/components/settings/router";
|
||||
|
||||
export default {
|
||||
name: "MsSettingMenu",
|
||||
data() {
|
||||
let getMenus = function (group) {
|
||||
let menus = [];
|
||||
Setting.children.forEach(child => {
|
||||
if (child.meta[group] === true) {
|
||||
let menu = {index: Setting.path + "/" + child.path}
|
||||
menu.title = child.meta.title;
|
||||
menu.roles = child.meta.roles;
|
||||
menus.push(menu);
|
||||
}
|
||||
})
|
||||
return menus;
|
||||
export default {
|
||||
name: "MsSettingMenu",
|
||||
data() {
|
||||
let getMenus = function (group) {
|
||||
let menus = [];
|
||||
Setting.children.forEach(child => {
|
||||
if (child.meta[group] === true) {
|
||||
let menu = {index: Setting.path + "/" + child.path}
|
||||
menu.title = child.meta.title;
|
||||
menu.roles = child.meta.roles;
|
||||
menu.valid = child.meta.valid;
|
||||
menus.push(menu);
|
||||
}
|
||||
})
|
||||
return menus;
|
||||
}
|
||||
return {
|
||||
systems: getMenus('system'),
|
||||
organizations: getMenus('organization'),
|
||||
workspaces: getMenus('workspace'),
|
||||
persons: getMenus('person'),
|
||||
isCurrentOrganizationAdmin: false,
|
||||
isCurrentWorkspaceUser: false,
|
||||
}
|
||||
},
|
||||
mounted() {
|
||||
this.valid();
|
||||
this.isCurrentOrganizationAdmin = checkoutCurrentOrganization();
|
||||
this.isCurrentWorkspaceUser = checkoutCurrentWorkspace();
|
||||
},
|
||||
methods: {
|
||||
valid() {
|
||||
let _this = this;
|
||||
this.result = this.$get("/license/valid", response => {
|
||||
let data = response.data;
|
||||
if (data === undefined || data != true) {
|
||||
this.systems.forEach(item => {
|
||||
if (item.valid != undefined && item.valid === true) {
|
||||
_this.systems.splice(this.systems.indexOf(item), 1);
|
||||
}
|
||||
})
|
||||
|
||||
this.organizations.forEach(item => {
|
||||
if (item.valid != undefined && item.valid === true) {
|
||||
_this.organizations.splice(this.organizations.indexOf(item), 1);
|
||||
}
|
||||
})
|
||||
|
||||
this.workspaces.forEach(item => {
|
||||
if (item.valid != undefined && item.valid === true) {
|
||||
_this.workspaces.splice(this.workspaces.indexOf(item), 1);
|
||||
}
|
||||
})
|
||||
|
||||
this.persons.forEach(item => {
|
||||
if (item.valid != undefined && item.valid === true) {
|
||||
_this.persons.splice(this.persons.indexOf(item), 1);
|
||||
}
|
||||
})
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
return {
|
||||
systems: getMenus('system'),
|
||||
organizations: getMenus('organization'),
|
||||
workspaces: getMenus('workspace'),
|
||||
persons: getMenus('person'),
|
||||
isCurrentOrganizationAdmin: false,
|
||||
isCurrentWorkspaceUser: false,
|
||||
}
|
||||
},
|
||||
mounted() {
|
||||
this.isCurrentOrganizationAdmin = checkoutCurrentOrganization();
|
||||
this.isCurrentWorkspaceUser = checkoutCurrentWorkspace();
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped>
|
||||
.setting {
|
||||
border-right: 0;
|
||||
}
|
||||
.setting {
|
||||
border-right: 0;
|
||||
}
|
||||
|
||||
.setting .setting-item {
|
||||
height: 40px;
|
||||
line-height: 40px;
|
||||
}
|
||||
.setting .setting-item {
|
||||
height: 40px;
|
||||
line-height: 40px;
|
||||
}
|
||||
|
||||
.icon {
|
||||
width: 24px;
|
||||
margin-right: 10px;
|
||||
}
|
||||
.icon {
|
||||
width: 24px;
|
||||
margin-right: 10px;
|
||||
}
|
||||
|
||||
.account {
|
||||
color: #5a78f0;
|
||||
}
|
||||
.account {
|
||||
color: #5a78f0;
|
||||
}
|
||||
|
||||
.organization {
|
||||
color: #b33a5b;
|
||||
}
|
||||
.organization {
|
||||
color: #b33a5b;
|
||||
}
|
||||
|
||||
.workspace {
|
||||
color: #44b349;
|
||||
}
|
||||
.workspace {
|
||||
color: #44b349;
|
||||
}
|
||||
</style>
|
||||
|
|
|
@ -32,7 +32,7 @@ export default {
|
|||
component: () => import(/* webpackChunkName: "setting" */ '@/business/components/settings/system/SystemParameterSetting'),
|
||||
meta: {system: true, title: 'commons.system_parameter_setting'}
|
||||
},
|
||||
...requireContext.keys().map(key => requireContext(key).system),
|
||||
...requireContext.keys().map(key => requireContext(key).system),...requireContext.keys().map(key => requireContext(key).license),
|
||||
{
|
||||
path: 'organizationmember',
|
||||
component: () => import(/* webpackChunkName: "setting" */ '@/business/components/settings/organization/OrganizationMember'),
|
||||
|
|
|
@ -1,86 +1,101 @@
|
|||
<template>
|
||||
<el-dialog v-loading="result.loading"
|
||||
:visible.sync="dialogVisible"
|
||||
:close-on-click-modal="false"
|
||||
>
|
||||
<el-table
|
||||
:data="tableData"
|
||||
highlight-current-row
|
||||
@current-change="handleCurrentChange"
|
||||
style="width: 100%">
|
||||
<el-table-column prop="name" :label="$t('commons.name')" show-overflow-tooltip/>
|
||||
<el-table-column prop="description" :label="$t('commons.description')" show-overflow-tooltip>
|
||||
<template v-slot:default="scope">
|
||||
{{ scope.row.description }}
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column
|
||||
sortable
|
||||
prop="createTime"
|
||||
:label="$t('commons.create_time')"
|
||||
show-overflow-tooltip>
|
||||
<template v-slot:default="scope">
|
||||
<span>{{ scope.row.createTime | timestampFormatDate }}</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column
|
||||
sortable
|
||||
prop="updateTime"
|
||||
:label="$t('commons.update_time')"
|
||||
show-overflow-tooltip>
|
||||
<template v-slot:default="scope">
|
||||
<span>{{ scope.row.updateTime | timestampFormatDate }}</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
</el-table>
|
||||
<template v-slot:footer>
|
||||
<div class="dialog-footer">
|
||||
<ms-dialog-footer
|
||||
@cancel="dialogVisible = false"
|
||||
@confirm="submit()"/>
|
||||
</div>
|
||||
</template>
|
||||
</el-dialog>
|
||||
<el-dialog v-loading="result.loading"
|
||||
:visible.sync="dialogVisible"
|
||||
:close-on-click-modal="false"
|
||||
class="ms-switch-project"
|
||||
>
|
||||
<ms-table-header :condition.sync="condition" @search="initData" title="" :show-create="false"/>
|
||||
<el-table
|
||||
:data="tableData"
|
||||
highlight-current-row
|
||||
@current-change="handleCurrentChange"
|
||||
style="width: 100%">
|
||||
<el-table-column prop="name" :label="$t('commons.name')" show-overflow-tooltip/>
|
||||
<el-table-column prop="description" :label="$t('commons.description')" show-overflow-tooltip>
|
||||
<template v-slot:default="scope">
|
||||
{{ scope.row.description }}
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column
|
||||
prop="createTime"
|
||||
:label="$t('commons.create_time')"
|
||||
show-overflow-tooltip>
|
||||
<template v-slot:default="scope">
|
||||
<span>{{ scope.row.createTime | timestampFormatDate }}</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column
|
||||
prop="updateTime"
|
||||
:label="$t('commons.update_time')"
|
||||
show-overflow-tooltip>
|
||||
<template v-slot:default="scope">
|
||||
<span>{{ scope.row.updateTime | timestampFormatDate }}</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
</el-table>
|
||||
<ms-table-pagination :change="initData" :current-page.sync="currentPage" :page-size.sync="pageSize"
|
||||
:total="total"/>
|
||||
<template v-slot:footer>
|
||||
<div class="dialog-footer">
|
||||
<ms-dialog-footer
|
||||
@cancel="dialogVisible = false"
|
||||
@confirm="submit()"/>
|
||||
</div>
|
||||
</template>
|
||||
</el-dialog>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import MsDialogFooter from "../../../common/components/MsDialogFooter";
|
||||
import MsDialogFooter from "../../../common/components/MsDialogFooter";
|
||||
import MsTableHeader from "../../../common/components/MsTableHeader";
|
||||
import MsTablePagination from "../../../common/pagination/TablePagination";
|
||||
|
||||
export default {
|
||||
name: "SwitchProject",
|
||||
components: {MsDialogFooter},
|
||||
data() {
|
||||
return {
|
||||
tableData: [],
|
||||
result: {},
|
||||
dialogVisible: false,
|
||||
projectId: ''
|
||||
export default {
|
||||
name: "SwitchProject",
|
||||
components: {MsDialogFooter, MsTableHeader, MsTablePagination},
|
||||
data() {
|
||||
return {
|
||||
tableData: [],
|
||||
result: {},
|
||||
dialogVisible: false,
|
||||
projectId: '',
|
||||
planId: '',
|
||||
condition: {},
|
||||
currentPage: 1,
|
||||
pageSize: 5,
|
||||
total: 0,
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
open(planId) {
|
||||
this.dialogVisible = true;
|
||||
this.planId = planId;
|
||||
this.initData();
|
||||
},
|
||||
initData() {
|
||||
this.condition.planId = this.planId;
|
||||
this.result = this.$post("/test/plan/project/" + this.currentPage + "/" + this.pageSize, this.condition, res => {
|
||||
const data = res.data;
|
||||
this.total = data.itemCount;
|
||||
this.tableData = data.listObject;
|
||||
})
|
||||
},
|
||||
handleCurrentChange(currentRow) {
|
||||
// initData 改变表格数据会触发此方法
|
||||
if (currentRow) {
|
||||
this.projectId = currentRow.id;
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
open(planId) {
|
||||
this.dialogVisible = true;
|
||||
this.initData(planId);
|
||||
},
|
||||
initData(planId) {
|
||||
this.result = this.$get("/test/plan/project/" + planId,res => {
|
||||
this.tableData = res.data;
|
||||
})
|
||||
},
|
||||
handleCurrentChange(currentRow) {
|
||||
// initData 改变表格数据会触发此方法
|
||||
if (currentRow) {
|
||||
this.projectId = currentRow.id;
|
||||
}
|
||||
},
|
||||
submit() {
|
||||
this.$emit('getProjectNode', this.projectId);
|
||||
this.dialogVisible = false;
|
||||
}
|
||||
submit() {
|
||||
this.$emit('getProjectNode', this.projectId);
|
||||
this.dialogVisible = false;
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped>
|
||||
|
||||
.ms-switch-project >>> .el-dialog__body {
|
||||
padding: 0 15px !important;
|
||||
}
|
||||
</style>
|
||||
|
|
|
@ -192,8 +192,8 @@ export default {
|
|||
this.total = data.itemCount;
|
||||
this.tableData = data.listObject;
|
||||
for (let i = 0; i < this.tableData.length; i++) {
|
||||
let path = "/test/plan/project/" + this.tableData[i].id;
|
||||
this.$get(path, res => {
|
||||
let path = "/test/plan/project";
|
||||
this.$post(path,{planId: this.tableData[i].id}, res => {
|
||||
let arr = res.data;
|
||||
let projectName = arr.map(data => data.name).join("、");
|
||||
let projectIds = arr.map(data => data.id);
|
||||
|
|
|
@ -256,7 +256,7 @@
|
|||
},
|
||||
getProject() {
|
||||
if (this.planId) {
|
||||
this.$get("/test/plan/project/" + this.planId,res => {
|
||||
this.$post("/test/plan/project/", {planId: this.planId},res => {
|
||||
let data = res.data;
|
||||
if (data) {
|
||||
this.projects = data;
|
||||
|
|
|
@ -110,6 +110,7 @@ export default {
|
|||
please_save: 'Please save first',
|
||||
formatErr: 'Format Error',
|
||||
id: 'ID',
|
||||
cannot_be_null: 'not null ',
|
||||
millisecond: 'ms',
|
||||
please_upload: 'Please upload file',
|
||||
reference_documentation: "Reference documentation",
|
||||
|
@ -153,6 +154,18 @@ export default {
|
|||
}
|
||||
}
|
||||
},
|
||||
license:{
|
||||
title: 'Authorization management',
|
||||
corporation: 'corporation',
|
||||
expired: 'expired',
|
||||
product: 'product',
|
||||
edition: 'edition',
|
||||
licenseVersion: 'licenseVersion',
|
||||
count: 'count',
|
||||
valid_license: 'valid license',
|
||||
show_license: 'show license',
|
||||
valid_license_error: 'validate license error',
|
||||
},
|
||||
workspace: {
|
||||
create: 'Create Workspace',
|
||||
update: 'Update Workspace',
|
||||
|
@ -639,6 +652,7 @@ export default {
|
|||
upload_limit_count: "Only one file can be uploaded at a time",
|
||||
upload_limit_format: "Upload files can only be XLS, XLSX format!",
|
||||
upload_limit_size: "Upload file size cannot exceed 20MB!",
|
||||
upload_limit_other_size: "Upload file size cannot exceed",
|
||||
success: "Import success!",
|
||||
importing: "Importing...",
|
||||
},
|
||||
|
|
|
@ -113,6 +113,7 @@ export default {
|
|||
reference_documentation: "参考文档",
|
||||
id: 'ID',
|
||||
millisecond: '毫秒',
|
||||
cannot_be_null: '不能为空',
|
||||
date: {
|
||||
select_date: '选择日期',
|
||||
start_date: '开始日期',
|
||||
|
@ -153,6 +154,18 @@ export default {
|
|||
}
|
||||
}
|
||||
},
|
||||
license:{
|
||||
title: '授权管理',
|
||||
corporation: '客户名称',
|
||||
expired: '授权时间',
|
||||
product: '产品名称',
|
||||
edition: '产品版本',
|
||||
licenseVersion: '授权版本',
|
||||
count: '授权数量',
|
||||
valid_license: '授权验证',
|
||||
show_license: '查看授权',
|
||||
valid_license_error: '授权验证失败',
|
||||
},
|
||||
workspace: {
|
||||
create: '创建工作空间',
|
||||
update: '修改工作空间',
|
||||
|
@ -639,6 +652,7 @@ export default {
|
|||
download_template: "下载模版",
|
||||
click_upload: "点击上传",
|
||||
upload_limit: "只能上传xls/xlsx文件,且不超过20M",
|
||||
upload_limit_other_size: "上传文件大小不能超过",
|
||||
upload_limit_count: "一次只能上传一个文件",
|
||||
upload_limit_format: "上传文件只能是 xls、xlsx格式!",
|
||||
upload_limit_size: "上传文件大小不能超过 20MB!",
|
||||
|
|
|
@ -108,6 +108,7 @@ export default {
|
|||
formatErr: '格式錯誤',
|
||||
please_save: '請先保存',
|
||||
id: 'ID',
|
||||
cannot_be_null: '不能为空',
|
||||
millisecond: '毫秒',
|
||||
reference_documentation: "參考文檔",
|
||||
please_upload: '請上傳文件',
|
||||
|
@ -151,6 +152,19 @@ export default {
|
|||
}
|
||||
}
|
||||
},
|
||||
license:{
|
||||
title: '授權管理',
|
||||
corporation: '客戶名稱',
|
||||
expired: '授權時間',
|
||||
product: '產品名稱',
|
||||
edition: '產品版本',
|
||||
licenseVersion: '授權版本',
|
||||
count: '授權數量',
|
||||
valid_license: '授權验证',
|
||||
show_license: '查看授權',
|
||||
valid_license_error: '授權验证失败',
|
||||
},
|
||||
|
||||
workspace: {
|
||||
create: '創建工作空間',
|
||||
update: '修改工作空間',
|
||||
|
@ -638,6 +652,7 @@ export default {
|
|||
upload_limit_count: "一次只能上傳一個文件",
|
||||
upload_limit_format: "上傳文件只能是 xls、xlsx格式!",
|
||||
upload_limit_size: "上傳文件大小不能超過 20MB!",
|
||||
upload_limit_other_size: "上傳文件大小不能超過",
|
||||
success: "導入成功!",
|
||||
importing: "導入中...",
|
||||
},
|
||||
|
|
Loading…
Reference in New Issue