blob: 441ff16ad9334f8dff82ccd2ef2ca9f3e7c2345a [file] [log] [blame]
Ben Murdoch4a90d5f2016-03-22 12:00:34 +00001// Copyright 2015 the V8 project authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
Ben Murdoch4a90d5f2016-03-22 12:00:34 +00005var target = {};
6var configurable_desc = {
7 value: 123,
8 configurable: true,
9 writable: true,
10 enumerable: false,
11};
12Object.defineProperty(target, "configurable", configurable_desc);
13var nonconfigurable_desc = {
14 value: 234,
15 configurable: false,
16 writable: false,
17 enumerable: true
18}
19Object.defineProperty(target, "nonconfigurable", nonconfigurable_desc);
20
21var proxied_desc = {
22 value: 345,
23 configurable: true
24};
25
26var handler = {
27 "getOwnPropertyDescriptor": function(target, name) {
28 if (name === "proxied") {
29 return proxied_desc;
30 }
31 if (name === "return_null") {
32 return null;
33 }
34 return Object.getOwnPropertyDescriptor(target, name);
35 }
36};
37
38var proxy = new Proxy(target, handler);
39var proxy_without_handler = new Proxy(target, {});
40
41// Checking basic functionality:
42
43assertEquals(configurable_desc,
44 Object.getOwnPropertyDescriptor(proxy, "configurable"));
45assertEquals(nonconfigurable_desc,
46 Object.getOwnPropertyDescriptor(proxy, "nonconfigurable"));
47assertEquals({ value: proxied_desc.value,
48 configurable: proxied_desc.configurable,
49 enumerable: false,
50 writable: false },
51 Object.getOwnPropertyDescriptor(proxy, "proxied"));
52assertEquals(configurable_desc,
53 Object.getOwnPropertyDescriptor(proxy_without_handler,
54 "configurable"));
55assertEquals(nonconfigurable_desc,
56 Object.getOwnPropertyDescriptor(proxy_without_handler,
57 "nonconfigurable"));
58
59assertThrows('Object.getOwnPropertyDescriptor(proxy, "return_null")');
60
61handler.getOwnPropertyDescriptor = undefined;
62assertEquals(configurable_desc,
63 Object.getOwnPropertyDescriptor(proxy, "configurable"));
64
65// Checking invariants mentioned explicitly by the ES spec:
66
67// (Inv-1) "A property cannot be reported as non-existent, if it exists as a
68// non-configurable own property of the target object."
69handler.getOwnPropertyDescriptor = function(target, name) { return undefined; };
70assertThrows('Object.getOwnPropertyDescriptor(proxy, "nonconfigurable")');
71assertEquals(undefined, Object.getOwnPropertyDescriptor(proxy, "configurable"));
72
73// (Inv-2) "A property cannot be reported as non-configurable, if it does not
74// exist as an own property of the target object or if it exists as a
75// configurable own property of the target object."
76handler.getOwnPropertyDescriptor = function(target, name) {
77 return {value: 234, configurable: false, enumerable: true};
78};
79assertThrows('Object.getOwnPropertyDescriptor(proxy, "nonexistent")');
80assertThrows('Object.getOwnPropertyDescriptor(proxy, "configurable")');
81assertEquals(
82 false,
83 Object.getOwnPropertyDescriptor(proxy, "nonconfigurable").configurable);
84
85// (Inv-3) "A property cannot be reported as non-existent, if it exists as an
86// own property of the target object and the target object is not extensible."
87Object.seal(target);
88handler.getOwnPropertyDescriptor = function(target, name) { return undefined; };
89assertThrows('Object.getOwnPropertyDescriptor(proxy, "configurable")');
90assertThrows('Object.getOwnPropertyDescriptor(proxy, "nonconfigurable")');
91assertEquals(undefined, Object.getOwnPropertyDescriptor(proxy, "nonexistent"));
92
93// (Inv-4) "A property cannot be reported as existent, if it does not exist as
94// an own property of the target object and the target object is not
95// extensible."
96var existent_desc = {value: "yes"};
97handler.getOwnPropertyDescriptor = function() { return existent_desc; };
98assertThrows('Object.getOwnPropertyDescriptor(proxy, "nonexistent")');
99assertEquals(
100 {value: "yes", writable: false, enumerable: false, configurable: false},
101 Object.getOwnPropertyDescriptor(proxy, "configurable"));
102
103// Checking individual bailout points in the implementation:
104
105// Step 6: Trap is not callable.
106handler.getOwnPropertyDescriptor = {};
107assertThrows('Object.getOwnPropertyDescriptor(proxy, "configurable")');
108
109// Step 8: Trap throws.
110handler.getOwnPropertyDescriptor = function() { throw "ball"; };
111assertThrows('Object.getOwnPropertyDescriptor(proxy, "configurable")');
112
113// Step 9: Trap result is neither undefined nor an object.
114handler.getOwnPropertyDescriptor = function() { return 1; }
115assertThrows('Object.getOwnPropertyDescriptor(proxy, "configurable")');
116
117// Step 11b: See (Inv-1) above.
118// Step 11e: See (Inv-3) above.
119
120// Step 16: Incompatible PropertyDescriptor; a non-configurable property
121// cannot be reported as configurable. (Inv-4) above checks more cases.
122handler.getOwnPropertyDescriptor = function(target, name) {
123 return {value: 456, configurable: true, writable: true}
124};
125assertThrows('Object.getOwnPropertyDescriptor(proxy, "nonconfigurable")');
126
127// Step 17: See (Inv-2) above.