
在 Vue3 的响应式系统中,watch 是监听数据变化的核心 API 之一。随着 Composition API 的普及,开发者需要更清晰地理解副作用管理机制。
一、Vue3 的 watch 机制1.1 基本用法
import { ref, watch } from 'vue'const count = ref(0)// 基本监听模式const stopWatch = watch(count, (newVal, oldVal) => { console.log(`值从 ${oldVal} 变为 ${newVal}`)})// 停止监听// stopWatch() // 手动调用停止监听1.2 自动停止机制
当在组件 setup() 中同步创建时,Vue3 会自动关联生命周期:
export default { setup() { const count = ref(0) // 自动绑定组件生命周期 watch(count, (val) => { console.log('Count changed:', val) }) return { count } }}组件卸载时,Vue 会自动停止这些监听器,无需手动干预。
二、必须手动清除的 3 种场景2.1 异步创建的监听器
import { onMounted, onUnmounted } from'vue'exportdefault { setup() { let stopWatch = null onMounted(() => { // 异步创建监听器 setTimeout(() => { stopWatch = watch(/* ... */) }, 1000) }) onUnmounted(() => { if (stopWatch) { stopWatch() // 必须手动清除 } }) }}关键点:Vue 无法追踪异步创建的监听器,需要开发者自行管理
2.2 动态条件监听
const searchKeyword = ref('')let searchWatch = null// 根据用户操作动态创建function enableSearch() { searchWatch = watch(searchKeyword, () => { // 执行搜索逻辑 })}function disableSearch() { searchWatch?.() // 主动销毁}典型场景:需要运行时动态启用的监听逻辑。
2.3 全局状态监听
// store.jsimport { watch } from'vue'import store from'./store'// 全局监听(危险操作!)let globalWatcher = nullexportfunction initGlobalWatch() { globalWatcher = watch( () => store.state.user, (user) => { console.log('User changed:', user) } )}exportfunction cleanupGlobalWatch() { globalWatcher?.()}风险提示:全局监听器不会自动销毁,必须提供显式清理接口。
三、智能管理方案3.1 自动管理组合式函数
import { watchEffect, onScopeDispose } from'vue'exportfunction useAutoCleanWatcher() {const stop = watchEffect(() => { // 副作用逻辑 })// 自动注册清理 onScopeDispose(() => { stop() })return { stop }}优势:利用 onScopeDispose 实现自动清理。
3.2 监听器工厂模式
function createSmartWatcher(source, callback) {const stop = watch(source, callback)return { stop, restart: () => { stop() return createSmartWatcher(source, callback) } }}// 使用示例const { stop } = createSmartWatcher(value, () => {})扩展性:封装重启功能,增强可维护性。