Merge remote-tracking branch 'origin/master'

This commit is contained in:
q4speed 2020-10-20 18:30:30 +08:00
commit 5fe7786d2e
18 changed files with 235 additions and 59 deletions

View File

@ -10,4 +10,5 @@ public class ExtractCommon extends ExtractType {
private String value; // value: ${variable} private String value; // value: ${variable}
private String expression; private String expression;
private String description; private String description;
private Boolean multipleMatching;
} }

View File

@ -11,5 +11,5 @@ public interface ExtTestReviewCaseMapper {
List<TestReviewCaseDTO> list(@Param("request") QueryCaseReviewRequest request); List<TestReviewCaseDTO> list(@Param("request") QueryCaseReviewRequest request);
List<String> getStatusByReviewId(String reviewId); List<String> getStatusByReviewId(String reviewId);
List<String> findRelateTestReviewId(String userId, String workspaceId); List<String> findRelateTestReviewId(@Param("userId") String userId, @Param("workspaceId") String workspaceId);
} }

View File

@ -167,7 +167,7 @@ public class TestCaseController {
} }
@PostMapping("/file/download") @PostMapping("/file/download")
public ResponseEntity<byte[]> downloadJmx(@RequestBody FileOperationRequest fileOperationRequest) { public ResponseEntity<byte[]> download(@RequestBody FileOperationRequest fileOperationRequest) {
byte[] bytes = fileService.loadFileAsBytes(fileOperationRequest.getId()); byte[] bytes = fileService.loadFileAsBytes(fileOperationRequest.getId());
return ResponseEntity.ok() return ResponseEntity.ok()
.contentType(MediaType.parseMediaType("application/octet-stream")) .contentType(MediaType.parseMediaType("application/octet-stream"))
@ -175,4 +175,13 @@ public class TestCaseController {
.body(bytes); .body(bytes);
} }
@GetMapping("/file/preview/{fileId}")
public ResponseEntity<byte[]> preview(@PathVariable String fileId) {
byte[] bytes = fileService.loadFileAsBytes(fileId);
return ResponseEntity.ok()
.contentType(MediaType.parseMediaType("application/octet-stream"))
.header(HttpHeaders.CONTENT_DISPOSITION, "attachment; filename=\"" + fileId + "\"")
.body(bytes);
}
} }

View File

@ -263,25 +263,22 @@ public class TestCaseService {
.map(TestCase::getName) .map(TestCase::getName)
.collect(Collectors.toSet()); .collect(Collectors.toSet());
List<ExcelErrData<TestCaseExcelData>> errList = null; List<ExcelErrData<TestCaseExcelData>> errList = null;
if (multipartFile == null) if (multipartFile == null) {
MSException.throwException(Translator.get("upload_fail")); MSException.throwException(Translator.get("upload_fail"));
}
if (multipartFile.getOriginalFilename().endsWith(".xmind")) { if (multipartFile.getOriginalFilename().endsWith(".xmind")) {
try { try {
errList = new ArrayList<>();
XmindCaseParser xmindParser = new XmindCaseParser(this, userId, projectId, testCaseNames); XmindCaseParser xmindParser = new XmindCaseParser(this, userId, projectId, testCaseNames);
String processLog = xmindParser.parse(multipartFile); errList = xmindParser.parse(multipartFile);
if (!StringUtils.isEmpty(processLog)) { if (xmindParser.getNodePaths().isEmpty() && xmindParser.getTestCase().isEmpty()) {
excelResponse.setSuccess(false); if (errList == null) {
ExcelErrData excelErrData = new ExcelErrData(null, 1, Translator.get("upload_fail") + "" + processLog); errList = new ArrayList<>();
errList.add(excelErrData); }
excelResponse.setErrList(errList);
} else if (xmindParser.getNodePaths().isEmpty() && xmindParser.getTestCase().isEmpty()) {
excelResponse.setSuccess(false);
ExcelErrData excelErrData = new ExcelErrData(null, 1, Translator.get("upload_fail") + "" + Translator.get("upload_content_is_null")); ExcelErrData excelErrData = new ExcelErrData(null, 1, Translator.get("upload_fail") + "" + Translator.get("upload_content_is_null"));
errList.add(excelErrData); errList.add(excelErrData);
excelResponse.setErrList(errList); excelResponse.setErrList(errList);
} else { }
if (errList.isEmpty()) {
if (!xmindParser.getNodePaths().isEmpty()) { if (!xmindParser.getNodePaths().isEmpty()) {
testCaseNodeService.createNodes(xmindParser.getNodePaths(), projectId); testCaseNodeService.createNodes(xmindParser.getNodePaths(), projectId);
} }
@ -290,7 +287,6 @@ public class TestCaseService {
this.saveImportData(xmindParser.getTestCase(), projectId); this.saveImportData(xmindParser.getTestCase(), projectId);
xmindParser.clear(); xmindParser.clear();
} }
excelResponse.setSuccess(true);
} }
} catch (Exception e) { } catch (Exception e) {
LogUtil.error(e.getMessage(), e); LogUtil.error(e.getMessage(), e);

View File

@ -6,12 +6,14 @@ import com.google.common.collect.ImmutableMap;
import io.metersphere.base.domain.TestCaseWithBLOBs; import io.metersphere.base.domain.TestCaseWithBLOBs;
import io.metersphere.commons.constants.TestCaseConstants; import io.metersphere.commons.constants.TestCaseConstants;
import io.metersphere.commons.utils.BeanUtils; import io.metersphere.commons.utils.BeanUtils;
import io.metersphere.excel.domain.ExcelErrData;
import io.metersphere.excel.domain.TestCaseExcelData; import io.metersphere.excel.domain.TestCaseExcelData;
import io.metersphere.i18n.Translator; import io.metersphere.i18n.Translator;
import io.metersphere.track.service.TestCaseService; import io.metersphere.track.service.TestCaseService;
import io.metersphere.xmind.parser.XmindParser; import io.metersphere.xmind.parser.XmindParser;
import io.metersphere.xmind.parser.pojo.Attached; import io.metersphere.xmind.parser.pojo.Attached;
import io.metersphere.xmind.parser.pojo.JsonRootBean; import io.metersphere.xmind.parser.pojo.JsonRootBean;
import io.metersphere.xmind.utils.DetailUtil;
import org.apache.commons.lang3.StringUtils; import org.apache.commons.lang3.StringUtils;
import org.springframework.web.multipart.MultipartFile; import org.springframework.web.multipart.MultipartFile;
@ -32,7 +34,7 @@ public class XmindCaseParser {
/** /**
* 过程校验记录 * 过程校验记录
*/ */
private StringBuffer process; private DetailUtil process;
/** /**
* 已存在用例名称 * 已存在用例名称
*/ */
@ -57,7 +59,7 @@ public class XmindCaseParser {
this.testCaseNames = testCaseNames; this.testCaseNames = testCaseNames;
testCases = new LinkedList<>(); testCases = new LinkedList<>();
compartDatas = new ArrayList<>(); compartDatas = new ArrayList<>();
process = new StringBuffer(); process = new DetailUtil();
nodePaths = new ArrayList<>(); nodePaths = new ArrayList<>();
} }
@ -90,15 +92,15 @@ public class XmindCaseParser {
nodePaths.forEach(nodePath -> { nodePaths.forEach(nodePath -> {
String[] nodes = nodePath.split("/"); String[] nodes = nodePath.split("/");
if (nodes.length > TestCaseConstants.MAX_NODE_DEPTH + 1) { if (nodes.length > TestCaseConstants.MAX_NODE_DEPTH + 1) {
process.append(Translator.get("test_case_node_level_tip") + process.add(Translator.get("test_case_node_level_tip") +
TestCaseConstants.MAX_NODE_DEPTH + Translator.get("test_case_node_level") + "; "); TestCaseConstants.MAX_NODE_DEPTH + Translator.get("test_case_node_level"), nodePath);
} }
String path = ""; String path = "";
for (int i = 0; i < nodes.length; i++) { for (int i = 0; i < nodes.length; i++) {
if (i != 0 && StringUtils.equals(nodes[i].trim(), "")) { if (i != 0 && StringUtils.equals(nodes[i].trim(), "")) {
process.append(Translator.get("module") + ":【" + path + "" + Translator.get("module_not_null") + "; "); process.add(Translator.get("module_not_null"), path);
} else if (nodes[i].trim().length() > 30) { } else if (nodes[i].trim().length() > 30) {
process.append(nodes[i].trim() + "" + Translator.get("test_track.length_less_than") + "30 ;"); process.add(Translator.get("module") + Translator.get("test_track.length_less_than") + "30", path + nodes[i].trim());
} else { } else {
path += nodes[i].trim() + "/"; path += nodes[i].trim() + "/";
} }
@ -109,7 +111,7 @@ public class XmindCaseParser {
/** /**
* 验证用例的合规性 * 验证用例的合规性
*/ */
private boolean validate(TestCaseWithBLOBs data) { private void validate(TestCaseWithBLOBs data) {
String nodePath = data.getNodePath(); String nodePath = data.getNodePath();
if (!nodePath.startsWith("/")) { if (!nodePath.startsWith("/")) {
nodePath = "/" + nodePath; nodePath = "/" + nodePath;
@ -119,37 +121,36 @@ public class XmindCaseParser {
} }
data.setNodePath(nodePath); data.setNodePath(nodePath);
StringBuilder stringBuilder = new StringBuilder();
if (data.getName().length() > 50) { if (data.getName().length() > 50) {
stringBuilder.append(data.getName() + "" + Translator.get("test_case") + Translator.get("test_track.length_less_than") + "50 ;"); process.add(Translator.get("test_case") + Translator.get("test_track.length_less_than") + "50", nodePath + data.getName());
} }
if (!StringUtils.isEmpty(nodePath)) { if (!StringUtils.isEmpty(nodePath)) {
String[] nodes = nodePath.split("/"); String[] nodes = nodePath.split("/");
if (nodes.length > TestCaseConstants.MAX_NODE_DEPTH + 1) { if (nodes.length > TestCaseConstants.MAX_NODE_DEPTH + 1) {
stringBuilder.append(Translator.get("test_case_node_level_tip") + process.add(Translator.get("test_case_node_level_tip") +
TestCaseConstants.MAX_NODE_DEPTH + Translator.get("test_case_node_level") + "; "); TestCaseConstants.MAX_NODE_DEPTH + Translator.get("test_case_node_level"), nodePath);
} }
for (int i = 0; i < nodes.length; i++) { for (int i = 0; i < nodes.length; i++) {
if (i != 0 && StringUtils.equals(nodes[i].trim(), "")) { if (i != 0 && StringUtils.equals(nodes[i].trim(), "")) {
stringBuilder.append(Translator.get("test_case") + ":【" + data.getName() + "" + Translator.get("module_not_null") + "; "); process.add(Translator.get("test_case") + Translator.get("module_not_null"), nodePath + data.getName());
break; break;
} else if (nodes[i].trim().length() > 30) { } else if (nodes[i].trim().length() > 30) {
stringBuilder.append(nodes[i].trim() + "" + Translator.get("module") + Translator.get("test_track.length_less_than") + "30 ;"); process.add(Translator.get("module") + Translator.get("test_track.length_less_than") + "30 ", nodes[i].trim());
break; break;
} }
} }
} }
if (StringUtils.equals(data.getType(), TestCaseConstants.Type.Functional.getValue()) && StringUtils.equals(data.getMethod(), TestCaseConstants.Method.Auto.getValue())) { if (StringUtils.equals(data.getType(), TestCaseConstants.Type.Functional.getValue()) && StringUtils.equals(data.getMethod(), TestCaseConstants.Method.Auto.getValue())) {
stringBuilder.append(Translator.get("functional_method_tip") + "; "); process.add(Translator.get("functional_method_tip"), nodePath + data.getName());
} }
if (testCaseNames.contains(data.getName())) { if (testCaseNames.contains(data.getName())) {
boolean dbExist = testCaseService.exist(data); boolean dbExist = testCaseService.exist(data);
if (dbExist) { if (dbExist) {
stringBuilder.append(Translator.get("test_case_already_exists_excel") + "" + data.getName() + "; "); process.add(Translator.get("test_case_already_exists_excel"), nodePath + "/" + data.getName());
} }
} else { } else {
testCaseNames.add(data.getName()); testCaseNames.add(data.getName());
@ -157,26 +158,19 @@ public class XmindCaseParser {
// 用例等级和用例性质处理 // 用例等级和用例性质处理
if (!priorityList.contains(data.getPriority())) { if (!priorityList.contains(data.getPriority())) {
stringBuilder.append(data.getName() + "" + Translator.get("test_case_priority") + Translator.get("incorrect_format") + "; "); process.add(Translator.get("test_case_priority") + Translator.get("incorrect_format"), nodePath + data.getName());
} }
if (data.getType() == null) { if (data.getType() == null) {
stringBuilder.append(data.getName() + "" + Translator.get("test_case_type") + Translator.get("incorrect_format") + "; "); process.add(Translator.get("test_case_type") + Translator.get("incorrect_format"), nodePath + data.getName());
} }
// 重复用例校验 // 重复用例校验
TestCaseExcelData compartData = new TestCaseExcelData(); TestCaseExcelData compartData = new TestCaseExcelData();
BeanUtils.copyBean(compartData, data); BeanUtils.copyBean(compartData, data);
if (compartDatas.contains(compartData)) { if (compartDatas.contains(compartData)) {
stringBuilder.append(Translator.get("test_case_already_exists_excel") + "" + compartData.getName() + "; "); process.add(Translator.get("test_case_already_exists_excel"), nodePath + "/" + compartData.getName());
}
if (!StringUtils.isEmpty(stringBuilder.toString())) {
process.append(stringBuilder.toString());
return false;
} }
compartDatas.add(compartData); compartDatas.add(compartData);
return true;
} }
/** /**
@ -267,7 +261,7 @@ public class XmindCaseParser {
String tc = title.replace("", ":"); String tc = title.replace("", ":");
String[] tcArr = tc.split(":"); String[] tcArr = tc.split(":");
if (tcArr.length != 2) { if (tcArr.length != 2) {
process.append(Translator.get("test_case_name") + "" + title + "" + Translator.get("incorrect_format")); process.add(Translator.get("test_case_name") + Translator.get("incorrect_format"), title);
return; return;
} }
// 用例名称 // 用例名称
@ -301,17 +295,15 @@ public class XmindCaseParser {
}); });
} }
testCase.setSteps(this.getSteps(steps)); testCase.setSteps(this.getSteps(steps));
testCases.add(testCase);
// 校验合规性 // 校验合规性
if (validate(testCase)) { validate(testCase);
testCases.add(testCase);
}
} }
/** /**
* 导入思维导图处理 * 导入思维导图处理
*/ */
public String parse(MultipartFile multipartFile) { public List<ExcelErrData<TestCaseExcelData>> parse(MultipartFile multipartFile) {
try { try {
// 获取思维导图内容 // 获取思维导图内容
List<JsonRootBean> roots = XmindParser.parseObject(multipartFile); List<JsonRootBean> roots = XmindParser.parseObject(multipartFile);
@ -321,7 +313,7 @@ public class XmindCaseParser {
for (Attached item : root.getRootTopic().getChildren().getAttached()) { for (Attached item : root.getRootTopic().getChildren().getAttached()) {
// 用例 // 用例
if (isAvailable(item.getTitle(), TC_REGEX)) { if (isAvailable(item.getTitle(), TC_REGEX)) {
return replace(item.getTitle(), TC_REGEX) + "" + Translator.get("test_case_create_module_fail"); return process.parse(replace(item.getTitle(), TC_REGEX) + "" + Translator.get("test_case_create_module_fail"));
} else { } else {
String nodePath = item.getTitle(); String nodePath = item.getTitle();
item.setPath(nodePath); item.setPath(nodePath);
@ -344,8 +336,8 @@ public class XmindCaseParser {
//检查目录合规性 //检查目录合规性
this.validate(); this.validate();
} catch (Exception ex) { } catch (Exception ex) {
return ex.getMessage(); return process.parse(ex.getMessage());
} }
return process.toString(); return process.parse();
} }
} }

View File

@ -73,7 +73,7 @@ public class XmindParser {
JsonRootBean jsonRootBean = JSON.parseObject(content, JsonRootBean.class); JsonRootBean jsonRootBean = JSON.parseObject(content, JsonRootBean.class);
jsonRootBeans.add(jsonRootBean); jsonRootBeans.add(jsonRootBean);
} }
if (caseCount > 500) { if (caseCount > 800) {
MSException.throwException(Translator.get("import_xmind_count_error")); MSException.throwException(Translator.get("import_xmind_count_error"));
} }
} }

View File

@ -0,0 +1,59 @@
package io.metersphere.xmind.utils;
import io.metersphere.excel.domain.ExcelErrData;
import io.metersphere.excel.domain.TestCaseExcelData;
import lombok.Getter;
import lombok.Setter;
import java.io.Serializable;
import java.util.ArrayList;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
@Getter
@Setter
public class DetailUtil implements Serializable {
private Map<String, StringBuilder> process;
public DetailUtil() {
process = new LinkedHashMap<>();
}
public void add(String type, String msContent) {
if (process.containsKey(type)) {
process.get(type).append(msContent + "");
} else {
process.put(type, new StringBuilder(msContent + ""));
}
}
public List<ExcelErrData<TestCaseExcelData>> parse(String content) {
List<ExcelErrData<TestCaseExcelData>> errList = new ArrayList<>();
ExcelErrData excelErrData = new ExcelErrData(null, 1, content);
errList.add(excelErrData);
return errList;
}
public List<ExcelErrData<TestCaseExcelData>> parse() {
List<ExcelErrData<TestCaseExcelData>> errList = new ArrayList<>();
List<String> result = new ArrayList<>();
process.entrySet().parallelStream().reduce(result, (first, second) -> {
first.add(second.getKey() + "" + second.getValue());
return first;
}, (first, second) -> {
if (first == second) {
return first;
}
first.addAll(second);
return first;
});
for (int i = 0; i < result.size(); i++) {
ExcelErrData excelErrData = new ExcelErrData(null, i, result.get(i));
errList.add(excelErrData);
}
return errList;
}
}

@ -1 +1 @@
Subproject commit cf6b06526324326a563d933e07118fac014a63b4 Subproject commit ee74568be0beba46da19616f5832e83f9164c688

View File

@ -35,7 +35,8 @@
"jspdf": "^2.1.1", "jspdf": "^2.1.1",
"yan-progress": "^1.0.3", "yan-progress": "^1.0.3",
"nprogress": "^0.2.0", "nprogress": "^0.2.0",
"el-table-infinite-scroll": "^1.0.10" "el-table-infinite-scroll": "^1.0.10",
"vue-pdf": "^4.2.0"
}, },
"devDependencies": { "devDependencies": {
"@vue/cli-plugin-babel": "^4.1.0", "@vue/cli-plugin-babel": "^4.1.0",

View File

@ -29,6 +29,10 @@
type: Boolean, type: Boolean,
default: true default: true
}, },
showCopyTipWithMultiple: {
type: Boolean,
default: false
},
}, },
data() { data() {
@ -63,7 +67,7 @@
computed: { computed: {
variable() { variable() {
return "${" + this.value + "}"; return "${" + (this.showCopyTipWithMultiple ? (this.value + "_n") : this.value) + "}";
} }
} }

View File

@ -8,12 +8,17 @@
</el-col> </el-col>
<el-col> <el-col>
<ms-api-variable-input :is-read-only="isReadOnly" v-model="common.variable" size="small" maxlength="60" <ms-api-variable-input :is-read-only="isReadOnly" v-model="common.variable" size="small" maxlength="60"
@change="change" show-word-limit :placeholder="$t('api_test.variable_name')"/> @change="change" :show-copy-tip-with-multiple="common.multipleMatching" show-word-limit :placeholder="$t('api_test.variable_name')"/>
</el-col> </el-col>
<el-col> <el-col>
<el-input :disabled="isReadOnly" v-model="common.expression" size="small" show-word-limit <el-input :disabled="isReadOnly" v-model="common.expression" size="small" show-word-limit
:placeholder="expression"/> :placeholder="expression"/>
</el-col> </el-col>
<el-col class="multiple_checkbox">
<el-checkbox v-model="common.multipleMatching" :disabled="isReadOnly">
{{ $t('api_test.request.extract.multiple_matching') }}
</el-checkbox>
</el-col>
<el-col class="extract-btn"> <el-col class="extract-btn">
<el-button :disabled="isReadOnly" type="danger" size="mini" icon="el-icon-delete" circle @click="remove" <el-button :disabled="isReadOnly" type="danger" size="mini" icon="el-icon-delete" circle @click="remove"
v-if="edit"/> v-if="edit"/>
@ -159,4 +164,10 @@
.extract-btn { .extract-btn {
width: 60px; width: 60px;
} }
.multiple_checkbox {
text-align: center;
width: 120px;
}
</style> </style>

View File

@ -855,6 +855,7 @@ export class ExtractCommon extends ExtractType {
this.value = ""; // ${variable} this.value = ""; // ${variable}
this.expression = undefined; this.expression = undefined;
this.description = undefined; this.description = undefined;
this.multipleMatching = undefined;
this.set(options); this.set(options);
} }
@ -1460,6 +1461,7 @@ class JMXGenerator {
let props = { let props = {
name: extractCommon.variable, name: extractCommon.variable,
expression: extractCommon.expression, expression: extractCommon.expression,
match: extractCommon.multipleMatching ? -1 : undefined
} }
let testName = props.name let testName = props.name
switch (extractCommon.type) { switch (extractCommon.type) {

View File

@ -252,6 +252,10 @@
<el-table-column <el-table-column
:label="$t('commons.operating')"> :label="$t('commons.operating')">
<template v-slot:default="scope"> <template v-slot:default="scope">
<el-button @click="preview(scope.row)" :disabled="!scope.row.id || readOnly" type="primary"
v-if="isPreview(scope.row)"
icon="el-icon-view"
size="mini" circle/>
<el-button @click="handleDownload(scope.row)" :disabled="!scope.row.id || readOnly" type="primary" <el-button @click="handleDownload(scope.row)" :disabled="!scope.row.id || readOnly" type="primary"
icon="el-icon-download" icon="el-icon-download"
size="mini" circle/> size="mini" circle/>
@ -277,6 +281,7 @@
</el-dialog> </el-dialog>
<test-case-file ref="testCaseFile"/>
</div> </div>
@ -289,10 +294,11 @@ import MsDialogFooter from '../../../common/components/MsDialogFooter'
import {listenGoBack, removeGoBackListener} from "../../../../../common/js/utils"; import {listenGoBack, removeGoBackListener} from "../../../../../common/js/utils";
import {LIST_CHANGE, TrackEvent} from "@/business/components/common/head/ListEvent"; import {LIST_CHANGE, TrackEvent} from "@/business/components/common/head/ListEvent";
import {Message} from "element-ui"; import {Message} from "element-ui";
import TestCaseFile from "@/business/components/track/case/components/TestCaseFile";
export default { export default {
name: "TestCaseEdit", name: "TestCaseEdit",
components: {MsDialogFooter}, components: {MsDialogFooter, TestCaseFile},
data() { data() {
return { return {
result: {}, result: {},
@ -718,7 +724,13 @@ export default {
/// todo: /// todo:
return file.size > 0; return file.size > 0;
}, },
preview(row) {
this.$refs.testCaseFile.open(row);
},
isPreview(row) {
const fileType = row.type;
return fileType === 'JPG' || fileType === 'JPEG' || fileType === 'PDF' || fileType === 'PNG';
}
} }
} }
</script> </script>

View File

@ -0,0 +1,48 @@
<template>
<el-dialog :visible.sync="dialogVisible" width="80%" :destroy-on-close="true" :before-close="close">
<div>
<img :src="'/test/case/file/preview/' + file.id" alt="图片显示异常" style="width: 100%;height: 100%;"
v-if="file.type === 'JPG' || file.type === 'JPEG' || file.type === 'PNG'">
<div v-if="file.type === 'PDF'">
<test-case-pdf :file-id="file.id"/>
</div>
</div>
</el-dialog>
</template>
<script>
import TestCasePdf from "@/business/components/track/case/components/TestCasePdf";
export default {
name: "TestCaseFiles",
components: {TestCasePdf},
props: {},
data() {
return {
file: {
id: '',
type: ''
},
dialogVisible: false,
}
},
methods: {
open(file) {
this.file = file;
this.dialogVisible = true;
},
close() {
this.file = {
id: '',
type: ''
};
this.dialogVisible = false;
}
}
}
</script>
<style scoped>
</style>

View File

@ -0,0 +1,38 @@
<template>
<div v-loading="loading">
<pdf ref="pdf" v-for="i in numPages" :key="i" :src="loadingTask" :page="i"/>
</div>
</template>
<script>
import pdf from "vue-pdf";
export default {
name: "TestCasePdf",
components: {pdf},
props: {
fileId: String
},
data() {
return {
loading: false,
numPages: null,
loadingTask: null,
}
},
mounted() {
this.loading = true;
this.loadingTask = pdf.createLoadingTask("/test/case/file/preview/" + this.fileId);
this.loadingTask.promise.then(pdf => {
this.numPages = pdf.numPages
this.loading = false;
}).catch(() => {
this.loading = false;
this.$error("pdf 加载失败");
})
}
}
</script>
<style scoped>
</style>

View File

@ -554,6 +554,7 @@ export default {
select_type: "Choose type", select_type: "Choose type",
description: "Extract data from the response and store it in variables. Use the variables in subsequent requests.", description: "Extract data from the response and store it in variables. Use the variables in subsequent requests.",
regex: "Regex", regex: "Regex",
multiple_matching: "Multiple matching",
regex_expression: "Regular expression", regex_expression: "Regular expression",
json_path_expression: "JSONPath expression", json_path_expression: "JSONPath expression",
xpath_expression: "XPath expression", xpath_expression: "XPath expression",
@ -748,7 +749,7 @@ export default {
click_upload: "Upload", click_upload: "Upload",
upload_limit: "Only XLS/XLSX/XMIND files can be uploaded, and no more than 20M", upload_limit: "Only XLS/XLSX/XMIND files can be uploaded, and no more than 20M",
upload_xmind_format: "Upload files can only be .xmind format", upload_xmind_format: "Upload files can only be .xmind format",
upload_xmind: "Only xmind files can be uploaded, and no more than 500", upload_xmind: "Only xmind files can be uploaded, and no more than 800",
upload_limit_count: "Only one file can be uploaded at a time", 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_format: "Upload files can only be XLS, XLSX format!",
upload_limit_size: "Upload file size cannot exceed 20MB!", upload_limit_size: "Upload file size cannot exceed 20MB!",

View File

@ -554,6 +554,7 @@ export default {
}, },
extract: { extract: {
label: "提取", label: "提取",
multiple_matching: "匹配多条",
select_type: "请选择类型", select_type: "请选择类型",
description: "从响应结果中提取数据并将其存储在变量中,在后续请求中使用变量。", description: "从响应结果中提取数据并将其存储在变量中,在后续请求中使用变量。",
regex: "正则", regex: "正则",
@ -751,7 +752,7 @@ export default {
download_template: "下载模版", download_template: "下载模版",
click_upload: "点击上传", click_upload: "点击上传",
upload_limit: "只能上传xls/xlsx文件且不超过20M", upload_limit: "只能上传xls/xlsx文件且不超过20M",
upload_xmind: "支持文件类型:.xmind一次至多导入500 条用例", upload_xmind: "支持文件类型:.xmind一次至多导入800 条用例",
upload_xmind_format: "上传文件只能是 .xmind 格式", upload_xmind_format: "上传文件只能是 .xmind 格式",
upload_limit_other_size: "上传文件大小不能超过", upload_limit_other_size: "上传文件大小不能超过",
upload_limit_count: "一次只能上传一个文件", upload_limit_count: "一次只能上传一个文件",

View File

@ -554,6 +554,7 @@ export default {
}, },
extract: { extract: {
label: "提取", label: "提取",
multiple_matching: "匹配多條",
select_type: "請選擇類型", select_type: "請選擇類型",
description: "從響應結果中提取數據並將其存儲在變量中,在後續請求中使用變量。", description: "從響應結果中提取數據並將其存儲在變量中,在後續請求中使用變量。",
regex: "正則", regex: "正則",
@ -751,7 +752,7 @@ export default {
download_template: "下載模版", download_template: "下載模版",
click_upload: "點擊上傳", click_upload: "點擊上傳",
upload_limit: "只能上傳xls/xlsx文件且不超過20M", upload_limit: "只能上傳xls/xlsx文件且不超過20M",
upload_xmind: "支持文件類型:.xmind壹次至多導入500 條用例", upload_xmind: "支持文件類型:.xmind壹次至多導入800 條用例",
upload_xmind_format: "上傳文件只能是 .xmind 格式", upload_xmind_format: "上傳文件只能是 .xmind 格式",
upload_limit_other_size: "上傳文件大小不能超過", upload_limit_other_size: "上傳文件大小不能超過",
upload_limit_count: "壹次只能上傳壹個文件", upload_limit_count: "壹次只能上傳壹個文件",