直接监听 localStorage 不行,需用 ref 封装其读写逻辑实现响应式:初始化时从 localStorage 读取,修改时自动同步;watchEffect 可追踪该 ref;跨标签页需监听 storage 事件;推荐封装为 useLocalStorage 组合式函数。

直接监听 localStorage 本身不行,因为它是普通 JS 对象,不具备响应式能力。watchEffect 只能追踪 Vue 的响应式数据(如 ref、reactive),所以关键在于:把本地存储的读写逻辑封装进响应式变量,并在变化时同步存取 localStorage。
用 ref 封装 localStorage 值
创建一个 ref 来代理 localStorage 中的字段,读取时从 localStorage 初始化,写入时自动同步回去:
- 定义 ref 时,先从 localStorage 取值(注意类型转换,比如 JSON.parse)
- 每次修改 ref.value 后,立刻调用 localStorage.setItem 更新存储
- 这样 watchEffect 就能正常追踪该 ref 的变化了
watchEffect 自动响应变更
只要 ref 被正确更新,watchEffect 就会立即执行并拿到最新值。例如监听用户主题偏好:
递归分析 Vue 项目组件依赖,从入口文件生成组件层级图,支持 Vue 2/3,输出组件名、文件路径和属性。适用于分析组件结构、排查依赖或了解项目架构。
- const theme = ref(localStorage.getItem('theme') || 'light')
- 后续所有 theme.value = 'dark' 都会触发 localStorage.setItem('theme', 'dark')
- watchEffect(() => { document.documentElement.setAttribute('data-theme', theme.value) }) 就能实时生效
处理跨标签页变更(可选增强)
单个页面内 ref 更新能触发 watchEffect,但其他标签页修改 localStorage 不会自动通知当前页。要支持多窗口同步,需监听 storage 事件:
立即学习“前端免费学习笔记(深入)”;
- 在 setup 中添加 window.addEventListener('storage', e => { if (e.key === 'theme') theme.value = e.newValue || 'light' })
- 这样其他标签页改了主题,当前页也能响应并触发 watchEffect 重跑
- 注意:storage 事件不触发当前页的 localStorage 修改,只通知其他页
封装成可复用的组合式函数
避免重复逻辑,推荐抽成 useLocalStorage:
- 接收 key 和默认值,返回一个响应式 ref
- 内部处理初始化、setItem、storage 事件监听和清理
- 调用时只需 const darkMode = useLocalStorage('darkMode', false)
- 之后 watchEffect(() => { if (darkMode.value) enableDark() }) 即可

















