JavaScript里的Proxy目标与Object

lxf2023-12-20 23:40:02

在JavaScript中,我们一般适用对象来封装数据与行为,并通过浏览对象的属性去操作数据与执行行为。可是,在我们必须对特性浏览跟对象实际操作开展更粗粒度控制时,原生的目标体制很有可能也会变得不足灵便。比如,我们也许需要限定对象属性的载入和设定,或是纪录目标操控的日志,此刻Proxy目标就能派上用场。

JavaScript里的Proxy目标是ES6(ECMAScript 2015)引进的一个新特点,它允许创建一个代理对象,用以在目标用户的前提下提供一个额外抽象层。该代理对象允许阻拦和界定一些默认实际操作,比如特性浏览、函数调用、目标枚举类型等。Proxy目标与Object.defineProperty()方法与getter和setter方式相近,但它提供了更多性能和更加好的支持定制性。

建立Proxy对象词法如下所示:

const proxy = new Proxy(target, handler);

在其中,target提出要建立代理对象的目标用户,handler是一个目标,它重新定义了要阻拦的操作。handler目标能够包括一组特殊方式,这个方法允许阻拦并界定默认实际操作,比如get()set()apply()等。

以下属于一些可利用的方式:

  • get(target, prop, receiver):阻拦对象属性的载入实际操作。
  • set(target, prop, value, receiver):阻拦对象属性设置实际操作。
  • has(target, prop):阻拦目标in操作符的操作。
  • apply(target, thisArg, argumentsList):阻拦函数的调用实际操作。
  • construct(target, argumentsList, newTarget):阻拦new运算符的操作。
  • getOwnPropertyDescriptor(target, prop):阻拦Object.getOwnPropertyDescriptor()的操作。
  • defineProperty(target, prop, descriptor):阻拦Object.defineProperty()的操作。
  • deleteProperty(target, prop):阻拦对象属性的移除实际操作。
  • getPrototypeOf(target):阻拦Object.getPrototypeOf()的操作。
  • setPrototypeOf(target, prototype):阻拦Object.setPrototypeOf()的操作。
  • isExtensible(target):阻拦Object.isExtensible()的操作。
  • preventExtensions(target):阻拦Object.preventExtensions()的操作。
  • enumerate(target):阻拦for...in循环的操作。
  • ownKeys(target):阻拦Object.getOwnPropertyNames()和Object.getOwnPropertySymbols()的操作。

每一个方式函数公式都能被传送一些主要参数,包含目标用户、属性名、值等。我们可以在函数中解决这些主要参数,随后回到你最期待的结果。

下列是一个应用Proxy目标的事例,用以纪录对象属性的载入和设定实际操作:

const target = {
  name: 'John',
  age: 30
};

const handler = {
  get: function(target, prop, receiver) {
    console.log(`Getting ${prop} value`);
    return target[prop];
  },

  set: function(target, prop, value, receiver) { 
    console.log(`Setting ${prop} value to ${value}`);
    target[prop] = value; 
  }
};

const proxy = new Proxy(target, handler);

console.log(proxy.name); // 导出 "Getting name value" 和 "John" 
proxy.age = 40; // 导出 "Setting age value to 40" 
console.log(proxy.age); // 导出 "Getting age value" 和 "40"

在后面的例子中,使用Proxy目标创建了一个代理对象proxy,它代理商了目标用户target的载入和设定实际操作。在handler目标中,大家重新定义了get()set()方式来阻拦载入和设定实际操作,做好记录了操控的日志。在代理对象上载入和设定特性时,我们会看到对应的日志导出。

除了以上的办法,Proxy目标还提供一些其他的特点,比如“可撤销代理商”。可撤销代理商是一种专项计划的代理对象,它允许撤消代理对象的操作并复原到初始目标。我们可以通过启用Proxy.revocable()方式来创建一个可撤销代理对象。

下列是一个应用可撤销代理商的事例:

const target = { name: 'John', age: 30 };

const handler = { 
    get: function(target, prop) { 
        return target[prop]; 
    } 
};

const {proxy, revoke} = Proxy.revocable(target, handler);

console.log(proxy.name); // 导出 "John"

revoke(); // 撤消代理对象

console.log(proxy.name); 
// 抛出去 TypeError: Cannot perform 'get' on a proxy that has been revoked

在后面的例子中,使用Proxy.revocable()方式创建了一个可撤销代理对象。我们能像一般代理对象一样使用这些,可是在我们启用revoke()方式撤消代理对象时,每一个实际操作要被复原到初始目标上。在这样一个例子中,大家在撤消代理对象后重新浏览代理商对象的属性,会提出一个TypeError出现异常。

总而言之,Proxy目标是一个强劲且灵便的特点,它能让你以一种非常粗粒度的形式被控对象的浏览及使用,同时提供了很多有意思和有价值的作用。尽管应用Proxy目标一定要谨慎,但当你必须能够更好地被控对象状况时,它是一个非常有使用价值的一种手段。

本站是一个以CSS、JavaScript、Vue、HTML为中心的前端开发技术网址。我们的使命是为众多前端工程师者提供全方位、全方位、好用的前端工程师专业知识和技术服务。 在网站上,大家可以学到最新前端开发技术,掌握前端工程师最新发布的趋势和良好实践。大家提供大量实例教程和实例,让大家可以快速上手前端工程师的关键技术和程序。 本站还提供了一系列好用的工具软件,帮助你更高效地开展前端工程师工作中。公司提供的一种手段和软件都要经过精心策划和改进,能够帮助你节约时间精力,提高研发效率。 此外,本站还拥有一个有活力的小区,你可以在社区里与其它前端工程师者沟通交流技术性、交流经验、处理问题。我们坚信,街道的能量能够帮助你能够更好地进步与成长。 在网站上,大家可以寻找你需要的一切前端工程师网络资源,使您成为一名更加出色的网页开发者。欢迎你添加我们的大家庭,一起探索前端工程师的无限潜能!