| // Copyright 2014 the V8 project authors. All rights reserved. |
| // Use of this source code is governed by a BSD-style license that can be |
| // found in the LICENSE file. |
| |
| // Flags: --harmony-proxies |
| |
| |
| // TODO(arv): Once proxies can intercept symbols, add more tests. |
| |
| |
| function TestBasics() { |
| var log = []; |
| |
| var proxy = Proxy.create({ |
| getPropertyDescriptor: function(key) { |
| log.push(key); |
| if (key === 'x') { |
| return { |
| value: 1, |
| configurable: true |
| }; |
| } |
| return undefined; |
| } |
| }); |
| |
| var x = 'local'; |
| |
| with (proxy) { |
| assertEquals(1, x); |
| } |
| |
| // One 'x' for HasBinding and one for GetBindingValue |
| assertEquals(['assertEquals', 'x', 'x'], log); |
| } |
| TestBasics(); |
| |
| |
| function TestInconsistent() { |
| var log = []; |
| var calls = 0; |
| |
| var proxy = Proxy.create({ |
| getPropertyDescriptor: function(key) { |
| log.push(key); |
| if (key === 'x' && calls < 1) { |
| calls++; |
| return { |
| value: 1, |
| configurable: true |
| }; |
| } |
| return undefined; |
| } |
| }); |
| |
| var x = 'local'; |
| |
| with (proxy) { |
| assertEquals(void 0, x); |
| } |
| |
| // One 'x' for HasBinding and one for GetBindingValue |
| assertEquals(['assertEquals', 'x', 'x'], log); |
| } |
| TestInconsistent(); |
| |
| |
| function TestUseProxyAsUnscopables() { |
| var x = 1; |
| var object = { |
| x: 2 |
| }; |
| var calls = 0; |
| var proxy = Proxy.create({ |
| has: function(key) { |
| assertUnreachable(); |
| }, |
| getPropertyDescriptor: function(key) { |
| calls++; |
| assertEquals('x', key); |
| return { |
| value: calls === 2 ? true : undefined, |
| configurable: true, |
| enumerable: true, |
| writable: true, |
| }; |
| } |
| }); |
| |
| object[Symbol.unscopables] = proxy; |
| |
| with (object) { |
| assertEquals(2, x); |
| assertEquals(1, x); |
| } |
| |
| // HasBinding, HasBinding |
| assertEquals(2, calls); |
| } |
| TestUseProxyAsUnscopables(); |
| |
| |
| function TestThrowInHasUnscopables() { |
| var x = 1; |
| var object = { |
| x: 2 |
| }; |
| |
| function CustomError() {} |
| |
| var calls = 0; |
| var proxy = Proxy.create({ |
| has: function(key) { |
| assertUnreachable(); |
| }, |
| getPropertyDescriptor: function(key) { |
| if (calls++ === 0) { |
| throw new CustomError(); |
| } |
| assertUnreachable(); |
| } |
| }); |
| |
| object[Symbol.unscopables] = proxy; |
| |
| assertThrows(function() { |
| with (object) { |
| x; |
| } |
| }, CustomError); |
| } |
| TestThrowInHasUnscopables(); |
| |
| |
| var global = this; |
| function TestGlobalShouldIgnoreUnscopables() { |
| global.x = 1; |
| var proxy = Proxy.create({ |
| getPropertyDescriptor: function() { |
| assertUnreachable(); |
| } |
| }); |
| global[Symbol.unscopables] = proxy; |
| |
| assertEquals(1, global.x); |
| assertEquals(1, x); |
| |
| global.x = 2; |
| assertEquals(2, global.x); |
| assertEquals(2, x); |
| |
| x = 3; |
| assertEquals(3, global.x); |
| assertEquals(3, x); |
| } |
| TestGlobalShouldIgnoreUnscopables(); |