29

使用JavaScript的Proxy监听对象属性变化并进行类public/private的访问控制

 4 years ago
source link: https://www.tuicool.com/articles/zuyAbmz
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.

Proxy是ES6的引入的一个对象监听机制。可视为JavaScript对象的一个代理中间件。用户在访问对象时,会触发自定义行为。

监听属性变化

Proxy最简单的用法是可以监听对象属性的变化,比如下面的,当 obj 的 visit 属性改变时,自动更新页面上相应的 input元素值。

<form>

<input type="text" name="visit">

</form>

<script type="text/javascript">

var obj = {}

var handler = {

set: function(target, name, value) {    

//改变被代理对象的值,使之保持一致

target[name] = value

var input = document.querySelector('[name=' + name + ']')

if (input) {

input.value = value

}

}

}

var proxy = new Proxy(obj, handler);

proxy.visit = 100

setInterval(function() {

proxy.visit++

}, 1000)

</script>

Proxy还可以用来检查设置的值是否规范:

var obj = {}

var handler = {
  set: function(target, name, value) {    
    if (isNaN(Number(value))) {
      throw 'Type error'
    }

    target[name] = value
  }
}

var proxy = new Proxy(obj, handler);

执行结果:

proxy.visit = 'OurJS'
> Uncaught Type error

proxy.visit = 100
> 100

用Proxy实现private/ public

ES6已经有了关于private属性的提案,但是浏览器目前还没有实施,代码如下:

class Something {
  #property;

  constructor(){
    this.#property = "test";
  }
}

const instance = new Something();
console.log(instance.property); //=> undefined

这个提案的缺陷很明显,private私有属性必须以'#'开头的方式命名。用Proxy就可以简单实现这个方案:

var obj = { '#user': 'OurJS' }
var proxy = new Proxy(obj, {
  get: function(target, name) {
    if (name[0]=='#') {
      throw 'Access forbidden'
    }
  }
});

执行结果:

console.log(proxy['#user'])
> Uncaught Access forbidden

控制 in 语法

Proxy可以控制in语法

var obj = { _visit: 100, name: 'OurJS' }

var proxy = new Proxy(obj, {
  has: function(target, name) {
    return name[0] != '_'
  }
})

使用

_visit in proxy
> VM306:1 Uncaught ReferenceError: _visit is not defined

name in proxy
true

类似的可以控制枚举等。


About Joyk


Aggregate valuable and interesting links.
Joyk means Joy of geeK