Compare commits
16 Commits
dependabot
...
master
| Author | SHA1 | Date |
|---|---|---|
|
|
17e41ce1fc | |
|
|
baae56f715 | |
|
|
9a7493c99c | |
|
|
cc60ff1a27 | |
|
|
c0e5f2ccec | |
|
|
3fa8995690 | |
|
|
a4d4b28ce3 | |
|
|
d7a530db46 | |
|
|
7f5fbb7426 | |
|
|
6000da4220 | |
|
|
c0aec854af | |
|
|
8062905b17 | |
|
|
baf063f9ea | |
|
|
8d42b936e5 | |
|
|
da1dafda54 | |
|
|
f0d60a8242 |
|
|
@ -1,3 +1,5 @@
|
||||||
|
|
||||||
|
|
||||||
简体中文 | [English](./README.en-US.md)
|
简体中文 | [English](./README.en-US.md)
|
||||||
<h1 align="center">Vue Antd Admin</h1>
|
<h1 align="center">Vue Antd Admin</h1>
|
||||||
|
|
||||||
|
|
@ -6,6 +8,12 @@
|
||||||
[Ant Design Pro](https://github.com/ant-design/ant-design-pro) 的 Vue 实现版本
|
[Ant Design Pro](https://github.com/ant-design/ant-design-pro) 的 Vue 实现版本
|
||||||
开箱即用的中后台前端/设计解决方案
|
开箱即用的中后台前端/设计解决方案
|
||||||
|
|
||||||
|
:star::star::star:
|
||||||
|
vue3 版本现已推出,更名为
|
||||||
|
[stepin-template](https://github.com/stepui/stepin-template),欢迎体验,
|
||||||
|
[立即前往](https://github.com/stepui/stepin-template)
|
||||||
|
--
|
||||||
|
|
||||||
[](https://github.com/iczer/vue-antd-admin/blob/master/LICENSE)
|
[](https://github.com/iczer/vue-antd-admin/blob/master/LICENSE)
|
||||||
[](https://david-dm.org/iczer/vue-antd-admin)
|
[](https://david-dm.org/iczer/vue-antd-admin)
|
||||||
[](https://david-dm.org/iczer/vue-antd-admin?type=dev)
|
[](https://david-dm.org/iczer/vue-antd-admin?type=dev)
|
||||||
|
|
|
||||||
|
|
@ -44,7 +44,7 @@ const tokenCheck = {
|
||||||
* `options: Object`: 应用配置,包含: {router, i18n, store, message},可根据需要扩展。
|
* `options: Object`: 应用配置,包含: {router, i18n, store, message},可根据需要扩展。
|
||||||
|
|
||||||
### onRejected
|
### onRejected
|
||||||
我们会为 onFulfilled 钩子函数注入 error 和 options 两个参数:
|
我们会为 onRejected 钩子函数注入 error 和 options 两个参数:
|
||||||
* `error: Error`: axios 请求错误对象
|
* `error: Error`: axios 请求错误对象
|
||||||
* `options: Object`: 应用配置,包含: {router, i18n, store, message},可根据需要扩展。
|
* `options: Object`: 应用配置,包含: {router, i18n, store, message},可根据需要扩展。
|
||||||
|
|
||||||
|
|
@ -128,4 +128,4 @@ export default {
|
||||||
response: [resp401, resp403] // 响应拦截
|
response: [resp401, resp403] // 响应拦截
|
||||||
}
|
}
|
||||||
```
|
```
|
||||||
:::
|
:::
|
||||||
|
|
|
||||||
|
|
@ -23,7 +23,7 @@
|
||||||
:expandedRowKeys="expandedRowKeys"
|
:expandedRowKeys="expandedRowKeys"
|
||||||
:expandedRowRender="expandedRowRender"
|
:expandedRowRender="expandedRowRender"
|
||||||
@change="onChange"
|
@change="onChange"
|
||||||
:rowSelection="selectedRows ? {selectedRowKeys: selectedRowKeys, onChange: updateSelect} : undefined"
|
:rowSelection="selectedRows ? {selectedRowKeys, onSelect, onSelectAll} : undefined"
|
||||||
>
|
>
|
||||||
<template slot-scope="text, record, index" :slot="slot" v-for="slot in Object.keys($scopedSlots).filter(key => key !== 'expandedRowRender') ">
|
<template slot-scope="text, record, index" :slot="slot" v-for="slot in Object.keys($scopedSlots).filter(key => key !== 'expandedRowRender') ">
|
||||||
<slot :name="slot" v-bind="{text, record, index}"></slot>
|
<slot :name="slot" v-bind="{text, record, index}"></slot>
|
||||||
|
|
@ -64,22 +64,70 @@ export default {
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
methods: {
|
methods: {
|
||||||
updateSelect (selectedRowKeys, selectedRows) {
|
equals(record1, record2) {
|
||||||
this.$emit('update:selectedRows', selectedRows)
|
if (record1 === record2) {
|
||||||
this.$emit('selectedRowChange', selectedRowKeys, selectedRows)
|
return true
|
||||||
|
}
|
||||||
|
const {rowKey} = this
|
||||||
|
if (rowKey && typeof rowKey === 'string') {
|
||||||
|
return record1[rowKey] === record2[rowKey]
|
||||||
|
} else if (rowKey && typeof rowKey === 'function') {
|
||||||
|
return rowKey(record1) === rowKey(record2)
|
||||||
|
}
|
||||||
|
return false
|
||||||
|
},
|
||||||
|
contains(arr, item) {
|
||||||
|
if (!arr || arr.length === 0) {
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
const {equals} = this
|
||||||
|
for (let i = 0; i < arr.length; i++) {
|
||||||
|
if (equals(arr[i], item)) {
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false
|
||||||
|
},
|
||||||
|
onSelectAll(selected, rows) {
|
||||||
|
const {getKey, contains} = this
|
||||||
|
const unselected = this.dataSource.filter(item => !contains(rows, item, this.rowKey))
|
||||||
|
const _selectedRows = this.selectedRows.filter(item => !contains(unselected, item, this.rowKey))
|
||||||
|
const set = {}
|
||||||
|
_selectedRows.forEach(item => set[getKey(item)] = item)
|
||||||
|
rows.forEach(item => set[getKey(item)] = item)
|
||||||
|
const _rows = Object.values(set)
|
||||||
|
this.$emit('update:selectedRows', _rows)
|
||||||
|
this.$emit('selectedRowChange', _rows.map(item => getKey(item)), _rows)
|
||||||
|
},
|
||||||
|
getKey(record) {
|
||||||
|
const {rowKey} = this
|
||||||
|
if (!rowKey || !record) {
|
||||||
|
return undefined
|
||||||
|
}
|
||||||
|
if (typeof rowKey === 'string') {
|
||||||
|
return record[rowKey]
|
||||||
|
} else {
|
||||||
|
return rowKey(record)
|
||||||
|
}
|
||||||
|
},
|
||||||
|
onSelect(record, selected) {
|
||||||
|
const {equals, selectedRows, getKey} = this
|
||||||
|
const _selectedRows = selected ? [...selectedRows, record] : selectedRows.filter(row => !equals(row, record))
|
||||||
|
this.$emit('update:selectedRows', _selectedRows)
|
||||||
|
this.$emit('selectedRowChange', _selectedRows.map(item => getKey(item)), _selectedRows)
|
||||||
},
|
},
|
||||||
initTotalList (columns) {
|
initTotalList (columns) {
|
||||||
const totalList = columns.filter(item => item.needTotal)
|
return columns.filter(item => item.needTotal)
|
||||||
.map(item => {
|
.map(item => {
|
||||||
return {
|
return {
|
||||||
...item,
|
...item,
|
||||||
total: 0
|
total: 0
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
return totalList
|
|
||||||
},
|
},
|
||||||
onClear() {
|
onClear() {
|
||||||
this.updateSelect([], [])
|
this.$emit('update:selectedRows', [])
|
||||||
|
this.$emit('selectedRowChange', [], [])
|
||||||
this.$emit('clear')
|
this.$emit('clear')
|
||||||
},
|
},
|
||||||
onChange(pagination, filters, sorter, {currentDataSource}) {
|
onChange(pagination, filters, sorter, {currentDataSource}) {
|
||||||
|
|
@ -110,10 +158,8 @@ export default {
|
||||||
},
|
},
|
||||||
computed: {
|
computed: {
|
||||||
selectedRowKeys() {
|
selectedRowKeys() {
|
||||||
return this.selectedRows.map(record => {
|
return this.selectedRows.map(record => this.getKey(record))
|
||||||
return (typeof this.rowKey === 'function') ? this.rowKey(record) : record[this.rowKey]
|
},
|
||||||
})
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
</script>
|
</script>
|
||||||
|
|
|
||||||
|
|
@ -22,10 +22,11 @@ const ANTD = {
|
||||||
'component-background': '#fff',
|
'component-background': '#fff',
|
||||||
'heading-color': 'rgba(0, 0, 0, 0.85)',
|
'heading-color': 'rgba(0, 0, 0, 0.85)',
|
||||||
'text-color': 'rgba(0, 0, 0, 0.65)',
|
'text-color': 'rgba(0, 0, 0, 0.65)',
|
||||||
'text-color-inverse': '#fff',
|
'text-color-inverse': '#fefefe',
|
||||||
'text-color-secondary': 'rgba(0, 0, 0, 0.45)',
|
'text-color-secondary': 'rgba(0, 0, 0, 0.45)',
|
||||||
'shadow-color': 'rgba(0, 0, 0, 0.15)',
|
'shadow-color': 'rgba(0, 0, 0, 0.15)',
|
||||||
'border-color-split': '#f0f0f0',
|
'border-color-split': '#f0f0f0',
|
||||||
|
'border-color-base': '#d9d9d9',
|
||||||
'background-color-light': '#fafafa',
|
'background-color-light': '#fafafa',
|
||||||
'background-color-base': '#f5f5f5',
|
'background-color-base': '#f5f5f5',
|
||||||
'table-selected-row-bg': '#fafafa',
|
'table-selected-row-bg': '#fafafa',
|
||||||
|
|
@ -34,8 +35,9 @@ const ANTD = {
|
||||||
'disabled-color': 'rgba(0, 0, 0, 0.25)',
|
'disabled-color': 'rgba(0, 0, 0, 0.25)',
|
||||||
'menu-dark-color': 'rgba(254, 254, 254, 0.65)',
|
'menu-dark-color': 'rgba(254, 254, 254, 0.65)',
|
||||||
'menu-dark-highlight-color': '#fefefe',
|
'menu-dark-highlight-color': '#fefefe',
|
||||||
|
'menu-dark-selected-item-icon-color': '#fefefe',
|
||||||
'menu-dark-arrow-color': '#fefefe',
|
'menu-dark-arrow-color': '#fefefe',
|
||||||
'btn-primary-color': '#fff',
|
'btn-primary-color': '#fefefe',
|
||||||
},
|
},
|
||||||
light: {
|
light: {
|
||||||
'layout-body-background': '#f0f2f5',
|
'layout-body-background': '#f0f2f5',
|
||||||
|
|
@ -43,10 +45,11 @@ const ANTD = {
|
||||||
'component-background': '#fff',
|
'component-background': '#fff',
|
||||||
'heading-color': 'rgba(0, 0, 0, 0.85)',
|
'heading-color': 'rgba(0, 0, 0, 0.85)',
|
||||||
'text-color': 'rgba(0, 0, 0, 0.65)',
|
'text-color': 'rgba(0, 0, 0, 0.65)',
|
||||||
'text-color-inverse': '#fff',
|
'text-color-inverse': '#fefefe',
|
||||||
'text-color-secondary': 'rgba(0, 0, 0, 0.45)',
|
'text-color-secondary': 'rgba(0, 0, 0, 0.45)',
|
||||||
'shadow-color': 'rgba(0, 0, 0, 0.15)',
|
'shadow-color': 'rgba(0, 0, 0, 0.15)',
|
||||||
'border-color-split': '#f0f0f0',
|
'border-color-split': '#f0f0f0',
|
||||||
|
'border-color-base': '#d9d9d9',
|
||||||
'background-color-light': '#fafafa',
|
'background-color-light': '#fafafa',
|
||||||
'background-color-base': '#f5f5f5',
|
'background-color-base': '#f5f5f5',
|
||||||
'table-selected-row-bg': '#fafafa',
|
'table-selected-row-bg': '#fafafa',
|
||||||
|
|
@ -55,8 +58,9 @@ const ANTD = {
|
||||||
'disabled-color': 'rgba(0, 0, 0, 0.25)',
|
'disabled-color': 'rgba(0, 0, 0, 0.25)',
|
||||||
'menu-dark-color': 'rgba(1, 1, 1, 0.65)',
|
'menu-dark-color': 'rgba(1, 1, 1, 0.65)',
|
||||||
'menu-dark-highlight-color': '#fefefe',
|
'menu-dark-highlight-color': '#fefefe',
|
||||||
|
'menu-dark-selected-item-icon-color': '#fefefe',
|
||||||
'menu-dark-arrow-color': '#fefefe',
|
'menu-dark-arrow-color': '#fefefe',
|
||||||
'btn-primary-color': '#fff',
|
'btn-primary-color': '#fefefe',
|
||||||
},
|
},
|
||||||
night: {
|
night: {
|
||||||
'layout-body-background': '#000',
|
'layout-body-background': '#000',
|
||||||
|
|
@ -64,10 +68,11 @@ const ANTD = {
|
||||||
'component-background': '#141414',
|
'component-background': '#141414',
|
||||||
'heading-color': 'rgba(255, 255, 255, 0.85)',
|
'heading-color': 'rgba(255, 255, 255, 0.85)',
|
||||||
'text-color': 'rgba(255, 255, 255, 0.85)',
|
'text-color': 'rgba(255, 255, 255, 0.85)',
|
||||||
'text-color-inverse': '#141414',
|
'text-color-inverse': '#fefefe',
|
||||||
'text-color-secondary': 'rgba(255, 255, 255, 0.45)',
|
'text-color-secondary': 'rgba(255, 255, 255, 0.45)',
|
||||||
'shadow-color': 'rgba(255, 255, 255, 0.15)',
|
'shadow-color': 'rgba(255, 255, 255, 0.15)',
|
||||||
'border-color-split': '#303030',
|
'border-color-split': '#303030',
|
||||||
|
'border-color-base': '#282828',
|
||||||
'background-color-light': '#ffffff0a',
|
'background-color-light': '#ffffff0a',
|
||||||
'background-color-base': '#2a2a2a',
|
'background-color-base': '#2a2a2a',
|
||||||
'table-selected-row-bg': '#ffffff0a',
|
'table-selected-row-bg': '#ffffff0a',
|
||||||
|
|
@ -76,8 +81,9 @@ const ANTD = {
|
||||||
'disabled-color': 'rgba(255, 255, 255, 0.25)',
|
'disabled-color': 'rgba(255, 255, 255, 0.25)',
|
||||||
'menu-dark-color': 'rgba(254, 254, 254, 0.65)',
|
'menu-dark-color': 'rgba(254, 254, 254, 0.65)',
|
||||||
'menu-dark-highlight-color': '#fefefe',
|
'menu-dark-highlight-color': '#fefefe',
|
||||||
|
'menu-dark-selected-item-icon-color': '#fefefe',
|
||||||
'menu-dark-arrow-color': '#fefefe',
|
'menu-dark-arrow-color': '#fefefe',
|
||||||
'btn-primary-color': '#141414',
|
'btn-primary-color': '#fefefe',
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -92,7 +92,7 @@ export default {
|
||||||
let routes = this.$route.matched
|
let routes = this.$route.matched
|
||||||
const path = this.$route.path
|
const path = this.$route.path
|
||||||
let breadcrumb = []
|
let breadcrumb = []
|
||||||
routes.filter(item => path.includes(item.path))
|
routes.filter(item => path.includes(item.path) || item.regex.test(path))
|
||||||
.forEach(route => {
|
.forEach(route => {
|
||||||
const path = route.path.length === 0 ? '/home' : route.path
|
const path = route.path.length === 0 ? '/home' : route.path
|
||||||
breadcrumb.push(this.$t(getI18nKey(path)))
|
breadcrumb.push(this.$t(getI18nKey(path)))
|
||||||
|
|
|
||||||
|
|
@ -95,8 +95,7 @@
|
||||||
this.$emit('contextmenu', pageKey, e)
|
this.$emit('contextmenu', pageKey, e)
|
||||||
},
|
},
|
||||||
pageName(page) {
|
pageName(page) {
|
||||||
const pagePath = page.fullPath.split('?')[0]
|
const custom = this.customTitles.find(item => item.path === page.path)
|
||||||
const custom = this.customTitles.find(item => item.path === pagePath)
|
|
||||||
return (custom && custom.title) || page.title || this.$t(getI18nKey(page.keyPath))
|
return (custom && custom.title) || page.title || this.$t(getI18nKey(page.keyPath))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -13,7 +13,7 @@
|
||||||
<div :class="['tabs-view-content', layout, pageWidth]" :style="`margin-top: ${multiPage ? -24 : 0}px`">
|
<div :class="['tabs-view-content', layout, pageWidth]" :style="`margin-top: ${multiPage ? -24 : 0}px`">
|
||||||
<page-toggle-transition :disabled="animate.disabled" :animate="animate.name" :direction="animate.direction">
|
<page-toggle-transition :disabled="animate.disabled" :animate="animate.name" :direction="animate.direction">
|
||||||
<a-keep-alive :exclude-keys="excludeKeys" v-if="multiPage && cachePage" v-model="clearCaches">
|
<a-keep-alive :exclude-keys="excludeKeys" v-if="multiPage && cachePage" v-model="clearCaches">
|
||||||
<router-view v-if="!refreshing" ref="tabContent" :key="$route.path" />
|
<router-view v-if="!refreshing" ref="tabContent" :key="$route.fullPath" />
|
||||||
</a-keep-alive>
|
</a-keep-alive>
|
||||||
<router-view ref="tabContent" v-else-if="!refreshing" />
|
<router-view ref="tabContent" v-else-if="!refreshing" />
|
||||||
</page-toggle-transition>
|
</page-toggle-transition>
|
||||||
|
|
@ -62,10 +62,10 @@ export default {
|
||||||
this.loadCacheConfig(this.$router?.options?.routes)
|
this.loadCacheConfig(this.$router?.options?.routes)
|
||||||
this.loadCachedTabs()
|
this.loadCachedTabs()
|
||||||
const route = this.$route
|
const route = this.$route
|
||||||
if (this.pageList.findIndex(item => item.path === route.path) === -1) {
|
if (this.pageList.findIndex(item => item.path === route.fullPath) === -1) {
|
||||||
this.pageList.push(this.createPage(route))
|
this.pageList.push(this.createPage(route))
|
||||||
}
|
}
|
||||||
this.activePage = route.path
|
this.activePage = route.fullPath
|
||||||
if (this.multiPage) {
|
if (this.multiPage) {
|
||||||
this.$nextTick(() => {
|
this.$nextTick(() => {
|
||||||
this.setCachedKey(route)
|
this.setCachedKey(route)
|
||||||
|
|
@ -86,8 +86,8 @@ export default {
|
||||||
this.loadCacheConfig(val)
|
this.loadCacheConfig(val)
|
||||||
},
|
},
|
||||||
'$route': function (newRoute) {
|
'$route': function (newRoute) {
|
||||||
this.activePage = newRoute.path
|
this.activePage = newRoute.fullPath
|
||||||
const page = this.pageList.find(item => item.path === newRoute.path)
|
const page = this.pageList.find(item => item.path === newRoute.fullPath)
|
||||||
if (!this.multiPage) {
|
if (!this.multiPage) {
|
||||||
this.pageList = [this.createPage(newRoute)]
|
this.pageList = [this.createPage(newRoute)]
|
||||||
} else if (page) {
|
} else if (page) {
|
||||||
|
|
@ -261,7 +261,7 @@ export default {
|
||||||
return {
|
return {
|
||||||
keyPath: route.matched[route.matched.length - 1].path,
|
keyPath: route.matched[route.matched.length - 1].path,
|
||||||
fullPath: route.fullPath, loading: false,
|
fullPath: route.fullPath, loading: false,
|
||||||
path: route.path,
|
path: route.fullPath,
|
||||||
title: route.meta && route.meta.page && route.meta.page.title,
|
title: route.meta && route.meta.page && route.meta.page.title,
|
||||||
unclose: route.meta && route.meta.page && (route.meta.page.closable === false),
|
unclose: route.meta && route.meta.page && (route.meta.page.closable === false),
|
||||||
}
|
}
|
||||||
|
|
@ -271,7 +271,7 @@ export default {
|
||||||
* @param route 页面对应的路由
|
* @param route 页面对应的路由
|
||||||
*/
|
*/
|
||||||
setCachedKey(route) {
|
setCachedKey(route) {
|
||||||
const page = this.pageList.find(item => item.path === route.path)
|
const page = this.pageList.find(item => item.path === route.fullPath)
|
||||||
page.unclose = route.meta && route.meta.page && (route.meta.page.closable === false)
|
page.unclose = route.meta && route.meta.page && (route.meta.page.closable === false)
|
||||||
if (!page._init_) {
|
if (!page._init_) {
|
||||||
const vnode = this.$refs.tabContent.$vnode
|
const vnode = this.$refs.tabContent.$vnode
|
||||||
|
|
@ -301,7 +301,7 @@ export default {
|
||||||
routes.forEach(item => {
|
routes.forEach(item => {
|
||||||
const cacheAble = item.meta?.page?.cacheAble ?? pCache ?? true
|
const cacheAble = item.meta?.page?.cacheAble ?? pCache ?? true
|
||||||
if (!cacheAble) {
|
if (!cacheAble) {
|
||||||
this.excludeKeys.push(new RegExp(`${item.path}\\d+$`))
|
this.excludeKeys.push(new RegExp(`${item.path.replace(/:[^/]*/g, '[^/]*')}(\\?.*)?\\d*$`))
|
||||||
}
|
}
|
||||||
if (item.children) {
|
if (item.children) {
|
||||||
this.loadCacheConfig(item.children, cacheAble)
|
this.loadCacheConfig(item.children, cacheAble)
|
||||||
|
|
|
||||||
|
|
@ -5,6 +5,7 @@ import '@/mock/user/login'
|
||||||
import '@/mock/workplace'
|
import '@/mock/workplace'
|
||||||
import '@/mock/user/routes'
|
import '@/mock/user/routes'
|
||||||
import '@/mock/goods'
|
import '@/mock/goods'
|
||||||
|
import '@/mock/list'
|
||||||
|
|
||||||
// 设置全局延时
|
// 设置全局延时
|
||||||
Mock.setup({
|
Mock.setup({
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,52 @@
|
||||||
|
import Mock from 'mockjs'
|
||||||
|
import '@/mock/extend'
|
||||||
|
import {parseUrlParams} from '@/utils/request'
|
||||||
|
|
||||||
|
const current = new Date().getTime()
|
||||||
|
|
||||||
|
const source = Mock.mock({
|
||||||
|
'list|100': [{
|
||||||
|
'key|+1': 0,
|
||||||
|
'no': `${current}-@integer(1,100)`,
|
||||||
|
'description': '这是一段描述',
|
||||||
|
'callNo|0-50': 5,
|
||||||
|
'status|1-4': 1,
|
||||||
|
'updatedAt': '@DATETIME',
|
||||||
|
}]
|
||||||
|
})
|
||||||
|
|
||||||
|
Mock.mock(RegExp(`${process.env.VUE_APP_API_BASE_URL}/list` + '.*'),'get', ({url}) => {
|
||||||
|
const params = parseUrlParams(decodeURI(url))
|
||||||
|
let {page, pageSize} = params
|
||||||
|
page = eval(page) - 1 || 0
|
||||||
|
pageSize = eval(pageSize) || 10
|
||||||
|
|
||||||
|
delete params.page
|
||||||
|
delete params.pageSize
|
||||||
|
|
||||||
|
let result = source.list.filter(item => {
|
||||||
|
for (let [key, value] of Object.entries(params)) {
|
||||||
|
if (item[key] !== value) {
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return true
|
||||||
|
})
|
||||||
|
const total = result.length
|
||||||
|
if ((page) * pageSize > total) {
|
||||||
|
result = []
|
||||||
|
} else {
|
||||||
|
result = result.slice(page * pageSize, (page + 1) * pageSize)
|
||||||
|
}
|
||||||
|
|
||||||
|
return {
|
||||||
|
code: 0,
|
||||||
|
message: 'success',
|
||||||
|
data: {
|
||||||
|
page: page + 1,
|
||||||
|
pageSize,
|
||||||
|
total: 100,
|
||||||
|
list: result
|
||||||
|
}
|
||||||
|
}
|
||||||
|
})
|
||||||
|
|
@ -98,6 +98,7 @@
|
||||||
:selectedRows.sync="selectedRows"
|
:selectedRows.sync="selectedRows"
|
||||||
@clear="onClear"
|
@clear="onClear"
|
||||||
@change="onChange"
|
@change="onChange"
|
||||||
|
:pagination="{...pagination, onChange: onPageChange}"
|
||||||
@selectedRowChange="onSelectChange"
|
@selectedRowChange="onSelectChange"
|
||||||
>
|
>
|
||||||
<div slot="description" slot-scope="{text}">
|
<div slot="description" slot-scope="{text}">
|
||||||
|
|
@ -128,6 +129,7 @@
|
||||||
|
|
||||||
<script>
|
<script>
|
||||||
import StandardTable from '@/components/table/StandardTable'
|
import StandardTable from '@/components/table/StandardTable'
|
||||||
|
import {request} from '@/utils/request'
|
||||||
const columns = [
|
const columns = [
|
||||||
{
|
{
|
||||||
title: '规则编号',
|
title: '规则编号',
|
||||||
|
|
@ -161,19 +163,6 @@ const columns = [
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
|
|
||||||
const dataSource = []
|
|
||||||
|
|
||||||
for (let i = 0; i < 100; i++) {
|
|
||||||
dataSource.push({
|
|
||||||
key: i,
|
|
||||||
no: 'NO ' + i,
|
|
||||||
description: '这是一段描述',
|
|
||||||
callNo: Math.floor(Math.random() * 1000),
|
|
||||||
status: Math.floor(Math.random() * 10) % 4,
|
|
||||||
updatedAt: '2018-07-26'
|
|
||||||
})
|
|
||||||
}
|
|
||||||
|
|
||||||
export default {
|
export default {
|
||||||
name: 'QueryList',
|
name: 'QueryList',
|
||||||
components: {StandardTable},
|
components: {StandardTable},
|
||||||
|
|
@ -181,14 +170,37 @@ export default {
|
||||||
return {
|
return {
|
||||||
advanced: true,
|
advanced: true,
|
||||||
columns: columns,
|
columns: columns,
|
||||||
dataSource: dataSource,
|
dataSource: [],
|
||||||
selectedRows: []
|
selectedRows: [],
|
||||||
|
pagination: {
|
||||||
|
current: 1,
|
||||||
|
pageSize: 10,
|
||||||
|
total: 0
|
||||||
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
authorize: {
|
authorize: {
|
||||||
deleteRecord: 'delete'
|
deleteRecord: 'delete'
|
||||||
},
|
},
|
||||||
|
mounted() {
|
||||||
|
this.getData()
|
||||||
|
},
|
||||||
methods: {
|
methods: {
|
||||||
|
onPageChange(page, pageSize) {
|
||||||
|
this.pagination.current = page
|
||||||
|
this.pagination.pageSize = pageSize
|
||||||
|
this.getData()
|
||||||
|
},
|
||||||
|
getData() {
|
||||||
|
request(process.env.VUE_APP_API_BASE_URL + '/list', 'get', {page: this.pagination.current,
|
||||||
|
pageSize: this.pagination.pageSize}).then(res => {
|
||||||
|
const {list, page, pageSize, total} = res?.data?.data ?? {}
|
||||||
|
this.dataSource = list
|
||||||
|
this.pagination.current = page
|
||||||
|
this.pagination.pageSize = pageSize
|
||||||
|
this.pagination.total = total
|
||||||
|
})
|
||||||
|
},
|
||||||
deleteRecord(key) {
|
deleteRecord(key) {
|
||||||
this.dataSource = this.dataSource.filter(item => item.key !== key)
|
this.dataSource = this.dataSource.filter(item => item.key !== key)
|
||||||
this.selectedRows = this.selectedRows.filter(item => item.key !== key)
|
this.selectedRows = this.selectedRows.filter(item => item.key !== key)
|
||||||
|
|
|
||||||
|
|
@ -17,8 +17,9 @@ const TabsPagePlugin = {
|
||||||
},
|
},
|
||||||
$setPageTitle(route, title) {
|
$setPageTitle(route, title) {
|
||||||
if (title) {
|
if (title) {
|
||||||
let path = typeof route === 'object' ? route.path : route
|
// let path = typeof route === 'object' ? route.path : route
|
||||||
path = path && path.split('?')[0]
|
// path = path && path.split('?')[0]
|
||||||
|
let path = typeof route === 'object' ? this.$router.resolve(route).route.fullPath : route
|
||||||
this.$store.commit('setting/setCustomTitle', {path, title})
|
this.$store.commit('setting/setCustomTitle', {path, title})
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -26,8 +27,8 @@ const TabsPagePlugin = {
|
||||||
computed: {
|
computed: {
|
||||||
customTitle() {
|
customTitle() {
|
||||||
const customTitles = this.$store.state.setting.customTitles
|
const customTitles = this.$store.state.setting.customTitles
|
||||||
const path = this.$route.path.split('?')[0]
|
// const path = this.$route.path.split('?')[0]
|
||||||
const custom = customTitles.find(item => item.path === path)
|
const custom = customTitles.find(item => item.path === this.$route.fullPath)
|
||||||
return custom && custom.title
|
return custom && custom.title
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -8,10 +8,12 @@ function hasPermission(authority, permissions) {
|
||||||
let required = '*'
|
let required = '*'
|
||||||
if (typeof authority === 'string') {
|
if (typeof authority === 'string') {
|
||||||
required = authority
|
required = authority
|
||||||
|
} else if (Array.isArray(authority)) {
|
||||||
|
required = authority
|
||||||
} else if (typeof authority === 'object') {
|
} else if (typeof authority === 'object') {
|
||||||
required = authority.permission
|
required = authority.permission
|
||||||
}
|
}
|
||||||
return required === '*' || (permissions && permissions.findIndex(item => item === required || item.id === required) !== -1)
|
return required === '*' || hasAnyItem(required, permissions, (r, t) => !!(r === t || r === t.id))
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
@ -24,25 +26,23 @@ function hasRole(authority, roles) {
|
||||||
if (typeof authority === 'object') {
|
if (typeof authority === 'object') {
|
||||||
required = authority.role
|
required = authority.role
|
||||||
}
|
}
|
||||||
return authority === '*' || hasAnyRole(required, roles)
|
return authority === '*' || hasAnyItem(required, roles, (r, t) => !!(r === t || r === t.id))
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 判断是否有需要的任意一个角色
|
* 判断目标数组是否有所需元素
|
||||||
* @param required {String | Array[String]} 需要的角色,可以是单个角色或者一个角色数组
|
* @param {String | String[]}required 所需元素,数组或单个元素
|
||||||
* @param roles 拥有的角色
|
* @param {String[]|Object[]} source 目标数组
|
||||||
|
* @param {Function} filter 匹配条件
|
||||||
|
* (r: String, s: String|Object) => boolean
|
||||||
* @returns {boolean}
|
* @returns {boolean}
|
||||||
*/
|
*/
|
||||||
function hasAnyRole(required, roles) {
|
function hasAnyItem(required, source, filter) {
|
||||||
if (!required) {
|
if (!required) {
|
||||||
return false
|
return false
|
||||||
} else if(Array.isArray(required)) {
|
|
||||||
return roles.findIndex(role => {
|
|
||||||
return required.findIndex(item => item === role || item === role.id) !== -1
|
|
||||||
}) !== -1
|
|
||||||
} else {
|
|
||||||
return roles.findIndex(role => role === required || role.id === required) !== -1
|
|
||||||
}
|
}
|
||||||
|
let checkedList = Array.isArray(required) ? required : [required]
|
||||||
|
return !!source.find(s => checkedList.find(r => filter(r, s)))
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
|
||||||
|
|
@ -75,6 +75,9 @@ function parseRoutes(routesConfig, routerMap) {
|
||||||
redirect: routeCfg.redirect || router.redirect,
|
redirect: routeCfg.redirect || router.redirect,
|
||||||
meta: {...meta, authority: meta.authority || '*'}
|
meta: {...meta, authority: meta.authority || '*'}
|
||||||
}
|
}
|
||||||
|
if (router.beforeEnter) {
|
||||||
|
route.beforeEnter = router.beforeEnter
|
||||||
|
}
|
||||||
if (routeCfg.invisible || router.invisible) {
|
if (routeCfg.invisible || router.invisible) {
|
||||||
route.meta.invisible = true
|
route.meta.invisible = true
|
||||||
}
|
}
|
||||||
|
|
@ -212,7 +215,7 @@ function formatAuthority(routes, pAuthorities = []) {
|
||||||
let authority = {}
|
let authority = {}
|
||||||
if (!meta.authority) {
|
if (!meta.authority) {
|
||||||
authority = defaultAuthority
|
authority = defaultAuthority
|
||||||
}else if (typeof meta.authority === 'string') {
|
}else if (typeof meta.authority === 'string' || Array.isArray(meta.authority)) {
|
||||||
authority.permission = meta.authority
|
authority.permission = meta.authority
|
||||||
} else if (typeof meta.authority === 'object') {
|
} else if (typeof meta.authority === 'object') {
|
||||||
authority = meta.authority
|
authority = meta.authority
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue