effectscope 是 vue 3.2+ 提供的副作用容器,用于统一管理 watch、computed、watcheffect 等响应式副作用的生命周期;它不改变响应性,而是解决自动清理问题,支持批量注册、一键停止、嵌套/独立作用域及与组件生命周期对齐。

effectScope 是 Vue 3.2+ 提供的副作用容器,核心用途就是把 watch、computed、watchEffect、定时器、事件监听等响应式副作用“打包”进一个可统一控制的生命周期单元里。它不改变数据响应性,而是解决“谁来管清理”这个实际问题。
批量注册与一键停止
在 scope.run() 内部创建的响应式 API 会自动归属到该作用域,无需手动关联:
- 调用 scope.stop() 时,Vue 自动遍历并停止所有已注册的 watch、watchEffect、computed;同时触发所有通过 onScopeDispose 注册的清理函数(如 clearTimeout、removeEventListener)
- 已停止的作用域不可恢复,再次调用 run 不生效;需新建 scope 才能重新启用
- stop 后,相关 computed 不再更新,watch 不再响应变化,watchEffect 彻底静默
组合式函数中封装清理逻辑
让 useXxx 函数自带“自销毁”能力,调用方无需关心内部资源:
- 在函数内部创建 effectScope,并在 run 回调中定义副作用和 onScopeDispose 清理项
- 返回一个显式 stop 方法,或直接在 onUnmounted / onScopeDispose 中调用 scope.stop()
- 例如 usePolling 可封装定时请求 + 自动取消,useMouse 可绑定/解绑 move 事件,全部由 scope 统一兜底
嵌套与独立作用域的灵活控制
支持层级化管理,适应不同粒度的生命周期需求:
- 默认嵌套:子 scope 创建时不传参,父 scope.stop() 时子 scope 自动停止
- 独立作用域:用 effectScope(true) 创建 detached 作用域,不受外部作用域影响,适合跨组件共享或长期驻留的逻辑
- 可在 setup 中创建多个 scope,按功能模块划分(如表单校验、实时搜索、图表联动),互不干扰
与组件生命周期自然对齐
虽然 effectScope 是手动创建的,但它能无缝融入 Vue 的销毁流程:
- 在 onMounted 中调用 scope.run(),在 onUnmounted 中调用 scope.stop(),行为与组件生命周期一致
- 也可配合 onScopeDispose(在当前活跃作用域中注册清理),它会在所在作用域停止时自动执行,比手动写 onUnmounted 更通用
- 注意:setup() 本身就在一个隐式作用域中运行,组件卸载时该默认作用域自动 stop —— effectScope 是把这个机制显式暴露给你用









