mirror of
https://github.com/dataease/dataease.git
synced 2026-05-20 19:48:18 +08:00
feat: 数据同步 定时报告 优化
This commit is contained in:
@@ -61,8 +61,11 @@
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import msgCfm from "@/components/msgCfm/index";
|
||||
|
||||
export default {
|
||||
name: "TemplateList",
|
||||
mixins: [msgCfm],
|
||||
components: {},
|
||||
props: {
|
||||
templateType: {
|
||||
@@ -119,22 +122,13 @@ export default {
|
||||
this.$emit("showTemplateEditDialog", "new");
|
||||
},
|
||||
templateDelete(template) {
|
||||
this.$alert(
|
||||
this.$t("panel.confirm_delete") +
|
||||
this.$t("panel.category") +
|
||||
": " +
|
||||
template.name +
|
||||
"?",
|
||||
"",
|
||||
{
|
||||
confirmButtonText: this.$t("panel.confirm_delete"),
|
||||
callback: (action) => {
|
||||
if (action === "confirm") {
|
||||
this.$emit("templateDelete", template.id);
|
||||
}
|
||||
},
|
||||
}
|
||||
);
|
||||
const options = {
|
||||
title: 'system_parameter_setting.delete_this_category',
|
||||
content: 'system_parameter_setting.also_be_deleted',
|
||||
type: "primary",
|
||||
cb: () => this.$emit("templateDelete", template.id),
|
||||
};
|
||||
this.handlerConfirm(options);
|
||||
},
|
||||
templateEdit(template) {
|
||||
this.$emit("templateEdit", template);
|
||||
|
||||
@@ -208,29 +208,12 @@ export default {
|
||||
}
|
||||
},
|
||||
templateDeleteConfirm(template) {
|
||||
// const options = {
|
||||
// title: 'jkjhjjhhkh',
|
||||
// showCancelButton: false,
|
||||
// type: 'primary',
|
||||
// }
|
||||
// this.handlerConfirm(options);
|
||||
// return
|
||||
this.$alert(
|
||||
this.$t("panel.confirm_delete") +
|
||||
this.$t("panel.template") +
|
||||
": " +
|
||||
this.template.name +
|
||||
"?",
|
||||
"",
|
||||
{
|
||||
confirmButtonText: this.$t("panel.confirm"),
|
||||
callback: (action) => {
|
||||
if (action === "confirm") {
|
||||
this.templateDelete(template.id);
|
||||
}
|
||||
},
|
||||
}
|
||||
);
|
||||
const options = {
|
||||
title: 'system_parameter_setting.delete_this_template',
|
||||
type: "primary",
|
||||
cb: () => this.templateDelete(template.id),
|
||||
};
|
||||
this.handlerConfirm(options);
|
||||
},
|
||||
handleClick(tab, event) {
|
||||
this.getTree();
|
||||
@@ -247,11 +230,7 @@ export default {
|
||||
templateDelete(id) {
|
||||
if (id) {
|
||||
templateDelete(id).then((response) => {
|
||||
this.$message({
|
||||
message: this.$t("commons.delete_success"),
|
||||
type: "success",
|
||||
showClose: true,
|
||||
});
|
||||
this.openMessageSuccess('commons.delete_success');
|
||||
this.getTree();
|
||||
});
|
||||
}
|
||||
|
||||
@@ -258,9 +258,9 @@ export default {
|
||||
z-index: 10;
|
||||
}
|
||||
|
||||
.el-radio {
|
||||
margin-right: 0;
|
||||
width: 156px;
|
||||
}
|
||||
.el-radio:not(:last-child) {
|
||||
margin-right: 0;
|
||||
width: 156px;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
268
frontend/src/views/system/task/TableSelector.vue
Normal file
268
frontend/src/views/system/task/TableSelector.vue
Normal file
@@ -0,0 +1,268 @@
|
||||
<template>
|
||||
<el-dialog
|
||||
:title="$t('chart.select_dataset')"
|
||||
:visible.sync="selectDatasetFlag"
|
||||
width="1200px"
|
||||
class="de-dialog-form"
|
||||
append-to-body
|
||||
>
|
||||
<div class="dataset-task-table">
|
||||
<div class="dataset-tree">
|
||||
<el-input
|
||||
v-model="filterText"
|
||||
size="mini"
|
||||
:placeholder="$t('commons.search')"
|
||||
prefix-icon="el-icon-search"
|
||||
clearable
|
||||
/>
|
||||
<div class="tree" v-loading="treeLoading">
|
||||
<el-tree
|
||||
ref="datasetTreeRef"
|
||||
current-node-key="id"
|
||||
:data="treeData"
|
||||
node-key="id"
|
||||
highlight-current
|
||||
:expand-on-click-node="true"
|
||||
:filter-node-method="filterNode"
|
||||
@node-click="nodeClick"
|
||||
>
|
||||
<span slot-scope="{ data }" class="custom-tree-node">
|
||||
<span v-if="data.modelInnerType === 'group'">
|
||||
<svg-icon icon-class="scene" class="ds-icon-scene" />
|
||||
<span
|
||||
style="
|
||||
margin-left: 6px;
|
||||
white-space: nowrap;
|
||||
overflow: hidden;
|
||||
text-overflow: ellipsis;
|
||||
"
|
||||
:title="data.name"
|
||||
>{{ data.name }}</span
|
||||
>
|
||||
</span>
|
||||
<span v-else>
|
||||
<span>
|
||||
<svg-icon
|
||||
:icon-class="`ds-${data.modelInnerType}`"
|
||||
:class="`ds-icon-${data.modelInnerType}`"
|
||||
/>
|
||||
</span>
|
||||
<span
|
||||
style="
|
||||
margin-left: 6px;
|
||||
white-space: nowrap;
|
||||
overflow: hidden;
|
||||
text-overflow: ellipsis;
|
||||
"
|
||||
:title="data.name"
|
||||
>{{ data.name }}</span
|
||||
>
|
||||
</span>
|
||||
</span>
|
||||
</el-tree>
|
||||
</div>
|
||||
</div>
|
||||
<div v-loading="dataLoading" class="dataset-tree-table">
|
||||
<p v-if="tableName" class="table-name">
|
||||
{{ tableName }} <span>{{ $t("chart.preview_100_data") }}</span>
|
||||
</p>
|
||||
<el-table border v-if="table.length" style="width: 100%" :data="table">
|
||||
<el-table-column
|
||||
v-for="field in fields"
|
||||
:key="field.dataeaseName"
|
||||
min-width="200"
|
||||
:prop="field.dataeaseName"
|
||||
:resizable="true"
|
||||
>
|
||||
<template slot="header">
|
||||
<svg-icon
|
||||
:icon-class="iconFormate(field.deType).iconClass"
|
||||
:class="iconFormate(field.deType).class"
|
||||
/>
|
||||
<span>{{ field.name }}</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
</el-table>
|
||||
<el-empty v-else :description="$t('暂无数据')"></el-empty>
|
||||
</div>
|
||||
</div>
|
||||
<div slot="footer" class="dialog-footer">
|
||||
<deBtn secondary @click="selectDatasetFlag = false">{{
|
||||
$t("chart.cancel")
|
||||
}}</deBtn>
|
||||
<deBtn @click="setIdName" :disabled="!tableName" type="primary">{{
|
||||
$t("fu.table.ok")
|
||||
}}</deBtn>
|
||||
</div>
|
||||
</el-dialog>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { queryAuthModel } from "@/api/authModel/authModel";
|
||||
import { post } from "@/api/dataset/dataset";
|
||||
|
||||
export default {
|
||||
props: {
|
||||
customType: {
|
||||
type: Array,
|
||||
required: false,
|
||||
default: null,
|
||||
},
|
||||
mode: {
|
||||
type: Number,
|
||||
required: false,
|
||||
default: -1,
|
||||
},
|
||||
privileges: {
|
||||
type: String,
|
||||
required: false,
|
||||
default: "use",
|
||||
},
|
||||
clearEmptyDir: {
|
||||
type: Boolean,
|
||||
required: false,
|
||||
default: false,
|
||||
},
|
||||
},
|
||||
watch: {
|
||||
filterText(val) {
|
||||
this.$refs.datasetTreeRef.filter(val);
|
||||
},
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
selectDatasetFlag: false,
|
||||
tableName: "",
|
||||
tableId: "",
|
||||
treeData: [],
|
||||
table: [],
|
||||
filterText: "",
|
||||
fields: [],
|
||||
tableName: "",
|
||||
dataLoading: false,
|
||||
treeLoading: false,
|
||||
};
|
||||
},
|
||||
mounted() {
|
||||
this.treeNode();
|
||||
},
|
||||
methods: {
|
||||
iconFormate(deType) {
|
||||
const val = ["text", "time", "value", "value", "location"][deType];
|
||||
return {
|
||||
class: `field-icon-${val}`,
|
||||
iconClass: `field_${val}`,
|
||||
};
|
||||
},
|
||||
treeNode() {
|
||||
this.treeLoading = true;
|
||||
const modelInnerTypeArray = Array.isArray(this.customType)
|
||||
? [...this.customType, "group"]
|
||||
: null;
|
||||
queryAuthModel(
|
||||
{
|
||||
modelType: "dataset",
|
||||
privileges: this.privileges,
|
||||
datasetMode: this.mode,
|
||||
clearEmptyDir: this.clearEmptyDir,
|
||||
mode: this.mode < 0 ? null : this.mode,
|
||||
modelInnerTypeArray,
|
||||
},
|
||||
true
|
||||
)
|
||||
.then((res) => {
|
||||
this.treeData = res.data;
|
||||
})
|
||||
.finally(() => {
|
||||
this.treeLoading = false;
|
||||
});
|
||||
},
|
||||
filterNode(value, data) {
|
||||
if (!value) return true;
|
||||
return data.label.indexOf(value) !== -1;
|
||||
},
|
||||
initData(table) {
|
||||
this.dataLoading = true;
|
||||
table.row = 100;
|
||||
post("/dataset/table/getPreviewData/1/100", table, false, 30000)
|
||||
.then((response) => {
|
||||
this.fields = response.data.fields;
|
||||
this.table = response.data.data;
|
||||
})
|
||||
.finally((res) => {
|
||||
this.dataLoading = false;
|
||||
});
|
||||
},
|
||||
init() {
|
||||
this.tableName = "";
|
||||
this.tableId = "";
|
||||
this.selectDatasetFlag = true;
|
||||
},
|
||||
setIdName() {
|
||||
this.$emit("getTableId", this.tableId, this.tableName);
|
||||
this.selectDatasetFlag = false;
|
||||
},
|
||||
nodeClick(data) {
|
||||
const { id, name, modelInnerType: type } = data;
|
||||
if (type === "group") return;
|
||||
this.tableName = name;
|
||||
this.tableId = id;
|
||||
this.initData(data);
|
||||
},
|
||||
},
|
||||
};
|
||||
</script>
|
||||
|
||||
<style lang="scss">
|
||||
.dataset-task-table {
|
||||
box-sizing: border-box;
|
||||
height: 628px;
|
||||
border: 1px solid #dee0e3;
|
||||
border-radius: 4px;
|
||||
display: flex;
|
||||
max-height: 628px;
|
||||
.el-tree-node__content {
|
||||
height: 40px;
|
||||
border-radius: 4px;
|
||||
&:hover {
|
||||
background-color: var(--deWhiteHover, #3370ff) !important;
|
||||
.custom-tree-node {
|
||||
color: var(--primary, #3370ff);
|
||||
}
|
||||
}
|
||||
}
|
||||
.dataset-tree {
|
||||
width: 253px;
|
||||
border-right: 1px solid #dee0e3;
|
||||
padding: 16px;
|
||||
|
||||
.tree {
|
||||
padding-top: 16px;
|
||||
overflow-y: auto;
|
||||
height: calc(100% - 30px);
|
||||
}
|
||||
}
|
||||
.dataset-tree-table {
|
||||
flex: 1;
|
||||
padding: 16px;
|
||||
overflow-y: auto;
|
||||
.table-name {
|
||||
margin: 0;
|
||||
margin-bottom: 16px;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: space-between;
|
||||
font-family: PingFang SC;
|
||||
font-size: 16px;
|
||||
font-weight: 500;
|
||||
line-height: 24px;
|
||||
color: var(--deTextPrimary, #000000);
|
||||
span {
|
||||
font-size: 14px;
|
||||
font-weight: 400;
|
||||
color: #646a73;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
||||
@@ -1,8 +1,66 @@
|
||||
<template>
|
||||
<el-col>
|
||||
<el-row v-loading="$store.getters.loadingMap[$store.getters.currentPath]" style="margin-top: 10px;">
|
||||
<complex-table :data="data" :columns="columns" local-key="datasetTaskRecord" :search-config="searchConfig" :trans-condition="transCondition" :pagination-config="paginationConfig" @select="select" @search="search" @sort-change="sortChange">
|
||||
<el-table-column prop="name" :label="$t('dataset.task_name')">
|
||||
<div class="dataset-on-time">
|
||||
<el-row class="top-operate">
|
||||
<el-col :span="10">
|
||||
<deBtn
|
||||
secondary
|
||||
>{{ $t("zip.export") }}</deBtn
|
||||
>
|
||||
</el-col>
|
||||
<el-col :span="14" class="right-user">
|
||||
<el-input
|
||||
:placeholder="$t('通过任务名称搜索')"
|
||||
prefix-icon="el-icon-search"
|
||||
class="name-email-search"
|
||||
size="small"
|
||||
clearable
|
||||
ref="search"
|
||||
v-model="nikeName"
|
||||
@blur="initSearch"
|
||||
@clear="initSearch"
|
||||
>
|
||||
</el-input>
|
||||
<deBtn
|
||||
:secondary="!cacheCondition.length"
|
||||
:plain="!!cacheCondition.length"
|
||||
icon="iconfont icon-icon-filter"
|
||||
@click="filterShow"
|
||||
>{{ $t("user.filter")
|
||||
}}<template v-if="filterTexts.length">
|
||||
({{ cacheCondition.length }})
|
||||
</template>
|
||||
</deBtn>
|
||||
</el-col>
|
||||
</el-row>
|
||||
<div class="filter-texts" v-if="filterTexts.length">
|
||||
<span class="sum">{{ paginationConfig.total }}</span>
|
||||
<span class="title">{{$t('user.result_one')}}</span>
|
||||
<el-divider direction="vertical"></el-divider>
|
||||
<i @click="scrollPre" v-if="showScroll" class="el-icon-arrow-left arrow-filter"></i>
|
||||
<div class="filter-texts-container">
|
||||
<p class="text" v-for="(ele, index) in filterTexts" :key="ele">
|
||||
{{ ele }} <i @click="clearOneFilter(index)" class="el-icon-close"></i>
|
||||
</p>
|
||||
</div>
|
||||
<i @click="scrollNext" v-if="showScroll" class="el-icon-arrow-right arrow-filter"></i>
|
||||
<el-button
|
||||
type="text"
|
||||
class="clear-btn"
|
||||
icon="el-icon-delete"
|
||||
@click="clearFilter"
|
||||
>{{$t('user.clear_filter')}}</el-button
|
||||
>
|
||||
</div>
|
||||
<div id="resize-for-filter" class="table-container">
|
||||
<grid-table
|
||||
v-loading="$store.getters.loadingMap[$store.getters.currentPath]"
|
||||
:tableData="data"
|
||||
:columns="[]"
|
||||
:pagination="paginationConfig"
|
||||
@size-change="handleSizeChange"
|
||||
@current-change="handleCurrentChange"
|
||||
>
|
||||
<el-table-column prop="name" :label="$t('dataset.task_name')">
|
||||
<template slot-scope="scope">
|
||||
<span>
|
||||
<el-link :type="matchLogId && scope.row.id === matchLogId ? 'danger': ''" style="font-size: 12px" @click="jumpTask(scope.row)">{{ scope.row.name }}</el-link>
|
||||
@@ -23,44 +81,48 @@
|
||||
|
||||
<el-table-column prop="status" :label="$t('dataset.status')">
|
||||
<template slot-scope="scope">
|
||||
<span v-if="scope.row.status === 'Completed'" style="color: green">{{ $t('dataset.completed') }}</span>
|
||||
<span v-if="scope.row.status === 'Underway'" class="blue-color">
|
||||
<i class="el-icon-loading" />
|
||||
{{ $t('dataset.underway') }}
|
||||
</span>
|
||||
<span v-if="scope.row.status === 'Error'" style="color: red">
|
||||
<el-link type="danger" style="font-size: 12px" @click="showErrorMassage(scope.row.info)">{{ $t('dataset.error') }}</el-link>
|
||||
<span :class="[`de-${scope.row.status}`, 'de-status']"
|
||||
>{{
|
||||
$t(`dataset.${scope.row.status.toLocaleLowerCase()}`)
|
||||
}}
|
||||
<i
|
||||
v-if="scope.row.status === 'Error'"
|
||||
class="el-icon-question"
|
||||
@click="showErrorMassage(scope.row.msg)"
|
||||
></i>
|
||||
</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
</complex-table>
|
||||
</el-row>
|
||||
</grid-table>
|
||||
<keep-alive>
|
||||
<filterUser ref="filterUser" @search="filterDraw"></filterUser>
|
||||
</keep-alive>
|
||||
</div>
|
||||
<el-dialog
|
||||
v-dialogDrag
|
||||
:title="$t('dataset.detail')"
|
||||
:visible="show_error_massage"
|
||||
:show-close="false"
|
||||
width="50%"
|
||||
class="dialog-css"
|
||||
:title="$t('dataset.error') + $t('dataset.detail')"
|
||||
:visible.sync="show_error_massage"
|
||||
width="600px"
|
||||
class="de-dialog-form"
|
||||
>
|
||||
<span class="err-msg">{{ error_massage }}</span>
|
||||
<span slot="footer" class="dialog-footer">
|
||||
<el-button size="mini" @click="show_error_massage = false">{{ $t('dataset.close') }}</el-button>
|
||||
<deBtn secondary @click="show_error_massage = false">{{ $t('dataset.close') }}</deBtn>
|
||||
</span>
|
||||
</el-dialog>
|
||||
</el-col>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import ComplexTable from '@/components/business/complex-table'
|
||||
import { formatCondition, formatQuickCondition, addOrder, formatOrders } from '@/utils/index'
|
||||
import '@riophae/vue-treeselect/dist/vue-treeselect.css'
|
||||
import { formatOrders } from '@/utils/index'
|
||||
import { post } from '@/api/dataset/dataset'
|
||||
import { loadMenus } from '@/permission'
|
||||
import GridTable from "@/components/gridTable/index.vue";
|
||||
import filterUser from "./filterUserRecord.vue";
|
||||
import _ from 'lodash';
|
||||
|
||||
export default {
|
||||
name: 'TaskRecord',
|
||||
components: { ComplexTable },
|
||||
components: { GridTable, filterUser },
|
||||
props: {
|
||||
param: {
|
||||
type: Object,
|
||||
@@ -73,48 +135,18 @@ export default {
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
header: '',
|
||||
columns: [],
|
||||
buttons: [
|
||||
{
|
||||
label: this.$t('commons.edit'), icon: 'el-icon-edit', type: 'primary', click: this.edit,
|
||||
show: this.checkPermission(['user:edit'])
|
||||
}
|
||||
],
|
||||
searchConfig: {
|
||||
useQuickSearch: true,
|
||||
useComplexSearch: true,
|
||||
quickPlaceholder: this.$t('dataset.task.search_by_name'),
|
||||
components: [
|
||||
{ field: 'dataset_table_task.name', label: this.$t('dataset.task_name'), component: 'FuComplexInput' },
|
||||
{ field: 'dataset_table_task.id', label: this.$t('dataset.task_id'), component: 'FuComplexInput' },
|
||||
{ field: 'dataset_table.name', label: this.$t('dataset.name'), component: 'DeComplexInput' },
|
||||
{ field: 'dataset_table_task_log.status', label: this.$t('commons.status'), component: 'FuComplexSelect', options: [{ label: this.$t('dataset.completed'), value: 'Completed' }, { label: this.$t('dataset.underway'), value: 'Underway' }, { label: this.$t('dataset.error'), value: 'Error' }], multiple: false }
|
||||
]
|
||||
},
|
||||
nikeName: '',
|
||||
showScroll: false,
|
||||
filterTexts: [],
|
||||
cacheCondition: [],
|
||||
paginationConfig: {
|
||||
currentPage: 1,
|
||||
pageSize: 10,
|
||||
total: 0
|
||||
},
|
||||
data: [],
|
||||
dialogVisible: false,
|
||||
editPasswordVisible: false,
|
||||
form: {
|
||||
roles: [{
|
||||
id: ''
|
||||
}]
|
||||
},
|
||||
checkPasswordForm: {},
|
||||
ruleForm: {},
|
||||
defaultForm: { id: null, username: null, nickName: null, gender: '男', email: null, enabled: 1, deptId: null, phone: null },
|
||||
depts: null,
|
||||
roles: [],
|
||||
roleDatas: [],
|
||||
userRoles: [],
|
||||
formType: 'add',
|
||||
orderConditions: [],
|
||||
last_condition: null,
|
||||
show_error_massage: false,
|
||||
error_massage: '',
|
||||
matchLogId: null,
|
||||
@@ -133,14 +165,72 @@ export default {
|
||||
}
|
||||
this.createTimer()
|
||||
},
|
||||
mounted() {
|
||||
this.resizeObserver();
|
||||
},
|
||||
watch: {
|
||||
filterTexts: {
|
||||
handler() {
|
||||
this.getScrollStatus();
|
||||
},
|
||||
deep: true,
|
||||
},
|
||||
},
|
||||
beforeDestroy() {
|
||||
this.destroyTimer()
|
||||
},
|
||||
methods: {
|
||||
getScrollStatus() {
|
||||
this.$nextTick(() => {
|
||||
const dom = document.querySelector(".filter-texts-container");
|
||||
this.showScroll = dom && dom.scrollWidth > dom.offsetWidth;
|
||||
});
|
||||
},
|
||||
resizeObserver() {
|
||||
this.resizeForFilter = new ResizeObserver(entries => {
|
||||
if (!this.filterTexts.length) return;
|
||||
this.layoutResize();
|
||||
});
|
||||
this.resizeForFilter.observe(document.querySelector('#resize-for-filter'));
|
||||
},
|
||||
layoutResize: _.debounce(function () {
|
||||
this.getScrollStatus()
|
||||
}, 200),
|
||||
scrollPre() {
|
||||
const dom = document.querySelector('.filter-texts-container');
|
||||
dom.scrollLeft -= 10
|
||||
if (dom.scrollLeft <= 0) {
|
||||
dom.scrollLeft = 0
|
||||
}
|
||||
},
|
||||
scrollNext() {
|
||||
const dom = document.querySelector('.filter-texts-container');
|
||||
dom.scrollLeft += 10
|
||||
const width = dom.scrollWidth - dom.offsetWidth
|
||||
if (dom.scrollLeft > width) {
|
||||
dom.scrollLeft = width
|
||||
}
|
||||
},
|
||||
clearFilter() {
|
||||
this.$refs.filterUser.clearFilter();
|
||||
},
|
||||
clearOneFilter(index) {
|
||||
this.$refs.filterUser.clearOneFilter(index);
|
||||
this.$refs.filterUser.search();
|
||||
},
|
||||
filterDraw(condition, filterTexts = []) {
|
||||
this.cacheCondition = condition;
|
||||
this.filterTexts = filterTexts;
|
||||
this.initSearch();
|
||||
},
|
||||
filterShow() {
|
||||
this.$refs.filterUser.init();
|
||||
},
|
||||
createTimer() {
|
||||
this.initSearch();
|
||||
if (!this.timer) {
|
||||
this.timer = setInterval(() => {
|
||||
this.timerSearch(this.last_condition, false)
|
||||
this.timerSearch(false)
|
||||
}, 15000)
|
||||
}
|
||||
},
|
||||
@@ -150,36 +240,36 @@ export default {
|
||||
this.timer = null
|
||||
}
|
||||
},
|
||||
sortChange({ column, prop, order }) {
|
||||
this.orderConditions = []
|
||||
if (!order) {
|
||||
this.search(this.last_condition)
|
||||
return
|
||||
}
|
||||
if (prop === 'dept') {
|
||||
prop = 'u.deptId'
|
||||
}
|
||||
if (prop === 'status') {
|
||||
prop = 'u.enabled'
|
||||
}
|
||||
this.orderConditions = []
|
||||
addOrder({ field: prop, value: order }, this.orderConditions)
|
||||
this.search(this.last_condition)
|
||||
handleSizeChange(pageSize) {
|
||||
this.paginationConfig.currentPage = 1;
|
||||
this.paginationConfig.pageSize = pageSize;
|
||||
this.search();
|
||||
},
|
||||
select(selection) {
|
||||
handleCurrentChange(currentPage) {
|
||||
this.paginationConfig.currentPage = currentPage;
|
||||
this.search();
|
||||
},
|
||||
timerSearch(condition, showLoading = true) {
|
||||
initSearch() {
|
||||
this.handleCurrentChange(1);
|
||||
},
|
||||
timerSearch(showLoading = true) {
|
||||
if (!this.lastRequestComplete) {
|
||||
return
|
||||
} else {
|
||||
this.lastRequestComplete = false
|
||||
}
|
||||
|
||||
this.last_condition = condition
|
||||
condition = formatQuickCondition(condition, 'dataset_table_task.name')
|
||||
const temp = formatCondition(condition)
|
||||
const param = temp || {}
|
||||
param['orders'] = formatOrders(this.orderConditions)
|
||||
const param = {
|
||||
orders: formatOrders(this.orderConditions),
|
||||
conditions: [...this.cacheCondition],
|
||||
};
|
||||
if (this.nikeName) {
|
||||
param.conditions.push({
|
||||
field: `dataset_table_task.name`,
|
||||
operator: "like",
|
||||
value: this.nikeName,
|
||||
});
|
||||
}
|
||||
post('/dataset/taskLog/list/notexcel/' + this.paginationConfig.currentPage + '/' + this.paginationConfig.pageSize, param, showLoading).then(response => {
|
||||
this.data = response.data.listObject
|
||||
this.paginationConfig.total = response.data.itemCount
|
||||
@@ -189,11 +279,17 @@ export default {
|
||||
})
|
||||
},
|
||||
search(condition, showLoading = true) {
|
||||
this.last_condition = condition
|
||||
condition = formatQuickCondition(condition, 'dataset_table_task.name')
|
||||
const temp = formatCondition(condition)
|
||||
const param = temp || {}
|
||||
param['orders'] = formatOrders(this.orderConditions)
|
||||
const param = {
|
||||
orders: formatOrders(this.orderConditions),
|
||||
conditions: [...this.cacheCondition],
|
||||
};
|
||||
if (this.nikeName) {
|
||||
param.conditions.push({
|
||||
field: `dataset_table_task.name`,
|
||||
operator: "like",
|
||||
value: this.nikeName,
|
||||
});
|
||||
}
|
||||
post('/dataset/taskLog/list/notexcel/' + this.paginationConfig.currentPage + '/' + this.paginationConfig.pageSize, param, showLoading).then(response => {
|
||||
this.data = response.data.listObject
|
||||
this.paginationConfig.total = response.data.itemCount
|
||||
@@ -255,3 +351,202 @@ span{
|
||||
}
|
||||
|
||||
</style>
|
||||
<style lang="scss" scoped>
|
||||
.dataset-on-time {
|
||||
margin: 0;
|
||||
width: 100%;
|
||||
overflow: auto;
|
||||
background-color: var(--ContentBG, #fff);
|
||||
padding: 24px;
|
||||
height: 100%;
|
||||
}
|
||||
.table-container {
|
||||
height: calc(100% - 50px);
|
||||
|
||||
.text-btn {
|
||||
font-family: PingFang SC;
|
||||
font-size: 14px;
|
||||
font-weight: 400;
|
||||
line-height: 22px;
|
||||
letter-spacing: 0px;
|
||||
text-align: center;
|
||||
margin-left: 2px;
|
||||
border: none;
|
||||
padding: 2px 4px;
|
||||
}
|
||||
|
||||
.text-btn:hover {
|
||||
background: rgba(51, 112, 255, 0.1);
|
||||
}
|
||||
|
||||
.mar6 {
|
||||
margin-right: 6px;
|
||||
}
|
||||
|
||||
.mar3 {
|
||||
margin-left: -3px;
|
||||
}
|
||||
}
|
||||
|
||||
.table-container-filter {
|
||||
height: calc(100% - 110px);
|
||||
}
|
||||
.filter-texts {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
margin: 17px 0;
|
||||
font-family: "PingFang SC";
|
||||
font-weight: 400;
|
||||
|
||||
.sum {
|
||||
color: #1f2329;
|
||||
}
|
||||
|
||||
.title {
|
||||
color: #999999;
|
||||
margin-left: 8px;
|
||||
}
|
||||
|
||||
.text {
|
||||
max-width: 280px;
|
||||
overflow: hidden;
|
||||
text-overflow: ellipsis;
|
||||
white-space: nowrap;
|
||||
padding: 1px 22px 1px 6px;
|
||||
display: inline-block;
|
||||
align-items: center;
|
||||
color: #0c296e;
|
||||
font-size: 14px;
|
||||
line-height: 22px;
|
||||
background: rgba(51, 112, 255, 0.1);
|
||||
border-radius: 2px;
|
||||
margin: 0;
|
||||
margin-right: 8px;
|
||||
position: relative;
|
||||
i {
|
||||
position: absolute;
|
||||
right: 2px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
cursor: pointer;
|
||||
}
|
||||
}
|
||||
|
||||
.clear-btn {
|
||||
color: #646a73;
|
||||
}
|
||||
|
||||
.clear-btn:hover {
|
||||
color: #3370ff;
|
||||
}
|
||||
|
||||
.filter-texts-container::-webkit-scrollbar { display: none; }
|
||||
|
||||
.arrow-filter {
|
||||
font-size: 16px;
|
||||
width: 24px;
|
||||
height: 24px;
|
||||
cursor: pointer;
|
||||
color: #646A73;
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
}
|
||||
.arrow-filter:hover {
|
||||
background: rgba(31, 35, 41, 0.1);
|
||||
border-radius: 4px;
|
||||
}
|
||||
|
||||
.el-icon-arrow-right.arrow-filter {
|
||||
margin-left: 5px;
|
||||
}
|
||||
|
||||
.el-icon-arrow-left.arrow-filter {
|
||||
margin-right: 5px;
|
||||
}
|
||||
.filter-texts-container {
|
||||
flex: 1;
|
||||
overflow-x: auto;
|
||||
white-space: nowrap;
|
||||
height: 24px;
|
||||
}
|
||||
}
|
||||
.top-operate {
|
||||
margin-bottom: 16px;
|
||||
.right-user {
|
||||
text-align: right;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: flex-end;
|
||||
|
||||
.de-button {
|
||||
margin-left: 12px;
|
||||
}
|
||||
|
||||
.el-input--medium .el-input__icon {
|
||||
line-height: 32px;
|
||||
}
|
||||
}
|
||||
|
||||
.name-email-search {
|
||||
width: 240px;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
<style lang="scss">
|
||||
.de-status {
|
||||
position: relative;
|
||||
margin-left: 15px;
|
||||
&::before {
|
||||
content: "";
|
||||
position: absolute;
|
||||
top: 50%;
|
||||
left: -13px;
|
||||
transform: translateY(-50%);
|
||||
width: 5px;
|
||||
height: 5px;
|
||||
border-radius: 50%;
|
||||
}
|
||||
}
|
||||
|
||||
.de-Completed {
|
||||
&::before {
|
||||
background: var(--primary, #3370ff);
|
||||
}
|
||||
}
|
||||
|
||||
.de-Underway {
|
||||
&::before {
|
||||
background: #8f959e;
|
||||
}
|
||||
}
|
||||
|
||||
.de-Pending {
|
||||
&::before {
|
||||
background: #8f959e;
|
||||
}
|
||||
}
|
||||
|
||||
.de-Exec {
|
||||
&::before {
|
||||
background: var(--primary, #3370ff);
|
||||
}
|
||||
}
|
||||
|
||||
.de-Stopped {
|
||||
&::before {
|
||||
background: var(--deSuccess, #3370ff);
|
||||
}
|
||||
}
|
||||
|
||||
.de-Error {
|
||||
&::before {
|
||||
background: var(--deDanger, #3370ff);
|
||||
}
|
||||
|
||||
.el-icon-question {
|
||||
color: #646A73;
|
||||
cursor: pointer;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
@@ -1,113 +1,123 @@
|
||||
<template>
|
||||
<layout-content>
|
||||
|
||||
<el-row>
|
||||
<de-layout-content>
|
||||
<div class="organization">
|
||||
<el-tabs v-model="tabActive" @tab-click="changeTab">
|
||||
<el-tab-pane :label="$t('dataset.task.list')" name="DatasetTaskList">
|
||||
<dataset-task-list v-if="tabActive=='DatasetTaskList'" :param="task" :trans-condition="transCondition" @jumpTaskRecord="jumpTaskRecord" />
|
||||
</el-tab-pane>
|
||||
<el-tab-pane :label="$t('dataset.task.record')" name="TaskRecord">
|
||||
<task-record v-if="tabActive=='TaskRecord'" ref="task_record" :param="task" :trans-condition="transCondition" @jumpTask="jumpTask" />
|
||||
</el-tab-pane>
|
||||
</el-tabs>
|
||||
</el-row>
|
||||
</layout-content>
|
||||
<div class="tabs-container">
|
||||
<dataset-task-list
|
||||
v-if="tabActive == 'DatasetTaskList'"
|
||||
:param="task"
|
||||
:trans-condition="transCondition"
|
||||
@jumpTaskRecord="jumpTaskRecord"
|
||||
/>
|
||||
<task-record
|
||||
v-if="tabActive == 'TaskRecord'"
|
||||
ref="task_record"
|
||||
:param="task"
|
||||
:trans-condition="transCondition"
|
||||
@jumpTask="jumpTask"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
</de-layout-content>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import DeLayoutContent from "@/components/business/DeLayoutContent";
|
||||
|
||||
import LayoutContent from '@/components/business/LayoutContent'
|
||||
import DatasetTaskList from "@/views/system/task/DatasetTaskList";
|
||||
import TaskRecord from "@/views/system/task/TaskRecord";
|
||||
|
||||
import DatasetTaskList from '@/views/system/task/DatasetTaskList'
|
||||
import TaskRecord from '@/views/system/task/TaskRecord'
|
||||
|
||||
import bus from '@/utils/bus'
|
||||
import { mapGetters } from 'vuex'
|
||||
import bus from "@/utils/bus";
|
||||
import { mapGetters } from "vuex";
|
||||
export default {
|
||||
components: { LayoutContent, DatasetTaskList, TaskRecord },
|
||||
components: { DeLayoutContent, DatasetTaskList, TaskRecord },
|
||||
data() {
|
||||
return {
|
||||
tabActive: 'DatasetTaskList',
|
||||
tabActive: "DatasetTaskList",
|
||||
transCondition: {},
|
||||
task: null
|
||||
}
|
||||
task: null,
|
||||
};
|
||||
},
|
||||
computed: {
|
||||
...mapGetters([
|
||||
'permission_routes'
|
||||
])
|
||||
...mapGetters(["permission_routes"]),
|
||||
},
|
||||
mounted() {
|
||||
bus.$on('to-msg-dataset', this.toMsgShare)
|
||||
bus.$on("to-msg-dataset", this.toMsgShare);
|
||||
},
|
||||
beforeDestroy() {
|
||||
bus.$off('to-msg-dataset', this.toMsgShare)
|
||||
bus.$off("to-msg-dataset", this.toMsgShare);
|
||||
},
|
||||
created() {
|
||||
this.$store.dispatch('app/toggleSideBarHide', false)
|
||||
const routerParam = this.$router.currentRoute.params
|
||||
routerParam && this.$nextTick(() => {
|
||||
this.toMsgShare(routerParam)
|
||||
})
|
||||
this.$store.dispatch("app/toggleSideBarHide", false);
|
||||
const routerParam = this.$router.currentRoute.params;
|
||||
routerParam &&
|
||||
this.$nextTick(() => {
|
||||
this.toMsgShare(routerParam);
|
||||
});
|
||||
},
|
||||
methods: {
|
||||
changeTab() {
|
||||
this.task = null
|
||||
this.transCondition = {}
|
||||
this.task = null;
|
||||
this.transCondition = {};
|
||||
},
|
||||
jumpTaskRecord(task) {
|
||||
this.transCondition['dataset_table_task.id'] = {
|
||||
operator: 'eq',
|
||||
value: task.id
|
||||
}
|
||||
this.tabActive = 'TaskRecord'
|
||||
this.transCondition["dataset_table_task.id"] = {
|
||||
operator: "eq",
|
||||
value: task.id,
|
||||
};
|
||||
this.tabActive = "TaskRecord";
|
||||
},
|
||||
jumpTask(taskRecord) {
|
||||
this.transCondition['dataset_table_task.id'] = {
|
||||
operator: 'eq',
|
||||
value: taskRecord.taskId
|
||||
}
|
||||
this.tabActive = 'DatasetTaskList'
|
||||
this.transCondition["dataset_table_task.id"] = {
|
||||
operator: "eq",
|
||||
value: taskRecord.taskId,
|
||||
};
|
||||
this.tabActive = "DatasetTaskList";
|
||||
},
|
||||
toMsgShare(routerParam) {
|
||||
if (routerParam !== null && routerParam.msgNotification) {
|
||||
const panelShareTypeIds = [4, 5, 6]
|
||||
const panelShareTypeIds = [4, 5, 6];
|
||||
// 说明是从消息通知跳转过来的
|
||||
if (panelShareTypeIds.includes(routerParam.msgType)) { // 是数据集同步
|
||||
if (panelShareTypeIds.includes(routerParam.msgType)) {
|
||||
// 是数据集同步
|
||||
if (routerParam.sourceParam) {
|
||||
this.openSystem()
|
||||
this.openSystem();
|
||||
try {
|
||||
const msgParam = JSON.parse(routerParam.sourceParam)
|
||||
const msgParam = JSON.parse(routerParam.sourceParam);
|
||||
// this.param = msgParam.tableId
|
||||
|
||||
this.$nextTick(() => {
|
||||
// 目标组件存在定时器 这种方式会被定时器阻塞
|
||||
// this.$refs.task_record && this.$refs.task_record.msg2Current && this.$refs.task_record.msg2Current(msgParam)
|
||||
this.task = msgParam
|
||||
this.tabActive = 'TaskRecord'
|
||||
})
|
||||
this.task = msgParam;
|
||||
this.tabActive = "TaskRecord";
|
||||
});
|
||||
} catch (error) {
|
||||
console.error(error)
|
||||
console.error(error);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
openSystem() {
|
||||
const path = '/system'
|
||||
const path = "/system";
|
||||
let route = this.permission_routes.find(
|
||||
item => item.path === '/' + path.split('/')[1]
|
||||
)
|
||||
(item) => item.path === "/" + path.split("/")[1]
|
||||
);
|
||||
// 如果找不到这个路由,说明是首页
|
||||
if (!route) {
|
||||
route = this.permission_routes.find(item => item.path === '/')
|
||||
route = this.permission_routes.find((item) => item.path === "/");
|
||||
}
|
||||
this.$store.commit('permission/SET_CURRENT_ROUTES', route)
|
||||
this.$store.commit("permission/SET_CURRENT_ROUTES", route);
|
||||
// this.setSidebarHide(route)
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
},
|
||||
},
|
||||
};
|
||||
</script>
|
||||
|
||||
<style lang="scss" scoped>
|
||||
@@ -119,7 +129,7 @@ export default {
|
||||
padding: 10px 10px;
|
||||
}
|
||||
|
||||
::v-deep .el-radio-button__orig-radio:checked+.el-radio-button__inner {
|
||||
::v-deep .el-radio-button__orig-radio:checked + .el-radio-button__inner {
|
||||
color: #fff;
|
||||
background-color: #0a7be0;
|
||||
border-color: #0a7be0;
|
||||
@@ -128,10 +138,32 @@ export default {
|
||||
}
|
||||
}
|
||||
.de-msg-a:hover {
|
||||
text-decoration: underline !important;
|
||||
color: #0a7be0 !important;
|
||||
cursor: pointer !important;
|
||||
|
||||
text-decoration: underline !important;
|
||||
color: #0a7be0 !important;
|
||||
cursor: pointer !important;
|
||||
}
|
||||
</style>
|
||||
<style scoped lang="scss">
|
||||
.organization {
|
||||
height: 100%;
|
||||
background-color: var(--MainBG, #f5f6f7);
|
||||
|
||||
.tabs-container {
|
||||
height: calc(100% - 48px);
|
||||
background: var(--ContentBG, #ffffff);
|
||||
overflow-x: auto;
|
||||
}
|
||||
|
||||
>>> .el-tabs__header {
|
||||
margin: 0 0 12px;
|
||||
}
|
||||
|
||||
>>> .el-tabs__item {
|
||||
height: 24px;
|
||||
line-height: 24px;
|
||||
margin-bottom: 9px;
|
||||
padding: 0 12px;
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
</style>
|
||||
|
||||
466
frontend/src/views/system/task/filterUser.vue
Normal file
466
frontend/src/views/system/task/filterUser.vue
Normal file
@@ -0,0 +1,466 @@
|
||||
<template>
|
||||
<el-drawer
|
||||
:title="$t('user.filter_method')"
|
||||
:visible.sync="userDrawer"
|
||||
custom-class="user-drawer"
|
||||
size="680px"
|
||||
v-closePress
|
||||
direction="rtl"
|
||||
>
|
||||
<div class="filter">
|
||||
<span>{{ $t("dataset.datalist") }}</span>
|
||||
<div class="filter-item">
|
||||
<span
|
||||
class="item"
|
||||
@click="activeDatasetChange(ele.id)"
|
||||
:class="[activeDataset.includes(ele.id) ? 'active' : '']"
|
||||
:key="ele.id"
|
||||
v-for="ele in selectDatasetsCahe"
|
||||
>{{ ele.name }}</span
|
||||
>
|
||||
<el-popover
|
||||
placement="bottom"
|
||||
popper-class="user-popper"
|
||||
width="200"
|
||||
trigger="click"
|
||||
>
|
||||
<el-popover
|
||||
placement="bottom"
|
||||
popper-class="user-popper dept"
|
||||
width="200"
|
||||
trigger="click"
|
||||
v-loading="treeLoading"
|
||||
>
|
||||
<el-tree
|
||||
ref="datasetTreeRef"
|
||||
current-node-key="id"
|
||||
:data="treeData"
|
||||
node-key="id"
|
||||
highlight-current
|
||||
:filter-node-method="filterNode"
|
||||
:expand-on-click-node="true"
|
||||
@node-click="nodeClick"
|
||||
>
|
||||
<span slot-scope="{ data }" class="custom-tree-node">
|
||||
<span v-if="data.modelInnerType === 'group'">
|
||||
<svg-icon icon-class="scene" class="ds-icon-scene" />
|
||||
<span
|
||||
style="
|
||||
margin-left: 6px;
|
||||
white-space: nowrap;
|
||||
overflow: hidden;
|
||||
text-overflow: ellipsis;
|
||||
"
|
||||
:title="data.name"
|
||||
>{{ data.name }}</span
|
||||
>
|
||||
</span>
|
||||
<span v-else>
|
||||
<span>
|
||||
<svg-icon
|
||||
:icon-class="`ds-${data.modelInnerType}`"
|
||||
:class="`ds-icon-${data.modelInnerType}`"
|
||||
/>
|
||||
</span>
|
||||
<span
|
||||
style="
|
||||
margin-left: 6px;
|
||||
white-space: nowrap;
|
||||
overflow: hidden;
|
||||
text-overflow: ellipsis;
|
||||
"
|
||||
:title="data.name"
|
||||
>{{ data.name }}</span
|
||||
>
|
||||
</span>
|
||||
</span>
|
||||
</el-tree>
|
||||
|
||||
<el-select
|
||||
ref="datasetSelect"
|
||||
v-model="selectDatasets"
|
||||
slot="reference"
|
||||
popper-class="tree-select"
|
||||
multiple
|
||||
:placeholder="$t('commons.please_select')"
|
||||
value-key="id"
|
||||
>
|
||||
<el-option
|
||||
v-for="item in selectDatasets"
|
||||
:key="item.name"
|
||||
:label="item.name"
|
||||
:value="item"
|
||||
/>
|
||||
</el-select>
|
||||
</el-popover>
|
||||
<span class="more" slot="reference">+ {{ $t("panel.more") }}</span>
|
||||
</el-popover>
|
||||
</div>
|
||||
</div>
|
||||
<div v-for="ele in filterDataset" :key="ele.name" class="filter">
|
||||
<span>{{ $t(ele.name) }}</span>
|
||||
<div class="filter-item">
|
||||
<span
|
||||
class="item"
|
||||
@click="statusChange(item.value, ele.activeType)"
|
||||
:class="[active[ele.activeType].includes(item.value) ? 'active' : '']"
|
||||
:key="item.name"
|
||||
v-for="item in ele.list"
|
||||
>{{ $t(item.name) }}</span
|
||||
>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="filter">
|
||||
<span>{{ $t("dedaterange.label") }}</span>
|
||||
<div class="filter-item">
|
||||
<el-date-picker
|
||||
v-model="dataRange"
|
||||
size="small"
|
||||
type="daterange"
|
||||
range-separator=""
|
||||
start-placeholder="开始日期"
|
||||
end-placeholder="结束日期"
|
||||
>
|
||||
</el-date-picker>
|
||||
</div>
|
||||
</div>
|
||||
<div class="foot">
|
||||
<el-button class="btn normal" @click="reset">{{
|
||||
$t("commons.reset")
|
||||
}}</el-button>
|
||||
<el-button type="primary" class="btn" @click="search">{{
|
||||
$t("commons.adv_search.search")
|
||||
}}</el-button>
|
||||
</div>
|
||||
</el-drawer>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { filterDataset, dateFormat } from "./options";
|
||||
import { allRoles } from "@/api/system/user";
|
||||
import { getDatasetTree, treeByDatasetId } from "@/api/system/dept";
|
||||
import { queryAuthModel } from "@/api/authModel/authModel";
|
||||
|
||||
export default {
|
||||
data() {
|
||||
return {
|
||||
treeLoading: false,
|
||||
dataRange: [],
|
||||
selectDatasets: [],
|
||||
datasetCahe: [],
|
||||
activeDataset: [],
|
||||
selectDatasetsCahe: [],
|
||||
treeData: [],
|
||||
filterDataset,
|
||||
active: {
|
||||
execStatus: [],
|
||||
status: [],
|
||||
rate: [],
|
||||
},
|
||||
userDrawer: false,
|
||||
};
|
||||
},
|
||||
mounted() {
|
||||
this.treeNode();
|
||||
},
|
||||
methods: {
|
||||
treeNode() {
|
||||
this.treeLoading = true;
|
||||
queryAuthModel(
|
||||
{
|
||||
modelType: "dataset",
|
||||
privileges: "manage",
|
||||
datasetMode: 1,
|
||||
clearEmptyDir: true,
|
||||
mode: 1,
|
||||
modelInnerTypeArray: ["db", "sql", "api", "group"],
|
||||
},
|
||||
true
|
||||
)
|
||||
.then((res) => {
|
||||
this.treeData = res.data;
|
||||
})
|
||||
.finally(() => {
|
||||
this.treeLoading = false;
|
||||
});
|
||||
},
|
||||
nodeClick(data) {
|
||||
const { id, name, modelInnerType: type } = data;
|
||||
if (type === "group") return;
|
||||
this.handleNodeClick(id, name);
|
||||
},
|
||||
filterNode(value, data) {
|
||||
if (!value) return true;
|
||||
return !this.activeDataset.includes(data.id);
|
||||
},
|
||||
clearFilter() {
|
||||
this.active = {
|
||||
execStatus: [],
|
||||
status: [],
|
||||
rate: [],
|
||||
};
|
||||
this.dataRange = [];
|
||||
this.activeDataset = [];
|
||||
this.selectDatasets = [];
|
||||
this.datasetCahe = [];
|
||||
this.selectDatasetsCahe = [];
|
||||
this.$emit("search", [], []);
|
||||
},
|
||||
clearOneFilter(index) {
|
||||
(this.filterTextMap[index] || []).forEach((ele) => {
|
||||
const eleKey = ele.split(".");
|
||||
if (eleKey.length === 2) {
|
||||
const [p, c] = eleKey;
|
||||
this[p][c] = [];
|
||||
} else {
|
||||
this[ele] = [];
|
||||
}
|
||||
});
|
||||
},
|
||||
statusChange(value, type) {
|
||||
const statusIndex = this.active[type].findIndex((ele) => ele === value);
|
||||
if (statusIndex === -1) {
|
||||
this.active[type].push(value);
|
||||
} else {
|
||||
this.active[type].splice(statusIndex, 1);
|
||||
}
|
||||
},
|
||||
handleNodeClick(id, name) {
|
||||
const datasetIdx = this.selectDatasets.findIndex((ele) => ele.id === id);
|
||||
if (datasetIdx !== -1) {
|
||||
this.selectDatasets.splice(datasetIdx, 1);
|
||||
this.selectDatasetsCahe = this.selectDatasetsCahe.filter(
|
||||
(ele) => ele.id !== id
|
||||
);
|
||||
this.datasetCahe = this.datasetCahe.filter((ele) => ele.id !== id);
|
||||
this.$refs.datasetTreeRef.filter(id);
|
||||
return;
|
||||
}
|
||||
this.activeDataset.push(id);
|
||||
this.selectDatasetsCahe.push({ id, name });
|
||||
this.datasetCahe.push({ id, name });
|
||||
this.$refs.datasetTreeRef.filter(id);
|
||||
},
|
||||
activeDatasetChange(id) {
|
||||
const dataset = this.datasetCahe.find((ele) => ele.id === id);
|
||||
this.selectDatasets.push(dataset);
|
||||
this.activeDataset = this.activeDataset.filter((ele) => ele !== id);
|
||||
this.selectDatasetsCahe = this.selectDatasetsCahe.filter(
|
||||
(ele) => ele.id !== id
|
||||
);
|
||||
},
|
||||
search() {
|
||||
this.userDrawer = false;
|
||||
this.$emit("search", this.formatCondition(), this.formatText());
|
||||
},
|
||||
formatText() {
|
||||
this.filterTextMap = [];
|
||||
const params = [];
|
||||
if (this.activeDataset.length) {
|
||||
let str = `${this.$t("dataset.datalist")}:${this.activeDataset.reduce(
|
||||
(pre, next) =>
|
||||
(this.datasetCahe.find((ele) => ele.id === next) || {}).name +
|
||||
"、" +
|
||||
pre,
|
||||
""
|
||||
)}`;
|
||||
params.push(str.slice(0, str.length - 1));
|
||||
this.filterTextMap.push([
|
||||
"activeDataset",
|
||||
"selectDatasets",
|
||||
"selectDatasetsCahe",
|
||||
"datasetCahe",
|
||||
]);
|
||||
}
|
||||
[
|
||||
"dataset.execute_rate",
|
||||
"dataset.task.task_status",
|
||||
"dataset.task.last_exec_status",
|
||||
].forEach((ele, index) => {
|
||||
const { activeType: type, list } =
|
||||
filterDataset[index];
|
||||
if (this.active[type].length) {
|
||||
params.push(
|
||||
`${this.$t(ele)}:${this.active[type]
|
||||
.map((item) => this.$t(list.find((itx) => itx.value === item).name))
|
||||
.join("、")}`
|
||||
);
|
||||
this.filterTextMap.push([`active.${type}`]);
|
||||
}
|
||||
});
|
||||
if (this.dataRange.length) {
|
||||
params.push(
|
||||
`${this.$t("dedaterange.label")}:${this.dataRange
|
||||
.map((ele) => {
|
||||
return dateFormat("YYYY-mm-dd", ele);
|
||||
})
|
||||
.join("-")}`
|
||||
);
|
||||
this.filterTextMap.push(["dataRange"]);
|
||||
}
|
||||
return params;
|
||||
},
|
||||
formatCondition() {
|
||||
const fildMap = {
|
||||
"dataset_table_task.rate": this.active.rate,
|
||||
"dataset_table_task.status": this.active.status,
|
||||
"dataset_table_task.last_exec_status": this.active.execStatus,
|
||||
"dataset_table.id": this.activeDataset,
|
||||
};
|
||||
const conditions = [];
|
||||
Object.keys(fildMap).forEach((ele) => {
|
||||
if (fildMap[ele].length) {
|
||||
conditions.push({
|
||||
field: ele,
|
||||
operator: "in",
|
||||
value: fildMap[ele],
|
||||
});
|
||||
}
|
||||
});
|
||||
const [min, max] = this.dataRange;
|
||||
if (min && max) {
|
||||
conditions.push({
|
||||
field: "dataset_table_task.last_exec_time",
|
||||
operator: "between",
|
||||
value: [+min, +max],
|
||||
});
|
||||
}
|
||||
return conditions;
|
||||
},
|
||||
init() {
|
||||
this.userDrawer = true;
|
||||
},
|
||||
reset() {
|
||||
this.clearFilter();
|
||||
this.userDrawer = false;
|
||||
},
|
||||
},
|
||||
};
|
||||
</script>
|
||||
|
||||
<style lang="scss">
|
||||
.user-drawer {
|
||||
.el-drawer__header {
|
||||
padding: 16px 24px;
|
||||
margin: 0;
|
||||
font-family: PingFang SC;
|
||||
font-size: 16px;
|
||||
font-weight: 500;
|
||||
line-height: 24px;
|
||||
color: #1f2329;
|
||||
position: relative;
|
||||
box-sizing: border-box;
|
||||
height: 57px;
|
||||
mix-blend-mode: normal;
|
||||
border-bottom: 1px solid rgba(187, 191, 196, 0.5);
|
||||
|
||||
.el-drawer__close-btn {
|
||||
position: absolute;
|
||||
right: 24px;
|
||||
top: 16px;
|
||||
padding: 4px;
|
||||
border-radius: 4px;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.el-drawer__close-btn:hover {
|
||||
background: #e9e9ea;
|
||||
}
|
||||
}
|
||||
|
||||
.el-drawer__body {
|
||||
padding: 12px 24px 24px 24px;
|
||||
position: relative;
|
||||
}
|
||||
|
||||
.filter {
|
||||
display: flex;
|
||||
min-height: 46px;
|
||||
> :nth-child(1) {
|
||||
color: #1f2329;
|
||||
font-family: "PingFang SC";
|
||||
font-style: normal;
|
||||
font-weight: 400;
|
||||
font-size: 14px;
|
||||
line-height: 24px;
|
||||
white-space: nowrap;
|
||||
width: 116px;
|
||||
}
|
||||
.filter-item {
|
||||
flex: 1;
|
||||
.item,
|
||||
.more {
|
||||
font-family: PingFang SC;
|
||||
white-space: nowrap;
|
||||
font-size: 14px;
|
||||
font-weight: 400;
|
||||
line-height: 24px;
|
||||
margin-right: 12px;
|
||||
text-align: center;
|
||||
padding: 1px 6px;
|
||||
background: #f5f6f7;
|
||||
border-radius: 2px;
|
||||
cursor: pointer;
|
||||
display: inline-block;
|
||||
margin-bottom: 12px;
|
||||
}
|
||||
|
||||
.active,
|
||||
.more:hover {
|
||||
background: rgba(51, 112, 255, 0.1);
|
||||
color: #0c296e;
|
||||
}
|
||||
.more {
|
||||
white-space: nowrap;
|
||||
}
|
||||
}
|
||||
}
|
||||
.btn {
|
||||
border-radius: 4px;
|
||||
padding: 5px 26px 5px 26px;
|
||||
font-family: PingFang SC;
|
||||
font-size: 14px;
|
||||
font-weight: 400;
|
||||
line-height: 20px;
|
||||
letter-spacing: 0px;
|
||||
text-align: center;
|
||||
border: none;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
.normal {
|
||||
color: #1f2329;
|
||||
border: 1px solid #bbbfc4;
|
||||
margin-left: 12px;
|
||||
}
|
||||
|
||||
.foot {
|
||||
position: absolute;
|
||||
right: 24px;
|
||||
bottom: 24px;
|
||||
text-align: right;
|
||||
}
|
||||
}
|
||||
.user-popper {
|
||||
padding: 0;
|
||||
background: #fff;
|
||||
.popper__arrow {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
.tree-select {
|
||||
.el-select-dropdown__empty,
|
||||
.el-scrollbar__wrap,
|
||||
.popper__arrow {
|
||||
display: none !important;
|
||||
}
|
||||
}
|
||||
|
||||
.user-popper.dept {
|
||||
height: 400px;
|
||||
overflow: auto;
|
||||
}
|
||||
</style>
|
||||
459
frontend/src/views/system/task/filterUserRecord.vue
Normal file
459
frontend/src/views/system/task/filterUserRecord.vue
Normal file
@@ -0,0 +1,459 @@
|
||||
<template>
|
||||
<el-drawer
|
||||
:title="$t('user.filter_method')"
|
||||
:visible.sync="userDrawer"
|
||||
custom-class="user-drawer"
|
||||
size="680px"
|
||||
v-closePress
|
||||
direction="rtl"
|
||||
>
|
||||
<div class="filter">
|
||||
<span>{{ $t("dataset.datalist") }}</span>
|
||||
<div class="filter-item">
|
||||
<span
|
||||
class="item"
|
||||
@click="activeDatasetChange(ele.id)"
|
||||
:class="[activeDataset.includes(ele.id) ? 'active' : '']"
|
||||
:key="ele.id"
|
||||
v-for="ele in selectDatasetsCahe"
|
||||
>{{ ele.name }}</span
|
||||
>
|
||||
<el-popover
|
||||
placement="bottom"
|
||||
popper-class="user-popper"
|
||||
width="200"
|
||||
trigger="click"
|
||||
>
|
||||
<el-popover
|
||||
placement="bottom"
|
||||
popper-class="user-popper dept"
|
||||
width="200"
|
||||
trigger="click"
|
||||
v-loading="treeLoading"
|
||||
>
|
||||
<el-tree
|
||||
ref="datasetTreeRef"
|
||||
current-node-key="id"
|
||||
:data="treeData"
|
||||
node-key="id"
|
||||
highlight-current
|
||||
:filter-node-method="filterNode"
|
||||
:expand-on-click-node="true"
|
||||
@node-click="nodeClick"
|
||||
>
|
||||
<span slot-scope="{ data }" class="custom-tree-node">
|
||||
<span v-if="data.modelInnerType === 'group'">
|
||||
<svg-icon icon-class="scene" class="ds-icon-scene" />
|
||||
<span
|
||||
style="
|
||||
margin-left: 6px;
|
||||
white-space: nowrap;
|
||||
overflow: hidden;
|
||||
text-overflow: ellipsis;
|
||||
"
|
||||
:title="data.name"
|
||||
>{{ data.name }}</span
|
||||
>
|
||||
</span>
|
||||
<span v-else>
|
||||
<span>
|
||||
<svg-icon
|
||||
:icon-class="`ds-${data.modelInnerType}`"
|
||||
:class="`ds-icon-${data.modelInnerType}`"
|
||||
/>
|
||||
</span>
|
||||
<span
|
||||
style="
|
||||
margin-left: 6px;
|
||||
white-space: nowrap;
|
||||
overflow: hidden;
|
||||
text-overflow: ellipsis;
|
||||
"
|
||||
:title="data.name"
|
||||
>{{ data.name }}</span
|
||||
>
|
||||
</span>
|
||||
</span>
|
||||
</el-tree>
|
||||
|
||||
<el-select
|
||||
ref="datasetSelect"
|
||||
v-model="selectDatasets"
|
||||
slot="reference"
|
||||
popper-class="tree-select"
|
||||
multiple
|
||||
:placeholder="$t('commons.please_select')"
|
||||
value-key="id"
|
||||
>
|
||||
<el-option
|
||||
v-for="item in selectDatasets"
|
||||
:key="item.name"
|
||||
:label="item.name"
|
||||
:value="item"
|
||||
/>
|
||||
</el-select>
|
||||
</el-popover>
|
||||
<span class="more" slot="reference">+ {{ $t("panel.more") }}</span>
|
||||
</el-popover>
|
||||
</div>
|
||||
</div>
|
||||
<div v-for="ele in filterDataset" :key="ele.name" class="filter">
|
||||
<span>{{ $t(ele.name) }}</span>
|
||||
<div class="filter-item">
|
||||
<span
|
||||
class="item"
|
||||
@click="statusChange(item.value, ele.activeType)"
|
||||
:class="[active[ele.activeType].includes(item.value) ? 'active' : '']"
|
||||
:key="item.name"
|
||||
v-for="item in ele.list"
|
||||
>{{ $t(item.name) }}</span
|
||||
>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="filter">
|
||||
<span>{{ $t("dedaterange.label") }}</span>
|
||||
<div class="filter-item">
|
||||
<el-date-picker
|
||||
v-model="dataRange"
|
||||
size="small"
|
||||
type="daterange"
|
||||
range-separator=""
|
||||
start-placeholder="开始日期"
|
||||
end-placeholder="结束日期"
|
||||
>
|
||||
</el-date-picker>
|
||||
</div>
|
||||
</div>
|
||||
<div class="foot">
|
||||
<el-button class="btn normal" @click="reset">{{
|
||||
$t("commons.reset")
|
||||
}}</el-button>
|
||||
<el-button type="primary" class="btn" @click="search">{{
|
||||
$t("commons.adv_search.search")
|
||||
}}</el-button>
|
||||
</div>
|
||||
</el-drawer>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { filterDatasetRecord, dateFormat } from "./options";
|
||||
import { queryAuthModel } from "@/api/authModel/authModel";
|
||||
|
||||
export default {
|
||||
data() {
|
||||
return {
|
||||
treeLoading: false,
|
||||
filterTextMap: [],
|
||||
dataRange: [],
|
||||
selectDatasets: [],
|
||||
datasetCahe: [],
|
||||
activeDataset: [],
|
||||
selectDatasetsCahe: [],
|
||||
treeData: [],
|
||||
filterDataset: [filterDatasetRecord],
|
||||
active: {
|
||||
execStatus: [],
|
||||
},
|
||||
userDrawer: false,
|
||||
};
|
||||
},
|
||||
mounted() {
|
||||
this.treeNode();
|
||||
},
|
||||
methods: {
|
||||
treeNode() {
|
||||
this.treeLoading = true;
|
||||
queryAuthModel(
|
||||
{
|
||||
modelType: "dataset",
|
||||
privileges: "manage",
|
||||
datasetMode: 1,
|
||||
clearEmptyDir: true,
|
||||
mode: 1,
|
||||
modelInnerTypeArray: ["db", "sql", "api", "group"],
|
||||
},
|
||||
true
|
||||
)
|
||||
.then((res) => {
|
||||
this.treeData = res.data;
|
||||
})
|
||||
.finally(() => {
|
||||
this.treeLoading = false;
|
||||
});
|
||||
},
|
||||
nodeClick(data) {
|
||||
const { id, name, modelInnerType: type } = data;
|
||||
if (type === "group") return;
|
||||
this.handleNodeClick(id, name);
|
||||
},
|
||||
filterNode(value, data) {
|
||||
if (!value) return true;
|
||||
return !this.activeDataset.includes(data.id);
|
||||
},
|
||||
clearFilter() {
|
||||
this.active = {
|
||||
execStatus: [],
|
||||
}
|
||||
this.dataRange = [];
|
||||
this.activeDataset = [];
|
||||
this.selectDatasets = [];
|
||||
this.datasetCahe = [];
|
||||
this.selectDatasetsCahe = [];
|
||||
this.$emit("search", [], []);
|
||||
},
|
||||
clearOneFilter(index) {
|
||||
(this.filterTextMap[index] || []).forEach(ele => {
|
||||
const eleKey = ele.split('.');
|
||||
if (eleKey.length === 2) {
|
||||
const [p, c ] = eleKey;
|
||||
this[p][c] = []
|
||||
} else {
|
||||
this[ele] = []
|
||||
}
|
||||
})
|
||||
},
|
||||
statusChange(value, type) {
|
||||
const statusIndex = this.active[type].findIndex((ele) => ele === value);
|
||||
if (statusIndex === -1) {
|
||||
this.active[type].push(value);
|
||||
} else {
|
||||
this.active[type].splice(statusIndex, 1);
|
||||
}
|
||||
},
|
||||
handleNodeClick(id, name) {
|
||||
const datasetIdx = this.selectDatasets.findIndex((ele) => ele.id === id);
|
||||
if (datasetIdx !== -1) {
|
||||
this.selectDatasets.splice(datasetIdx, 1);
|
||||
this.selectDatasetsCahe = this.selectDatasetsCahe.filter(
|
||||
(ele) => ele.id !== id
|
||||
);
|
||||
this.datasetCahe = this.datasetCahe.filter((ele) => ele.id !== id);
|
||||
this.$refs.datasetTreeRef.filter(id);
|
||||
return;
|
||||
}
|
||||
this.activeDataset.push(id);
|
||||
this.selectDatasetsCahe.push({ id, name });
|
||||
this.datasetCahe.push({ id, name });
|
||||
this.$refs.datasetTreeRef.filter(id);
|
||||
},
|
||||
activeDatasetChange(id) {
|
||||
const dataset = this.datasetCahe.find((ele) => ele.id === id);
|
||||
this.selectDatasets.push(dataset);
|
||||
this.activeDataset = this.activeDataset.filter((ele) => ele !== id);
|
||||
this.selectDatasetsCahe = this.selectDatasetsCahe.filter(
|
||||
(ele) => ele.id !== id
|
||||
);
|
||||
},
|
||||
search() {
|
||||
this.userDrawer = false;
|
||||
this.$emit("search", this.formatCondition(), this.formatText());
|
||||
},
|
||||
formatText() {
|
||||
this.filterTextMap = [];
|
||||
const params = [];
|
||||
if (this.activeDataset.length) {
|
||||
let str = `${this.$t("dataset.datalist")}:${this.activeDataset.reduce(
|
||||
(pre, next) =>
|
||||
(this.datasetCahe.find((ele) => ele.id === next) || {}).name +
|
||||
"、" +
|
||||
pre,
|
||||
""
|
||||
)}`;
|
||||
params.push(str.slice(0, str.length - 1));
|
||||
this.filterTextMap.push([
|
||||
"activeDataset",
|
||||
"selectDatasets",
|
||||
"selectDatasetsCahe",
|
||||
"datasetCahe",
|
||||
]);
|
||||
}
|
||||
[
|
||||
"dataset.task.last_exec_status",
|
||||
].forEach((ele, index) => {
|
||||
const { activeType: type, list } =
|
||||
this.filterDataset[index];
|
||||
console.log('type', type);
|
||||
if (this.active[type].length) {
|
||||
params.push(
|
||||
`${this.$t(ele)}:${this.active[type]
|
||||
.map((item) => this.$t(list.find((itx) => itx.value === item).name))
|
||||
.join("、")}`
|
||||
);
|
||||
this.filterTextMap.push([`active.${type}`]);
|
||||
}
|
||||
});
|
||||
if (this.dataRange.length) {
|
||||
params.push(
|
||||
`${this.$t("dedaterange.label")}:${this.dataRange
|
||||
.map((ele) => {
|
||||
return dateFormat("YYYY-mm-dd", ele);
|
||||
})
|
||||
.join("-")}`
|
||||
);
|
||||
this.filterTextMap.push(["dataRange"]);
|
||||
}
|
||||
return params;
|
||||
},
|
||||
formatCondition() {
|
||||
const fildMap = {
|
||||
"dataset_table_task.last_exec_status": this.active.execStatus,
|
||||
"dataset_table.id": this.activeDataset,
|
||||
};
|
||||
const conditions = [];
|
||||
Object.keys(fildMap).forEach((ele) => {
|
||||
if (fildMap[ele].length) {
|
||||
conditions.push({
|
||||
field: ele,
|
||||
operator: "in",
|
||||
value: fildMap[ele],
|
||||
});
|
||||
}
|
||||
});
|
||||
const [ min, max ] = this.dataRange;
|
||||
if (min && max) {
|
||||
console.log(1, +min, +max);
|
||||
conditions.push({
|
||||
field: 'dataset_table_task.last_exec_time',
|
||||
operator: "between",
|
||||
value: [ +min, +max ],
|
||||
})
|
||||
}
|
||||
return conditions;
|
||||
},
|
||||
init() {
|
||||
this.userDrawer = true;
|
||||
},
|
||||
reset() {
|
||||
this.clearFilter();
|
||||
this.userDrawer = false;
|
||||
},
|
||||
},
|
||||
};
|
||||
</script>
|
||||
|
||||
<style lang="scss">
|
||||
.user-drawer {
|
||||
.el-drawer__header {
|
||||
padding: 16px 24px;
|
||||
margin: 0;
|
||||
font-family: PingFang SC;
|
||||
font-size: 16px;
|
||||
font-weight: 500;
|
||||
line-height: 24px;
|
||||
color: #1f2329;
|
||||
position: relative;
|
||||
box-sizing: border-box;
|
||||
height: 57px;
|
||||
mix-blend-mode: normal;
|
||||
border-bottom: 1px solid rgba(187, 191, 196, 0.5);
|
||||
|
||||
.el-drawer__close-btn {
|
||||
position: absolute;
|
||||
right: 24px;
|
||||
top: 16px;
|
||||
padding: 4px;
|
||||
border-radius: 4px;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.el-drawer__close-btn:hover {
|
||||
background: #e9e9ea;
|
||||
}
|
||||
}
|
||||
|
||||
.el-drawer__body {
|
||||
padding: 12px 24px 24px 24px;
|
||||
position: relative;
|
||||
}
|
||||
|
||||
.filter {
|
||||
display: flex;
|
||||
min-height: 46px;
|
||||
> :nth-child(1) {
|
||||
color: #1f2329;
|
||||
font-family: "PingFang SC";
|
||||
font-style: normal;
|
||||
font-weight: 400;
|
||||
font-size: 14px;
|
||||
line-height: 24px;
|
||||
white-space: nowrap;
|
||||
width: 116px;
|
||||
}
|
||||
.filter-item {
|
||||
flex: 1;
|
||||
.item,
|
||||
.more {
|
||||
font-family: PingFang SC;
|
||||
white-space: nowrap;
|
||||
font-size: 14px;
|
||||
font-weight: 400;
|
||||
line-height: 24px;
|
||||
margin-right: 12px;
|
||||
text-align: center;
|
||||
padding: 1px 6px;
|
||||
background: #f5f6f7;
|
||||
border-radius: 2px;
|
||||
cursor: pointer;
|
||||
display: inline-block;
|
||||
margin-bottom: 12px;
|
||||
}
|
||||
|
||||
.active,
|
||||
.more:hover {
|
||||
background: rgba(51, 112, 255, 0.1);
|
||||
color: #0c296e;
|
||||
}
|
||||
.more {
|
||||
white-space: nowrap;
|
||||
}
|
||||
}
|
||||
}
|
||||
.btn {
|
||||
border-radius: 4px;
|
||||
padding: 5px 26px 5px 26px;
|
||||
font-family: PingFang SC;
|
||||
font-size: 14px;
|
||||
font-weight: 400;
|
||||
line-height: 20px;
|
||||
letter-spacing: 0px;
|
||||
text-align: center;
|
||||
border: none;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
.normal {
|
||||
color: #1f2329;
|
||||
border: 1px solid #bbbfc4;
|
||||
margin-left: 12px;
|
||||
}
|
||||
|
||||
.foot {
|
||||
position: absolute;
|
||||
right: 24px;
|
||||
bottom: 24px;
|
||||
text-align: right;
|
||||
}
|
||||
}
|
||||
.user-popper {
|
||||
padding: 0;
|
||||
background: #fff;
|
||||
.popper__arrow {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
.tree-select {
|
||||
.el-select-dropdown__empty,
|
||||
.el-scrollbar__wrap,
|
||||
.popper__arrow {
|
||||
display: none !important;
|
||||
}
|
||||
}
|
||||
|
||||
.user-popper.dept {
|
||||
height: 400px;
|
||||
overflow: auto;
|
||||
}
|
||||
</style>
|
||||
@@ -1,14 +1,615 @@
|
||||
<template>
|
||||
<div>数据同步表单</div>
|
||||
<de-layout-content>
|
||||
<div class="dataset-editer-form">
|
||||
<div class="w600">
|
||||
<el-form
|
||||
ref="taskForm"
|
||||
:form="taskForm"
|
||||
:model="taskForm"
|
||||
:disabled="disableForm"
|
||||
label-width="100px"
|
||||
class="de-form-item"
|
||||
:rules="taskFormRules"
|
||||
>
|
||||
<el-form-item
|
||||
@click.native="selectDataset"
|
||||
:label="$t('chart.select_dataset')"
|
||||
prop="datasetName"
|
||||
>
|
||||
<el-input
|
||||
v-model="taskForm.datasetName"
|
||||
size="small"
|
||||
readonly
|
||||
:placeholder="$t('dataset.task_name')"
|
||||
/>
|
||||
</el-form-item>
|
||||
<el-form-item :label="$t('dataset.task_name')" prop="name">
|
||||
<el-input
|
||||
v-model="taskForm.name"
|
||||
size="small"
|
||||
:placeholder="$t('dataset.task_name')"
|
||||
/>
|
||||
</el-form-item>
|
||||
<el-form-item :label="$t('dataset.update_type')" prop="type">
|
||||
<el-radio-group v-model="taskForm.type">
|
||||
<el-radio label="all_scope">{{
|
||||
$t("dataset.all_scope")
|
||||
}}</el-radio>
|
||||
<el-radio label="add_scope">
|
||||
{{ $t("dataset.add_scope") }}</el-radio
|
||||
>
|
||||
</el-radio-group>
|
||||
</el-form-item>
|
||||
<div class="add-scope-cont" v-if="taskForm.type === 'add_scope'">
|
||||
<el-form-item :label="$t('dataset.incremental_update_type')">
|
||||
<el-radio-group
|
||||
v-model="incrementalUpdateType"
|
||||
size="small"
|
||||
@change="incrementalUpdateTypeChange"
|
||||
>
|
||||
<el-radio label="incrementalAdd">{{
|
||||
$t("dataset.incremental_add")
|
||||
}}</el-radio>
|
||||
<el-radio label="incrementalDelete">{{
|
||||
$t("dataset.incremental_delete")
|
||||
}}</el-radio>
|
||||
</el-radio-group>
|
||||
<div class="param-title">
|
||||
<span>{{ $t("dataset.param") }}</span>
|
||||
<div class="param-title-btn">
|
||||
<el-button
|
||||
type="text"
|
||||
size="small"
|
||||
@click="insertParamToCodeMirror('${__last_update_time__}')"
|
||||
>{{ $t("dataset.last_update_time") }}</el-button
|
||||
>
|
||||
<el-button
|
||||
type="text"
|
||||
size="small"
|
||||
@click="
|
||||
insertParamToCodeMirror('${__current_update_time__}')
|
||||
"
|
||||
>{{ $t("dataset.current_update_time") }}</el-button
|
||||
>
|
||||
</div>
|
||||
</div>
|
||||
<div class="codemirror-cont">
|
||||
<codemirror
|
||||
ref="myCm"
|
||||
v-model="sql"
|
||||
class="codemirror"
|
||||
:options="sqlOption"
|
||||
@ready="onCmReady"
|
||||
@focus="onCmFocus"
|
||||
@input="onCmCodeChange"
|
||||
/>
|
||||
</div>
|
||||
</el-form-item>
|
||||
</div>
|
||||
|
||||
<el-form-item :label="$t('dataset.execute_rate')" prop="rate">
|
||||
<el-radio-group v-model="taskForm.rate" @change="onRateChange">
|
||||
<el-radio label="SIMPLE">{{
|
||||
$t("dataset.execute_once")
|
||||
}}</el-radio>
|
||||
<el-radio label="CRON">{{ $t("dataset.cron_config") }}</el-radio>
|
||||
<el-radio label="SIMPLE_CRON">{{
|
||||
$t("dataset.simple_cron")
|
||||
}}</el-radio>
|
||||
</el-radio-group>
|
||||
</el-form-item>
|
||||
<div class="execute-rate-cont" v-if="taskForm.rate !== 'SIMPLE'">
|
||||
<el-form-item
|
||||
v-if="taskForm.rate === 'SIMPLE_CRON'"
|
||||
:label="$t('dataset.execute_rate')"
|
||||
prop="rate"
|
||||
>
|
||||
<div class="simple-cron">
|
||||
{{ $t("cron.every") }}
|
||||
<el-input-number
|
||||
v-model="taskForm.extraData.simple_cron_value"
|
||||
controls-position="right"
|
||||
:min="1"
|
||||
size="small"
|
||||
></el-input-number>
|
||||
<el-select
|
||||
v-model="taskForm.extraData.simple_cron_type"
|
||||
filterable
|
||||
size="small"
|
||||
@change="onSimpleCronChange()"
|
||||
>
|
||||
<el-option
|
||||
:label="$t('分钟')"
|
||||
value="minute"
|
||||
/>
|
||||
<el-option :label="$t('小时')" value="hour" />
|
||||
<el-option :label="$t('天')" value="day" />
|
||||
</el-select>
|
||||
{{ $t("cron.every_exec") }}
|
||||
</div>
|
||||
</el-form-item>
|
||||
<el-form-item
|
||||
prop="cron"
|
||||
v-if="taskForm.rate === 'CRON'"
|
||||
:label="$t('emailtask.cron_exp')"
|
||||
>
|
||||
<el-popover v-model="cronEdit">
|
||||
<cron v-model="taskForm.cron" @close="cronEdit = false" />
|
||||
<el-input
|
||||
slot="reference"
|
||||
v-model="taskForm.cron"
|
||||
size="small"
|
||||
style="width: 50%"
|
||||
@click="cronEdit = true"
|
||||
/>
|
||||
</el-popover>
|
||||
</el-form-item>
|
||||
<el-form-item
|
||||
v-if="taskForm.rate !== 'SIMPLE'"
|
||||
:label="$t('dataset.start_time')"
|
||||
prop="startTime"
|
||||
>
|
||||
<el-date-picker
|
||||
v-model="taskForm.startTime"
|
||||
type="datetime"
|
||||
:placeholder="$t('dataset.start_time')"
|
||||
size="small"
|
||||
/>
|
||||
</el-form-item>
|
||||
<el-form-item
|
||||
v-if="taskForm.rate !== 'SIMPLE'"
|
||||
:label="$t('dataset.end_time')"
|
||||
prop="end"
|
||||
>
|
||||
<el-radio-group v-model="taskForm.end">
|
||||
<el-radio label="0">{{ $t("dataset.no_limit") }}</el-radio>
|
||||
<el-radio label="1"> {{ $t("dataset.set_end_time") }}</el-radio>
|
||||
</el-radio-group>
|
||||
<el-date-picker
|
||||
v-if="taskForm.end === '1'"
|
||||
v-model="taskForm.endTime"
|
||||
type="datetime"
|
||||
:placeholder="$t('dataset.end_time')"
|
||||
size="small"
|
||||
/>
|
||||
</el-form-item>
|
||||
</div>
|
||||
</el-form>
|
||||
<table-selector
|
||||
ref="tableSelector"
|
||||
previewForTask="true"
|
||||
privileges="manage"
|
||||
@getTableId="getTableId"
|
||||
:mode="1"
|
||||
:clear-empty-dir="true"
|
||||
:custom-type="['db', 'sql', 'api']"
|
||||
show-mode="datasetTask"
|
||||
/>
|
||||
</div>
|
||||
<div class="de-foot-layout">
|
||||
<div class="cont">
|
||||
<deBtn secondary @click="closeTask">{{ $t("dataset.cancel") }}</deBtn>
|
||||
<deBtn v-if="!disableForm" type="primary" @click="saveTask(taskForm)">{{
|
||||
$t("dataset.confirm")
|
||||
}}</deBtn>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</de-layout-content>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { post } from "@/api/dataset/dataset";
|
||||
import DeLayoutContent from "@/components/business/DeLayoutContent";
|
||||
import { hasDataPermission } from "@/utils/permission";
|
||||
import msgCfm from "@/components/msgCfm/index";
|
||||
|
||||
import cron from "@/components/cron/cron";
|
||||
import { codemirror } from "vue-codemirror";
|
||||
import "codemirror/lib/codemirror.css";
|
||||
import "codemirror/theme/eclipse.css";
|
||||
import "codemirror/mode/sql/sql.js";
|
||||
import "codemirror/addon/selection/active-line.js";
|
||||
import "codemirror/addon/edit/closebrackets.js";
|
||||
import "codemirror/mode/clike/clike.js";
|
||||
import "codemirror/addon/edit/matchbrackets.js";
|
||||
import "codemirror/addon/comment/comment.js";
|
||||
import "codemirror/addon/dialog/dialog.js";
|
||||
import "codemirror/addon/dialog/dialog.css";
|
||||
import "codemirror/addon/search/searchcursor.js";
|
||||
import "codemirror/addon/search/search.js";
|
||||
import "codemirror/keymap/emacs.js";
|
||||
import "codemirror/addon/hint/show-hint.css";
|
||||
import "codemirror/addon/hint/sql-hint";
|
||||
import "codemirror/addon/hint/show-hint";
|
||||
import TableSelector from "./TableSelector";
|
||||
|
||||
export default {
|
||||
name: 'AppearanceSetting',
|
||||
components: { cron, codemirror, TableSelector, DeLayoutContent },
|
||||
mixins: [msgCfm],
|
||||
data() {
|
||||
return {
|
||||
disableForm: false,
|
||||
table: {
|
||||
name: "",
|
||||
id: "",
|
||||
},
|
||||
taskForm: {
|
||||
name: "",
|
||||
type: "all_scope",
|
||||
startTime: "",
|
||||
tableId: "",
|
||||
rate: "SIMPLE",
|
||||
cron: "",
|
||||
endTime: "",
|
||||
end: "0",
|
||||
extraData: {
|
||||
simple_cron_type: "hour",
|
||||
simple_cron_value: 1,
|
||||
},
|
||||
},
|
||||
taskFormRules: {
|
||||
name: [
|
||||
{
|
||||
required: true,
|
||||
message: this.$t("dataset.required"),
|
||||
trigger: "change",
|
||||
},
|
||||
{
|
||||
min: 2,
|
||||
max: 50,
|
||||
message: this.$t("datasource.input_limit_2_50", [2, 50]),
|
||||
trigger: "blur",
|
||||
},
|
||||
],
|
||||
type: [
|
||||
{
|
||||
required: true,
|
||||
message: this.$t("dataset.required"),
|
||||
trigger: "change",
|
||||
},
|
||||
],
|
||||
startTime: [
|
||||
{
|
||||
required: true,
|
||||
message: this.$t("dataset.required"),
|
||||
trigger: "change",
|
||||
},
|
||||
],
|
||||
rate: [
|
||||
{
|
||||
required: true,
|
||||
message: this.$t("dataset.required"),
|
||||
trigger: "change",
|
||||
},
|
||||
],
|
||||
end: [
|
||||
{
|
||||
required: true,
|
||||
message: this.$t("dataset.required"),
|
||||
trigger: "change",
|
||||
},
|
||||
],
|
||||
cron: [
|
||||
{
|
||||
required: true,
|
||||
message: this.$t("dataset.required"),
|
||||
trigger: "change",
|
||||
},
|
||||
],
|
||||
datasetName: [
|
||||
{
|
||||
required: true,
|
||||
trigger: "change",
|
||||
},
|
||||
],
|
||||
},
|
||||
cronEdit: false,
|
||||
sqlOption: {
|
||||
tabSize: 2,
|
||||
styleActiveLine: true,
|
||||
lineNumbers: true,
|
||||
line: true,
|
||||
mode: "text/x-sql",
|
||||
theme: "eclipse",
|
||||
hintOptions: {
|
||||
// 自定义提示选项
|
||||
completeSingle: false, // 当匹配只有一项的时候是否自动补全
|
||||
},
|
||||
},
|
||||
incrementalConfig: {},
|
||||
sql: "",
|
||||
incrementalUpdateType: "incrementalAdd",
|
||||
};
|
||||
},
|
||||
created() {
|
||||
const { datasetName, id } = this.$route.query;
|
||||
this.taskDetail = { datasetName, id };
|
||||
if (!id) return;
|
||||
this.getTaskDetail(id);
|
||||
},
|
||||
methods: {
|
||||
getTaskDetail(id) {
|
||||
post(`/dataset/task/detail/${id}`, {}).then((res) => {
|
||||
if(res.data.extraData) {
|
||||
res.data.extraData = JSON.parse(res.data.extraData)
|
||||
}
|
||||
this.taskForm = res.data;
|
||||
this.disableForm = this.disableEdit();
|
||||
});
|
||||
},
|
||||
selectDataset() {
|
||||
if (this.taskForm.id) return;
|
||||
this.$refs.tableSelector.init();
|
||||
},
|
||||
getTableId(id, name) {
|
||||
this.taskForm.tableId = id;
|
||||
this.taskForm.datasetName = name;
|
||||
},
|
||||
onRateChange() {
|
||||
if (this.taskForm.rate === "SIMPLE") {
|
||||
this.taskForm.end = "0";
|
||||
this.taskForm.endTime = "";
|
||||
this.taskForm.cron = "";
|
||||
}
|
||||
if (this.taskForm.rate === "SIMPLE_CRON") {
|
||||
this.taskForm.cron = "0 0 0/1 * * ? *";
|
||||
}
|
||||
if (this.taskForm.rate === "CRON") {
|
||||
this.taskForm.cron = "00 00 * ? * * *";
|
||||
}
|
||||
},
|
||||
disableEdit() {
|
||||
const { privileges, rate, status } = this.taskForm;
|
||||
return (
|
||||
rate === "SIMPLE" ||
|
||||
status === "Stopped" ||
|
||||
!hasDataPermission("manage", privileges)
|
||||
);
|
||||
},
|
||||
onCmReady(cm) {
|
||||
// this.codemirror.setSize("-webkit-fill-available", "auto");
|
||||
},
|
||||
onCmFocus(cm) {},
|
||||
onCmCodeChange(newCode) {
|
||||
this.sql = newCode;
|
||||
this.$emit("codeChange", this.sql);
|
||||
},
|
||||
closeTask() {
|
||||
this.$router.back();
|
||||
},
|
||||
onSimpleCronChange() {
|
||||
if (this.taskForm.extraData.simple_cron_type === "minute") {
|
||||
if (
|
||||
this.taskForm.extraData.simple_cron_value < 1 ||
|
||||
this.taskForm.extraData.simple_cron_value > 59
|
||||
) {
|
||||
this.$message({
|
||||
message: this.$t("cron.minute_limit"),
|
||||
type: "warning",
|
||||
showClose: true,
|
||||
});
|
||||
this.taskForm.extraData.simple_cron_value = 59;
|
||||
}
|
||||
this.taskForm.cron =
|
||||
"0 0/" + this.taskForm.extraData.simple_cron_value + " * * * ? *";
|
||||
return;
|
||||
}
|
||||
if (this.taskForm.extraData.simple_cron_type === "hour") {
|
||||
if (
|
||||
this.taskForm.extraData.simple_cron_value < 1 ||
|
||||
this.taskForm.extraData.simple_cron_value > 23
|
||||
) {
|
||||
this.$message({
|
||||
message: this.$t("cron.hour_limit"),
|
||||
type: "warning",
|
||||
showClose: true,
|
||||
});
|
||||
this.taskForm.extraData.simple_cron_value = 23;
|
||||
}
|
||||
this.taskForm.cron =
|
||||
"0 0 0/" + this.taskForm.extraData.simple_cron_value + " * * ? *";
|
||||
return;
|
||||
}
|
||||
if (this.taskForm.extraData.simple_cron_type === "day") {
|
||||
if (
|
||||
this.taskForm.extraData.simple_cron_value < 1 ||
|
||||
this.taskForm.extraData.simple_cron_value > 31
|
||||
) {
|
||||
this.$message({
|
||||
message: this.$t("cron.day_limit"),
|
||||
type: "warning",
|
||||
showClose: true,
|
||||
});
|
||||
this.taskForm.extraData.simple_cron_value = 31;
|
||||
}
|
||||
this.taskForm.cron =
|
||||
"0 0 0 1/" + this.taskForm.extraData.simple_cron_value + " * ? *";
|
||||
return;
|
||||
}
|
||||
},
|
||||
insertParamToCodeMirror(param) {
|
||||
const pos1 = this.$refs.myCm.codemirror.getCursor();
|
||||
const pos2 = {};
|
||||
pos2.line = pos1.line;
|
||||
pos2.ch = pos1.ch;
|
||||
this.$refs.myCm.codemirror.replaceRange(param, pos2);
|
||||
},
|
||||
saveTask(task) {
|
||||
this.$refs.taskForm.validate((valid) => {
|
||||
if (valid) {
|
||||
if (task.rate !== "SIMPLE") {
|
||||
if (this.incrementalUpdateType === "incrementalAdd") {
|
||||
this.incrementalConfig.incrementalAdd = this.sql;
|
||||
} else {
|
||||
this.incrementalConfig.incrementalDelete = this.sql;
|
||||
}
|
||||
this.incrementalConfig.tableId = task.tableId;
|
||||
}
|
||||
task.startTime = new Date(task.startTime).getTime();
|
||||
task.endTime = new Date(task.endTime).getTime();
|
||||
const form = JSON.parse(JSON.stringify(task));
|
||||
form.extraData = JSON.stringify(form.extraData);
|
||||
const dataSetTaskRequest = {
|
||||
datasetTableTask: form,
|
||||
datasetTableIncrementalConfig:
|
||||
task.type === "add_scope" ? this.incrementalConfig : undefined,
|
||||
};
|
||||
post("/dataset/task/save", dataSetTaskRequest).then((response) => {
|
||||
this.openMessageSuccess("dataset.save_success");
|
||||
this.closeTask();
|
||||
});
|
||||
} else {
|
||||
return false;
|
||||
}
|
||||
});
|
||||
},
|
||||
getIncrementalConfig(tableId) {
|
||||
post("/dataset/table/incrementalConfig", { tableId: tableId }).then(
|
||||
(response) => {
|
||||
this.incrementalConfig = response.data;
|
||||
|
||||
if (
|
||||
this.incrementalConfig.incrementalAdd.length === 0 &&
|
||||
this.incrementalConfig.incrementalDelete.length === 0
|
||||
) {
|
||||
this.incrementalUpdateType = "incrementalAdd";
|
||||
this.sql = "";
|
||||
return;
|
||||
}
|
||||
if (this.incrementalConfig.incrementalAdd.length > 0) {
|
||||
this.incrementalUpdateType = "incrementalAdd";
|
||||
this.sql = this.incrementalConfig.incrementalAdd;
|
||||
} else {
|
||||
this.incrementalUpdateType = "incrementalDelete";
|
||||
this.sql = this.incrementalConfig.incrementalDelete;
|
||||
}
|
||||
}
|
||||
);
|
||||
},
|
||||
incrementalUpdateTypeChange: function () {
|
||||
if (this.incrementalUpdateType === "incrementalAdd") {
|
||||
if (this.sql) {
|
||||
this.incrementalConfig.incrementalDelete = this.sql;
|
||||
} else {
|
||||
this.incrementalConfig.incrementalDelete = "";
|
||||
}
|
||||
if (this.incrementalConfig.incrementalAdd) {
|
||||
this.sql = this.incrementalConfig.incrementalAdd;
|
||||
} else {
|
||||
this.sql = "";
|
||||
}
|
||||
}
|
||||
|
||||
if (this.incrementalUpdateType === "incrementalDelete") {
|
||||
if (this.sql) {
|
||||
this.incrementalConfig.incrementalAdd = this.sql;
|
||||
} else {
|
||||
this.incrementalConfig.incrementalAdd = "";
|
||||
}
|
||||
if (this.incrementalConfig.incrementalDelete) {
|
||||
this.sql = this.incrementalConfig.incrementalDelete;
|
||||
} else {
|
||||
this.sql = "";
|
||||
}
|
||||
}
|
||||
},
|
||||
},
|
||||
};
|
||||
</script>
|
||||
|
||||
<style lang="scss">
|
||||
.dataset-editer-form {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
.w600 {
|
||||
width: 600px;
|
||||
padding-top: 24px;
|
||||
padding-bottom: 24px;
|
||||
.el-radio:not(:last-child) {
|
||||
margin-right: 0;
|
||||
width: 156px;
|
||||
}
|
||||
|
||||
.simple-cron {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
width: 100%;
|
||||
.el-input-number,
|
||||
.el-select {
|
||||
width: 140px;
|
||||
margin-left: 8px;
|
||||
}
|
||||
|
||||
.el-select {
|
||||
margin-right: 8px;
|
||||
}
|
||||
}
|
||||
|
||||
.execute-rate-cont {
|
||||
box-sizing: border-box;
|
||||
padding: 20px;
|
||||
width: 100%;
|
||||
background: #f5f6f7;
|
||||
border-radius: 4px;
|
||||
|
||||
.el-input__inner {
|
||||
background: #ffffff !important;
|
||||
}
|
||||
|
||||
.el-date-editor {
|
||||
width: 100%;
|
||||
}
|
||||
}
|
||||
|
||||
.add-scope-cont {
|
||||
height: 350px;
|
||||
width: 100%;
|
||||
border-radius: 4px;
|
||||
padding: 20px;
|
||||
|
||||
.param-title {
|
||||
width: 100%;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: space-between;
|
||||
padding-bottom: 9px;
|
||||
&:nth-child(1) {
|
||||
font-family: PingFang SC;
|
||||
font-size: 14px;
|
||||
font-weight: 400;
|
||||
color: var(--deTextPrimary, #1f2329);
|
||||
}
|
||||
}
|
||||
|
||||
.codemirror-cont {
|
||||
box-sizing: border-box;
|
||||
width: 560px;
|
||||
height: 200px;
|
||||
background: #ffffff;
|
||||
border: 1px solid #bbbfc4;
|
||||
border-radius: 4px;
|
||||
overflow: auto;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
.de-foot-layout {
|
||||
position: absolute;
|
||||
width: calc(100% - 48px);
|
||||
height: 80px;
|
||||
bottom: 0;
|
||||
right: 24px;
|
||||
background: #ffffff;
|
||||
box-shadow: 0px -2px 4px rgba(0, 0, 0, 0.08);
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
z-index: 10;
|
||||
.cont {
|
||||
width: 600px;
|
||||
text-align: right;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
80
frontend/src/views/system/task/options.js
Normal file
80
frontend/src/views/system/task/options.js
Normal file
@@ -0,0 +1,80 @@
|
||||
const filterDatasetRecord = {
|
||||
name: 'dataset.task.last_exec_status',
|
||||
type: 'dataset_table_task.last_exec_status',
|
||||
activeType: 'execStatus',
|
||||
list: [{
|
||||
name: 'xpacktask.success',
|
||||
value: 'Completed',
|
||||
}, {
|
||||
name: 'dataset.task.exec',
|
||||
value: 'Underway',
|
||||
},
|
||||
{
|
||||
name: 'xpacktask.error',
|
||||
value: 'Error',
|
||||
}]
|
||||
}
|
||||
const filterDataset = [{
|
||||
name: 'dataset.execute_rate',
|
||||
type: 'dataset_table_task.rate',
|
||||
activeType: 'rate',
|
||||
list: [{
|
||||
name: 'dataset.execute_once',
|
||||
value: 'SIMPLE',
|
||||
}, {
|
||||
name: 'dataset.cron_config',
|
||||
value: 'CRON',
|
||||
},
|
||||
{
|
||||
name: 'dataset.simple_cron',
|
||||
value: 'SIMPLE_CRON',
|
||||
}]
|
||||
}, {
|
||||
name: 'dataset.task.task_status',
|
||||
type: 'dataset_table_task.status',
|
||||
activeType: 'status',
|
||||
list: [{
|
||||
name: 'dataset.task.underway',
|
||||
value: 'Underway',
|
||||
}, {
|
||||
name: 'dataset.task.exec',
|
||||
value: 'Exec',
|
||||
},
|
||||
{
|
||||
name: 'dataset.task.pending',
|
||||
value: 'Pending',
|
||||
}, {
|
||||
name: 'dataset.task.stopped',
|
||||
value: 'Stopped',
|
||||
}]
|
||||
}, {
|
||||
...filterDatasetRecord
|
||||
}]
|
||||
|
||||
|
||||
// 入参 fmt-格式 date-日期
|
||||
function dateFormat(fmt, date) {
|
||||
let ret;
|
||||
const opt = {
|
||||
"Y+": date.getFullYear().toString(), // 年
|
||||
"m+": (date.getMonth() + 1).toString(), // 月
|
||||
"d+": date.getDate().toString(), // 日
|
||||
"H+": date.getHours().toString(), // 时
|
||||
"M+": date.getMinutes().toString(), // 分
|
||||
"S+": date.getSeconds().toString() // 秒
|
||||
// 有其他格式化字符需求可以继续添加,必须转化成字符串
|
||||
};
|
||||
for (let k in opt) {
|
||||
ret = new RegExp("(" + k + ")").exec(fmt);
|
||||
if (ret) {
|
||||
fmt = fmt.replace(ret[1], (ret[1].length == 1) ? (opt[k]) : (opt[k].padStart(ret[1].length, "0")))
|
||||
};
|
||||
};
|
||||
return fmt;
|
||||
}
|
||||
|
||||
export {
|
||||
filterDataset,
|
||||
dateFormat,
|
||||
filterDatasetRecord
|
||||
}
|
||||
@@ -861,72 +861,4 @@ export default {
|
||||
}
|
||||
}
|
||||
</style>
|
||||
<style lang="scss">
|
||||
.de-confirm {
|
||||
border: none;
|
||||
.el-message-box__header {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.el-message-box__content {
|
||||
padding: 24px;
|
||||
}
|
||||
|
||||
.el-message-box__container {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
}
|
||||
.el-message-box__status {
|
||||
height: 22px;
|
||||
width: 22px;
|
||||
font-size: 22px !important;
|
||||
margin-right: 17px;
|
||||
}
|
||||
|
||||
.el-message-box__message {
|
||||
//styleName: 中文/桌面端/四级标题 16 24 Medium;
|
||||
font-family: PingFang SC;
|
||||
font-size: 16px;
|
||||
font-weight: 500;
|
||||
line-height: 24px;
|
||||
letter-spacing: 0px;
|
||||
text-align: left;
|
||||
color: #1f2329;
|
||||
}
|
||||
|
||||
.el-message-box__btns {
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
.de-confirm-fail-btn {
|
||||
height: 32px;
|
||||
width: 80px;
|
||||
border-radius: 4px;
|
||||
font-family: PingFang SC;
|
||||
font-size: 14px;
|
||||
font-weight: 400;
|
||||
line-height: 22px;
|
||||
text-align: center;
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
.de-confirm-fail-cancel {
|
||||
background: #ffffff;
|
||||
border: 1px solid #bbbfc4;
|
||||
color: #1f2329;
|
||||
}
|
||||
|
||||
.de-confirm-fail-confirm {
|
||||
background: #f54a45;
|
||||
border: none;
|
||||
color: #ffffff;
|
||||
}
|
||||
}
|
||||
|
||||
.de-confirm-fail {
|
||||
padding: 0 24px 24px 0 !important;
|
||||
.el-message-box__status {
|
||||
color: #ff8800 !important;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
Reference in New Issue
Block a user