第4章 Vue Router与路由管理:路由配置、导航守卫、动态路由、路由懒加载
📌 章节核心能力画像:路由配置规范 | 守卫执行流程 | 动态路由设计 | 性能优化策略
📋 路由配置核心维度一览
| 维度 | 核心配置 / 方法 | 面试高频考点 |
|---|---|---|
| 基础配置 | routes 数组 + path/component/children | 命名路由、命名视图、重定向与别名 |
| 导航守卫 | 全局 beforeEach / 路由 beforeEnter / 组件内守卫 | 执行顺序、next() 调用时机、权限校验 |
| 动态路由 | addRoute() / addRoutes() + 通配符 :param | 权限动态挂载、路由重置、重复添加处理 |
| 路由懒加载 | 动态 import() + webpackChunkName | 打包分片策略、首屏加载优化、预加载 |
🃏 问答卡片 1 · 路由懒加载
面试问题:Vue 路由懒加载有哪几种实现方式?它们的工作原理是什么?
🎯 考察点
- 是否了解代码分割与按需加载
- 对动态 import() 语法的掌握程度
- 能否结合 webpack 分包机制说明
📐 回答框架
- 先点明懒加载目的:减小首屏体积
- 列出实现方式:import()、require.ensure(已废弃)
- 说明 webpackChunkName 自定义分包
- 补充预加载 prefetch/preload 优化
💬 示例回答:
路由懒加载通过动态
import() 实现代码分割,webpack 自动为每个路由生成独立 chunk。使用 webpackChunkName: 'admin' 可合并分包。原理是浏览器在路由匹配时才请求对应 JS 文件,减少首屏加载体积。Vue 3 中推荐配合 Suspense 处理异步组件加载状态。
❓ 可能追问
- 懒加载与预加载的区别?
- 多个路由共用一个 chunk 如何配置?
- SSR 场景下懒加载如何处理?
⚠️ 避坑提醒
- 不要用 require.ensure(已废弃)
- 动态 import 不要写成字符串模板拼接
- 注意 chunk 命名冲突问题
🃏 问答卡片 2 · 导航守卫执行流程
面试问题:Vue Router 导航守卫的执行顺序是怎样的?请结合一个权限校验场景说明。
🎯 考察点
- 对三种守卫类型的熟悉程度
- 执行顺序的精确记忆
- 能否在实际场景中合理使用
📐 回答框架
- 全局 beforeEach → 路由 beforeEnter → 组件 beforeRouteEnter
- 全局 beforeResolve → 全局 afterEach
- 组件内 beforeRouteUpdate / beforeRouteLeave
- 结合权限场景:登录校验 + 角色鉴权
💬 示例回答:
完整执行顺序:全局 beforeEach → 路由 beforeEnter → 组件 beforeRouteEnter → 全局 beforeResolve → 全局 afterEach。权限场景:在 beforeEach 中检查 ,无 跳转登录页;有 则通过 meta.roles 校验角色,无权限时 next('/403'),最后在 afterEach 中设置页面标题。
❓ 可能追问
- next() 调用多次会怎样?
- 异步守卫怎么处理?
- Vue 3 中守卫有变化吗?
⚠️ 避坑提醒
- 务必调用 next() 否则导航挂起
- 避免在守卫中执行重逻辑
- beforeRouteLeave 中不能访问 this
🃏 问答卡片 3 · 动态路由与权限控制
面试问题:如何基于用户角色动态添加路由?有哪些注意事项?
🎯 考察点
- 是否掌握 addRoute 动态挂载
- 权限数据的组织方式
- 路由重复添加与重置策略
📐 回答框架
- 登录后获取用户权限列表
- 根据权限过滤路由表,调用 addRoute
- 使用 router.hasRoute 避免重复
- 退出登录时重置路由
💬 示例回答:
登录后在 store 中保存 role,在 beforeEach 中判断:若已登录且无动态路由,调用
filterRoutes(role) 生成权限路由数组,遍历执行 router.addRoute(route),并 next({...to, replace: true}) 重新触发导航。退出时 router.getRoutes().forEach(r => router.removeRoute(r.name)) 清理。
❓ 可能追问
- addRoute 添加的层级如何控制?
- 如何防止路由权限越级?
- 动态路由在刷新后丢失怎么处理?
⚠️ 避坑提醒
- addRoute 前先检查 hasRoute 避免重复
- 动态路由刷新后需重新挂载
- 不要将权限路由写死在初始化配置中
🏗️ 项目案例 · 后台管理系统路由权限中心
项目名称
「AdminPro」企业级中后台权限管理系统
业务背景
支持多租户、多角色的后台管理平台,包含用户管理、订单、报表等 20+ 模块,不同角色可见菜单和操作按钮均不同。
规模指标
- 路由总数:80+(含动态路由 60+)
- 角色类型:6 种(超级管理员 / 运营 / 商务 / 客服 / 审计 / 只读)
- 页面访问 QPS:峰值 1200+
- 路由懒加载后首屏体积减少 62%
技术栈
Vue 3 + TypeScript + Vite + Pinia + Vue Router 4 + Axios + Element Plus
核心难点
- 多层嵌套动态路由:addRoute 添加子路由时需指定 parent name
- 刷新后路由持久化:结合 localStorage + store 重新挂载
- 按钮级权限:路由元信息 meta.permissions 配合 v-permission 指令
- 路由过渡动画:动态路由切换时保持过渡一致性
🎤 面试高频追问
- 动态路由如果出现 name 冲突怎么解决?
- 如何实现路由级别的 keep-alive 按需缓存?
- 菜单与路由如何联动生成?
- 角色变更时如何动态刷新路由?
📌 可迁移回答话术
“在我负责的后台项目中,路由权限的核心思路是分层过滤:全局守卫做登录态拦截,路由元信息做角色匹配,动态路由用 addRoute 按需挂载。关键在于 刷新后重新挂载 —— 将权限路由表存入 localStorage,app 初始化时从 store 读取并执行 addRoute,确保权限不丢失。”
💡 面试加分提示:面试官看重的不只是 API 用法,更是你对“权限闭环”的理解 —— 从登录 → 获取权限 → 动态挂载 → 刷新持久化 → 退出清理,每个环节都要能讲清楚数据流向和边界处理。
⚠️ 常见失分点:只说 addRoute 但没提 hasRoute 防重复;没说刷新后路由丢失的解决方案;把静态路由和动态路由混在一起写死,失去了动态扩展能力。