标签:filter target cto func object user 访问规则 方法 接收
①、Proxy 的概念和常用方法
{ let obj = { //1、定义原始数据对象 对用户不可见 time: ‘2017-09-20‘, name: ‘net‘, _r: 123 }; let monitor = new Proxy(obj, { //2、通过Proxy新生成一个对象 映射obj 代理所有对obj的操作 //拦截对象的属性读取 get(target, key){ //设置访问规则 return target[key].replace(‘2017‘, ‘2018‘); }, set(target, key, value){ //设置修改规则 if (key === name) { return target[key] = value; //只允许修改name } else { return target[key]; } }, //拦截 key in object 操作 has(target, key){ if (key === ‘name‘) { return target[key]; //只暴露name属性 } else { return false } }, //拦截对 delete 操作 deleteProperty(target, key){ if (key.startsWith(‘_‘)) { //只允许删除以 ‘_‘开头的属性 delete target[key]; } else { return target[key]; } }, //拦截Object.keys(),Object.getOwnPropertySymbols(),Object,getOwnPropertyNames() 等方法 ownKeys(target){ return Object.keys(target).filter(item=>item != ‘time‘); //过滤掉 time 属性 } }); //3、用户访问的是 monitor console.log(‘get‘, monitor.time); //get 2018-09-20 读取的数据被代理修改了 monitor.time = ‘2018-01-15‘; monitor.name = ‘com‘; console.log(‘set‘, monitor.time, monitor.name); //set 2018-09-20 net time属性的修改无法生效 console.log(‘has‘, ‘name‘ in monitor, ‘time‘ in monitor); //has true false time属性被我们拦截了 delete monitor.time; delete monitor._r; console.log(‘delete‘, monitor); //delete Proxy {time: "2017-09-20", name: "net"} _r属性被删除 而对time的操作被拦截 console.log(‘ownKeys‘, Object.keys(monitor)) //ownKeys ["name"] time属性被拦截 }
②、Reflect 的概念和用法
{ **同Proxy let obj = { time: ‘2017-09-20‘, name: ‘net‘, _r: 123 }; // Reflect.get/set/has/ownKeys...(target,key,value); console.log(‘Reflect get‘, Reflect.get(obj, ‘time‘)); //Reflect get 2017-09-20 console.log(‘Reflect set‘, Reflect.set(obj, ‘name‘, ‘com‘), obj); //Reflect set true {time: "2017-09-20", name: "com", _r: 123} console.log(‘Reflect has‘, Reflect.has(obj, ‘_r‘)); //Reflect has true
③、使用 Proxy 和 Reflect 实现业务的解耦
function validator(target, validator) { return new Proxy(target, { //返回一个对target的代理 _validator: validator, //接收 验证规则 set(target, key, value, proxy){ //定义 对 target的 修改规则 if (target.hasOwnProperty(key)) { //判断 target 的 key 是否存在 let vali = this._validator[key]; //去除对应key 的验证规则 if (!!vali(value)) { return Reflect.set(target, key, value, proxy); } else { throw Error(`无法设置${value}到${key}`); } } else { throw Error(`${key}不存在`) } } }); } const userValidator = { //定义验证规则 name(val){ return /[a-zA-Z0-9_]{3,12}/.test(val); }, phone(val){ return /^1[3|4|5|8][0-9]\d{4,8}$/.test(val) } } class User{ constructor(name,phone){ this.name=name; this.phone= phone; return validator(this,userValidator); //得到一个 user的代理对象 } } let u = new User(); //初始化 得到 user 的代理 //u.name = ‘a‘ //不符合 验证规则 抛出错误 无法设置a到name console.log(u.name=‘Lain‘,u.phone=13797154666,u); //Proxy {name: "Lain", phone: 13797154666}
标签:filter target cto func object user 访问规则 方法 接收
原文地址:http://www.cnblogs.com/sunyaaa/p/ES6.html