f
This commit is contained in:
@@ -1,12 +1,13 @@
|
||||
import { useUserStore } from '@/stores/user'
|
||||
import { createRouter, createWebHistory } from 'vue-router'
|
||||
import { isCurrentOrigin, isPortalDomainConfigReady, isSubPortal, mainPortalOrigin, subPortalOrigin } from '@/constants/portal'
|
||||
import { statisticsRoutes } from './modules/statistics'
|
||||
|
||||
// 路由配置
|
||||
const routes = [
|
||||
{
|
||||
path: '/',
|
||||
redirect: '/dashboard'
|
||||
redirect: () => (isSubPortal ? '/sub/auth/login' : '/dashboard')
|
||||
},
|
||||
{
|
||||
path: '/auth',
|
||||
@@ -51,6 +52,44 @@ const routes = [
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
path: '/sub/auth',
|
||||
component: () => import('@/layouts/AuthLayout.vue'),
|
||||
meta: { requiresAuth: false },
|
||||
children: [
|
||||
{
|
||||
path: 'login',
|
||||
name: 'SubLogin',
|
||||
component: () => import('@/pages/sub-portal/SubLogin.vue'),
|
||||
meta: { title: '子账号登录' }
|
||||
},
|
||||
{
|
||||
path: 'register',
|
||||
name: 'SubRegister',
|
||||
component: () => import('@/pages/sub-portal/SubRegister.vue'),
|
||||
meta: { title: '子账号注册' }
|
||||
},
|
||||
{
|
||||
path: 'reset',
|
||||
name: 'SubResetPassword',
|
||||
component: () => import('@/pages/auth/ResetPassword.vue'),
|
||||
meta: { title: '重置密码' }
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
path: '/parent/subordinates',
|
||||
component: () => import('@/layouts/MainLayout.vue'),
|
||||
meta: { requiresAuth: true, title: '下属' },
|
||||
children: [
|
||||
{
|
||||
path: '',
|
||||
name: 'ParentSubordinates',
|
||||
component: () => import('@/pages/parent/SubordinateManagement.vue'),
|
||||
meta: { title: '下属' }
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
path: '/products',
|
||||
component: () => import('@/layouts/MainLayout.vue'),
|
||||
@@ -344,9 +383,34 @@ const router = createRouter({
|
||||
// 路由守卫
|
||||
router.beforeEach(async (to, from, next) => {
|
||||
const userStore = useUserStore()
|
||||
const loginPathByRoute = to.path.startsWith('/sub/') ? '/sub/auth/login' : '/auth/login'
|
||||
const isSubAuthRoute = to.path.startsWith('/sub/auth')
|
||||
const isMainAuthRoute = to.path.startsWith('/auth')
|
||||
const subAuthToMainAuthPath = to.path.replace('/sub/auth', '/auth')
|
||||
const mainAuthToSubAuthPath = to.path.replace('/auth', '/sub/auth')
|
||||
|
||||
// 域名级认证路由隔离:子域只允许 /sub/auth/*,主域禁止 /sub/auth/*
|
||||
if (isPortalDomainConfigReady) {
|
||||
const onSubDomain = isCurrentOrigin(subPortalOrigin)
|
||||
const onMainDomain = isCurrentOrigin(mainPortalOrigin)
|
||||
|
||||
if (onSubDomain && isMainAuthRoute) {
|
||||
next(mainAuthToSubAuthPath)
|
||||
return
|
||||
}
|
||||
|
||||
if (onMainDomain && isSubAuthRoute) {
|
||||
next(subAuthToMainAuthPath)
|
||||
return
|
||||
}
|
||||
} else if (isSubPortal && isMainAuthRoute) {
|
||||
// 子站壳模式下,即使未配置双域名,也只允许进入 /sub/auth/*
|
||||
next(mainAuthToSubAuthPath)
|
||||
return
|
||||
}
|
||||
|
||||
// 对于不需要认证的路由(如登录页),不等待初始化,直接放行
|
||||
const isAuthRoute = to.path.startsWith('/auth')
|
||||
const isAuthRoute = to.path.startsWith('/auth') || to.path.startsWith('/sub/auth')
|
||||
const requiresAuth = to.meta.requiresAuth
|
||||
|
||||
// 只有在需要认证的路由上才等待初始化
|
||||
@@ -366,7 +430,7 @@ router.beforeEach(async (to, from, next) => {
|
||||
|
||||
// 检查是否需要认证
|
||||
if (requiresAuth && !userStore.isLoggedIn) {
|
||||
next('/auth/login')
|
||||
next(loginPathByRoute)
|
||||
return
|
||||
}
|
||||
|
||||
@@ -376,12 +440,57 @@ router.beforeEach(async (to, from, next) => {
|
||||
return
|
||||
}
|
||||
|
||||
// 已登录用户访问认证页面,重定向到数据大厅
|
||||
if (isAuthRoute && userStore.isLoggedIn) {
|
||||
// 登录态下强制要求主/子域配置完整,避免混域运行
|
||||
if (userStore.isLoggedIn && !isPortalDomainConfigReady) {
|
||||
if (import.meta.env.PROD) {
|
||||
userStore.logout()
|
||||
next(loginPathByRoute)
|
||||
return
|
||||
}
|
||||
}
|
||||
|
||||
// 域名隔离:子账号登录态必须在子账号专属域名
|
||||
if (userStore.isLoggedIn && userStore.accountKind === 'subordinate' && subPortalOrigin && !isCurrentOrigin(subPortalOrigin)) {
|
||||
window.location.replace(`${subPortalOrigin}${to.fullPath}`)
|
||||
return
|
||||
}
|
||||
|
||||
// 域名隔离:普通/管理员账号不应停留在子账号专属域名
|
||||
if (userStore.isLoggedIn && userStore.accountKind !== 'subordinate' && subPortalOrigin && isCurrentOrigin(subPortalOrigin)) {
|
||||
if (mainPortalOrigin) {
|
||||
window.location.replace(`${mainPortalOrigin}${to.fullPath}`)
|
||||
return
|
||||
}
|
||||
next('/products')
|
||||
return
|
||||
}
|
||||
|
||||
// 已登录用户访问认证页面,按账号类型重定向到对应首页
|
||||
if (isAuthRoute && userStore.isLoggedIn) {
|
||||
next(userStore.accountKind === 'subordinate' ? '/subscriptions' : '/dashboard')
|
||||
return
|
||||
}
|
||||
|
||||
// 子站壳:禁止进入主站登录/注册路由(可合并子账号入口到 /sub/auth)
|
||||
if (isSubPortal && (to.path.startsWith('/auth/login') || to.path.startsWith('/auth/register'))) {
|
||||
next(to.path.replace('/auth/', '/sub/auth/'))
|
||||
return
|
||||
}
|
||||
|
||||
// 主站与「子站壳」共仓:/sub/auth/* 始终可用,子账号注册/登录与主站 /auth 并存,邀请链接不依赖单独构建
|
||||
|
||||
// 下属账号不可进入主账号「下属」管理页
|
||||
if (to.path.startsWith('/parent/subordinates') && userStore.accountKind === 'subordinate') {
|
||||
next('/subscriptions')
|
||||
return
|
||||
}
|
||||
|
||||
// 下属账号不允许访问仪表盘
|
||||
if (to.path.startsWith('/dashboard') && userStore.accountKind === 'subordinate') {
|
||||
next('/subscriptions')
|
||||
return
|
||||
}
|
||||
|
||||
next()
|
||||
})
|
||||
|
||||
|
||||
Reference in New Issue
Block a user