发布日期:2024年7月25日
一、系统架构设计
本教程将构建一个完整的企业级中台系统,采用微前端架构:
- 主应用:Vue3 + TypeScript核心框架
- 微应用:React/Vue2/Vue3多技术栈集成
- 状态管理:Pinia + 共享状态方案
- 权限控制:RBAC动态路由系统
- 数据可视化:ECharts + Three.js大屏
技术栈:Vue3 + TypeScript + Pinia + Qiankun + ECharts
二、项目初始化与配置
1. 创建主应用
# 使用Vite创建Vue3项目
npm create vite@latest main-app --template vue-ts
cd main-app
# 安装核心依赖
npm install pinia qiankun axios echarts
npm install -D @types/node
2. 目录结构规划
src/
├── apis/ # 接口服务
├── components/ # 公共组件
├── micro-apps/ # 微应用配置
├── router/ # 路由配置
│ └── permission.ts # 权限控制
├── stores/ # Pinia状态
│ ├── app.ts # 应用状态
│ └── user.ts # 用户状态
├── styles/ # 全局样式
├── utils/ # 工具函数
├── views/ # 页面组件
│ ├── dashboard/ # 数据大屏
│ └── layout/ # 布局组件
├── App.vue
└── main.ts
三、微前端集成
1. 主应用配置
// micro-apps/index.ts
import { registerMicroApps, start } from 'qiankun'
const apps = [
{
name: 'react-app',
entry: '//localhost:7101',
container: '#subapp-container',
activeRule: '/react',
props: {
baseApi: import.meta.env.VITE_API_URL,
token: localStorage.getItem('token')
}
},
{
name: 'vue2-app',
entry: '//localhost:7102',
container: '#subapp-container',
activeRule: '/vue2'
}
]
export function registerApps() {
registerMicroApps(apps)
start({
prefetch: true,
sandbox: {
strictStyleIsolation: true,
experimentalStyleIsolation: true
}
})
}
2. 子应用适配(Vue3)
// 子应用入口文件
import { createApp } from 'vue'
import App from './App.vue'
import { renderWithQiankun, qiankunWindow } from 'vite-plugin-qiankun/dist/helper'
let app: App
function render(props: any = {}) {
const { container } = props
app = createApp(App)
app.mount(container?.querySelector('#app') || '#app')
}
renderWithQiankun({
mount(props) {
render(props)
},
bootstrap() {
console.log('bootstrap')
},
unmount() {
app.unmount()
}
})
if (!qiankunWindow.__POWERED_BY_QIANKUN__) {
render()
}
四、权限控制系统
1. 动态路由实现
// router/permission.ts
import { RouteRecordRaw } from 'vue-router'
import { useUserStore } from '@/stores/user'
export async function generateRoutes(): Promise {
const userStore = useUserStore()
if (!userStore.roles.length) {
await userStore.fetchUserInfo()
}
const permissionRoutes: RouteRecordRaw[] = []
// 根据角色过滤路由
userStore.roles.forEach(role => {
const routes = asyncRoutes.filter(route => {
return route.meta?.roles?.includes(role)
})
permissionRoutes.push(...routes)
})
return permissionRoutes
}
// 路由守卫
router.beforeEach(async (to, from, next) => {
if (to.meta.requiresAuth && !useUserStore().token) {
next(`/login?redirect=${to.path}`)
return
}
if (!router.hasRoute(to.name!)) {
const routes = await generateRoutes()
routes.forEach(route => router.addRoute(route))
next(to.fullPath)
return
}
next()
})
2. 权限指令
// directives/permission.ts
import { Directive } from 'vue'
import { useUserStore } from '@/stores/user'
export const permission: Directive = {
mounted(el, binding) {
const { value } = binding
const userStore = useUserStore()
if (value && Array.isArray(value)) {
const hasPermission = userStore.roles.some(role => {
return value.includes(role)
})
if (!hasPermission) {
el.parentNode?.removeChild(el)
}
} else {
throw new Error('权限指令需要传入数组,例如 v-permission="['admin']"')
}
}
}
五、可视化大屏开发
1. ECharts组件封装
<script setup lang="ts">
import * as echarts from 'echarts'
import { onMounted, onUnmounted, ref, watch } from 'vue'
const props = defineProps<{
options: echarts.EChartsOption
theme?: string
width?: string
height?: string
}>()
const chartRef = ref<HTMLElement>()
let chart: echarts.ECharts | null = null
const initChart = () => {
if (!chartRef.value) return
chart = echarts.init(chartRef.value, props.theme)
chart.setOption(props.options)
const resize = () => chart?.resize()
window.addEventListener('resize', resize)
onUnmounted(() => {
window.removeEventListener('resize', resize)
chart?.dispose()
})
}
watch(() => props.options, (newVal) => {
chart?.setOption(newVal)
}, { deep: true })
onMounted(initChart)
</script>
<template>
<div ref="chartRef" :style="{ width, height }"></div>
</template>
2. 实时数据大屏
// views/dashboard/RealtimeDashboard.vue
import { useWebSocket } from '@/utils/websocket'
import { ref } from 'vue'
const metrics = ref({
userCount: 0,
orderCount: 0,
revenue: 0
})
const { connect } = useWebSocket('dashboard', {
onMessage(data) {
metrics.value = {
userCount: data.current_users,
orderCount: data.orders_today,
revenue: data.daily_revenue
}
updateCharts(data)
}
})
onMounted(() => {
connect()
fetchInitialData()
})
六、状态管理方案
1. Pinia模块化设计
// stores/app.ts
import { defineStore } from 'pinia'
export const useAppStore = defineStore('app', {
state: () => ({
sidebarCollapsed: false,
theme: 'light',
microApps: []
}),
actions: {
toggleSidebar() {
this.sidebarCollapsed = !this.sidebarCollapsed
},
async fetchMicroApps() {
const res = await api.getMicroApps()
this.microApps = res.data
}
},
persist: {
enabled: true,
strategies: [
{
key: 'app',
storage: localStorage
}
]
}
})
2. 跨应用状态共享
// stores/shared.ts
import { defineStore } from 'pinia'
export const useSharedStore = defineStore('shared', {
state: () => ({
globalUser: null,
notifications: []
}),
actions: {
setGlobalUser(user) {
this.globalUser = user
// 通过qiankun通信
if (window.__POWERED_BY_QIANKUN__) {
window.dispatchEvent(new CustomEvent('global-user-change', {
detail: user
}))
}
}
}
})
// 主应用中监听状态变化
window.addEventListener('global-user-change', (e) => {
useSharedStore().setGlobalUser(e.detail)
})
七、性能优化实践
1. 组件懒加载
// router/index.ts
const routes: RouteRecordRaw[] = [
{
path: '/dashboard',
component: () => import(/* webpackChunkName: "dashboard" */ '@/views/Dashboard.vue'),
meta: { requiresAuth: true }
},
{
path: '/user/:id',
component: () => import(/* webpackChunkName: "user" */ '@/views/UserDetail.vue')
}
]
2. 虚拟滚动优化
<template>
<VirtualList
:data="largeList"
:item-size="60"
:height="500"
>
<template #default="{ item }">
<UserCard :user="item" />
</template>
</VirtualList>
</template>
<script setup>
import { ref } from 'vue'
import VirtualList from '@/components/VirtualList.vue'
import { fetchLargeData } from '@/api'
const largeList = ref([])
fetchLargeData().then(data => {
largeList.value = data
})
</script>
八、总结与扩展
通过本教程,您已经掌握了:
- 微前端架构设计与实现
- 动态权限控制系统
- 数据可视化大屏开发
- 跨应用状态管理方案
- 大型应用性能优化
扩展学习方向:
- Web Workers处理复杂计算
- SSR服务端渲染集成
- 自动化部署流水线
- 微前端模块联邦