merge: with dev

This commit is contained in:
ibuler
2020-06-16 12:24:47 +08:00
23 changed files with 275 additions and 113 deletions

View File

@@ -1,6 +1,7 @@
<template> <template>
<IBox fa="fa-info-circle" :title="title" v-bind="$attrs"> <IBox fa="fa-info-circle" :title="title" v-bind="$attrs">
<div class="quick-actions"> <div class="quick-actions">
<p v-if="iTag.length === 0">{{ $t('common.Nothing') }}</p>
<el-tag v-for="i in iTag" :key="i" type="info">{{ i }}</el-tag> <el-tag v-for="i in iTag" :key="i" type="info">{{ i }}</el-tag>
</div> </div>
</IBox> </IBox>

View File

@@ -221,6 +221,9 @@ export default {
}, },
addObjects() { addObjects() {
const objects = this.$refs.select2.getOptionsByValues(this.select2.value) const objects = this.$refs.select2.getOptionsByValues(this.select2.value)
if (objects.length === 0) {
return
}
this.performAdd(objects, this).then( this.performAdd(objects, this).then(
() => this.onAddSuccess(objects, this) () => this.onAddSuccess(objects, this)
) )

View File

@@ -181,6 +181,7 @@
"MoreActions": "更多操作", "MoreActions": "更多操作",
"Name": "名称", "Name": "名称",
"No": "否", "No": "否",
"Nothing": "无",
"NoData": "暂无数据", "NoData": "暂无数据",
"Open": "打开", "Open": "打开",
"Other": "其它", "Other": "其它",
@@ -207,6 +208,8 @@
"activateSelected": "激活所选", "activateSelected": "激活所选",
"bulkDeleteErrorMsg": "批量删除失败: ", "bulkDeleteErrorMsg": "批量删除失败: ",
"bulkDeleteSuccessMsg": "批量删除成功", "bulkDeleteSuccessMsg": "批量删除成功",
"bulkRemoveErrorMsg": "批量移除失败: ",
"bulkRemoveSuccessMsg": "批量移除成功",
"createBy": "创建者", "createBy": "创建者",
"createErrorMsg": "创建失败", "createErrorMsg": "创建失败",
"createSuccessMsg": "创建成功", "createSuccessMsg": "创建成功",
@@ -260,6 +263,8 @@
"updateSuccessMsg": "更新成功", "updateSuccessMsg": "更新成功",
"SelectProperties": "选择属性", "SelectProperties": "选择属性",
"ObjectNotFoundOrDeletedMsg": "没有找到对应资源或者已被删除", "ObjectNotFoundOrDeletedMsg": "没有找到对应资源或者已被删除",
"removeSelected": "移除所选",
"removeWarningMsg": "你确定要移除",
"password": { "password": {
"UPPER_CASE_REQUIRED": "须包含大写字母", "UPPER_CASE_REQUIRED": "须包含大写字母",
"LOWER_CASE_REQUIRED": "须包含小写字母", "LOWER_CASE_REQUIRED": "须包含小写字母",
@@ -341,7 +346,8 @@
"totalVersions": "版本数量", "totalVersions": "版本数量",
"version": "版本", "version": "版本",
"versionDetail": "版本详情", "versionDetail": "版本详情",
"versionRunExecution": "执行历史" "versionRunExecution": "执行历史",
"Unkown": "未知"
}, },
"perms": { "perms": {
"": "", "": "",

View File

@@ -142,6 +142,7 @@
"ReLogin": "Re-Login" "ReLogin": "Re-Login"
}, },
"common": { "common": {
"Nothing": "Nothing",
"Action": "Action", "Action": "Action",
"Actions": "Actions", "Actions": "Actions",
"Activate": "Activate", "Activate": "Activate",
@@ -208,6 +209,8 @@
"activateSelected": "Activate selected", "activateSelected": "Activate selected",
"bulkDeleteErrorMsg": "Bulk delete failed: ", "bulkDeleteErrorMsg": "Bulk delete failed: ",
"bulkDeleteSuccessMsg": "Bulk delete success", "bulkDeleteSuccessMsg": "Bulk delete success",
"bulkRemoveErrorMsg": "Bulk remove failed: ",
"bulkRemoveSuccessMsg": "Bulk remove success",
"createBy": "Create by", "createBy": "Create by",
"createErrorMsg": "Create error", "createErrorMsg": "Create error",
"createSuccessMsg": "Create success", "createSuccessMsg": "Create success",
@@ -260,6 +263,8 @@
"updateSuccessMsg": "Update success", "updateSuccessMsg": "Update success",
"SelectProperties": "Select properties", "SelectProperties": "Select properties",
"ObjectNotFoundOrDeletedMsg": "Resource lost or deleted", "ObjectNotFoundOrDeletedMsg": "Resource lost or deleted",
"removeSelected": "Remove selected",
"removeWarningMsg": "Are you sure to remove ",
"password": { "password": {
"UPPER_CASE_REQUIRED": "Upper case required", "UPPER_CASE_REQUIRED": "Upper case required",
"LOWER_CASE_REQUIRED": "Lower case required", "LOWER_CASE_REQUIRED": "Lower case required",
@@ -341,7 +346,8 @@
"totalVersions": "Total versions", "totalVersions": "Total versions",
"version": "Version", "version": "Version",
"versionDetail": "Version detail", "versionDetail": "Version detail",
"versionRunExecution": "Version run execution" "versionRunExecution": "Version run execution",
"Unkown": "Unkown"
}, },
"perms": { "perms": {
"": "", "": "",

View File

@@ -30,7 +30,7 @@ export default {
name: 'Detail' name: 'Detail'
} }
], ],
hasRightSide: this.hasRightSide hasRightSide: this.$route.params.id > 7
} }
} }
}, },

View File

@@ -60,4 +60,10 @@ export default {
.box-margin { .box-margin {
margin-bottom: 20px; margin-bottom: 20px;
} }
.el-table::before{
display: none;
}
.el-table >>> td{
border-bottom: none;
}
</style> </style>

View File

@@ -57,7 +57,7 @@ export default {
formatter: (row) => { formatter: (row) => {
const label = this.$t('audits.View') const label = this.$t('audits.View')
const route = { to: { name: 'CeleryTaskLog', params: { id: row.id }}} const route = { to: { name: 'CeleryTaskLog', params: { id: row.id }}}
return <router-link {...{ attrs: route }}>{ label }</router-link> return <router-link {...{ attrs: route }} target='_blank'>{ label }</router-link>
} }
}, },
date_start: { date_start: {

View File

@@ -1,7 +1,7 @@
<template> <template>
<IBox :fa="icon" :type="type" :title="title" v-bind="$attrs"> <IBox :fa="icon" :type="type" :title="title" v-bind="$attrs">
<table class="run-info"> <table class="run-info">
<tr> <tr v-for="content in contents" :key="content.hostname">
<td>{{ content.hostname }}</td> <td>{{ content.hostname }}</td>
<td>{{ content.result }}</td> <td>{{ content.result }}</td>
</tr> </tr>
@@ -26,9 +26,9 @@ export default {
type: String, type: String,
default: '' default: ''
}, },
content: { contents: {
type: Object, type: Array,
default: () => ({}) default: () => ([])
}, },
url: { url: {
type: String, type: String,

View File

@@ -4,8 +4,8 @@
<DetailCard :title="cardTitle" :items="detailCardItems" /> <DetailCard :title="cardTitle" :items="detailCardItems" />
</el-col> </el-col>
<el-col :span="10"> <el-col :span="10">
<RunInfoCard type="primary" v-bind="RunSuccessConfig" />
<RunInfoCard type="danger" style="margin-top: 15px" v-bind="RunFailedConfig" /> <RunInfoCard type="danger" style="margin-top: 15px" v-bind="RunFailedConfig" />
<RunInfoCard type="info" v-bind="RunSuccessConfig" />
</el-col> </el-col>
</el-row> </el-row>
</template> </template>
@@ -14,6 +14,7 @@
import DetailCard from '@/components/DetailCard/index' import DetailCard from '@/components/DetailCard/index'
import { toSafeLocalDateStr } from '@/utils/common' import { toSafeLocalDateStr } from '@/utils/common'
import RunInfoCard from '../../RunInfoCard' import RunInfoCard from '../../RunInfoCard'
import { toLastFailureDisplay, toLastSucessDisplay } from '../business'
export default { export default {
name: 'AdhocDetail', name: 'AdhocDetail',
@@ -32,24 +33,18 @@ export default {
RunSuccessConfig: { RunSuccessConfig: {
icon: 'fa-info', icon: 'fa-info',
title: this.$t('ops.lastRunSuccessHosts'), title: this.$t('ops.lastRunSuccessHosts'),
content: { contents: toLastSucessDisplay(this.object.latest_execution)
hostname: 'linux',
result: 'api没有该数据api没有该数据api没有该数据api没有该数据api没有该数据api没有该数据api没有该数据api没有该数据api没有该数据api没有该数据api没有该数据api没有该数据'
}
}, },
RunFailedConfig: { RunFailedConfig: {
icon: 'fa-info', icon: 'fa-info',
title: this.$t('ops.lastRunFailedHosts'), title: this.$t('ops.lastRunFailedHosts'),
content: { contents: toLastFailureDisplay(this.object.latest_execution)
hostname: 'window',
result: 'api没有该数据api没有该数据api没有该数据api没有该数据api没有该数据api没有该数据api没有该数据api没有该数据'
}
} }
} }
}, },
computed: { computed: {
cardTitle() { cardTitle() {
return 'api 没有该数据' return `${this.object.task_name}: ${this.object.short_id}`
}, },
detailCardItems() { detailCardItems() {
return [ return [
@@ -80,7 +75,7 @@ export default {
}, },
{ {
key: this.$t('common.createBy'), key: this.$t('common.createBy'),
value: 'api 没有该数据' value: this.object.created_by
}, },
{ {
key: this.$t('common.dateCreated'), key: this.$t('common.dateCreated'),
@@ -88,27 +83,34 @@ export default {
}, },
{ {
key: this.$t('ops.runTimes'), key: this.$t('ops.runTimes'),
value: 'api 没有该数据' value: this.object.run_times
}, },
{ {
key: this.$t('ops.lastRun'), key: this.$t('ops.lastRun'),
value: 'api 没有该数据' value: this.object.latest_execution.last_run
}, },
{ {
key: this.$t('ops.timeDelta'), key: this.$t('ops.timeDelta'),
value: 'api 没有该数据' value: this.object.latest_execution.timedelta
}, },
{ {
key: this.$t('ops.isFinished'), key: this.$t('ops.isFinished'),
value: 'api 没有该数据' value: this.toBooleanDisplay(this.object.latest_execution.is_finished)
}, },
{ {
key: this.$t('ops.isSuccess'), key: this.$t('ops.isSuccess'),
value: 'api 没有该数据' value: this.toBooleanDisplay(this.object.latest_execution.is_success)
}, },
{ {
key: this.$t('ops.tasks'), key: this.$t('ops.tasks'),
value: 'api 没有该数据' value: this.toContentsDisplay(this.object.tasks),
formatter(row, value) {
return (<div>{
value.map((content) => {
return <div>{ content }</div>
})}
</div>)
}
} }
] ]
} }
@@ -122,6 +124,23 @@ export default {
}, },
disPlayOptions(options) { disPlayOptions(options) {
return options.replace(/:/g, '=').replace(/'/g, '').replace('{', '').replace('}', '') return options.replace(/:/g, '=').replace(/'/g, '').replace('{', '').replace('}', '')
},
toContentsDisplay(contents) {
const lines = []
for (let i = 0; i < contents.length; i++) {
const content = contents[i]
lines.push(`${i}. ${content.name} ::: ${content.action.module}`)
}
return lines
},
toBooleanDisplay(value) {
if (value === true) {
return this.$t('ops.Yes')
} else if (value === false) {
return this.$t('ops.No')
} else {
return this.$t('ops.Unkown')
}
} }
} }
} }

View File

@@ -4,8 +4,8 @@
<DetailCard :title="cardTitle" :items="detailCardItems" /> <DetailCard :title="cardTitle" :items="detailCardItems" />
</el-col> </el-col>
<el-col :span="10"> <el-col :span="10">
<RunInfoCard type="primary" v-bind="RunSuccessConfig" />
<RunInfoCard type="danger" style="margin-top: 15px" v-bind="RunFailedConfig" /> <RunInfoCard type="danger" style="margin-top: 15px" v-bind="RunFailedConfig" />
<RunInfoCard type="info" v-bind="RunSuccessConfig" />
</el-col> </el-col>
</el-row> </el-row>
</template> </template>
@@ -14,6 +14,7 @@
import DetailCard from '@/components/DetailCard' import DetailCard from '@/components/DetailCard'
import { toSafeLocalDateStr } from '@/utils/common' import { toSafeLocalDateStr } from '@/utils/common'
import RunInfoCard from '../../RunInfoCard' import RunInfoCard from '../../RunInfoCard'
import { toLastFailureDisplay, toLastSucessDisplay } from '../business'
export default { export default {
name: 'HistoryExecutionDetail', name: 'HistoryExecutionDetail',
@@ -32,18 +33,12 @@ export default {
RunSuccessConfig: { RunSuccessConfig: {
icon: 'fa-info', icon: 'fa-info',
title: this.$t('ops.lastRunSuccessHosts'), title: this.$t('ops.lastRunSuccessHosts'),
content: { contents: toLastSucessDisplay(this.object)
hostname: 'linux',
result: 'api没有该数据==api没有该数据api没有该数据api没有该数据api没有该数据'
}
}, },
RunFailedConfig: { RunFailedConfig: {
icon: 'fa-info', icon: 'fa-info',
title: this.$t('ops.lastRunFailedHosts'), title: this.$t('ops.lastRunFailedHosts'),
content: { contents: toLastFailureDisplay(this.object)
hostname: 'linux',
result: 'api没有该数据==api没有该数据api没有该数据api没有该数据api没有该数据'
}
} }
} }
}, },

View File

@@ -4,8 +4,8 @@
<DetailCard :title="cardTitle" :items="detailCardItems" /> <DetailCard :title="cardTitle" :items="detailCardItems" />
</el-col> </el-col>
<el-col :span="10"> <el-col :span="10">
<RunInfoCard v-for="config in RunSuccessConfigs" :key="config.host" type="info" v-bind="config" /> <RunInfoCard type="danger" style="margin-top: 15px" v-bind="RunFailedConfig" />
<RunInfoCard v-for="config in RunFailedConfigs" :key="config.host" type="danger" style="margin-top: 15px" v-bind="config" /> <RunInfoCard type="info" v-bind="RunSuccessConfig" />
</el-col> </el-col>
</el-row> </el-row>
</template> </template>
@@ -13,6 +13,7 @@
<script type="text/jsx"> <script type="text/jsx">
import DetailCard from '@/components/DetailCard' import DetailCard from '@/components/DetailCard'
import RunInfoCard from '../RunInfoCard/index' import RunInfoCard from '../RunInfoCard/index'
import { toLastFailureDisplay, toLastSucessDisplay } from './business'
export default { export default {
name: 'TaskDetail', name: 'TaskDetail',
@@ -27,43 +28,17 @@ export default {
} }
}, },
data() { data() {
let last_success = this.object.last_success
last_success.length || (last_success = [''])
let last_failure = []
for (const host in this.object.last_failure) {
const task = this.object.last_failure[host]
const msgs = []
for (const name in task) {
msgs.push(`${name} => ${task[name].msg}`)
}
last_failure.push([host, msgs.join('\n')])
}
last_failure.length || (last_failure = [['', '']])
return {
RunSuccessConfigs: last_success.map(host => {
return { return {
RunSuccessConfig: {
icon: 'fa-info', icon: 'fa-info',
title: this.$t('ops.lastRunSuccessHosts'), title: this.$t('ops.lastRunSuccessHosts'),
content: { contents: toLastSucessDisplay(this.object.latest_execution)
hostname: host, },
result: '' RunFailedConfig: {
}
}
}),
RunFailedConfigs: last_failure.map(([host, msg]) => {
return {
icon: 'fa-info', icon: 'fa-info',
title: this.$t('ops.lastRunFailedHosts'), title: this.$t('ops.lastRunFailedHosts'),
content: { contents: toLastFailureDisplay(this.object.latest_execution)
hostname: host, },
result: msg
}
}
}),
taskData: {} taskData: {}
} }
}, },
@@ -115,7 +90,14 @@ export default {
}, },
{ {
key: this.$t('ops.contents'), key: this.$t('ops.contents'),
value: 'api 没有该数据' value: this.toContentsDisplay(this.object.contents),
formatter(row, value) {
return (<div>{
value.map((content) => {
return <div>{ content }</div>
})}
</div>)
}
}, },
{ {
key: this.$t('ops.lastExecutionOutput'), key: this.$t('ops.lastExecutionOutput'),
@@ -137,6 +119,14 @@ export default {
return this.$t('ops.No') return this.$t('ops.No')
} }
return this.$t('ops.Yes') return this.$t('ops.Yes')
},
toContentsDisplay(contents) {
const lines = []
for (let i = 0; i < contents.length; i++) {
const content = contents[i]
lines.push(`${i}. ${content.name} ::: ${content.action.module}`)
}
return lines
} }
} }
} }

View File

@@ -0,0 +1,36 @@
export const toLastSucessDisplay = function(object) {
const last_success = object && object.last_success
if (!(last_success instanceof Array)) return []
return last_success.map(host => {
return {
hostname: host,
result: ''
}
})
}
export const toLastFailureDisplay = function(object) {
const last_failure = object && object.last_failure
if (!(last_failure instanceof Object)) return []
const ret = []
for (const host in last_failure) {
const task = last_failure[host]
const msgs = []
for (const name in task) {
msgs.push(`${name} => ${task[name].msg}`)
}
ret.push(
{
hostname: host,
result: msgs.join('\n')
}
)
}
return ret
}

View File

@@ -57,9 +57,15 @@ export default {
} }
}, },
headerActions: { headerActions: {
hasSearch: false, hasSearch: true,
hasLeftActions: false, hasRefresh: true,
hasRightActions: false hasLeftActions: true,
hasRightActions: true,
hasExport: false,
hasImport: false,
hasCreate: false,
hasBulkDelete: false,
hasBulkUpdate: false
}, },
assetRelationConfig: { assetRelationConfig: {
icon: 'fa-edit', icon: 'fa-edit',

View File

@@ -54,9 +54,15 @@ export default {
} }
}, },
headerActions: { headerActions: {
hasSearch: false, hasSearch: true,
hasLeftActions: false, hasRefresh: true,
hasRightActions: false hasLeftActions: true,
hasRightActions: true,
hasExport: false,
hasImport: false,
hasCreate: false,
hasBulkDelete: false,
hasBulkUpdate: false
}, },
userRelationConfig: { userRelationConfig: {
icon: 'fa-user', icon: 'fa-user',

View File

@@ -1,7 +1,7 @@
<template> <template>
<el-row :gutter="20"> <el-row :gutter="20">
<el-col :md="14" :sm="24"> <el-col :md="14" :sm="24">
<ListTable ref="listTable" :table-config="tableConfig" :header-actions="headerActions" /> <ListTable ref="ListTable" :table-config="tableConfig" :header-actions="headerActions" />
</el-col> </el-col>
<el-col :md="10" :sm="24"> <el-col :md="10" :sm="24">
<RelationCard type="primary" v-bind="databaseAppRelationConfig" /> <RelationCard type="primary" v-bind="databaseAppRelationConfig" />
@@ -54,9 +54,15 @@ export default {
} }
}, },
headerActions: { headerActions: {
hasSearch: false, hasSearch: true,
hasLeftActions: false, hasRefresh: true,
hasRightActions: false hasLeftActions: true,
hasRightActions: true,
hasExport: false,
hasImport: false,
hasCreate: false,
hasBulkDelete: false,
hasBulkUpdate: false
}, },
databaseAppRelationConfig: { databaseAppRelationConfig: {
icon: 'fa-edit', icon: 'fa-edit',
@@ -82,7 +88,7 @@ export default {
that.iHasObjects = [...that.iHasObjects, ...objects] that.iHasObjects = [...that.iHasObjects, ...objects]
that.$refs.select2.clearSelected() that.$refs.select2.clearSelected()
this.$message.success(this.$t('common.updateSuccessMsg')) this.$message.success(this.$t('common.updateSuccessMsg'))
setTimeout(() => location.reload(), 300) this.$refs.ListTable.reloadTable()
} }
}, },
systemUserRelationConfig: { systemUserRelationConfig: {
@@ -116,7 +122,7 @@ export default {
that.iHasObjects = [...that.iHasObjects, ...objects] that.iHasObjects = [...that.iHasObjects, ...objects]
that.$refs.select2.clearSelected() that.$refs.select2.clearSelected()
this.$message.success(this.$t('common.updateSuccessMsg')) this.$message.success(this.$t('common.updateSuccessMsg'))
setTimeout(() => location.reload(), 300) this.$refs.ListTable.reloadTable()
}, },
performDelete: (item) => { performDelete: (item) => {
const itemId = item.value const itemId = item.value
@@ -133,7 +139,7 @@ export default {
that.select2.disabledValues.splice(i, 1) that.select2.disabledValues.splice(i, 1)
} }
this.$message.success(this.$t('common.deleteSuccessMsg')) this.$message.success(this.$t('common.deleteSuccessMsg'))
setTimeout(() => location.reload(), 300) this.$refs.ListTable.reloadTable()
} }
} }
} }

View File

@@ -1,7 +1,7 @@
<template> <template>
<el-row :gutter="20"> <el-row :gutter="20">
<el-col :md="14" :sm="24"> <el-col :md="14" :sm="24">
<ListTable ref="listTable" :table-config="tableConfig" :header-actions="headerActions" /> <ListTable ref="ListTable" :table-config="tableConfig" :header-actions="headerActions" />
</el-col> </el-col>
<el-col :md="10" :sm="24"> <el-col :md="10" :sm="24">
<RelationCard type="primary" v-bind="userRelationConfig" /> <RelationCard type="primary" v-bind="userRelationConfig" />
@@ -55,9 +55,15 @@ export default {
} }
}, },
headerActions: { headerActions: {
hasSearch: false, hasSearch: true,
hasLeftActions: false, hasRefresh: true,
hasRightActions: false hasLeftActions: true,
hasRightActions: true,
hasExport: false,
hasImport: false,
hasCreate: false,
hasBulkDelete: false,
hasBulkUpdate: false
}, },
userRelationConfig: { userRelationConfig: {
icon: 'fa-user', icon: 'fa-user',
@@ -86,7 +92,7 @@ export default {
that.iHasObjects = [...that.iHasObjects, ...objects] that.iHasObjects = [...that.iHasObjects, ...objects]
that.$refs.select2.clearSelected() that.$refs.select2.clearSelected()
this.$message.success(this.$t('common.updateSuccessMsg')) this.$message.success(this.$t('common.updateSuccessMsg'))
setTimeout(() => location.reload(), 300) this.$refs.ListTable.reloadTable()
} }
}, },
groupRelationConfig: { groupRelationConfig: {
@@ -112,7 +118,7 @@ export default {
that.iHasObjects = [...that.iHasObjects, ...objects] that.iHasObjects = [...that.iHasObjects, ...objects]
that.$refs.select2.clearSelected() that.$refs.select2.clearSelected()
this.$message.success(this.$t('common.updateSuccessMsg')) this.$message.success(this.$t('common.updateSuccessMsg'))
setTimeout(() => location.reload(), 300) this.$refs.ListTable.reloadTable()
}, },
performDelete: (item) => { performDelete: (item) => {
const objectId = this.object.id const objectId = this.object.id
@@ -129,7 +135,7 @@ export default {
that.select2.disabledValues.splice(i, 1) that.select2.disabledValues.splice(i, 1)
} }
this.$message.success(this.$t('common.deleteSuccessMsg')) this.$message.success(this.$t('common.deleteSuccessMsg'))
setTimeout(() => location.reload(), 300) this.$refs.ListTable.reloadTable()
} }
} }
} }

View File

@@ -1,7 +1,7 @@
<template> <template>
<el-row :gutter="20"> <el-row :gutter="20">
<el-col :md="14" :sm="24"> <el-col :md="14" :sm="24">
<ListTable ref="listTable" :table-config="tableConfig" :header-actions="headerActions" /> <ListTable ref="ListTable" :table-config="tableConfig" :header-actions="headerActions" />
</el-col> </el-col>
<el-col :md="10" :sm="24"> <el-col :md="10" :sm="24">
<RelationCard type="primary" v-bind="remoteAppRelationConfig" /> <RelationCard type="primary" v-bind="remoteAppRelationConfig" />
@@ -54,9 +54,15 @@ export default {
} }
}, },
headerActions: { headerActions: {
hasSearch: false, hasSearch: true,
hasLeftActions: false, hasRefresh: true,
hasRightActions: false hasLeftActions: true,
hasRightActions: true,
hasExport: false,
hasImport: false,
hasCreate: false,
hasBulkDelete: false,
hasBulkUpdate: false
}, },
remoteAppRelationConfig: { remoteAppRelationConfig: {
icon: 'fa-edit', icon: 'fa-edit',
@@ -78,7 +84,7 @@ export default {
that.iHasObjects = [...that.iHasObjects, ...objects] that.iHasObjects = [...that.iHasObjects, ...objects]
that.$refs.select2.clearSelected() that.$refs.select2.clearSelected()
this.$message.success(this.$t('common.updateSuccessMsg')) this.$message.success(this.$t('common.updateSuccessMsg'))
setTimeout(() => location.reload(), 300) this.$refs.ListTable.reloadTable()
} }
}, },
systemUserRelationConfig: { systemUserRelationConfig: {
@@ -109,12 +115,13 @@ export default {
that.iHasObjects = [...that.iHasObjects, ...objects] that.iHasObjects = [...that.iHasObjects, ...objects]
that.$refs.select2.clearSelected() that.$refs.select2.clearSelected()
this.$message.success(this.$t('common.updateSuccessMsg')) this.$message.success(this.$t('common.updateSuccessMsg'))
setTimeout(() => location.reload(), 300) this.$refs.ListTable.reloadTable()
}, },
performDelete: (item) => { performDelete: (item) => {
const objectId = this.object.id const objectId = this.object.id
const relationUrl = `/api/v1/perms/remote-app-permissions/${objectId}/` const relationUrl = `/api/v1/perms/remote-app-permissions/${objectId}/`
const objectOldRelationSystemUsers = this.object.system_users const objectOldRelationSystemUsers = this.object.system_users
console.log(1, objectOldRelationSystemUsers, item)
const objectNewRelationSystemUsers = objectOldRelationSystemUsers.filter(v => v !== item.value) const objectNewRelationSystemUsers = objectOldRelationSystemUsers.filter(v => v !== item.value)
const data = { system_users: objectNewRelationSystemUsers } const data = { system_users: objectNewRelationSystemUsers }
return this.$axios.patch(relationUrl, data) return this.$axios.patch(relationUrl, data)
@@ -128,7 +135,7 @@ export default {
that.select2.disabledValues.splice(i, 1) that.select2.disabledValues.splice(i, 1)
} }
this.$message.success(this.$t('common.deleteSuccessMsg')) this.$message.success(this.$t('common.deleteSuccessMsg'))
setTimeout(() => location.reload(), 300) this.$refs.ListTable.reloadTable()
} }
} }
} }

View File

@@ -1,7 +1,7 @@
<template> <template>
<el-row :gutter="20"> <el-row :gutter="20">
<el-col :md="14" :sm="24"> <el-col :md="14" :sm="24">
<ListTable ref="listTable" :table-config="tableConfig" :header-actions="headerActions" /> <ListTable ref="ListTable" :table-config="tableConfig" :header-actions="headerActions" />
</el-col> </el-col>
<el-col :md="10" :sm="24"> <el-col :md="10" :sm="24">
<RelationCard type="primary" v-bind="userRelationConfig" /> <RelationCard type="primary" v-bind="userRelationConfig" />
@@ -54,9 +54,15 @@ export default {
} }
}, },
headerActions: { headerActions: {
hasSearch: false, hasSearch: true,
hasLeftActions: false, hasRefresh: true,
hasRightActions: false hasLeftActions: true,
hasRightActions: true,
hasExport: false,
hasImport: false,
hasCreate: false,
hasBulkDelete: false,
hasBulkUpdate: false
}, },
userRelationConfig: { userRelationConfig: {
icon: 'fa-user', icon: 'fa-user',
@@ -81,7 +87,7 @@ export default {
that.iHasObjects = [...that.iHasObjects, ...objects] that.iHasObjects = [...that.iHasObjects, ...objects]
that.$refs.select2.clearSelected() that.$refs.select2.clearSelected()
this.$message.success(this.$t('common.updateSuccessMsg')) this.$message.success(this.$t('common.updateSuccessMsg'))
setTimeout(() => location.reload(), 300) this.$refs.ListTable.reloadTable()
} }
}, },
groupRelationConfig: { groupRelationConfig: {
@@ -104,7 +110,7 @@ export default {
that.iHasObjects = [...that.iHasObjects, ...objects] that.iHasObjects = [...that.iHasObjects, ...objects]
that.$refs.select2.clearSelected() that.$refs.select2.clearSelected()
this.$message.success(this.$t('common.updateSuccessMsg')) this.$message.success(this.$t('common.updateSuccessMsg'))
setTimeout(() => location.reload(), 300) this.$refs.ListTable.reloadTable()
}, },
performDelete: (item) => { performDelete: (item) => {
const objectId = this.object.id const objectId = this.object.id
@@ -123,7 +129,7 @@ export default {
that.select2.disabledValues.splice(i, 1) that.select2.disabledValues.splice(i, 1)
} }
this.$message.success(this.$t('common.deleteSuccessMsg')) this.$message.success(this.$t('common.deleteSuccessMsg'))
setTimeout(() => location.reload(), 300) this.$refs.ListTable.reloadTable()
} }
} }
} }

View File

@@ -29,7 +29,7 @@ export default {
tableConfig: { tableConfig: {
url: this.url, url: this.url,
columns: [ columns: [
'user', 'asset', 'system_user', 'remote_addr', 'protocol', 'login_from', 'index', 'user', 'asset', 'system_user', 'remote_addr', 'protocol', 'login_from',
'command_amount', 'date_start', 'duration', 'actions' 'command_amount', 'date_start', 'duration', 'actions'
], ],
columnsMeta: { columnsMeta: {
@@ -38,7 +38,9 @@ export default {
align: 'center', align: 'center',
width: '60px', width: '60px',
formatter: function(row, column, cellValue, index) { formatter: function(row, column, cellValue, index) {
return <a class='detail el-link el-link--success is-underline' href= { '/terminal/sessions/' + row.id }>{ index + 1}</a> const label = index + 1
const route = { to: { name: 'SessionDetail', params: { id: row.id }}}
return <router-link {...{ attrs: route }}>{ label }</router-link>
} }
}, },
command_amount: { command_amount: {

View File

@@ -1,7 +1,7 @@
<template> <template>
<ListTable :table-config="ticketTableConfig" :header-actions="ticketActions" /> <ListTable :table-config="ticketTableConfig" :header-actions="ticketActions" />
</template> </template>
<script> <script type="text/jsx">
import ListTable from '@/components/ListTable' import ListTable from '@/components/ListTable'
import { DetailFormatter } from '@/components/ListTable/formatters' import { DetailFormatter } from '@/components/ListTable/formatters'
import { toSafeLocalDateStr } from '@/utils/common' import { toSafeLocalDateStr } from '@/utils/common'

View File

@@ -13,6 +13,7 @@
import { mapGetters } from 'vuex' import { mapGetters } from 'vuex'
import { GenericListPage } from '@/layout/components' import { GenericListPage } from '@/layout/components'
import { GenericUpdateFormDialog } from '@/layout/components' import { GenericUpdateFormDialog } from '@/layout/components'
import { createSourceIdCache } from '@/api/common'
export default { export default {
components: { components: {
@@ -55,7 +56,16 @@ export default {
} }
}, },
headerActions: { headerActions: {
hasBulkDelete: false,
extraMoreActions: [ extraMoreActions: [
{
title: this.$t('common.deleteSelected'),
name: 'deleteSelected',
can({ selectedRows }) {
return selectedRows.length > 0
},
callback: this.bulkDeleteCallback.bind(this)
},
{ {
name: 'disableSelected', name: 'disableSelected',
title: this.$t('common.disableSelected'), title: this.$t('common.disableSelected'),
@@ -153,6 +163,11 @@ export default {
return this.currentOrg.id === 'DEFAULT' || this.currentOrg.id === '' return this.currentOrg.id === 'DEFAULT' || this.currentOrg.id === ''
} }
}, },
mounted() {
if (!this.currentOrgIsDefault) {
this.headerActions.extraMoreActions[0].title = this.$t('common.removeSelected')
}
},
methods: { methods: {
removeUserFromOrg({ row, col, reload }) { removeUserFromOrg({ row, col, reload }) {
const msg = this.$t('users.removeFromOrgWarningMsg') + ' "' + row.name + '"' const msg = this.$t('users.removeFromOrgWarningMsg') + ' "' + row.name + '"'
@@ -180,6 +195,52 @@ export default {
} }
} }
}) })
},
bulkDeleteCallback({ selectedRows, reloadTable }) {
let msgPrefix = this.$t('common.deleteWarningMsg')
if (!this.currentOrgIsDefault) {
msgPrefix = this.$t('common.removeWarningMsg')
}
const msg = msgPrefix + ' ' + selectedRows.length + ' ' + this.$t('common.rows') + ' ?'
const title = this.$t('common.Info')
const performDelete = this.performBulkDelete
this.$alert(msg, title, {
type: 'warning',
confirmButtonClass: 'el-button--danger',
showCancelButton: true,
beforeClose: async(action, instance, done) => {
if (action !== 'confirm') return done()
instance.confirmButtonLoading = true
try {
await performDelete(selectedRows)
done()
reloadTable()
let successMsg = this.$t('common.bulkDeleteSuccessMsg')
if (!this.currentOrgIsDefault) {
successMsg = this.$t('common.bulkRemoveSuccessMsg')
}
this.$message.success(successMsg)
} catch (error) {
let errorMsg = this.$t('common.bulkDeleteErrorMsg')
if (!this.currentOrgIsDefault) {
errorMsg = this.$t('common.bulkRemoveErrorMsg')
}
this.$message.error(errorMsg + error)
} finally {
instance.confirmButtonLoading = false
}
}
}).catch(() => {
/* 取消*/
})
},
async performBulkDelete(selectedRows) {
const ids = selectedRows.map((v) => {
return v.id
})
const data = await createSourceIdCache(ids)
const url = `${this.tableConfig.url}?spm=` + data.spm
return this.$axios.delete(url)
} }
} }
} }

View File

@@ -26,11 +26,11 @@ export default {
hidden: (formValue) => { hidden: (formValue) => {
return !formValue.is_periodic return !formValue.is_periodic
}, },
helpTips: this.$t('xpack.ChangeAuthPlan.HelpText.CrontabOfCreateUpdatePage') helpText: this.$t('xpack.ChangeAuthPlan.HelpText.CrontabOfCreateUpdatePage')
}, },
interval: { interval: {
label: this.$t('xpack.ChangeAuthPlan.CyclePerform'), label: this.$t('xpack.ChangeAuthPlan.CyclePerform'),
helpTips: this.$t('xpack.ChangeAuthPlan.HelpText.IntervalOfCreateUpdatePage'), helpText: this.$t('xpack.ChangeAuthPlan.HelpText.IntervalOfCreateUpdatePage'),
hidden: (formValue) => { hidden: (formValue) => {
return !formValue.is_periodic return !formValue.is_periodic
} }

View File

@@ -295,7 +295,7 @@ export default {
}, },
MFAConfirm() { MFAConfirm() {
if (this.MFAInput.length !== 6) { if (this.MFAInput.length !== 6) {
return this.$message.error(this.$t('common.updateErrorMsg')) return this.$message.error(this.$t('common.MFAErrorMsg'))
} }
this.$axios.post( this.$axios.post(
`/api/v1/authentication/otp/verify/`, { `/api/v1/authentication/otp/verify/`, {