All checks were successful
continuous-integration/drone/push Build is passing
- 侧边栏菜单增加「应用管理」和「企微应用」 - 租户订阅页面应用选择增加前端验证 - 后端增加 app_code 存在性验证
108 lines
3.3 KiB
Vue
108 lines
3.3 KiB
Vue
<script setup>
|
|
import { computed } from 'vue'
|
|
import { useRouter, useRoute } from 'vue-router'
|
|
import { useAuthStore } from '@/stores/auth'
|
|
import { ElMessageBox } from 'element-plus'
|
|
|
|
const router = useRouter()
|
|
const route = useRoute()
|
|
const authStore = useAuthStore()
|
|
|
|
// 菜单项
|
|
const menuItems = computed(() => {
|
|
const items = [
|
|
{ path: '/dashboard', title: '仪表盘', icon: 'Odometer' },
|
|
{ path: '/tenants', title: '租户管理', icon: 'OfficeBuilding' },
|
|
{ path: '/apps', title: '应用管理', icon: 'Grid' },
|
|
{ path: '/tenant-wechat-apps', title: '企微应用', icon: 'ChatDotRound' },
|
|
{ path: '/app-config', title: '租户订阅', icon: 'Setting' },
|
|
{ path: '/stats', title: '统计分析', icon: 'TrendCharts' },
|
|
{ path: '/logs', title: '日志查看', icon: 'Document' }
|
|
]
|
|
|
|
// 管理员才能看到用户管理
|
|
if (authStore.isAdmin) {
|
|
items.push({ path: '/users', title: '用户管理', icon: 'User' })
|
|
}
|
|
|
|
return items
|
|
})
|
|
|
|
const activeMenu = computed(() => route.path)
|
|
|
|
function handleMenuSelect(path) {
|
|
router.push(path)
|
|
}
|
|
|
|
function handleLogout() {
|
|
ElMessageBox.confirm('确定要退出登录吗?', '提示', {
|
|
confirmButtonText: '确定',
|
|
cancelButtonText: '取消',
|
|
type: 'warning'
|
|
}).then(() => {
|
|
authStore.logout()
|
|
router.push('/login')
|
|
})
|
|
}
|
|
</script>
|
|
|
|
<template>
|
|
<div class="layout">
|
|
<!-- 侧边栏 -->
|
|
<aside class="sidebar">
|
|
<div class="logo">
|
|
<el-icon><Platform /></el-icon>
|
|
<span style="margin-left: 8px">平台管理</span>
|
|
</div>
|
|
|
|
<el-menu
|
|
:default-active="activeMenu"
|
|
background-color="transparent"
|
|
text-color="rgba(255,255,255,0.7)"
|
|
active-text-color="#fff"
|
|
@select="handleMenuSelect"
|
|
>
|
|
<el-menu-item v-for="item in menuItems" :key="item.path" :index="item.path">
|
|
<el-icon><component :is="item.icon" /></el-icon>
|
|
<span>{{ item.title }}</span>
|
|
</el-menu-item>
|
|
</el-menu>
|
|
</aside>
|
|
|
|
<!-- 主内容区 -->
|
|
<div class="main-container">
|
|
<!-- 顶部栏 -->
|
|
<header class="header">
|
|
<div class="breadcrumb">
|
|
<el-breadcrumb separator="/">
|
|
<el-breadcrumb-item :to="{ path: '/' }">首页</el-breadcrumb-item>
|
|
<el-breadcrumb-item v-if="route.meta.title">{{ route.meta.title }}</el-breadcrumb-item>
|
|
</el-breadcrumb>
|
|
</div>
|
|
|
|
<div class="user-info">
|
|
<span class="username">{{ authStore.user?.nickname || authStore.user?.username }}</span>
|
|
<el-dropdown trigger="click">
|
|
<el-avatar :size="32">
|
|
{{ (authStore.user?.nickname || authStore.user?.username || 'U')[0].toUpperCase() }}
|
|
</el-avatar>
|
|
<template #dropdown>
|
|
<el-dropdown-menu>
|
|
<el-dropdown-item @click="handleLogout">
|
|
<el-icon><SwitchButton /></el-icon>
|
|
退出登录
|
|
</el-dropdown-item>
|
|
</el-dropdown-menu>
|
|
</template>
|
|
</el-dropdown>
|
|
</div>
|
|
</header>
|
|
|
|
<!-- 内容区 -->
|
|
<main class="main-content">
|
|
<router-view />
|
|
</main>
|
|
</div>
|
|
</div>
|
|
</template>
|