场景中心代码迭代
This commit is contained in:
parent
583759c70b
commit
86a6a25bf3
|
@ -0,0 +1,415 @@
|
||||||
|
<template>
|
||||||
|
<div class="editorItem">
|
||||||
|
<el-form-item>
|
||||||
|
<div class="editor-header" :style="indentStyle">
|
||||||
|
<span
|
||||||
|
v-if="row.children && row.children.length > 0"
|
||||||
|
class="toggle-btn"
|
||||||
|
@click="toggleCollapse"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
:class="
|
||||||
|
isCollapsed ? 'el-icon-caret-right' : 'el-icon-caret-bottom'
|
||||||
|
"
|
||||||
|
></i>
|
||||||
|
</span>
|
||||||
|
<span class="column-title"
|
||||||
|
>{{ row.column_name }}
|
||||||
|
<span style="font-size: 12px; margin-left: 5px; font-weight: bold">{{
|
||||||
|
row.column_comment
|
||||||
|
}}</span></span
|
||||||
|
>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="editor-container" :style="indentStyle">
|
||||||
|
<div
|
||||||
|
class="content-editor"
|
||||||
|
:ref="'contentEditor' + row.column_name + rowIndex"
|
||||||
|
:contenteditable="!viewFlag"
|
||||||
|
@keydown="handleKeyDown($event, row.column_name, rowIndex)"
|
||||||
|
@input="handleInput($event, row.column_name, rowIndex)"
|
||||||
|
@click="handleEditorClick($event, row.column_name, rowIndex)"
|
||||||
|
@paste="handlePaste($event, row.column_name, rowIndex)"
|
||||||
|
@focus="handleEditorFocus($event, row.column_name, rowIndex)"
|
||||||
|
@blur="handleEditorBlur($event, row.column_name, rowIndex)"
|
||||||
|
></div>
|
||||||
|
<div
|
||||||
|
v-if="!viewFlag"
|
||||||
|
class="editorIcon"
|
||||||
|
@click.stop="handleAddNodeToEditor(row.column_name, rowIndex)"
|
||||||
|
>
|
||||||
|
<i class="el-icon-circle-plus"></i>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
v-if="!viewFlag"
|
||||||
|
class="clearIcon"
|
||||||
|
@click.stop="handleClearNodeToEditor(row.column_name, rowIndex)"
|
||||||
|
>
|
||||||
|
<i class="el-icon-circle-close"></i>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</el-form-item>
|
||||||
|
|
||||||
|
<!-- 子项,只有在展开时才显示 -->
|
||||||
|
<EditorItem
|
||||||
|
v-if="!isCollapsed"
|
||||||
|
v-for="(child, index) in row.children"
|
||||||
|
:key="index"
|
||||||
|
:row="child"
|
||||||
|
:row-index="`${rowIndex}-${index}`"
|
||||||
|
v-bind="$attrs"
|
||||||
|
v-on="$listeners"
|
||||||
|
ref="childEditors"
|
||||||
|
ref-in-for
|
||||||
|
:viewFlag="viewFlag"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
|
||||||
|
<script>
|
||||||
|
export default {
|
||||||
|
name: "EditorItem",
|
||||||
|
props: {
|
||||||
|
row: Object,
|
||||||
|
rowIndex: [String, Number],
|
||||||
|
viewFlag: {
|
||||||
|
type: Boolean,
|
||||||
|
default: false,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
data() {
|
||||||
|
return {
|
||||||
|
isCollapsed: false,
|
||||||
|
};
|
||||||
|
},
|
||||||
|
computed: {
|
||||||
|
indentLevel() {
|
||||||
|
return String(this.rowIndex).split("-").length - 1;
|
||||||
|
},
|
||||||
|
indentStyle() {
|
||||||
|
return {
|
||||||
|
paddingLeft: this.indentLevel * 20 + "px",
|
||||||
|
};
|
||||||
|
},
|
||||||
|
},
|
||||||
|
mounted() {
|
||||||
|
this.$nextTick(() => {
|
||||||
|
const refName = "contentEditor" + this.row.column_name + this.rowIndex;
|
||||||
|
const editor = this.$refs[refName];
|
||||||
|
// 确保 editor 是 DOM 元素而非 undefined/数组
|
||||||
|
if (Array.isArray(editor)) {
|
||||||
|
if (editor.length > 0) {
|
||||||
|
this.$emit("register-editor", refName, editor[0]);
|
||||||
|
}
|
||||||
|
} else if (editor) {
|
||||||
|
this.$emit("register-editor", refName, editor);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
},
|
||||||
|
|
||||||
|
methods: {
|
||||||
|
// 获取当前组件及子组件的内容,递归返回数据
|
||||||
|
getEditorContent() {
|
||||||
|
// 当前编辑器 DOM 引用
|
||||||
|
const refName = "contentEditor" + this.row.column_name + this.rowIndex;
|
||||||
|
const editor = this.$refs[refName];
|
||||||
|
|
||||||
|
// 取当前编辑器内容
|
||||||
|
let html_label = "";
|
||||||
|
let whereCondition = "";
|
||||||
|
|
||||||
|
if (editor) {
|
||||||
|
html_label = editor.innerHTML.trim();
|
||||||
|
|
||||||
|
editor.childNodes.forEach((node) => {
|
||||||
|
if (node.nodeType === Node.TEXT_NODE) {
|
||||||
|
whereCondition += node.textContent;
|
||||||
|
} else if (node.nodeType === Node.ELEMENT_NODE) {
|
||||||
|
whereCondition += node.getAttribute("data-token-text") || "";
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
// 替换中文符号为英文符号
|
||||||
|
whereCondition = whereCondition
|
||||||
|
.replace(/,/g, ",")
|
||||||
|
.replace(/(/g, "(")
|
||||||
|
.replace(/)/g, ")");
|
||||||
|
}
|
||||||
|
|
||||||
|
// 递归收集子组件的内容
|
||||||
|
let children = [];
|
||||||
|
if (this.$refs.childEditors && this.$refs.childEditors.length > 0) {
|
||||||
|
children = this.$refs.childEditors.map((childComp) =>
|
||||||
|
childComp.getEditorContent()
|
||||||
|
);
|
||||||
|
}
|
||||||
|
return {
|
||||||
|
character_maximum_length: this.row.character_maximum_length,
|
||||||
|
column_comment: this.row.column_comment,
|
||||||
|
column_name: this.row.column_name,
|
||||||
|
data_type: this.row.data_type,
|
||||||
|
html_label: this.row.html_label,
|
||||||
|
is_nullable: this.row.is_nullable,
|
||||||
|
fieldName: this.row.column_name,
|
||||||
|
whereCondition,
|
||||||
|
html_label,
|
||||||
|
children,
|
||||||
|
};
|
||||||
|
},
|
||||||
|
toggleCollapse() {
|
||||||
|
this.isCollapsed = !this.isCollapsed;
|
||||||
|
},
|
||||||
|
// 直接复用父组件的事件,父组件传入逻辑无变化
|
||||||
|
handleKeyDown(e, columnName, rowIndex) {
|
||||||
|
this.$emit("handle-keydown", e, columnName, rowIndex);
|
||||||
|
},
|
||||||
|
handleInput(e, columnName, rowIndex) {
|
||||||
|
this.$emit("handle-input", e, columnName, rowIndex);
|
||||||
|
},
|
||||||
|
handleEditorClick(e, columnName, rowIndex) {
|
||||||
|
this.$emit("handle-editor-click", e, columnName, rowIndex);
|
||||||
|
},
|
||||||
|
handlePaste(e, columnName, rowIndex) {
|
||||||
|
this.$emit("handle-paste", e, columnName, rowIndex);
|
||||||
|
},
|
||||||
|
handleEditorFocus(e, columnName, rowIndex) {
|
||||||
|
this.$emit("handle-editor-focus", e, columnName, rowIndex);
|
||||||
|
},
|
||||||
|
handleEditorBlur(e, columnName, rowIndex) {
|
||||||
|
this.$emit("handle-editor-blur", e, columnName, rowIndex);
|
||||||
|
},
|
||||||
|
handleAddNodeToEditor(columnName, rowIndex) {
|
||||||
|
this.$emit("handle-add-node", columnName, rowIndex);
|
||||||
|
},
|
||||||
|
handleClearNodeToEditor(columnName, rowIndex) {
|
||||||
|
this.$emit("handle-clear-node", columnName, rowIndex);
|
||||||
|
},
|
||||||
|
},
|
||||||
|
components: {
|
||||||
|
EditorItem: () => import("./EditorItem.vue"),
|
||||||
|
},
|
||||||
|
};
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<style lang="scss" scoped>
|
||||||
|
// ------------------------
|
||||||
|
.editor-container {
|
||||||
|
flex: 1;
|
||||||
|
overflow: hidden;
|
||||||
|
position: relative;
|
||||||
|
}
|
||||||
|
.editorIcon {
|
||||||
|
position: absolute;
|
||||||
|
right: 10px;
|
||||||
|
top: 0;
|
||||||
|
font-size: 20px;
|
||||||
|
color: #999999;
|
||||||
|
}
|
||||||
|
|
||||||
|
.clearIcon {
|
||||||
|
display: none;
|
||||||
|
position: absolute;
|
||||||
|
top: 0;
|
||||||
|
right: 35px;
|
||||||
|
font-size: 20px;
|
||||||
|
color: #999999;
|
||||||
|
}
|
||||||
|
.editor-container:hover .clearIcon {
|
||||||
|
display: block;
|
||||||
|
}
|
||||||
|
/* hover 时显示 close-icon */
|
||||||
|
.editor-container:hover .close-icon {
|
||||||
|
display: inline-flex; /* 或 block,根据你的布局 */
|
||||||
|
}
|
||||||
|
.content-editor {
|
||||||
|
border: 1px solid #e5e7eb;
|
||||||
|
border-radius: 4px;
|
||||||
|
min-height: 40px;
|
||||||
|
padding: 0 50px 0 10px;
|
||||||
|
background: #fff;
|
||||||
|
position: relative;
|
||||||
|
font-size: 12px;
|
||||||
|
// line-height: 1.6;
|
||||||
|
overflow-y: auto;
|
||||||
|
outline: none;
|
||||||
|
word-wrap: break-word;
|
||||||
|
}
|
||||||
|
|
||||||
|
.content-editor:focus {
|
||||||
|
border-color: #409eff;
|
||||||
|
}
|
||||||
|
|
||||||
|
.content-editor:empty:before {
|
||||||
|
content: attr(data-placeholder);
|
||||||
|
color: #9ca3af;
|
||||||
|
font-style: italic;
|
||||||
|
pointer-events: none;
|
||||||
|
}
|
||||||
|
|
||||||
|
.content-editor:focus:empty:before {
|
||||||
|
content: "";
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 确保空编辑器也能显示光标 */
|
||||||
|
.content-editor:empty {
|
||||||
|
min-height: 40px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.content-editor:focus {
|
||||||
|
outline: none;
|
||||||
|
}
|
||||||
|
|
||||||
|
// --------------------------------
|
||||||
|
::v-deep .content-token {
|
||||||
|
display: unset !important;
|
||||||
|
padding: 3px 4px !important;
|
||||||
|
border-radius: 3px;
|
||||||
|
margin: 0 2px !important;
|
||||||
|
cursor: pointer;
|
||||||
|
transition: all 0.2s ease;
|
||||||
|
vertical-align: middle;
|
||||||
|
font-size: 12px;
|
||||||
|
font-weight: 500;
|
||||||
|
user-select: none;
|
||||||
|
}
|
||||||
|
::v-deep .token-function {
|
||||||
|
background: #ecfdf5;
|
||||||
|
color: #047857;
|
||||||
|
border: 1px solid #10b981;
|
||||||
|
}
|
||||||
|
|
||||||
|
::v-deep .repContainer {
|
||||||
|
width: 100%;
|
||||||
|
height: 100%;
|
||||||
|
background: #f5f5f5;
|
||||||
|
padding: 10px;
|
||||||
|
position: relative;
|
||||||
|
}
|
||||||
|
.treeNodeBox {
|
||||||
|
height: calc(100% - 50px);
|
||||||
|
overflow-y: auto;
|
||||||
|
}
|
||||||
|
|
||||||
|
.closeRepContainer {
|
||||||
|
position: absolute;
|
||||||
|
top: 20px;
|
||||||
|
right: 12px;
|
||||||
|
font-size: 14px;
|
||||||
|
cursor: pointer;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
|
||||||
|
i {
|
||||||
|
margin-right: 5px;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
.closeRepContainer:hover {
|
||||||
|
color: #409eff;
|
||||||
|
}
|
||||||
|
|
||||||
|
.repItem {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
margin-bottom: 8px;
|
||||||
|
cursor: pointer;
|
||||||
|
}
|
||||||
|
|
||||||
|
.repItem:hover .repItemValue {
|
||||||
|
color: #409eff;
|
||||||
|
}
|
||||||
|
|
||||||
|
.repItemValue {
|
||||||
|
color: #6b7280;
|
||||||
|
font-size: 13px;
|
||||||
|
margin-left: 10px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.token-editable-content {
|
||||||
|
display: inline-block;
|
||||||
|
min-width: 1em;
|
||||||
|
padding: 0 2px;
|
||||||
|
border-bottom: 1px dashed #aaa;
|
||||||
|
cursor: text;
|
||||||
|
outline: none;
|
||||||
|
}
|
||||||
|
::v-deep .content-token.token-edit {
|
||||||
|
display: inline-flex !important;
|
||||||
|
color: #5b21b6;
|
||||||
|
font-weight: bold;
|
||||||
|
padding: 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
.Columnsbtn {
|
||||||
|
margin: 10px 0;
|
||||||
|
display: flex;
|
||||||
|
justify-content: flex-end;
|
||||||
|
}
|
||||||
|
.fixedChildTable {
|
||||||
|
height: calc(100vh - 360px);
|
||||||
|
overflow: auto;
|
||||||
|
}
|
||||||
|
|
||||||
|
.drawParent {
|
||||||
|
position: relative;
|
||||||
|
}
|
||||||
|
.TestResultDisplayArea {
|
||||||
|
width: 400px;
|
||||||
|
height: calc(100% - 10px);
|
||||||
|
position: absolute;
|
||||||
|
right: 10px;
|
||||||
|
top: 5px;
|
||||||
|
background-color: #fff;
|
||||||
|
box-sizing: border-box;
|
||||||
|
box-shadow: 0 0 8px #0000001a;
|
||||||
|
border-radius: 4px;
|
||||||
|
z-index: 100;
|
||||||
|
overflow: hidden;
|
||||||
|
}
|
||||||
|
|
||||||
|
.testResultBoxTitle {
|
||||||
|
display: flex;
|
||||||
|
padding: 15px 10px;
|
||||||
|
background: #333333;
|
||||||
|
font-size: 14px;
|
||||||
|
font-weight: bold;
|
||||||
|
color: #fff;
|
||||||
|
justify-content: space-between;
|
||||||
|
border-radius: 4px 4px 0 0;
|
||||||
|
|
||||||
|
.closeTextBox {
|
||||||
|
cursor: pointer;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.jsonTestResultBox {
|
||||||
|
height: calc(100% - 90px);
|
||||||
|
overflow: auto;
|
||||||
|
}
|
||||||
|
|
||||||
|
::v-deep .el-alert {
|
||||||
|
padding: 10px !important;
|
||||||
|
}
|
||||||
|
|
||||||
|
.editor-header {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
margin-bottom: 5px;
|
||||||
|
font-weight: 500;
|
||||||
|
}
|
||||||
|
|
||||||
|
.toggle-btn {
|
||||||
|
cursor: pointer;
|
||||||
|
margin-right: 8px;
|
||||||
|
color: #606266;
|
||||||
|
font-size: 14px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.column-title {
|
||||||
|
font-size: 14px;
|
||||||
|
color: #333;
|
||||||
|
display: flex;
|
||||||
|
font-weight: bold;
|
||||||
|
}
|
||||||
|
|
||||||
|
</style>
|
|
@ -575,6 +575,35 @@
|
||||||
</el-select>
|
</el-select>
|
||||||
</el-form-item>
|
</el-form-item>
|
||||||
</el-form>
|
</el-form>
|
||||||
|
<div
|
||||||
|
class="tabs"
|
||||||
|
v-if="
|
||||||
|
currentRowData.options &&
|
||||||
|
currentRowData.options.appType != '9'
|
||||||
|
"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="tabsItem"
|
||||||
|
:class="{ active: parameterType === 'header' }"
|
||||||
|
@click="switchTabs('header')"
|
||||||
|
>
|
||||||
|
Headers入参
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="tabsItem"
|
||||||
|
:class="{ active: parameterType === 'query' }"
|
||||||
|
@click="switchTabs('query')"
|
||||||
|
>
|
||||||
|
Query入参
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="tabsItem"
|
||||||
|
:class="{ active: parameterType === 'body' }"
|
||||||
|
@click="switchTabs('body')"
|
||||||
|
>
|
||||||
|
Body入参
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
<div class="Columnsbtn" v-if="outsideColumns.length > 0">
|
<div class="Columnsbtn" v-if="outsideColumns.length > 0">
|
||||||
<el-button @click="saveTestTableEvent">暂存</el-button>
|
<el-button @click="saveTestTableEvent">暂存</el-button>
|
||||||
<el-button @click="saveTestTableEvent('hit')"
|
<el-button @click="saveTestTableEvent('hit')"
|
||||||
|
@ -617,91 +646,29 @@
|
||||||
style="margin: 0 10px"
|
style="margin: 0 10px"
|
||||||
>
|
>
|
||||||
<div id="editorContainer">
|
<div id="editorContainer">
|
||||||
<div
|
<EditorItem
|
||||||
v-for="(row, rowIndex) in outsideColumns"
|
v-for="(row, index) in outsideColumns"
|
||||||
:key="rowIndex"
|
:key="index"
|
||||||
class="editorItem"
|
:row="row"
|
||||||
>
|
:row-index="index"
|
||||||
<el-form-item :label="row.column_name">
|
@register-editor="registerEditorRef"
|
||||||
<div class="editor-container">
|
@handle-keydown="handleKeyDown"
|
||||||
<div
|
@handle-input="handleInput"
|
||||||
class="content-editor"
|
@handle-editor-click="handleEditorClick"
|
||||||
:ref="
|
@handle-paste="handlePaste"
|
||||||
'contentEditor' + row.column_name + rowIndex
|
@handle-editor-focus="handleEditorFocus"
|
||||||
"
|
@handle-editor-blur="handleEditorBlur"
|
||||||
contenteditable="true"
|
@handle-add-node="handleAddNodeToEditor"
|
||||||
@keydown="
|
@handle-clear-node="handleClearNodeToEditor"
|
||||||
handleKeyDown(
|
ref="editorRefs"
|
||||||
$event,
|
ref-in-for
|
||||||
row.column_name,
|
/>
|
||||||
rowIndex
|
|
||||||
)
|
|
||||||
"
|
|
||||||
@input="
|
|
||||||
handleInput(
|
|
||||||
$event,
|
|
||||||
row.column_name,
|
|
||||||
rowIndex
|
|
||||||
)
|
|
||||||
"
|
|
||||||
@click="
|
|
||||||
handleEditorClick(
|
|
||||||
$event,
|
|
||||||
row.column_name,
|
|
||||||
rowIndex
|
|
||||||
)
|
|
||||||
"
|
|
||||||
@paste="
|
|
||||||
handlePaste(
|
|
||||||
$event,
|
|
||||||
row.column_name,
|
|
||||||
rowIndex
|
|
||||||
)
|
|
||||||
"
|
|
||||||
@focus="
|
|
||||||
handleEditorFocus(
|
|
||||||
$event,
|
|
||||||
row.column_name,
|
|
||||||
rowIndex
|
|
||||||
)
|
|
||||||
"
|
|
||||||
@blur="
|
|
||||||
handleEditorBlur(
|
|
||||||
$event,
|
|
||||||
row.column_name,
|
|
||||||
rowIndex
|
|
||||||
)
|
|
||||||
"
|
|
||||||
></div>
|
|
||||||
<div
|
|
||||||
class="editorIcon"
|
|
||||||
@click.stop="
|
|
||||||
handleAddNodeToEditor(
|
|
||||||
row.column_name,
|
|
||||||
rowIndex
|
|
||||||
)
|
|
||||||
"
|
|
||||||
>
|
|
||||||
<i class="el-icon-circle-plus"></i>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="clearIcon"
|
|
||||||
@click.stop="
|
|
||||||
handleClearNodeToEditor(
|
|
||||||
row.column_name,
|
|
||||||
rowIndex
|
|
||||||
)
|
|
||||||
"
|
|
||||||
>
|
|
||||||
<i class="el-icon-circle-close"></i>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</el-form-item>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
</el-form>
|
</el-form>
|
||||||
</el-collapse-item>
|
</el-collapse-item>
|
||||||
</el-collapse>
|
</el-collapse>
|
||||||
|
|
||||||
|
<el-empty v-else description="暂无数据"></el-empty>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</el-tab-pane>
|
</el-tab-pane>
|
||||||
|
@ -732,6 +699,7 @@ import baseForm from "@/components/base/baseNewForm";
|
||||||
import treeNode from "./TreeNode";
|
import treeNode from "./TreeNode";
|
||||||
import IconsDialog from "../../tool/build/IconsDialog.vue";
|
import IconsDialog from "../../tool/build/IconsDialog.vue";
|
||||||
import jsonView from "vue-json-views";
|
import jsonView from "vue-json-views";
|
||||||
|
import EditorItem from "./EditorItem.vue";
|
||||||
export default {
|
export default {
|
||||||
components: {
|
components: {
|
||||||
editSence,
|
editSence,
|
||||||
|
@ -742,6 +710,7 @@ export default {
|
||||||
treeNode,
|
treeNode,
|
||||||
IconsDialog,
|
IconsDialog,
|
||||||
jsonView,
|
jsonView,
|
||||||
|
EditorItem,
|
||||||
},
|
},
|
||||||
data() {
|
data() {
|
||||||
return {
|
return {
|
||||||
|
@ -826,36 +795,61 @@ export default {
|
||||||
},
|
},
|
||||||
|
|
||||||
parameterType: "body", //参数类型
|
parameterType: "body", //参数类型
|
||||||
|
|
||||||
|
editorRefs: {}, // 用来保存所有子组件的 editor DOM
|
||||||
};
|
};
|
||||||
},
|
},
|
||||||
methods: {
|
methods: {
|
||||||
|
switchTabs(val) {
|
||||||
|
this.parameterType = val;
|
||||||
|
// 非数据库应用
|
||||||
|
if (this.currentRowData.options.appType != "9") {
|
||||||
|
this.queryApiConfig("tab");
|
||||||
|
}
|
||||||
|
},
|
||||||
async saveTestTableEvent(type) {
|
async saveTestTableEvent(type) {
|
||||||
if (!this.outsideFormData.tableName) {
|
if (
|
||||||
|
this.currentRowData.options.appType == "9" &&
|
||||||
|
!this.outsideFormData.tableName
|
||||||
|
) {
|
||||||
this.$vmNews("请先选择表");
|
this.$vmNews("请先选择表");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
this.openLoading("暂存");
|
this.openLoading("暂存");
|
||||||
// 使用示例:传入你这段 HTML 所在的 DOM 根节点
|
// 使用示例:传入你这段 HTML 所在的 DOM 根节点
|
||||||
const root = document.querySelector("#editorContainer");
|
const parsed = this.extractEditorItems();
|
||||||
const parsed = this.extractEditorItems(root);
|
|
||||||
let data = this.currentRowData.options;
|
let data = this.currentRowData.options;
|
||||||
let params = {
|
let params = {};
|
||||||
|
if (data && data.appType == "9") {
|
||||||
|
params = {
|
||||||
detailList: parsed,
|
detailList: parsed,
|
||||||
flowId: this.sceneID,
|
flowId: this.sceneID,
|
||||||
stepID: data.stepID,
|
stepID: data.stepID,
|
||||||
stepAccountId: data.step_acc_id,
|
stepAccountId: data.step_acc_id,
|
||||||
actionName: data.apiName || data.plugName,
|
actionName: data.apiName || data.plugName,
|
||||||
tableName: this.outsideFormData.tableName,
|
tableName: this.outsideFormData.tableName,
|
||||||
appType: this.currentRowData.options.appType,
|
appType: data.appType,
|
||||||
};
|
};
|
||||||
if (
|
if (data.apiName.includes("查询")) {
|
||||||
this.currentRowData.options &&
|
|
||||||
this.currentRowData.options.appType == "9" &&
|
|
||||||
this.currentRowData.options.apiName.includes("查询")
|
|
||||||
) {
|
|
||||||
params.rowNum = this.pageFormData.rowNum;
|
params.rowNum = this.pageFormData.rowNum;
|
||||||
params.pageLimit = this.pageFormData.pageLimit;
|
params.pageLimit = this.pageFormData.pageLimit;
|
||||||
}
|
}
|
||||||
|
} else {
|
||||||
|
params = {
|
||||||
|
flowId: this.sceneID,
|
||||||
|
stepID: data.stepID,
|
||||||
|
headerIn: "", //请求头入参
|
||||||
|
queryIn: "", //query入参
|
||||||
|
bodyIn: "", //bodyIn入参
|
||||||
|
};
|
||||||
|
if (this.parameterType == "body") {
|
||||||
|
params.bodyIn = parsed;
|
||||||
|
} else if (this.parameterType == "header") {
|
||||||
|
params.headerIn = parsed;
|
||||||
|
} else if (this.parameterType == "query") {
|
||||||
|
params.queryIn = parsed;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
let res = await authApi(
|
let res = await authApi(
|
||||||
"sysFlowStepConfigService",
|
"sysFlowStepConfigService",
|
||||||
|
@ -872,38 +866,18 @@ export default {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
extractEditorItems(rootElement) {
|
extractEditorItems() {
|
||||||
const result = [];
|
if (!this.$refs.editorRefs) return [];
|
||||||
const items = rootElement.querySelectorAll(".editorItem");
|
|
||||||
items.forEach((item) => {
|
|
||||||
const fieldName =
|
|
||||||
item.querySelector(".el-form-item__label")?.innerText.trim() || "";
|
|
||||||
const editor = item.querySelector(".content-editor");
|
|
||||||
if (!editor) return;
|
|
||||||
|
|
||||||
const html_label = editor.innerHTML.trim(); // 保留标签结构
|
return this.$refs.editorRefs.map((editorComp) =>
|
||||||
|
editorComp.getEditorContent()
|
||||||
let whereCondition = "";
|
);
|
||||||
editor.childNodes.forEach((node) => {
|
|
||||||
if (node.nodeType === Node.TEXT_NODE) {
|
|
||||||
whereCondition += node.textContent;
|
|
||||||
} else if (node.nodeType === Node.ELEMENT_NODE) {
|
|
||||||
whereCondition += node.getAttribute("data-token-text") || "";
|
|
||||||
}
|
|
||||||
});
|
|
||||||
// 替换中文符号为英文符号
|
|
||||||
whereCondition = whereCondition
|
|
||||||
.replace(/,/g, ",")
|
|
||||||
.replace(/(/g, "(")
|
|
||||||
.replace(/)/g, ")");
|
|
||||||
|
|
||||||
result.push({ fieldName, whereCondition, html_label });
|
|
||||||
});
|
|
||||||
|
|
||||||
return result;
|
|
||||||
},
|
},
|
||||||
async hitTesting() {
|
async hitTesting() {
|
||||||
if (!this.outsideFormData.tableName) {
|
if (
|
||||||
|
this.currentRowData.options.appType == "9" &&
|
||||||
|
!this.outsideFormData.tableName
|
||||||
|
) {
|
||||||
this.$vmNews("请先选择表");
|
this.$vmNews("请先选择表");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@ -913,7 +887,11 @@ export default {
|
||||||
let params = {
|
let params = {
|
||||||
stepID: data.stepID,
|
stepID: data.stepID,
|
||||||
tableName: this.outsideFormData.tableName,
|
tableName: this.outsideFormData.tableName,
|
||||||
|
appType: this.currentRowData.options.appType,
|
||||||
};
|
};
|
||||||
|
if (this.currentRowData.options.appType == "9") {
|
||||||
|
delete params.tableName;
|
||||||
|
}
|
||||||
let res = await authApi(
|
let res = await authApi(
|
||||||
"sysFlowStepConfigService",
|
"sysFlowStepConfigService",
|
||||||
"",
|
"",
|
||||||
|
@ -1169,6 +1147,9 @@ export default {
|
||||||
this.apiIDActiv = "";
|
this.apiIDActiv = "";
|
||||||
this.userActivId = "";
|
this.userActivId = "";
|
||||||
this.CurrentAppRow = {};
|
this.CurrentAppRow = {};
|
||||||
|
// 用来保存所有子组件的 editor DOM
|
||||||
|
this.editorRefs = {};
|
||||||
|
this.parameterType= "body"
|
||||||
|
|
||||||
if (index === 0) {
|
if (index === 0) {
|
||||||
this.activeTabName = "选择操作";
|
this.activeTabName = "选择操作";
|
||||||
|
@ -1443,6 +1424,13 @@ export default {
|
||||||
) {
|
) {
|
||||||
this.queryColumns(this.outsideFormData.tableName);
|
this.queryColumns(this.outsideFormData.tableName);
|
||||||
}
|
}
|
||||||
|
if (
|
||||||
|
this.activeOtherTabName == "配置应用" &&
|
||||||
|
this.apiIdActiv &&
|
||||||
|
this.currentRowData.options.appType != "9"
|
||||||
|
) {
|
||||||
|
this.getStepConfig();
|
||||||
|
}
|
||||||
},
|
},
|
||||||
/**
|
/**
|
||||||
* 应用搜索
|
* 应用搜索
|
||||||
|
@ -1679,7 +1667,7 @@ export default {
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
// 获取表字段
|
// 获取表字段
|
||||||
async queryApiConfig() {
|
async queryApiConfig(type) {
|
||||||
if (!this.currentRowData.options.apiId) {
|
if (!this.currentRowData.options.apiId) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@ -1700,7 +1688,9 @@ export default {
|
||||||
if (res.status == "200") {
|
if (res.status == "200") {
|
||||||
this.outsideColumns = res.attribute || [];
|
this.outsideColumns = res.attribute || [];
|
||||||
this.$nextTick(() => {
|
this.$nextTick(() => {
|
||||||
// this.getStepConfig();
|
if (type == "tab") {
|
||||||
|
this.getStepConfig();
|
||||||
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
@ -1876,15 +1866,29 @@ export default {
|
||||||
params
|
params
|
||||||
);
|
);
|
||||||
if (res.status == "200") {
|
if (res.status == "200") {
|
||||||
const root = document.querySelector("#editorContainer");
|
let detailList = [];
|
||||||
if (
|
if (
|
||||||
res.attribute &&
|
this.currentRowData.options.appType &&
|
||||||
res.attribute.detailList &&
|
this.currentRowData.options.appType == "9"
|
||||||
res.attribute.detailList.length > 0
|
|
||||||
) {
|
) {
|
||||||
res.attribute.detailList.forEach((item) => {
|
detailList = res.attribute?.detailList || [];
|
||||||
this.matchEditorItems(root, item.fieldName, item.html_label);
|
} else {
|
||||||
});
|
if (this.parameterType == "body") {
|
||||||
|
detailList = res.attribute?.bodyIn
|
||||||
|
? JSON.parse(res.attribute.bodyIn)
|
||||||
|
: [];
|
||||||
|
} else if (this.parameterType == "header") {
|
||||||
|
detailList = res.attribute?.headerIn
|
||||||
|
? JSON.parse(res.attribute.headerIn)
|
||||||
|
: [];
|
||||||
|
} else if (this.parameterType == "query") {
|
||||||
|
detailList = res.attribute?.queryIn
|
||||||
|
? JSON.parse(res.attribute.queryIn)
|
||||||
|
: [];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (detailList.length > 0) {
|
||||||
|
this.recursivelyApplyHtmlLabel(this.outsideColumns, detailList);
|
||||||
}
|
}
|
||||||
if (
|
if (
|
||||||
this.currentRowData.options &&
|
this.currentRowData.options &&
|
||||||
|
@ -1896,18 +1900,43 @@ export default {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
matchEditorItems(rootElement, rootName, rootHtml) {
|
// 匹配数据
|
||||||
const items = rootElement.querySelectorAll(".editorItem");
|
recursivelyApplyHtmlLabel(columns, detailList, path = []) {
|
||||||
items.forEach((item) => {
|
columns.forEach((col, index) => {
|
||||||
const fieldName =
|
const match = detailList.find(
|
||||||
item.querySelector(".el-form-item__label")?.innerText.trim() || "";
|
(item) => item.fieldName === col.column_name
|
||||||
const editor = item.querySelector(".content-editor");
|
);
|
||||||
if (!editor) return;
|
if (match && match.html_label) {
|
||||||
if (rootName == fieldName) {
|
this.matchEditorItems(match, index, path);
|
||||||
editor.innerHTML = rootHtml;
|
}
|
||||||
|
if (
|
||||||
|
col.children &&
|
||||||
|
col.children.length > 0 &&
|
||||||
|
match.children &&
|
||||||
|
match.children.length > 0
|
||||||
|
) {
|
||||||
|
this.recursivelyApplyHtmlLabel(col.children, match.children, [
|
||||||
|
...path,
|
||||||
|
index,
|
||||||
|
]);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
// 回显
|
||||||
|
matchEditorItems(match, index, path = []) {
|
||||||
|
const refName =
|
||||||
|
"contentEditor" + match.fieldName + [...path, index].join("-");
|
||||||
|
// 这里获取ref
|
||||||
|
const refEl = this.editorRefs[refName];
|
||||||
|
if (match && match.html_label && refEl) {
|
||||||
|
// 可能refEl是数组,取第一个元素
|
||||||
|
if (Array.isArray(refEl)) {
|
||||||
|
refEl[0].innerHTML = match.html_label;
|
||||||
|
} else if (refEl instanceof HTMLElement) {
|
||||||
|
refEl.innerHTML = match.html_label;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
/**
|
/**
|
||||||
* 获取插件列表
|
* 获取插件列表
|
||||||
* @param {string} appId 应用 ID
|
* @param {string} appId 应用 ID
|
||||||
|
@ -2066,9 +2095,13 @@ export default {
|
||||||
pageLimit: "100",
|
pageLimit: "100",
|
||||||
};
|
};
|
||||||
},
|
},
|
||||||
|
|
||||||
|
registerEditorRef(refName, dom) {
|
||||||
|
this.$set(this.editorRefs, refName, dom);
|
||||||
|
},
|
||||||
representationChange() {
|
representationChange() {
|
||||||
if (!this.currenrActiveNodeRef) return;
|
if (!this.currenrActiveNodeRef) return;
|
||||||
const editor = this.$refs[this.currenrActiveNodeRef][0];
|
const editor = this.editorRefs[this.currenrActiveNodeRef];
|
||||||
if (!editor) return;
|
if (!editor) return;
|
||||||
// 创建 range 和 selection
|
// 创建 range 和 selection
|
||||||
const range = document.createRange();
|
const range = document.createRange();
|
||||||
|
@ -2085,8 +2118,9 @@ export default {
|
||||||
this.saveRange();
|
this.saveRange();
|
||||||
},
|
},
|
||||||
handleKeyDown(e, columnName, rowIndex) {
|
handleKeyDown(e, columnName, rowIndex) {
|
||||||
const editor = this.$refs["contentEditor" + columnName + rowIndex][0];
|
const refName = "contentEditor" + columnName + rowIndex;
|
||||||
|
const editor = this.editorRefs[refName];
|
||||||
|
if (!editor) return;
|
||||||
if (e.key === "Backspace") {
|
if (e.key === "Backspace") {
|
||||||
// 检查是否在光标前有token需要删除
|
// 检查是否在光标前有token需要删除
|
||||||
const selection = window.getSelection();
|
const selection = window.getSelection();
|
||||||
|
@ -2123,8 +2157,10 @@ export default {
|
||||||
},
|
},
|
||||||
// 处理编辑器点击
|
// 处理编辑器点击
|
||||||
handleEditorClick(e, columnName, rowIndex) {
|
handleEditorClick(e, columnName, rowIndex) {
|
||||||
const editor = this.$refs["contentEditor" + columnName + rowIndex][0];
|
const refName = "contentEditor" + columnName + rowIndex;
|
||||||
this.currenrActiveNodeRef = "contentEditor" + columnName + rowIndex;
|
const editor = this.editorRefs[refName];
|
||||||
|
if (!editor) return;
|
||||||
|
this.currenrActiveNodeRef = refName;
|
||||||
editor.focus();
|
editor.focus();
|
||||||
this.saveRange();
|
this.saveRange();
|
||||||
},
|
},
|
||||||
|
@ -2135,7 +2171,9 @@ export default {
|
||||||
},
|
},
|
||||||
// 处理编辑器获得焦点
|
// 处理编辑器获得焦点
|
||||||
handleEditorFocus(e, columnName, rowIndex) {
|
handleEditorFocus(e, columnName, rowIndex) {
|
||||||
const editor = this.$refs["contentEditor" + columnName + rowIndex][0];
|
const refName = "contentEditor" + columnName + rowIndex;
|
||||||
|
const editor = this.editorRefs[refName];
|
||||||
|
if (!editor) return;
|
||||||
// 如果编辑器为空,设置光标到开始位置
|
// 如果编辑器为空,设置光标到开始位置
|
||||||
if (this.isEmpty(columnName, rowIndex)) {
|
if (this.isEmpty(columnName, rowIndex)) {
|
||||||
setTimeout(() => {
|
setTimeout(() => {
|
||||||
|
@ -2150,7 +2188,8 @@ export default {
|
||||||
},
|
},
|
||||||
// 判断当前编辑器是否为空
|
// 判断当前编辑器是否为空
|
||||||
isEmpty(columnName, rowIndex) {
|
isEmpty(columnName, rowIndex) {
|
||||||
const editor = this.$refs["contentEditor" + columnName + rowIndex][0];
|
const refName = "contentEditor" + columnName + rowIndex;
|
||||||
|
const editor = this.editorRefs[refName];
|
||||||
if (!editor) return true;
|
if (!editor) return true;
|
||||||
const content = editor.textContent.trim();
|
const content = editor.textContent.trim();
|
||||||
const hasTokens = editor.querySelectorAll(".content-token").length > 0;
|
const hasTokens = editor.querySelectorAll(".content-token").length > 0;
|
||||||
|
@ -2161,10 +2200,10 @@ export default {
|
||||||
// 可以在这里处理失去焦点的逻辑
|
// 可以在这里处理失去焦点的逻辑
|
||||||
},
|
},
|
||||||
handleClearNodeToEditor(columnName, rowIndex) {
|
handleClearNodeToEditor(columnName, rowIndex) {
|
||||||
const editor = this.$refs["contentEditor" + columnName + rowIndex][0];
|
const refName = "contentEditor" + columnName + rowIndex;
|
||||||
|
const editor = this.editorRefs[refName];
|
||||||
if (!editor) return;
|
if (!editor) return;
|
||||||
let nodeRef = "contentEditor" + columnName + rowIndex;
|
this.currenrActiveNodeRef = refName;
|
||||||
this.currenrActiveNodeRef = nodeRef;
|
|
||||||
|
|
||||||
editor.innerHTML = ""; // 先清空内容
|
editor.innerHTML = ""; // 先清空内容
|
||||||
this.$forceUpdate();
|
this.$forceUpdate();
|
||||||
|
@ -2187,15 +2226,14 @@ export default {
|
||||||
|
|
||||||
//添加节点
|
//添加节点
|
||||||
handleAddNodeToEditor(columnName, rowIndex) {
|
handleAddNodeToEditor(columnName, rowIndex) {
|
||||||
let nodeRef = "contentEditor" + columnName + rowIndex;
|
const refName = "contentEditor" + columnName + rowIndex;
|
||||||
this.currenrActiveNodeRef = nodeRef;
|
const editor = this.editorRefs[refName];
|
||||||
|
if (!editor) return;
|
||||||
|
this.currenrActiveNodeRef = refName;
|
||||||
this.representation = true;
|
this.representation = true;
|
||||||
this.TestResultDisplayArea = false;
|
this.TestResultDisplayArea = false;
|
||||||
this.representationActiveName = "first";
|
this.representationActiveName = "first";
|
||||||
|
|
||||||
// 这段代码的目的是 让光标停留在最后一个span标签后面
|
|
||||||
const editor = this.$refs[this.currenrActiveNodeRef][0];
|
|
||||||
if (!editor) return;
|
|
||||||
// 创建 range 和 selection
|
// 创建 range 和 selection
|
||||||
const range = document.createRange();
|
const range = document.createRange();
|
||||||
const selection = window.getSelection();
|
const selection = window.getSelection();
|
||||||
|
@ -2221,7 +2259,7 @@ export default {
|
||||||
insertToken(text, type) {
|
insertToken(text, type) {
|
||||||
if (!this.currenrActiveNodeRef) return;
|
if (!this.currenrActiveNodeRef) return;
|
||||||
|
|
||||||
const editor = this.$refs[this.currenrActiveNodeRef][0];
|
const editor = this.editorRefs[this.currenrActiveNodeRef];
|
||||||
if (!editor) return;
|
if (!editor) return;
|
||||||
|
|
||||||
// 确保编辑器有焦点
|
// 确保编辑器有焦点
|
||||||
|
@ -2289,7 +2327,7 @@ export default {
|
||||||
setCursorToEnd() {
|
setCursorToEnd() {
|
||||||
if (!this.currenrActiveNodeRef) return;
|
if (!this.currenrActiveNodeRef) return;
|
||||||
|
|
||||||
const editor = this.$refs[this.currenrActiveNodeRef][0];
|
const editor = this.editorRefs[this.currenrActiveNodeRef];
|
||||||
if (!editor) return;
|
if (!editor) return;
|
||||||
|
|
||||||
const range = document.createRange();
|
const range = document.createRange();
|
||||||
|
@ -2334,7 +2372,7 @@ export default {
|
||||||
setCursorToEnd() {
|
setCursorToEnd() {
|
||||||
// 清除之前的选中状态
|
// 清除之前的选中状态
|
||||||
if (!this.currenrActiveNodeRef) return;
|
if (!this.currenrActiveNodeRef) return;
|
||||||
const editor = this.$refs[this.currenrActiveNodeRef][0];
|
const editor = this.editorRefs[this.currenrActiveNodeRef];
|
||||||
if (!editor) return;
|
if (!editor) return;
|
||||||
|
|
||||||
const range = document.createRange();
|
const range = document.createRange();
|
||||||
|
@ -2353,7 +2391,7 @@ export default {
|
||||||
},
|
},
|
||||||
mounted() {
|
mounted() {
|
||||||
// 绑定事件监听器
|
// 绑定事件监听器
|
||||||
const editor = this.$refs[this.currenrActiveNodeRef]?.[0];
|
const editor = this.editorRefs[this.currenrActiveNodeRef];
|
||||||
if (editor) {
|
if (editor) {
|
||||||
editor.addEventListener("mouseup", this.saveRange);
|
editor.addEventListener("mouseup", this.saveRange);
|
||||||
editor.addEventListener("keyup", this.saveRange);
|
editor.addEventListener("keyup", this.saveRange);
|
||||||
|
@ -3304,6 +3342,33 @@ export default {
|
||||||
::v-deep .el-alert {
|
::v-deep .el-alert {
|
||||||
padding: 10px !important;
|
padding: 10px !important;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.tabs {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
height: 32px;
|
||||||
|
background: #fff;
|
||||||
|
border-radius: 4px;
|
||||||
|
padding: 2px;
|
||||||
|
width: fit-content;
|
||||||
|
margin-top: 10px;
|
||||||
|
|
||||||
|
.tabsItem {
|
||||||
|
height: 28px;
|
||||||
|
line-height: 28px;
|
||||||
|
background: #fff;
|
||||||
|
border-radius: 3px;
|
||||||
|
font-size: 14px;
|
||||||
|
color: #999;
|
||||||
|
padding: 0 10px;
|
||||||
|
cursor: pointer;
|
||||||
|
}
|
||||||
|
|
||||||
|
.active {
|
||||||
|
background: #f5f5f5;
|
||||||
|
color: #333;
|
||||||
|
}
|
||||||
|
}
|
||||||
</style>
|
</style>
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -389,45 +389,34 @@
|
||||||
></el-input>
|
></el-input>
|
||||||
</div>
|
</div>
|
||||||
</template>
|
</template>
|
||||||
|
<template
|
||||||
<!-- 字段 -->
|
v-if="
|
||||||
<template>
|
currentRowData.options &&
|
||||||
<div class="fixedChildTable">
|
currentRowData.options.appType != '9'
|
||||||
<el-collapse
|
|
||||||
v-model="activeNames"
|
|
||||||
v-if="outsideColumns.length > 0"
|
|
||||||
>
|
|
||||||
<el-collapse-item title="查询条件配置" name="1">
|
|
||||||
<el-form
|
|
||||||
ref="ColumnsForm"
|
|
||||||
label-width="80px"
|
|
||||||
label-position="top"
|
|
||||||
style="margin: 0 10px"
|
|
||||||
>
|
|
||||||
<div id="editorContainer">
|
|
||||||
<div
|
|
||||||
v-for="(row, rowIndex) in outsideColumns"
|
|
||||||
:key="rowIndex"
|
|
||||||
class="editorItem"
|
|
||||||
>
|
|
||||||
<el-form-item :label="row.column_name">
|
|
||||||
<div class="editor-container">
|
|
||||||
<div
|
|
||||||
class="content-editor"
|
|
||||||
:ref="
|
|
||||||
'contentEditor' +
|
|
||||||
row.column_name +
|
|
||||||
rowIndex
|
|
||||||
"
|
"
|
||||||
contenteditable="true"
|
>
|
||||||
></div>
|
<div class="tabs">
|
||||||
|
<div
|
||||||
|
class="tabsItem"
|
||||||
|
:class="{ active: parameterType === 'header' }"
|
||||||
|
@click="switchTabs('header')"
|
||||||
|
>
|
||||||
|
Headers入参
|
||||||
</div>
|
</div>
|
||||||
</el-form-item>
|
<div
|
||||||
|
class="tabsItem"
|
||||||
|
:class="{ active: parameterType === 'query' }"
|
||||||
|
@click="switchTabs('query')"
|
||||||
|
>
|
||||||
|
Query入参
|
||||||
</div>
|
</div>
|
||||||
|
<div
|
||||||
|
class="tabsItem"
|
||||||
|
:class="{ active: parameterType === 'body' }"
|
||||||
|
@click="switchTabs('body')"
|
||||||
|
>
|
||||||
|
Body入参
|
||||||
</div>
|
</div>
|
||||||
</el-form>
|
|
||||||
</el-collapse-item>
|
|
||||||
</el-collapse>
|
|
||||||
</div>
|
</div>
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
|
@ -472,6 +461,38 @@
|
||||||
></el-input>
|
></el-input>
|
||||||
</div>
|
</div>
|
||||||
</template>
|
</template>
|
||||||
|
<!-- 表字段展示 -->
|
||||||
|
<div class="fixedChildTable">
|
||||||
|
<!-- 表字段 -->
|
||||||
|
<el-collapse
|
||||||
|
v-model="activeNames"
|
||||||
|
v-if="outsideColumns.length > 0"
|
||||||
|
>
|
||||||
|
<el-collapse-item title="查询条件配置" name="1">
|
||||||
|
<el-form
|
||||||
|
ref="ColumnsForm"
|
||||||
|
label-width="80px"
|
||||||
|
label-position="top"
|
||||||
|
style="margin: 0 10px"
|
||||||
|
>
|
||||||
|
<div id="editorContainer">
|
||||||
|
<EditorItem
|
||||||
|
v-for="(row, index) in outsideColumns"
|
||||||
|
:key="index"
|
||||||
|
:row="row"
|
||||||
|
:row-index="index"
|
||||||
|
@register-editor="registerEditorRef"
|
||||||
|
ref="editorRefs"
|
||||||
|
ref-in-for
|
||||||
|
:viewFlag="true"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
</el-form>
|
||||||
|
</el-collapse-item>
|
||||||
|
</el-collapse>
|
||||||
|
|
||||||
|
<el-empty v-else description="暂无数据"></el-empty>
|
||||||
|
</div>
|
||||||
</template>
|
</template>
|
||||||
</div>
|
</div>
|
||||||
<!-- 操作展示 End -->
|
<!-- 操作展示 End -->
|
||||||
|
@ -513,6 +534,70 @@
|
||||||
spanWidth="80px"
|
spanWidth="80px"
|
||||||
>
|
>
|
||||||
</base-form>
|
</base-form>
|
||||||
|
<div class="globelTitle">运行记录</div>
|
||||||
|
<div class="OperationRecords">
|
||||||
|
<div
|
||||||
|
class="totalItem"
|
||||||
|
:class="OperationRecordsIndex == 2 ? 'active' : ''"
|
||||||
|
@click="RecordsChange(2)"
|
||||||
|
>
|
||||||
|
<span>总记录</span>
|
||||||
|
<span>{{
|
||||||
|
OperationRecords.total ? OperationRecords.total : 0
|
||||||
|
}}</span>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="totalItem"
|
||||||
|
:class="OperationRecordsIndex == 1 ? 'active' : ''"
|
||||||
|
@click="RecordsChange(1)"
|
||||||
|
>
|
||||||
|
<span>运行成功</span>
|
||||||
|
<span style="color: #00d104">{{
|
||||||
|
OperationRecords.success ? OperationRecords.success : 0
|
||||||
|
}}</span>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="totalItem"
|
||||||
|
:class="OperationRecordsIndex == 0 ? 'active' : ''"
|
||||||
|
@click="RecordsChange(0)"
|
||||||
|
>
|
||||||
|
<span>运行失败</span>
|
||||||
|
<span style="color: #fa0101">
|
||||||
|
{{
|
||||||
|
OperationRecords.error ? OperationRecords.error : 0
|
||||||
|
}}</span
|
||||||
|
>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div id="overProjectChart" class="pie"></div>
|
||||||
|
<div class="globelTitle">关联账户</div>
|
||||||
|
<div
|
||||||
|
class="userContentBox"
|
||||||
|
v-for="(item, index) in RelatedAccounts"
|
||||||
|
>
|
||||||
|
<div class="userItem">
|
||||||
|
<div class="userName">
|
||||||
|
{{ item.accountName }}
|
||||||
|
</div>
|
||||||
|
<div class="status">
|
||||||
|
<div
|
||||||
|
v-if="item.authenticationState == 1"
|
||||||
|
class="successBox"
|
||||||
|
>
|
||||||
|
验证成功
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
v-else-if="item.authenticationState == 2"
|
||||||
|
class="redBox"
|
||||||
|
>
|
||||||
|
验证失败
|
||||||
|
</div>
|
||||||
|
<div v-else="!item.authenticationState" class="redBox">
|
||||||
|
未验证
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</el-tab-pane>
|
</el-tab-pane>
|
||||||
|
@ -529,8 +614,9 @@ import FishCrontab from "fish-crontab";
|
||||||
import * as echarts from "echarts";
|
import * as echarts from "echarts";
|
||||||
import { authApi } from "@/api/apis/auth";
|
import { authApi } from "@/api/apis/auth";
|
||||||
import baseForm from "@/components/base/baseNewForm";
|
import baseForm from "@/components/base/baseNewForm";
|
||||||
|
import EditorItem from "./EditorItem.vue";
|
||||||
export default {
|
export default {
|
||||||
components: { FishCrontab, baseRightDialog, baseForm },
|
components: { FishCrontab, baseRightDialog, baseForm, EditorItem },
|
||||||
data() {
|
data() {
|
||||||
return {
|
return {
|
||||||
examineOperateDialog: false,
|
examineOperateDialog: false,
|
||||||
|
@ -617,6 +703,19 @@ export default {
|
||||||
rowNum: "1",
|
rowNum: "1",
|
||||||
pageLimit: "100",
|
pageLimit: "100",
|
||||||
},
|
},
|
||||||
|
|
||||||
|
parameterType: "body", //参数类型
|
||||||
|
|
||||||
|
editorRefs: {}, // 用来保存所有子组件的 editor DOM
|
||||||
|
|
||||||
|
// 运行记录
|
||||||
|
OperationRecords: {
|
||||||
|
total: 0,
|
||||||
|
success: 0,
|
||||||
|
error: 0,
|
||||||
|
},
|
||||||
|
OperationRecordsIndex: 2,
|
||||||
|
RelatedAccounts: [], //场景下关联的所有账户
|
||||||
};
|
};
|
||||||
},
|
},
|
||||||
methods: {
|
methods: {
|
||||||
|
@ -638,6 +737,7 @@ export default {
|
||||||
}
|
}
|
||||||
this.formRowData = formRow;
|
this.formRowData = formRow;
|
||||||
this.$refs.senceForm.choiceAssignment(formRow);
|
this.$refs.senceForm.choiceAssignment(formRow);
|
||||||
|
await this.GetSceneLog7Days();
|
||||||
await this.GetSceneStepList();
|
await this.GetSceneStepList();
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
@ -713,8 +813,14 @@ export default {
|
||||||
// 更新当前选中的步骤索引
|
// 更新当前选中的步骤索引
|
||||||
this.currentRowData = rowData;
|
this.currentRowData = rowData;
|
||||||
this.drawSelectIndex = index;
|
this.drawSelectIndex = index;
|
||||||
|
// 用来保存所有子组件的 editor DOM
|
||||||
|
this.editorRefs = {};
|
||||||
|
this.parameterType = "body";
|
||||||
this.GetSceneStepData();
|
this.GetSceneStepData();
|
||||||
},
|
},
|
||||||
|
registerEditorRef(refName, dom) {
|
||||||
|
this.$set(this.editorRefs, refName, dom);
|
||||||
|
},
|
||||||
/**
|
/**
|
||||||
* 获取场景步骤数据
|
* 获取场景步骤数据
|
||||||
*/
|
*/
|
||||||
|
@ -759,10 +865,52 @@ export default {
|
||||||
) {
|
) {
|
||||||
this.queryColumns();
|
this.queryColumns();
|
||||||
}
|
}
|
||||||
|
// 非数据库应用
|
||||||
|
if (
|
||||||
|
this.currentRowData.options.apiId &&
|
||||||
|
this.currentRowData.options.appType != "9"
|
||||||
|
) {
|
||||||
|
this.queryApiConfig();
|
||||||
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
switchTabs(val) {
|
||||||
|
this.parameterType = val;
|
||||||
|
// 非数据库应用
|
||||||
|
if (this.currentRowData.options.appType != "9") {
|
||||||
|
this.queryApiConfig("tab");
|
||||||
|
}
|
||||||
|
},
|
||||||
|
// 获取表字段
|
||||||
|
async queryApiConfig(type) {
|
||||||
|
if (!this.currentRowData.options.apiId) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
this.outsideColumns = [];
|
||||||
|
let params = {
|
||||||
|
stepId: this.currentRowData.options.stepID, //账户id
|
||||||
|
apiId: this.currentRowData.options.apiId,
|
||||||
|
type: this.parameterType,
|
||||||
|
};
|
||||||
|
let res = await authApi(
|
||||||
|
"sysFlowStepApiConfigService",
|
||||||
|
"",
|
||||||
|
"queryApiConfig",
|
||||||
|
"",
|
||||||
|
params
|
||||||
|
);
|
||||||
|
this.drawMask = false;
|
||||||
|
if (res.status == "200") {
|
||||||
|
this.outsideColumns = res.attribute || [];
|
||||||
|
this.$nextTick(() => {
|
||||||
|
if (type == "tab") {
|
||||||
|
this.getStepConfig();
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
},
|
||||||
// 获取表字段
|
// 获取表字段
|
||||||
async queryColumns() {
|
async queryColumns() {
|
||||||
this.outsideColumns = [];
|
this.outsideColumns = [];
|
||||||
|
@ -802,15 +950,29 @@ export default {
|
||||||
params
|
params
|
||||||
);
|
);
|
||||||
if (res.status == "200") {
|
if (res.status == "200") {
|
||||||
const root = document.querySelector("#editorContainer");
|
let detailList = [];
|
||||||
if (
|
if (
|
||||||
res.attribute &&
|
this.currentRowData.options.appType &&
|
||||||
res.attribute.detailList &&
|
this.currentRowData.options.appType == "9"
|
||||||
res.attribute.detailList.length > 0
|
|
||||||
) {
|
) {
|
||||||
res.attribute.detailList.forEach((item) => {
|
detailList = res.attribute?.detailList || [];
|
||||||
this.matchEditorItems(root, item.fieldName, item.html_label);
|
} else {
|
||||||
});
|
if (this.parameterType == "body") {
|
||||||
|
detailList = res.attribute?.bodyIn
|
||||||
|
? JSON.parse(res.attribute.bodyIn)
|
||||||
|
: [];
|
||||||
|
} else if (this.parameterType == "header") {
|
||||||
|
detailList = res.attribute?.headerIn
|
||||||
|
? JSON.parse(res.attribute.headerIn)
|
||||||
|
: [];
|
||||||
|
} else if (this.parameterType == "query") {
|
||||||
|
detailList = res.attribute?.queryIn
|
||||||
|
? JSON.parse(res.attribute.queryIn)
|
||||||
|
: [];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (detailList.length > 0) {
|
||||||
|
this.recursivelyApplyHtmlLabel(this.outsideColumns, detailList);
|
||||||
}
|
}
|
||||||
if (
|
if (
|
||||||
this.currentRowData.options &&
|
this.currentRowData.options &&
|
||||||
|
@ -822,16 +984,93 @@ export default {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
matchEditorItems(rootElement, rootName, rootHtml) {
|
// 匹配数据
|
||||||
const items = rootElement.querySelectorAll(".editorItem");
|
recursivelyApplyHtmlLabel(columns, detailList, path = []) {
|
||||||
items.forEach((item) => {
|
columns.forEach((col, index) => {
|
||||||
const fieldName =
|
const match = detailList.find(
|
||||||
item.querySelector(".el-form-item__label")?.innerText.trim() || "";
|
(item) => item.fieldName === col.column_name
|
||||||
const editor = item.querySelector(".content-editor");
|
);
|
||||||
if (!editor) return;
|
if (match && match.html_label) {
|
||||||
if (rootName == fieldName) {
|
this.matchEditorItems(match, index, path);
|
||||||
editor.innerHTML = rootHtml;
|
|
||||||
}
|
}
|
||||||
|
if (
|
||||||
|
col.children &&
|
||||||
|
col.children.length > 0 &&
|
||||||
|
match.children &&
|
||||||
|
match.children.length > 0
|
||||||
|
) {
|
||||||
|
this.recursivelyApplyHtmlLabel(col.children, match.children, [
|
||||||
|
...path,
|
||||||
|
index,
|
||||||
|
]);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
},
|
||||||
|
// 回显
|
||||||
|
matchEditorItems(match, index, path = []) {
|
||||||
|
const refName =
|
||||||
|
"contentEditor" + match.fieldName + [...path, index].join("-");
|
||||||
|
// 这里获取ref
|
||||||
|
const refEl = this.editorRefs[refName];
|
||||||
|
if (match && match.html_label && refEl) {
|
||||||
|
// 可能refEl是数组,取第一个元素
|
||||||
|
if (Array.isArray(refEl)) {
|
||||||
|
refEl[0].innerHTML = match.html_label;
|
||||||
|
} else if (refEl instanceof HTMLElement) {
|
||||||
|
refEl.innerHTML = match.html_label;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
// 场景记录改变
|
||||||
|
RecordsChange(type) {
|
||||||
|
this.OperationRecordsIndex = type;
|
||||||
|
},
|
||||||
|
// 获取最近7天运行统计
|
||||||
|
async GetSceneLog7Days() {
|
||||||
|
// let params = {
|
||||||
|
// sceneID: this.sceneID,
|
||||||
|
// isSuccess: this.flagRecordsIndex,
|
||||||
|
// };
|
||||||
|
// if (this.flagRecordsIndex == 2) {
|
||||||
|
// params.isSuccess = "";
|
||||||
|
// }
|
||||||
|
// let res = await GetSceneLog7Days(params);
|
||||||
|
// if (res.code == 1) {
|
||||||
|
let data = [];
|
||||||
|
let xData = [];
|
||||||
|
let yData = [];
|
||||||
|
data.forEach((item) => {
|
||||||
|
xData.push(item.column1);
|
||||||
|
yData.push(item.allCount);
|
||||||
|
});
|
||||||
|
this.renderChart(yData, xData);
|
||||||
|
// }
|
||||||
|
},
|
||||||
|
renderChart(data = [], xData = []) {
|
||||||
|
const option = {
|
||||||
|
tooltip: {
|
||||||
|
trigger: "axis",
|
||||||
|
},
|
||||||
|
xAxis: {
|
||||||
|
type: "category",
|
||||||
|
data: xData,
|
||||||
|
},
|
||||||
|
yAxis: {
|
||||||
|
type: "value",
|
||||||
|
},
|
||||||
|
series: [
|
||||||
|
{
|
||||||
|
name: "",
|
||||||
|
type: "line",
|
||||||
|
data: data,
|
||||||
|
},
|
||||||
|
],
|
||||||
|
};
|
||||||
|
this.$nextTick(() => {
|
||||||
|
const chartContainer = document.getElementById("overProjectChart");
|
||||||
|
const chart = echarts.init(chartContainer);
|
||||||
|
this.chartData = chart;
|
||||||
|
chart.setOption(option);
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
// 发布场景
|
// 发布场景
|
||||||
|
@ -1762,4 +2001,39 @@ export default {
|
||||||
::v-deep .el-form-item {
|
::v-deep .el-form-item {
|
||||||
margin-bottom: 0;
|
margin-bottom: 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.tabs {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
height: 32px;
|
||||||
|
background: #fff;
|
||||||
|
border-radius: 4px;
|
||||||
|
padding: 2px;
|
||||||
|
width: fit-content;
|
||||||
|
margin: 10px 0;
|
||||||
|
|
||||||
|
.tabsItem {
|
||||||
|
height: 28px;
|
||||||
|
line-height: 28px;
|
||||||
|
background: #fff;
|
||||||
|
border-radius: 3px;
|
||||||
|
font-size: 14px;
|
||||||
|
color: #999;
|
||||||
|
padding: 0 10px;
|
||||||
|
cursor: pointer;
|
||||||
|
}
|
||||||
|
|
||||||
|
.active {
|
||||||
|
background: #f5f5f5;
|
||||||
|
color: #333;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
::v-deep .el-collapse-item__header {
|
||||||
|
padding-left: 10px !important;
|
||||||
|
}
|
||||||
|
.pie {
|
||||||
|
height: 300px;
|
||||||
|
padding-bottom: 10px;
|
||||||
|
}
|
||||||
|
|
||||||
</style>
|
</style>
|
||||||
|
|
Loading…
Reference in New Issue