该方法用来监听常规的复杂数据,尤其是针对后端接口返回的数据,因此不包含 Set、Map、Function 等特殊类型。
该方法可以监听数据的属性修改、属性被删除、数组的变化等。
function createDeepProxy(target, callback) {
const proxyCache = new WeakMap();
let rootProxy;
const handler = {
get(target, key, receiver) {
const value = Reflect.get(target, key, receiver);
// 递归代理嵌套对象/数组
if (
value &&
typeof value === 'object' &&
(Array.isArray(value) || value.constructor === Object)
) {
if (!proxyCache.has(value)) {
proxyCache.set(value, new Proxy(value, handler));
}
return proxyCache.get(value);
}
return value;
},
set(target, key, value, receiver) {
const success = Reflect.set(target, key, value);
if (success) callback(rootProxy);
return success;
},
deleteProperty(target, key) {
const success = Reflect.deleteProperty(target, key);
if (success) callback(rootProxy);
return success;
},
};
// 验证初始数据类型
if (!(target instanceof Object) && !Array.isArray(target)) {
throw new Error('Only support Object and Array types');
}
// 创建根代理
rootProxy = new Proxy(target, handler);
return rootProxy;
}
测试:
const data = {
user: {
name: 'John',
hobbies: ['reading', 'coding'],
},
logs: [],
};
const proxy = createDeepProxy(data, (newData) => {
console.log('Data changed:', JSON.stringify(newData));
});
proxy.user.age = 30; // 对象属性添加
proxy.user.hobbies.push('swimming'); // 数组操作
proxy.logs = [{ time: '2023', msg: 'test' }]; // 整个数组替换
proxy.logs[0].msg = 'updated'; // 嵌套对象修改
delete proxy.user.name; // 删除对象属性
Reflect.deleteProperty(proxy, 'logs'); // 删除对象属性