Merge pull request #8754 from metersphere/pr@dev@fix_uploadissueimage
fix: 连续上传缺陷图片显示 bug
This commit is contained in:
commit
744308655e
|
@ -29,7 +29,7 @@ public class IssueCommentController {
|
|||
@PostMapping("/save")
|
||||
@RequiresPermissions(PermissionConstants.PROJECT_TRACK_REVIEW_READ_COMMENT)
|
||||
@SendNotice(taskType = NoticeConstants.TaskType.DEFECT_TASK, target = "#targetClass.get(#request.issuesId)", targetClass = IssuesService.class,
|
||||
event = NoticeConstants.Event.COMMENT, mailTemplate = "track/IssuesCommentUpdate", subject = "缺陷评论更新通知")
|
||||
event = NoticeConstants.Event.COMMENT, mailTemplate = "track/IssuesCommentUpdate", subject = "缺陷")
|
||||
public IssueComment saveComment(@RequestBody IssuesRelevanceRequest request) {
|
||||
request.setId(UUID.randomUUID().toString());
|
||||
return issueCommentService.saveComment(request);
|
||||
|
|
|
@ -10,7 +10,7 @@
|
|||
:key="index"
|
||||
:comment="comment"
|
||||
:read-only="readOnly"
|
||||
@refresh="getComments()"/>
|
||||
@refresh="getComments()" api-url="/test/case"/>
|
||||
<div v-if="comments.length === 0" style="text-align: center">
|
||||
<i class="el-icon-chat-line-square" style="font-size: 15px;color: #8a8b8d;">
|
||||
<span style="font-size: 15px; color: #8a8b8d;">
|
||||
|
|
|
@ -115,7 +115,7 @@
|
|||
<review-comment-item v-for="(comment,index) in comments"
|
||||
:key="index"
|
||||
:comment="comment"
|
||||
@refresh="getComments"/>
|
||||
@refresh="getComments" api-url="/test/case"/>
|
||||
<div v-if="comments.length === 0" style="text-align: center">
|
||||
<i class="el-icon-chat-line-square" style="font-size: 15px;color: #8a8b8d;">
|
||||
<span style="font-size: 15px; color: #8a8b8d;">
|
||||
|
|
|
@ -102,7 +102,7 @@
|
|||
<review-comment-item v-for="(comment,index) in comments"
|
||||
:key="index"
|
||||
:comment="comment"
|
||||
@refresh="getComments" :disabled="true"/>
|
||||
@refresh="getComments" :disabled="true" api-url="/test/case"/>
|
||||
<div v-if="comments.length === 0" style="text-align: center">
|
||||
<i class="el-icon-chat-line-square" style="font-size: 15px;color: #8a8b8d;">
|
||||
<span style="font-size: 15px; color: #8a8b8d;">
|
||||
|
|
|
@ -88,7 +88,7 @@ export default {
|
|||
}
|
||||
this.result = this.$post('/issues/comment/save', comment, () => {
|
||||
this.$success(this.$t('test_track.comment.send_success'));
|
||||
this.refresh(comment.IssueId);
|
||||
this.refresh(comment.issuesId);
|
||||
this.from.description = '';
|
||||
this.dialogTableVisible = false;
|
||||
});
|
||||
|
|
|
@ -29,10 +29,10 @@ export default {
|
|||
}
|
||||
},
|
||||
methods: {
|
||||
open(data) {
|
||||
open(data, type) {
|
||||
this.visible = true;
|
||||
this.$nextTick(() => {
|
||||
this.$refs.issueEditDetail.open(data);
|
||||
this.$refs.issueEditDetail.open(data, type);
|
||||
})
|
||||
},
|
||||
handleClose() {
|
||||
|
|
|
@ -235,8 +235,9 @@ export default {
|
|||
},
|
||||
},
|
||||
methods: {
|
||||
open(data) {
|
||||
open(data, type) {
|
||||
this.result.loading = true;
|
||||
this.type = type;
|
||||
this.$nextTick(() => {
|
||||
getIssuePartTemplateWithProject((template, project) => {
|
||||
this.currentProject = project;
|
||||
|
@ -244,17 +245,18 @@ export default {
|
|||
});
|
||||
});
|
||||
|
||||
if(data&&data.id){
|
||||
if (data && data.id) {
|
||||
this.$get('/issues/follow/' + data.id, response => {
|
||||
this.form.follows = response.data;
|
||||
for (let i = 0; i < response.data.length; i++) {
|
||||
if(response.data[i]===this.currentUser().id){
|
||||
if (response.data[i] === this.currentUser().id) {
|
||||
this.showFollow = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
})
|
||||
}else {
|
||||
} else {
|
||||
this.issueId = null;
|
||||
this.form.follows = [];
|
||||
}
|
||||
},
|
||||
|
@ -325,6 +327,7 @@ export default {
|
|||
}
|
||||
}
|
||||
this.customFieldForm = parseCustomField(this.form, this.issueTemplate, this.customFieldRules);
|
||||
this.comments = [];
|
||||
this.$nextTick(() => {
|
||||
if (this.$refs.testCaseIssueList) {
|
||||
this.$refs.testCaseIssueList.initTableData();
|
||||
|
@ -422,6 +425,10 @@ export default {
|
|||
}
|
||||
},
|
||||
openComment() {
|
||||
if (!this.issueId) {
|
||||
this.$warning(this.$t('test_track.issue.save_before_open_comment'));
|
||||
return;
|
||||
}
|
||||
this.$refs.issueComment.open();
|
||||
},
|
||||
getComments() {
|
||||
|
|
|
@ -295,17 +295,17 @@ export default {
|
|||
|
||||
},
|
||||
handleEdit(data) {
|
||||
this.$refs.issueEdit.open(data);
|
||||
this.$refs.issueEdit.open(data, 'edit');
|
||||
},
|
||||
handleCreate() {
|
||||
this.$refs.issueEdit.open();
|
||||
this.$refs.issueEdit.open(null, 'add');
|
||||
},
|
||||
handleCopy(data) {
|
||||
let copyData = {};
|
||||
Object.assign(copyData, data);
|
||||
copyData.id = null;
|
||||
copyData.name = data.name + '_copy';
|
||||
this.$refs.issueEdit.open(copyData);
|
||||
this.$refs.issueEdit.open(copyData, 'copy');
|
||||
},
|
||||
handleDelete(data) {
|
||||
this.page.result = this.$get('issues/delete/' + data.id, () => {
|
||||
|
|
|
@ -19,46 +19,45 @@
|
|||
</el-button>
|
||||
</span>
|
||||
<span class="comment-delete">
|
||||
<el-link icon="el-icon-edit" v-if="!isImage" style="font-size: 9px;margin-right: 6px;" @click="openEdit" :disabled="readOnly"/>
|
||||
<el-link icon="el-icon-edit" style="font-size: 9px;margin-right: 6px;" @click="openEdit" :disabled="readOnly"/>
|
||||
<el-link icon="el-icon-close" @click="deleteComment" :disabled="readOnly"/>
|
||||
</span>
|
||||
<br/>
|
||||
<!-- <div class="comment-desc" style="font-size: 10px;color: #303133">-->
|
||||
<!-- <pre>{{ comment.description }}</pre>-->
|
||||
<!-- </div>-->
|
||||
<div v-if="!isImage" class="comment-desc" style="font-size: 10px;color: #303133">
|
||||
|
||||
<div v-if="!isImage" class="comment-desc" style="font-size: 10px;color: #303133">
|
||||
<pre>{{ comment.description }}</pre>
|
||||
</div>
|
||||
<div v-if="isImage" class="demo-image__preview">
|
||||
<pre>{{ imgDescription }}</pre>
|
||||
<el-image
|
||||
:z-index="imageIndex"
|
||||
style="width: 100px; height: 100px;"
|
||||
fit="contain"
|
||||
:src="src"
|
||||
:preview-src-list="srcList">
|
||||
:z-index="imageIndex"
|
||||
style="width: 100px; height: 100px;"
|
||||
fit="contain"
|
||||
:src="src"
|
||||
:preview-src-list="srcList">
|
||||
</el-image>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<el-dialog
|
||||
:title="$t('commons.edit')"
|
||||
:visible.sync="visible"
|
||||
width="30%"
|
||||
:destroy-on-close="true"
|
||||
:append-to-body="true"
|
||||
:close-on-click-modal="false"
|
||||
show-close>
|
||||
<el-input
|
||||
type="textarea"
|
||||
:rows="5"
|
||||
v-model="description">
|
||||
</el-input>
|
||||
<span slot="footer" class="dialog-footer">
|
||||
<ms-dialog-footer
|
||||
@cancel="visible = false"
|
||||
@confirm="editComment"/>
|
||||
</span>
|
||||
<el-dialog :visible.sync="visible"
|
||||
:title="$t('commons.edit')"
|
||||
:destroy-on-close="true"
|
||||
:close-on-click-modal="false"
|
||||
append-to-body>
|
||||
|
||||
<div>
|
||||
<div class="editors_div_style">
|
||||
<div id="editorsDiv">
|
||||
<ms-mark-down-text prop="description" :data="comment" :toolbars="toolbars"/>
|
||||
</div>
|
||||
</div>
|
||||
<div>
|
||||
<el-button type="primary" size="mini" class="send-btn" @click="editComment">
|
||||
{{ $t('test_track.comment.send') }}
|
||||
</el-button>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
</el-dialog>
|
||||
</div>
|
||||
</template>
|
||||
|
@ -66,10 +65,11 @@
|
|||
<script>
|
||||
import MsDialogFooter from "@/business/components/common/components/MsDialogFooter";
|
||||
import {getCurrentUser} from "@/common/js/utils";
|
||||
import MsMarkDownText from "@/business/components/track/case/components/MsMarkDownText";
|
||||
|
||||
export default {
|
||||
name: "ReviewCommentItem",
|
||||
components: {MsDialogFooter},
|
||||
components: {MsDialogFooter, MsMarkDownText},
|
||||
props: {
|
||||
comment: Object,
|
||||
readOnly: {
|
||||
|
@ -83,16 +83,51 @@ export default {
|
|||
return {
|
||||
visible: false,
|
||||
imgDescription: "",
|
||||
imageIndex:99999,
|
||||
src:"",
|
||||
srcList:[],
|
||||
imgNameList:[],
|
||||
imageIndex: 99999,
|
||||
src: "",
|
||||
srcList: [],
|
||||
imgNameList: [],
|
||||
description: "",
|
||||
imageMatchPattern:"(\\!\\[)\\S+]\\(\\S+\\)",
|
||||
imageMatchPattern: "(\\!\\[)\\S+]\\(\\S+\\)",
|
||||
toolbars: {
|
||||
bold: false, // 粗体
|
||||
italic: false, // 斜体
|
||||
header: false, // 标题
|
||||
underline: false, // 下划线
|
||||
strikethrough: false, // 中划线
|
||||
mark: false, // 标记
|
||||
superscript: false, // 上角标
|
||||
subscript: false, // 下角标
|
||||
quote: false, // 引用
|
||||
ol: false, // 有序列表
|
||||
ul: false, // 无序列表
|
||||
link: false, // 链接
|
||||
imagelink: true, // 图片链接
|
||||
code: false, // code
|
||||
table: false, // 表格
|
||||
fullscreen: false, // 全屏编辑
|
||||
readmodel: false, // 沉浸式阅读
|
||||
htmlcode: false, // 展示html源码
|
||||
help: false, // 帮助
|
||||
/* 1.3.5 */
|
||||
undo: false, // 上一步
|
||||
redo: false, // 下一步
|
||||
trash: false, // 清空
|
||||
save: false, // 保存(触发events中的save事件)
|
||||
/* 1.4.2 */
|
||||
navigation: false, // 导航目录
|
||||
/* 2.1.8 */
|
||||
alignleft: false, // 左对齐
|
||||
aligncenter: false, // 居中
|
||||
alignright: false, // 右对齐
|
||||
/* 2.2.1 */
|
||||
subfield: false, // 单双栏模式
|
||||
preview: false, // 预览
|
||||
}
|
||||
}
|
||||
},
|
||||
computed:{
|
||||
isImage(){
|
||||
computed: {
|
||||
isImage() {
|
||||
return this.checkImage(this.comment.description);
|
||||
}
|
||||
},
|
||||
|
@ -102,7 +137,7 @@ export default {
|
|||
this.$warning(this.$t('test_track.comment.cannot_delete'));
|
||||
return;
|
||||
}
|
||||
if(this.imgNameList.length > 0){
|
||||
if (this.imgNameList.length > 0) {
|
||||
this.imgNameList.forEach(imgName => {
|
||||
this.$get('/resource/md/delete/' + imgName);
|
||||
});
|
||||
|
@ -121,90 +156,91 @@ export default {
|
|||
this.visible = true;
|
||||
},
|
||||
editComment() {
|
||||
this.$post(this.apiUrl + "/comment/edit", {id: this.comment.id, description: this.description}, () => {
|
||||
this.$post(this.apiUrl + "/comment/edit", {id: this.comment.id, description: this.comment.description}, () => {
|
||||
this.visible = false;
|
||||
this.$success(this.$t('commons.modify_success'));
|
||||
this.$emit("refresh");
|
||||
});
|
||||
},
|
||||
checkImage(){
|
||||
checkImage() {
|
||||
this.srcList = [];
|
||||
let param = this.comment.description;
|
||||
let returnFlag = false;
|
||||
if(param){
|
||||
let message = param+"";
|
||||
if (param) {
|
||||
let message = param + "";
|
||||
let matchIndex = message.indexOf("](/resource/md/get/");
|
||||
if(matchIndex > 0){
|
||||
if (matchIndex > 0) {
|
||||
let messageSplitArr = message.split("](/resource/md/get/");
|
||||
for(let itemIndex = 0;itemIndex < messageSplitArr.length; itemIndex ++){
|
||||
for (let itemIndex = 0; itemIndex < messageSplitArr.length; itemIndex++) {
|
||||
let itemStr = messageSplitArr[itemIndex];
|
||||
let picNameIndex = itemStr.indexOf("![");
|
||||
if( picNameIndex < 0){
|
||||
if (picNameIndex < 0) {
|
||||
let endUrlIndex = itemStr.indexOf(")");
|
||||
if( endUrlIndex > 0){
|
||||
let itemStrArr = itemStr.substr(0,endUrlIndex);
|
||||
if (endUrlIndex > 0) {
|
||||
let itemStrArr = itemStr.substr(0, endUrlIndex);
|
||||
//if(imgNameList.)
|
||||
if(this.imgNameList.indexOf(itemStrArr) < 0){
|
||||
if (this.imgNameList.indexOf(itemStrArr) < 0) {
|
||||
this.imgNameList.push(itemStrArr);
|
||||
}
|
||||
|
||||
let imgUrl = "/resource/md/get/"+itemStrArr;
|
||||
let imgUrl = "/resource/md/get/" + itemStrArr;
|
||||
this.src = imgUrl;
|
||||
if(this.srcList.indexOf(itemStrArr) < 0){
|
||||
if (this.srcList.indexOf(itemStrArr) < 0) {
|
||||
this.srcList.push(imgUrl);
|
||||
}
|
||||
}
|
||||
}else{
|
||||
let inputStr = itemStr.substr(0,picNameIndex);
|
||||
if(this.imgDescription === ""){
|
||||
} else {
|
||||
let inputStr = itemStr.substr(0, picNameIndex);
|
||||
if (this.imgDescription === "") {
|
||||
this.imgDescription = inputStr;
|
||||
}else {
|
||||
} else {
|
||||
this.imgDescription = "\n" + inputStr;
|
||||
}
|
||||
}
|
||||
}
|
||||
}else{
|
||||
} else {
|
||||
let imgUrlIndex = message.indexOf("](http");
|
||||
if(imgUrlIndex > 0){
|
||||
if (imgUrlIndex > 0) {
|
||||
let imgUrlSplitArr = message.split("](http");
|
||||
for(let itemIndex = 0;itemIndex < imgUrlSplitArr.length; itemIndex ++){
|
||||
for (let itemIndex = 0; itemIndex < imgUrlSplitArr.length; itemIndex++) {
|
||||
let itemStr = imgUrlSplitArr[itemIndex];
|
||||
let picNameIndex = itemStr.indexOf("![");
|
||||
if( picNameIndex < 0){
|
||||
if (picNameIndex < 0) {
|
||||
let endUrlIndex = itemStr.indexOf(")");
|
||||
if( endUrlIndex > 0){
|
||||
let itemStrArr = itemStr.substr(0,endUrlIndex);
|
||||
if (endUrlIndex > 0) {
|
||||
let itemStrArr = itemStr.substr(0, endUrlIndex);
|
||||
//if(imgNameList.)
|
||||
if(this.imgNameList.indexOf(itemStrArr) < 0){
|
||||
if (this.imgNameList.indexOf(itemStrArr) < 0) {
|
||||
this.imgNameList.push(itemStrArr);
|
||||
}
|
||||
let imgUrl = "http"+itemStrArr;
|
||||
let imgUrl = "http" + itemStrArr;
|
||||
this.src = imgUrl;
|
||||
if(this.srcList.indexOf(itemStrArr) < 0){
|
||||
if (this.srcList.indexOf(itemStrArr) < 0) {
|
||||
this.srcList.push(imgUrl);
|
||||
}
|
||||
}
|
||||
}else{
|
||||
let inputStr = itemStr.substr(0,picNameIndex);
|
||||
if(this.imgDescription === ""){
|
||||
} else {
|
||||
let inputStr = itemStr.substr(0, picNameIndex);
|
||||
if (this.imgDescription === "") {
|
||||
this.imgDescription = inputStr;
|
||||
}else {
|
||||
} else {
|
||||
this.imgDescription = "\n" + inputStr;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
if(this.srcList.length > 0){
|
||||
if (this.srcList.length > 0) {
|
||||
returnFlag = true;
|
||||
}
|
||||
}
|
||||
return returnFlag;
|
||||
},
|
||||
checkByUrls(url){
|
||||
checkByUrls(url) {
|
||||
let checkResultFlag = false;
|
||||
if(this.imgNameList.length > 0){
|
||||
if (this.imgNameList.length > 0) {
|
||||
this.imgNameList.forEach(imgName => {
|
||||
if(imgName === url){
|
||||
if (imgName === url) {
|
||||
checkResultFlag = true;
|
||||
}
|
||||
});
|
||||
|
@ -269,6 +305,11 @@ pre {
|
|||
}
|
||||
|
||||
/deep/ .el-button--mini, .el-button--mini.is-round {
|
||||
padding: 4px 9px;
|
||||
padding: 7px 15px;
|
||||
}
|
||||
|
||||
.send-btn {
|
||||
margin-top: 5px;
|
||||
width: 100%;
|
||||
}
|
||||
</style>
|
||||
|
|
|
@ -2085,7 +2085,7 @@ export default {
|
|||
comment: {
|
||||
no_comment: "No Comment",
|
||||
send_comment: "Post a comment (Ctrl + Enter to send)",
|
||||
send: "Send",
|
||||
send: "Confirm",
|
||||
description_is_null: "Comment content cannot be empty!",
|
||||
send_success: "Comment successful!",
|
||||
},
|
||||
|
@ -2236,7 +2236,8 @@ export default {
|
|||
third_party_integrated: "Third-party Platform Integrated",
|
||||
use_third_party: "Enable Jira Issue Template",
|
||||
update_third_party_bugs: "Update the defects of third-party platforms",
|
||||
sync_bugs: "Synchronization Issue"
|
||||
sync_bugs: "Synchronization Issue",
|
||||
save_before_open_comment: "Please save issue before comment",
|
||||
},
|
||||
report: {
|
||||
name: "Test Plan Report",
|
||||
|
|
|
@ -2089,7 +2089,7 @@ export default {
|
|||
comment: {
|
||||
no_comment: "暂无评论",
|
||||
send_comment: "发表评论(Ctrl+Enter发送)",
|
||||
send: "发送",
|
||||
send: "确定",
|
||||
description_is_null: "评论内容不能为空!",
|
||||
send_success: "评论成功!",
|
||||
cannot_edit: "无法编辑此评论!",
|
||||
|
@ -2240,7 +2240,8 @@ export default {
|
|||
third_party_integrated: "集成第三方平台",
|
||||
use_third_party: "使用 Jira 缺陷模板",
|
||||
update_third_party_bugs: "更新第三方平台的缺陷",
|
||||
sync_bugs: "同步缺陷"
|
||||
sync_bugs: "同步缺陷",
|
||||
save_before_open_comment: "请先保存缺陷再添加评论",
|
||||
},
|
||||
report: {
|
||||
name: "测试计划报告",
|
||||
|
|
|
@ -2089,7 +2089,7 @@ export default {
|
|||
comment: {
|
||||
no_comment: "暫無評論",
|
||||
send_comment: "發表評論(Ctrl+Enter發送)",
|
||||
send: "發送",
|
||||
send: "確定",
|
||||
description_is_null: "評論內容不能為空!",
|
||||
send_success: "評論成功!",
|
||||
cannot_edit: "無法編輯此評論!",
|
||||
|
@ -2240,7 +2240,8 @@ export default {
|
|||
third_party_integrated: "集成第三方平臺",
|
||||
use_third_party: "使用 Jira 缺陷模板",
|
||||
update_third_party_bugs: "更新第三方平臺的缺陷",
|
||||
sync_bugs: "同步缺陷"
|
||||
sync_bugs: "同步缺陷",
|
||||
save_before_open_comment: "請先保存缺陷再添加評論",
|
||||
},
|
||||
report: {
|
||||
name: "測試計劃報告",
|
||||
|
|
Loading…
Reference in New Issue