前言
最近在复习阮老师《ECMAScript6入门》,回顾以前学习的知识点,这已经是我第N遍看这本书了,每次看都能有不同的感受。今天在看Reflect.set api的时候,有这样一句话。
我在想为什么有这样一种行为?
对ES6有一定了解的朋友应该知道,在对一个对象使用Proxy时,如果需要默认行为,就离不开Reflect,像这样:
上面的例子说明一个问题,当要对"对象设置属性"这种行为使用Proxy,则需要使用Reflect.set这个api,像这样:
但是上文说到了,当给Reflect.set方法传入了receiver了,则会执行Proxy.defineProperty方法;
请见下面的分析过程。
分析
如果Reflect.set没有传入receiver,则会直接将Proxy中target对象修改键值对;
而传入receiver,则会将"修改"行为设置receiver对象上(receiver一般情况下为proxy对象),修改一个对象的属性底层调用的是Object.defineProperty方法,所以会触发proxy对象的definePropery行为,请见下面示例代码:
const target = {foo: 1};
const handler = {
set(target, key, value, receiver) {
console.log('进入handler的set方法...');
console.log('---enter---');
Reflect.set(...arguments);
console.log('---exit---');
},
defineProperty(target, key, desc) {
console.log('进入handler的defineProperty方法...');
console.log('值还未修改: ', Reflect.get(target, key));
Reflect.defineProperty(...arguments);
console.log('值已经修改: ', Reflect.get(target, key));
}
};
const p = new Proxy(target, handler);
p.foo = 2;
输出结果: