一不小心就踩了 keep-alive 的坑
前言
keep-alive 是 Vue 提供的一个内置组件,主要用来缓存动态组件或路由视图。当组件被包裹在 keep-alive 中时,切换页面后该组件不会被销毁,而是被缓存起来,下次切换回来时,组件会保持上一次的状态。
典型用法:
Vue 中,keep-alive 是一个非常实用的组件,通过缓存路由组件,可以优化性能和提升用户体验。而它也是一把双刃剑,随时等着你入坑!本文则围绕几个常见的使用场景,教大家如何避免 keep-alive 陷阱。
keep-alive 常见的坑
1. 生命周期钩子与预期不符
在 Vue 组件的生命周期中,组件挂载就会触发 onMounted
生命周期钩子,组件取消挂载就会触发 onUnMounted
生命周期钩子。
但组件在 <keep-alive>
包裹下,创建后的组件实例会被缓存,即便是切换至其他组件,也不会导致该组件被销毁。所以onMounted
只会触发一次,onUnMounted
不会触发。取而代之的是 onActivated
和 onDeactivated
钩子,分别在组件被激活或停用时触发。
需要注意的是,onActivated
和 onDeactivated
只在 <keep-alive>
下生效!
2. 无法重置数据状态
如果在 keep-alive
包裹下的组件中填写了一个表单,那么下次打开这个组件时,表单的内容可能没有被重置。同样的,如果是获取了一个数据列表,那么这个数据列表的值无论组件打开多少次都不会发生变化,因此无法获取最新的数据。
此时,需要我们人为的在 onActivated
生命周期钩子中触发重置表单或重新获取数据列表的逻辑。
3. 路由参数变化时无法监听
当使用动态路由时,路由参数变化但组件未更新。例如:/user/1
切换到 /user/2
后,仍然显示的是用户 1 的数据。因此,将读取路由参数的逻辑置于 onMounted
就失去了作用。
改为使用 watch
来监听路由的变化,非常有效!
4. 缓存组件过多导致内存占用高
如果 keep-alive
缓存了过多的组件,可能会导致内存占用过高,页面卡顿,甚至浏览器崩溃。使用 include
和 exclude
属性限制缓存的组件:
5. 与第三方库不兼容
某些第三方库(如动画库、滚动插件)依赖组件的初始化逻辑,在组件缓存后无法正常工作。keep-alive
下的 onMounted
会失效,因此,应该在 onActivate
钩子中重新初始化第三方库。
总结
keep-alive 是 Vue 提供的强大工具,用于优化组件性能和用户体验,但也隐藏着诸多陷阱。开发中需注意组件的生命周期变化,合理使用 onActivated 和 watch 解决数据状态重置和路由参数更新问题。同时,避免缓存过多组件以防内存占用过高,必要时使用 include 和 exclude 进行缓存控制。谨慎处理与第三方库的兼容性,确保组件在缓存和激活后的功能正常。合理规避这些问题,才能更好地发挥 keep-alive 的作用。