1// Copyright 2016 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 5// Flags: --harmony-object-own-property-descriptors 6// Flags: --allow-natives-syntax 7 8function DataDescriptor(value) { 9 return { "enumerable": true, "configurable": true, "writable": true, value }; 10} 11 12 13function TestMeta() { 14 assertEquals(1, Object.getOwnPropertyDescriptors.length); 15 assertEquals(Function.prototype, 16 Object.getPrototypeOf(Object.getOwnPropertyDescriptors)); 17 assertEquals( 18 'getOwnPropertyDescriptors', Object.getOwnPropertyDescriptors.name); 19 var desc = Reflect.getOwnPropertyDescriptor( 20 Object, 'getOwnPropertyDescriptors'); 21 assertFalse(desc.enumerable); 22 assertTrue(desc.writable); 23 assertTrue(desc.configurable); 24} 25TestMeta(); 26 27 28function TestToObject() { 29 assertThrows(function() { 30 Object.getOwnPropertyDescriptors(null); 31 }, TypeError); 32 33 assertThrows(function() { 34 Object.getOwnPropertyDescriptors(undefined); 35 }, TypeError); 36 37 assertThrows(function() { 38 Object.getOwnPropertyDescriptors(); 39 }, TypeError); 40} 41TestToObject(); 42 43 44function TestPrototypeProperties() { 45 function F() {}; 46 F.prototype.a = "A"; 47 F.prototype.b = "B"; 48 49 var F2 = new F(); 50 Object.defineProperties(F2, { 51 "b": { 52 enumerable: false, 53 configurable: true, 54 writable: false, 55 value: "Shadowed 'B'" 56 }, 57 "c": { 58 enumerable: false, 59 configurable: true, 60 writable: false, 61 value: "C" 62 } 63 }); 64 65 assertEquals({ 66 "b": { 67 enumerable: false, 68 configurable: true, 69 writable: false, 70 value: "Shadowed 'B'" 71 }, 72 "c": { 73 enumerable: false, 74 configurable: true, 75 writable: false, 76 value: "C" 77 } 78 }, Object.getOwnPropertyDescriptors(F2)); 79} 80TestPrototypeProperties(); 81 82 83function TestPrototypeProperties() { 84 function F() {}; 85 F.prototype.a = "A"; 86 F.prototype.b = "B"; 87 88 var F2 = new F(); 89 Object.defineProperties(F2, { 90 "b": { 91 enumerable: false, 92 configurable: true, 93 writable: false, 94 value: "Shadowed 'B'" 95 }, 96 "c": { 97 enumerable: false, 98 configurable: true, 99 writable: false, 100 value: "C" 101 } 102 }); 103 104 assertEquals({ 105 "b": { 106 enumerable: false, 107 configurable: true, 108 writable: false, 109 value: "Shadowed 'B'" 110 }, 111 "c": { 112 enumerable: false, 113 configurable: true, 114 writable: false, 115 value: "C" 116 } 117 }, Object.getOwnPropertyDescriptors(F2)); 118} 119TestPrototypeProperties(); 120 121 122function TestTypeFilteringAndOrder() { 123 var log = []; 124 var sym = Symbol("foo"); 125 var psym = %CreatePrivateSymbol("private"); 126 var O = { 127 0: 0, 128 [sym]: 3, 129 "a": 2, 130 [psym]: 4, 131 1: 1, 132 }; 133 var P = new Proxy(O, { 134 ownKeys(target) { 135 log.push("ownKeys()"); 136 return Reflect.ownKeys(target); 137 }, 138 getOwnPropertyDescriptor(target, name) { 139 log.push(`getOwnPropertyDescriptor(${String(name)})`); 140 return Reflect.getOwnPropertyDescriptor(target, name); 141 }, 142 get(target, name) { assertUnreachable(); }, 143 set(target, name, value) { assertUnreachable(); }, 144 deleteProperty(target, name) { assertUnreachable(); }, 145 defineProperty(target, name, desc) { assertUnreachable(); } 146 }); 147 148 var result1 = Object.getOwnPropertyDescriptors(O); 149 assertEquals({ 150 0: DataDescriptor(0), 151 1: DataDescriptor(1), 152 "a": DataDescriptor(2), 153 [sym]: DataDescriptor(3) 154 }, result1); 155 156 var result2 = Object.getOwnPropertyDescriptors(P); 157 assertEquals([ 158 "ownKeys()", 159 "getOwnPropertyDescriptor(0)", 160 "getOwnPropertyDescriptor(1)", 161 "getOwnPropertyDescriptor(a)", 162 "getOwnPropertyDescriptor(Symbol(foo))" 163 ], log); 164 assertEquals({ 165 0: DataDescriptor(0), 166 1: DataDescriptor(1), 167 "a": DataDescriptor(2), 168 [sym]: DataDescriptor(3) 169 }, result2); 170} 171TestTypeFilteringAndOrder(); 172 173 174function TestDuplicateKeys() { 175 var i = 0; 176 var log = []; 177 var P = new Proxy({}, { 178 ownKeys() { 179 log.push(`ownKeys()`); 180 return ["A", "A"]; 181 }, 182 getOwnPropertyDescriptor(t, name) { 183 log.push(`getOwnPropertyDescriptor(${name})`); 184 if (i++) return; 185 return { 186 configurable: true, 187 writable: false, 188 value: "VALUE" 189 }; 190 }, 191 get(target, name) { assertUnreachable(); }, 192 set(target, name, value) { assertUnreachable(); }, 193 deleteProperty(target, name) { assertUnreachable(); }, 194 defineProperty(target, name, desc) { assertUnreachable(); } 195 }); 196 197 var result = Object.getOwnPropertyDescriptors(P); 198 assertEquals({ "A": undefined }, result); 199 assertTrue(result.hasOwnProperty("A")); 200 assertEquals([ 201 "ownKeys()", 202 "getOwnPropertyDescriptor(A)", 203 "getOwnPropertyDescriptor(A)" 204 ], log); 205} 206TestDuplicateKeys(); 207