以下是如何在 Vue 3 项目中实现路由缓存与无缓存功能的详细指南(约 1200 字):
npm create vue@latest
# 选择安装 Router
// router/index.js
import { createRouter, createWebHistory } from 'vue-router'
const routes = [
{
path: '/',
name: 'Home',
component: () => import('@/views/Home.vue'),
meta: { keepAlive: true } // 需要缓存的页面
},
{
path: '/detail/:id',
name: 'Detail',
component: () => import('@/views/Detail.vue'),
meta: { keepAlive: false } // 不需要缓存的页面
},
{
path: '/news',
name: 'News',
component: () => import('@/views/News.vue')
// 默认不缓存
}
]
const router = createRouter({
history: createWebHistory(),
routes
})
export default router
<template>
<router-view v-slot="{ Component, route }">
<keep-alive :include="cachedViews">
<component
:is="Component"
:key="route.meta.usePathKey ? route.path : route.name"
/>
</keep-alive>
</router-view>
</template>
<script setup>
import { ref, watch } from 'vue'
import { useRoute } from 'vue-router'
const cachedViews = ref([])
const route = useRoute()
watch(route, (to) => {
if (to.meta.keepAlive && !cachedViews.value.includes(to.name)) {
cachedViews.value.push(to.name)
}
})
</script>
<script>
// Home.vue
export default {
name: 'Home', // 必须与路由的 name 一致
// 或使用 script setup 语法糖:
// defineOptions({ name: 'Home' })
activated() {
console.log('Home 被激活')
// 在此处刷新数据
},
deactivated() {
console.log('Home 被缓存')
}
}
</script>
<!-- 自动处理 -->
<keep-alive :include="cachedViews">
<!-- 未包含的组件自动不缓存 -->
</keep-alive>
<component
:is="Component"
:key="route.fullPath" // 使用完整路径作为 key
/>
{
path: '/detail/:id',
component: Detail,
meta: {
keepAlive: false,
usePathKey: true // 使用路径作为 key
}
}
// 在组件内
import { useRouter } from 'vue-router'
const router = useRouter()
function disableCache() {
router.currentRoute.value.meta.keepAlive = false
}
function enableCache() {
router.currentRoute.value.meta.keepAlive = true
}
const removeFromCache = (viewName) => {
const index = cachedViews.value.indexOf(viewName)
if (index > -1) {
cachedViews.value.splice(index, 1)
}
}
// router/index.js
const router = createRouter({
history: createWebHistory(),
routes,
scrollBehavior(to, from, savedPosition) {
if (savedPosition && to.meta.keepAlive) {
return savedPosition
}
return { top: 0 }
}
})
组件命名要求:
生命周期变化:
内存管理:
数据更新策略:
// 在需要刷新的组件中
onActivated(() => {
fetchData()
})
差异化缓存策略:
// 根据设备内存动态调整
const MAX_CACHE = navigator.deviceMemory > 4 ? 15 : 5
watch(cachedViews, (val) => {
if (val.length > MAX_CACHE) {
cachedViews.value = val.slice(-MAX_CACHE)
}
})
缓存状态持久化: ```javascript // 使用 localStorage 保存缓存状态 onMounted(() => { const saved = localStorage.getItem('cachedViews') if (saved) cachedViews.value = JSON.parse(saved) })
watch(cachedViews, (val) => { localStorage.setItem('cachedViews', JSON.stringify(val)) })
## 七、场景对比
| 场景 | 推荐方案 | 理由 |
|---------------------|---------------|----------------------------------------------------------------------|
| 列表页 -> 详情页 | 缓存列表页 | 保持列表滚动位置和筛选状态 |
| 表单页面 | 缓存 | 防止用户输入丢失 |
| 实时数据仪表盘 | 不缓存 | 需要保证每次进入都获取最新数据 |
| 多步骤向导 | 缓存 | 保持步骤状态 |
| 需要频繁更新的信息流 | 不缓存 | 确保内容及时刷新 |
## 八、常见问题解决
1. **缓存失效问题**:
- 检查组件 name 是否匹配
- 确认路由 meta 配置正确
- 使用 vue-devtools 查看缓存组件
2. **内存泄漏处理**:
```javascript
onBeforeUnmount(() => {
// 清理定时器等资源
})
// 使用路径作为 key
:key="route.path"
缓存策略:
最佳实践:
通过合理使用 keep-alive 缓存机制,可以显著提升 Vue 应用的性能表现和用户体验,但需注意平衡内存使用与功能需求。建议结合具体业务场景进行针对性优化,并通过性能监控工具持续跟踪应用表现。