Class 本身无响应式能力,真正起作用的是 Proxy 的拦截逻辑;Class 封装状态结构与生命周期,Proxy 实现按需递归代理、依赖收集与更新触发,并需兼容数组操作及边界情况。

Class 本身不带响应式能力,真正起作用的是 Proxy 对数据访问与修改的拦截逻辑。把 Class 当作状态容器和行为组织单元,用 Proxy 做“监听层”,两者配合就能构建出结构清晰、更新精准、支持深层嵌套的响应式模型。
用 Class 封装状态结构与生命周期
Class 提供明确的作用域和初始化入口,适合管理响应式数据的初始值、计算逻辑和副作用清理。构造函数中不直接操作 DOM 或执行副作用,而是准备 reactive 实例、注册依赖收集上下文、定义更新触发机制。
- 在 constructor 中调用 reactive() 包裹传入的初始数据,返回代理对象并赋给 this.state
- 避免在 class 字段中直接写原始对象(如 state = { count: 0 }),否则会绕过代理;应通过 reactive 初始化
- 可内置 effect runner(如 run() 方法),用于手动触发依赖更新,便于测试或特殊场景控制
Proxy 拦截读写并自动递归代理嵌套对象
响应灵敏的关键,在于 get 拦截器中判断返回值是否为对象或数组,并即时包装为新代理——不是一次性全量递归,而是“按需代理”,既节省性能又保证任意层级访问都可被追踪。
安全更新和维护 CLI Proxy API(CPA)部署与配置。用于 CPA 镜像升级、配置变更、认证目录兼容修复、上线验证与回滚。适用于用户提到“CPA 更新/升级/配置改了/容器重建/回滚”等场景。
- get 中使用 Reflect.get() 获取原值,再对 object/array 类型调用 reactive() 生成新代理
- 用 Map 缓存已代理对象,防止同一对象被重复代理(避免无限循环或内存泄漏)
- set 中必须 return Reflect.set(),否则赋值失败且无提示;成功后触发对应 key 的所有 effect 函数
依赖收集与触发更新靠 WeakMap + activeEffect 协同
Proxy 只负责“谁读了、谁改了”,而“读了之后该记谁、改了之后该通知谁”,需要额外的依赖映射系统。WeakMap 存对象级映射,Map 存属性级依赖集合,activeEffect 标识当前正在执行的副作用函数。
- 全局变量 activeEffect 在渲染函数执行前临时赋值,在 get 中检测它是否存在,存在才收集依赖
- 每个 target 对应一个 depsMap(WeakMap),每个 key 对应一个 effects Set,形成 target → key → [effect] 链路
- set 触发时,从 depsMap 找到 key 对应的 effects 集合,遍历执行;支持批量更新与防抖优化
兼容数组与边界操作,避免常见陷阱
数组索引赋值、push/pop、for...in、Object.keys() 等操作默认不进 get/set,需在 handler 中补充 ownKeys、has、getOwnPropertyDescriptor 等 trap,并统一触发 'keys' 或 'length' 依赖。
- 对 Array.isArray(value) 的返回值,用 reactive 包装新数组,而非原生数组(否则 arr[0] = x 不触发 set)
- 解构赋值会脱离响应链,应提供 toRefs 工具方法,为每个属性返回带 get/set 的 ref 对象
- JSON.stringify() 易导致死循环,可在 proxy 的 get 中对 Symbol.toStringTag 等特殊 key 做拦截处理

















