diff --git a/backend/src/main/java/io/metersphere/api/service/ApiDefinitionService.java b/backend/src/main/java/io/metersphere/api/service/ApiDefinitionService.java index a73d6f1c6c..f75c94201a 100644 --- a/backend/src/main/java/io/metersphere/api/service/ApiDefinitionService.java +++ b/backend/src/main/java/io/metersphere/api/service/ApiDefinitionService.java @@ -215,7 +215,6 @@ public class ApiDefinitionService { ApiDefinitionExample example = new ApiDefinitionExample(); if (request.getProtocol().equals(RequestType.HTTP)) { example.createCriteria().andMethodEqualTo(request.getMethod()).andStatusNotEqualTo("Trash") - .andProtocolEqualTo(request.getProtocol()).andPathEqualTo(request.getPath()) .andProjectIdEqualTo(request.getProjectId()).andIdNotEqualTo(request.getId()); return apiDefinitionMapper.selectByExample(example); } else { diff --git a/backend/src/main/java/io/metersphere/base/mapper/ext/ExtTestCaseMapper.java b/backend/src/main/java/io/metersphere/base/mapper/ext/ExtTestCaseMapper.java index 5ed9e3a7fa..17ae2078b3 100644 --- a/backend/src/main/java/io/metersphere/base/mapper/ext/ExtTestCaseMapper.java +++ b/backend/src/main/java/io/metersphere/base/mapper/ext/ExtTestCaseMapper.java @@ -71,5 +71,10 @@ public interface ExtTestCaseMapper { List countRelevanceMaintainer(@Param("projectId") String projectId); + int getTestPlanBug(@Param("planId") String planId); + int getTestPlanCase(@Param("planId") String planId); + int getTestPlanPassCase(@Param("planId") String planId); + + } diff --git a/backend/src/main/java/io/metersphere/base/mapper/ext/ExtTestCaseMapper.xml b/backend/src/main/java/io/metersphere/base/mapper/ext/ExtTestCaseMapper.xml index 17d5c37a6e..72d3a06e38 100644 --- a/backend/src/main/java/io/metersphere/base/mapper/ext/ExtTestCaseMapper.xml +++ b/backend/src/main/java/io/metersphere/base/mapper/ext/ExtTestCaseMapper.xml @@ -342,8 +342,9 @@ + + + \ No newline at end of file diff --git a/backend/src/main/java/io/metersphere/commons/utils/ShiroUtils.java b/backend/src/main/java/io/metersphere/commons/utils/ShiroUtils.java index 61f73dd9ad..79ad0b6f70 100644 --- a/backend/src/main/java/io/metersphere/commons/utils/ShiroUtils.java +++ b/backend/src/main/java/io/metersphere/commons/utils/ShiroUtils.java @@ -48,6 +48,7 @@ public class ShiroUtils { public static void ignoreCsrfFilter(Map filterChainDefinitionMap) { filterChainDefinitionMap.put("/", "apikey, authc"); // 跳转到 / 不用校验 csrf + filterChainDefinitionMap.put("/language", "apikey, authc");// 跳转到 /language 不用校验 csrf filterChainDefinitionMap.put("/document", "apikey, authc"); // 跳转到 /document 不用校验 csrf } diff --git a/backend/src/main/java/io/metersphere/performance/parse/xml/reader/jmx/JmeterDocumentParser.java b/backend/src/main/java/io/metersphere/performance/parse/xml/reader/jmx/JmeterDocumentParser.java index 13ffc9a34e..09fbda18a5 100644 --- a/backend/src/main/java/io/metersphere/performance/parse/xml/reader/jmx/JmeterDocumentParser.java +++ b/backend/src/main/java/io/metersphere/performance/parse/xml/reader/jmx/JmeterDocumentParser.java @@ -676,6 +676,13 @@ public class JmeterDocumentParser implements DocumentParser { ((List) durations).remove(0); duration = o.toString(); } + Object units = context.getProperty("unit"); + String unit = "S"; + if (units instanceof List) { + Object o = ((List) units).get(0); + ((List) units).remove(0); + unit = o.toString(); + } Object deleteds = context.getProperty("deleted"); String deleted = "false"; if (deleteds instanceof List) { @@ -691,6 +698,17 @@ public class JmeterDocumentParser implements DocumentParser { enabled = o.toString(); } + switch (unit) { + case "M": + duration = String.valueOf(Long.parseLong(duration) * 60); + break; + case "H": + duration = String.valueOf(Long.parseLong(duration) * 60 * 60); + break; + default: + break; + } + threadGroup.setAttribute("enabled", enabled); if (BooleanUtils.toBoolean(deleted)) { threadGroup.setAttribute("enabled", "false"); @@ -761,6 +779,13 @@ public class JmeterDocumentParser implements DocumentParser { ((List) holds).remove(0); hold = o.toString(); } + Object units = context.getProperty("unit"); + String unit = "S"; + if (units instanceof List) { + Object o = ((List) units).get(0); + ((List) units).remove(0); + unit = o.toString(); + } Object deleteds = context.getProperty("deleted"); String deleted = "false"; if (deleteds instanceof List) { @@ -776,6 +801,17 @@ public class JmeterDocumentParser implements DocumentParser { enabled = o.toString(); } + switch (unit) { + case "M": + hold = String.valueOf(Long.parseLong(hold) * 60); + break; + case "H": + hold = String.valueOf(Long.parseLong(hold) * 60 * 60); + break; + default: + break; + } + threadGroup.setAttribute("enabled", enabled); if (BooleanUtils.toBoolean(deleted)) { threadGroup.setAttribute("enabled", "false"); @@ -928,10 +964,10 @@ public class JmeterDocumentParser implements DocumentParser { } private Element createStringProp(Document document, String name, String value) { - Element unit = document.createElement(STRING_PROP); - unit.setAttribute("name", name); - unit.appendChild(document.createTextNode(value)); - return unit; + Element element = document.createElement(STRING_PROP); + element.setAttribute("name", name); + element.appendChild(document.createTextNode(value)); + return element; } private void processThreadGroupName(Element threadGroup) { diff --git a/backend/src/main/java/io/metersphere/track/controller/TrackController.java b/backend/src/main/java/io/metersphere/track/controller/TrackController.java index 2b0d66bfb0..c010d94bc2 100644 --- a/backend/src/main/java/io/metersphere/track/controller/TrackController.java +++ b/backend/src/main/java/io/metersphere/track/controller/TrackController.java @@ -87,7 +87,7 @@ public class TrackController { } @GetMapping("/bug/count/{projectId}") - public BugStatustics getBugStatustics(@PathVariable String projectId) { - return trackService.getBugStatustics(projectId); + public BugStatustics getBugStatistics(@PathVariable String projectId) { + return trackService.getBugStatistics(projectId); } } diff --git a/backend/src/main/java/io/metersphere/track/response/TestPlanBugCount.java b/backend/src/main/java/io/metersphere/track/response/TestPlanBugCount.java index 4c8a75b272..6802673d16 100644 --- a/backend/src/main/java/io/metersphere/track/response/TestPlanBugCount.java +++ b/backend/src/main/java/io/metersphere/track/response/TestPlanBugCount.java @@ -8,7 +8,7 @@ import lombok.Setter; public class TestPlanBugCount { private int index; private String planName; - private long creatTime; + private long createTime; private String status; private int caseSize; private int bugSize; diff --git a/backend/src/main/java/io/metersphere/track/response/TrackStatisticsDTO.java b/backend/src/main/java/io/metersphere/track/response/TrackStatisticsDTO.java index cb3aeffc88..264e0cf9cb 100644 --- a/backend/src/main/java/io/metersphere/track/response/TrackStatisticsDTO.java +++ b/backend/src/main/java/io/metersphere/track/response/TrackStatisticsDTO.java @@ -144,20 +144,22 @@ public class TrackStatisticsDTO { public void countRelevance(List relevanceResults) { for (TrackCountResult countResult : relevanceResults) { - switch (countResult.getGroupField().toUpperCase()){ + switch (countResult.getGroupField()){ case TrackCount.API: this.apiCaseCount += countResult.getCountNumber(); + this.allRelevanceCaseCount += countResult.getCountNumber(); break; case TrackCount.PERFORMANCE: this.performanceCaseCount += countResult.getCountNumber(); + this.allRelevanceCaseCount += countResult.getCountNumber(); break; case TrackCount.AUTOMATION: this.scenarioCaseCount += countResult.getCountNumber(); + this.allRelevanceCaseCount += countResult.getCountNumber(); break; default: break; } - this.allRelevanceCaseCount += countResult.getCountNumber(); } } diff --git a/backend/src/main/java/io/metersphere/track/service/TrackService.java b/backend/src/main/java/io/metersphere/track/service/TrackService.java index b2a01371bd..3bcdf1cf79 100644 --- a/backend/src/main/java/io/metersphere/track/service/TrackService.java +++ b/backend/src/main/java/io/metersphere/track/service/TrackService.java @@ -12,6 +12,7 @@ import org.springframework.stereotype.Service; import org.springframework.transaction.annotation.Transactional; import javax.annotation.Resource; import java.math.BigDecimal; +import java.text.DecimalFormat; import java.util.ArrayList; import java.util.Date; import java.util.List; @@ -110,59 +111,58 @@ public class TrackService { return charts; } - public BugStatustics getBugStatustics(String projectId) { + public BugStatustics getBugStatistics(String projectId) { TestPlanExample example = new TestPlanExample(); example.createCriteria().andProjectIdEqualTo(projectId); List plans = testPlanMapper.selectByExample(example); List list = new ArrayList<>(); BugStatustics bugStatustics = new BugStatustics(); int index = 1; + int totalBugSize = 0; + int totalCaseSize = 0; for (TestPlan plan : plans) { TestPlanBugCount testPlanBug = new TestPlanBugCount(); testPlanBug.setIndex(index++); testPlanBug.setPlanName(plan.getName()); - testPlanBug.setCreatTime(plan.getCreateTime()); + testPlanBug.setCreateTime(plan.getCreateTime()); testPlanBug.setStatus(plan.getStatus()); - testPlanBug.setCaseSize(getPlanCaseSize(plan.getId())); - testPlanBug.setBugSize(getPlanBugSize(plan.getId())); - testPlanBug.setPassRage(getPlanPassRage(plan.getId())); + + int planCaseSize = getPlanCaseSize(plan.getId()); + testPlanBug.setCaseSize(planCaseSize); + + int planBugSize = getPlanBugSize(plan.getId()); + testPlanBug.setBugSize(planBugSize); + testPlanBug.setPassRage(getPlanPassRage(plan.getId(), planCaseSize)); list.add(testPlanBug); + + totalBugSize += planBugSize; + totalCaseSize += planCaseSize; } - // todo bugStatustics.setList(list); - bugStatustics.setRage("1"); - bugStatustics.setBugTotalSize(2); + float rage =totalCaseSize == 0 ? 0 : (float) totalBugSize * 100 / totalCaseSize; + DecimalFormat df = new DecimalFormat("0.0"); + bugStatustics.setRage(df.format(rage) + "%"); + bugStatustics.setBugTotalSize(totalBugSize); return bugStatustics; } private int getPlanCaseSize(String planId) { - TestPlanTestCaseExample testPlanTestCaseExample = new TestPlanTestCaseExample(); - testPlanTestCaseExample.createCriteria().andPlanIdEqualTo(planId); - List testPlanTestCases = testPlanTestCaseMapper.selectByExample(testPlanTestCaseExample); - - TestPlanApiCaseExample testPlanApiCaseExample = new TestPlanApiCaseExample(); - testPlanApiCaseExample.createCriteria().andTestPlanIdEqualTo(planId); - List testPlanApiCases = testPlanApiCaseMapper.selectByExample(testPlanApiCaseExample); - - TestPlanLoadCaseExample example = new TestPlanLoadCaseExample(); - example.createCriteria().andTestPlanIdEqualTo(planId); - List testPlanLoadCases = testPlanLoadCaseMapper.selectByExample(example); - - TestPlanApiScenarioExample testPlanApiScenarioExample = new TestPlanApiScenarioExample(); - testPlanApiCaseExample.createCriteria().andTestPlanIdEqualTo(planId); - List testPlanApiScenarios = testPlanApiScenarioMapper.selectByExample(testPlanApiScenarioExample); - - - return testPlanTestCases.size() + testPlanApiCases.size() + testPlanLoadCases.size() + testPlanApiScenarios.size(); + return extTestCaseMapper.getTestPlanCase(planId); } private int getPlanBugSize(String planId) { - return 1; + return extTestCaseMapper.getTestPlanBug(planId); } - private String getPlanPassRage(String planId) { - return "10%"; + private String getPlanPassRage(String planId, int totalSize) { + if (totalSize == 0) { + return "-"; + } + int passSize = extTestCaseMapper.getTestPlanPassCase(planId); + float rage = (float) passSize * 100 / totalSize; + DecimalFormat df = new DecimalFormat("0.0"); + return df.format(rage) + "%"; } } diff --git a/frontend/src/business/components/api/automation/scenario/EditApiScenario.vue b/frontend/src/business/components/api/automation/scenario/EditApiScenario.vue index cfebd0feb7..38aaf8c4bb 100644 --- a/frontend/src/business/components/api/automation/scenario/EditApiScenario.vue +++ b/frontend/src/business/components/api/automation/scenario/EditApiScenario.vue @@ -114,12 +114,13 @@ 共享cookie - + - + {{$t('api_test.request.debug')}} + @@ -192,6 +193,17 @@ class="ms-sc-variable-header"/> + + + + + + + + @@ -224,6 +236,9 @@ import MsComponentConfig from "./component/ComponentConfig"; import {handleCtrlSEvent} from "../../../../../common/js/utils"; import EnvPopover from "@/business/components/api/automation/scenario/EnvPopover"; + import MaximizeScenario from "./maximize/MaximizeScenario"; + import ScenarioHeader from "./maximize/ScenarioHeader"; + import MsDrawer from "../../../common/components/MsDrawer"; let jsonPath = require('jsonpath'); export default { @@ -243,7 +258,10 @@ MsApiCustomize, ApiImport, MsComponentConfig, - EnvPopover + EnvPopover, + MaximizeScenario, + ScenarioHeader, + MsDrawer }, data() { return { @@ -293,6 +311,7 @@ projectEnvMap: new Map, projectList: [], debugResult: new Map, + drawer: false, } }, created() { @@ -423,6 +442,9 @@ } }, methods: { + showAllBtn() { + this.$refs.maximizeScenario.showAll(); + }, addListener() { document.addEventListener("keydown", this.createCtrlSHandle); // document.addEventListener("keydown", (even => handleCtrlSEvent(even, this.$refs.httpApi.saveApi))); @@ -443,6 +465,7 @@ // 直接更新场景防止编辑内容丢失 this.editScenario(); } + this.$refs.maximizeHeader.getVariableSize(); this.reload(); }, showButton(...names) { @@ -697,8 +720,7 @@ } this.sort(); this.reload(); - } - , + }, reload() { this.loading = true this.$nextTick(() => { @@ -1046,7 +1068,14 @@ // 把执行结果分发给各个请求 this.debugResult = result; this.sort() + }, + fullScreen() { + this.drawer = true; + }, + close() { + this.drawer = false; } + } } @@ -1112,7 +1141,7 @@ } /deep/ .el-card__body { - padding: 15px; + padding: 10px; } /deep/ .el-drawer__body { @@ -1182,4 +1211,17 @@ .ms-sc-variable-header >>> .el-dialog__body { padding: 0px 20px; } + + .alt-ico { + font-size: 15px; + margin: 0px 10px 0px; + color: #8c939d; + } + + .alt-ico:hover { + color: black; + cursor: pointer; + font-size: 18px; + } + diff --git a/frontend/src/business/components/api/automation/scenario/Setting.js b/frontend/src/business/components/api/automation/scenario/Setting.js index 9ddffe168a..28d54980b6 100644 --- a/frontend/src/business/components/api/automation/scenario/Setting.js +++ b/frontend/src/business/components/api/automation/scenario/Setting.js @@ -16,6 +16,9 @@ export const ELEMENTS = new Map([ ['Extract', []], ['JmeterElement', []], ['CustomizeReq', ["ConstantTimer", "JSR223PreProcessor", "JSR223PostProcessor", "Assertions", "Extract"]], + ['MaxSamplerProxy', ["JSR223PreProcessor", "JSR223PostProcessor", "Assertions", "Extract"]], + ['AllSamplerProxy', ["HTTPSamplerProxy", "DubboSampler", "JDBCSampler", "TCPSampler"]], + ]) export const ELEMENT_TYPE = { diff --git a/frontend/src/business/components/api/automation/scenario/common/ApiBaseComponent.vue b/frontend/src/business/components/api/automation/scenario/common/ApiBaseComponent.vue index 1090ac3b5b..dbd1d4102b 100644 --- a/frontend/src/business/components/api/automation/scenario/common/ApiBaseComponent.vue +++ b/frontend/src/business/components/api/automation/scenario/common/ApiBaseComponent.vue @@ -1,47 +1,46 @@ + + diff --git a/frontend/src/business/components/api/automation/scenario/maximize/MaximizeScenario.vue b/frontend/src/business/components/api/automation/scenario/maximize/MaximizeScenario.vue new file mode 100644 index 0000000000..ea3127afe3 --- /dev/null +++ b/frontend/src/business/components/api/automation/scenario/maximize/MaximizeScenario.vue @@ -0,0 +1,1050 @@ + + + + + diff --git a/frontend/src/business/components/api/automation/scenario/maximize/ScenarioHeader.vue b/frontend/src/business/components/api/automation/scenario/maximize/ScenarioHeader.vue new file mode 100644 index 0000000000..d957231385 --- /dev/null +++ b/frontend/src/business/components/api/automation/scenario/maximize/ScenarioHeader.vue @@ -0,0 +1,146 @@ + + + + + diff --git a/frontend/src/business/components/api/definition/components/assertion/ApiAssertions.vue b/frontend/src/business/components/api/definition/components/assertion/ApiAssertions.vue index 17a7d5d5a2..190d4bdc9e 100644 --- a/frontend/src/business/components/api/definition/components/assertion/ApiAssertions.vue +++ b/frontend/src/business/components/api/definition/components/assertion/ApiAssertions.vue @@ -6,6 +6,8 @@ @active="active" :data="assertions" :draggable="draggable" + :is-max="isMax" + :show-btn="showBtn" color="#A30014" background-color="#F7E6E9" :title="$t('api_test.definition.request.assertions_rule')"> @@ -87,6 +89,14 @@ type: Boolean, default: false, }, + isMax: { + type: Boolean, + default: false, + }, + showBtn: { + type: Boolean, + default: true, + }, assertions: {}, node: {}, request: {}, diff --git a/frontend/src/business/components/api/definition/components/extract/ApiExtract.vue b/frontend/src/business/components/api/definition/components/extract/ApiExtract.vue index edd56731f9..3b8fab00a6 100644 --- a/frontend/src/business/components/api/definition/components/extract/ApiExtract.vue +++ b/frontend/src/business/components/api/definition/components/extract/ApiExtract.vue @@ -5,6 +5,8 @@ @active="active" :data="extract" :draggable="draggable" + :is-max="isMax" + :show-btn="showBtn" color="#015478" background-color="#E6EEF2" :title="$t('api_test.definition.request.extract_param')"> @@ -41,26 +43,26 @@