157 lines
5.4 KiB
TypeScript
157 lines
5.4 KiB
TypeScript
/**
|
||
* 动态路由生成模块(Bidding 特定)
|
||
*
|
||
* 职责:
|
||
* 1. 提供 Bidding 特定的布局和组件配置
|
||
* 2. 调用 shared 中的通用路由生成方法
|
||
* 3. 将生成的路由添加到 Bidding 的 router 实例
|
||
*/
|
||
|
||
/// <reference types="vite/client" />
|
||
|
||
import {
|
||
generateSimpleRoutes,
|
||
loadViewsFromStorage,
|
||
type RouteGeneratorConfig,
|
||
type GenerateSimpleRoutesOptions
|
||
} from 'shared/utils/route'
|
||
import type { TbSysViewDTO } from 'shared/types'
|
||
import type { RouteRecordRaw } from 'vue-router'
|
||
import router from './index'
|
||
import { SidebarLayout, BlankLayout, SubSidebarLayout } from '@/layouts'
|
||
|
||
// Bidding 布局组件映射
|
||
const biddingLayoutMap: Record<string, () => Promise<any>> = {
|
||
'SidebarLayout': () => Promise.resolve({ default: SidebarLayout }),
|
||
'BlankLayout': () => Promise.resolve({ default: BlankLayout }),
|
||
'NavigationLayout': () => Promise.resolve({ default: SidebarLayout }),
|
||
'BasicLayout': () => Promise.resolve({ default: SidebarLayout }),
|
||
'SubSidebarLayout': () => Promise.resolve({ default: SubSidebarLayout })
|
||
}
|
||
|
||
// 视图组件加载器
|
||
const VIEW_MODULES = import.meta.glob<{ default: any }>('../views/**/*.vue')
|
||
|
||
/**
|
||
* 视图组件加载函数
|
||
* @param componentPath 组件路径(如 "bidding/Home" 或 "bidding/List")
|
||
*/
|
||
function viewLoader(componentPath: string): (() => Promise<any>) | null {
|
||
// 将后台路径转换为 ../views 格式
|
||
let path = componentPath
|
||
|
||
// 移除开头的斜杠(如果有)
|
||
if (path.startsWith('/')) {
|
||
path = path.substring(1)
|
||
}
|
||
|
||
// 补全 .vue 后缀(如果没有)
|
||
if (!path.endsWith('.vue')) {
|
||
path += '.vue'
|
||
}
|
||
|
||
// 转换为 ../views 格式(匹配 import.meta.glob 的 key)
|
||
const fullPath = `../views/${path}`
|
||
|
||
console.log('[Bidding viewLoader] 尝试加载组件:', componentPath, '→', fullPath)
|
||
|
||
const loader = VIEW_MODULES[fullPath]
|
||
|
||
if (!loader) {
|
||
console.warn('[Bidding viewLoader] 组件未找到:', fullPath)
|
||
console.log('[Bidding viewLoader] 可用的组件:', Object.keys(VIEW_MODULES))
|
||
return null
|
||
}
|
||
|
||
return loader as () => Promise<any>
|
||
}
|
||
|
||
// Bidding 路由生成器配置
|
||
const routeConfig: RouteGeneratorConfig = {
|
||
layoutMap: biddingLayoutMap,
|
||
viewLoader,
|
||
notFoundComponent: () => import('vue').then(({ h }) => ({
|
||
default: {
|
||
render() { return h('div', { style: { padding: '20px', textAlign: 'center' } }, '404 - 页面未找到') }
|
||
}
|
||
}))
|
||
}
|
||
|
||
// Bidding 路由生成选项
|
||
const routeOptions: GenerateSimpleRoutesOptions = {
|
||
asRootChildren: false, // 直接作为根级路由,不是某个布局的子路由
|
||
iframePlaceholder: () => import('shared/components').then(m => ({ default: m.IframeView })),
|
||
verbose: true // 启用详细日志
|
||
}
|
||
|
||
/**
|
||
* 添加动态路由(Bidding 特定)
|
||
* @param views 视图列表(用作菜单)
|
||
*/
|
||
export function addDynamicRoutes(views: TbSysViewDTO[]) {
|
||
if (!views || views.length === 0) {
|
||
console.warn('[Bidding] addDynamicRoutes: 视图列表为空')
|
||
return
|
||
}
|
||
|
||
console.log('[Bidding] addDynamicRoutes: 开始添加动态路由,视图数量:', views.length)
|
||
console.log('[Bidding] addDynamicRoutes: 路由配置:', routeConfig)
|
||
console.log('[Bidding] addDynamicRoutes: 路由选项:', routeOptions)
|
||
|
||
try {
|
||
// 使用 shared 中的通用方法生成路由
|
||
const routes = generateSimpleRoutes(views, routeConfig, routeOptions)
|
||
|
||
// 直接将路由添加到根级别(不是作为Root的children)
|
||
routes.forEach(route => {
|
||
console.log('[Bidding] addDynamicRoutes: 添加路由', route.path, '使用布局:', route.component?.name || 'unknown')
|
||
router.addRoute(route)
|
||
})
|
||
|
||
} catch (error) {
|
||
console.error('[Bidding] addDynamicRoutes: 添加路由失败', error)
|
||
throw error
|
||
}
|
||
}
|
||
|
||
/**
|
||
* 从 LocalStorage 获取菜单并生成路由(Bidding 特定)
|
||
*
|
||
* 使用 shared 中的通用 loadViewsFromStorage 方法
|
||
* 筛选出 service='bidding' 的视图
|
||
*/
|
||
export function loadRoutesFromStorage(): boolean {
|
||
try {
|
||
console.log('[Bidding] loadRoutesFromStorage: 开始加载动态路由')
|
||
|
||
// 使用 shared 中的通用方法加载视图数据
|
||
const allViews = loadViewsFromStorage('loginDomain', 'userViews')
|
||
|
||
console.log('[Bidding] loadRoutesFromStorage: 加载的所有视图数量:', allViews?.length || 0)
|
||
|
||
if (allViews) {
|
||
// 过滤出 bidding 服务的视图
|
||
const biddingViews = allViews.filter((view: TbSysViewDTO) =>
|
||
view.service === 'bidding'
|
||
)
|
||
|
||
console.log('[Bidding] loadRoutesFromStorage: 过滤后的 bidding 视图:', biddingViews)
|
||
|
||
if (biddingViews.length === 0) {
|
||
console.warn('[Bidding] loadRoutesFromStorage: 没有找到 bidding 服务的视图')
|
||
return false
|
||
}
|
||
|
||
// 使用 Bidding 的 addDynamicRoutes 添加路由
|
||
addDynamicRoutes(biddingViews)
|
||
return true
|
||
}
|
||
|
||
console.warn('[Bidding] loadRoutesFromStorage: 未能加载视图数据')
|
||
return false
|
||
} catch (error) {
|
||
console.error('[Bidding] loadRoutesFromStorage: 加载路由失败', error)
|
||
return false
|
||
}
|
||
}
|