OLD | NEW |
| (Empty) |
1 // 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 | |
5 // Flags: --harmony-destructuring-assignment --harmony-destructuring-bind | |
6 | |
7 // script-level tests | |
8 var ox, oy = {}, oz; | |
9 ({ | |
10 x: ox, | |
11 y: oy.value, | |
12 y2: oy["value2"], | |
13 z: ({ set v(val) { oz = val; } }).v | |
14 } = { | |
15 x: "value of x", | |
16 y: "value of y1", | |
17 y2: "value of y2", | |
18 z: "value of z" | |
19 }); | |
20 assertEquals("value of x", ox); | |
21 assertEquals("value of y1", oy.value); | |
22 assertEquals("value of y2", oy.value2); | |
23 assertEquals("value of z", oz); | |
24 | |
25 [ox, oy.value, oy["value2"], ...{ set v(val) { oz = val; } }.v] = [ | |
26 1007, | |
27 798432, | |
28 555, | |
29 1, 2, 3, 4, 5 | |
30 ]; | |
31 assertEquals(ox, 1007); | |
32 assertEquals(oy.value, 798432); | |
33 assertEquals(oy.value2, 555); | |
34 assertEquals(oz, [1, 2, 3, 4, 5]); | |
35 | |
36 | |
37 (function testInFunction() { | |
38 var x, y = {}, z; | |
39 ({ | |
40 x: x, | |
41 y: y.value, | |
42 y2: y["value2"], | |
43 z: ({ set v(val) { z = val; } }).v | |
44 } = { | |
45 x: "value of x", | |
46 y: "value of y1", | |
47 y2: "value of y2", | |
48 z: "value of z" | |
49 }); | |
50 assertEquals("value of x", x); | |
51 assertEquals("value of y1", y.value); | |
52 assertEquals("value of y2", y.value2); | |
53 assertEquals("value of z", z); | |
54 | |
55 [x, y.value, y["value2"], ...{ set v(val) { z = val; } }.v] = [ | |
56 1007, | |
57 798432, | |
58 555, | |
59 1, 2, 3, 4, 5 | |
60 ]; | |
61 assertEquals(x, 1007); | |
62 assertEquals(y.value, 798432); | |
63 assertEquals(y.value2, 555); | |
64 assertEquals(z, [1, 2, 3, 4, 5]); | |
65 })(); | |
66 | |
67 | |
68 (function testArrowFunctionInitializers() { | |
69 var fn = (config = { | |
70 value: defaults.value, | |
71 nada: { nada: defaults.nada } = { nada: "nothing" } | |
72 } = { value: "BLAH" }) => config; | |
73 var defaults = {}; | |
74 assertEquals({ value: "BLAH" }, fn()); | |
75 assertEquals("BLAH", defaults.value); | |
76 assertEquals("nothing", defaults.nada); | |
77 })(); | |
78 | |
79 | |
80 (function testArrowFunctionInitializers2() { | |
81 var fn = (config = [ | |
82 defaults.value, | |
83 { nada: defaults.nada } = { nada: "nothing" } | |
84 ] = ["BLAH"]) => config; | |
85 var defaults = {}; | |
86 assertEquals(["BLAH"], fn()); | |
87 assertEquals("BLAH", defaults.value); | |
88 assertEquals("nothing", defaults.nada); | |
89 })(); | |
90 | |
91 | |
92 (function testFunctionInitializers() { | |
93 function fn(config = { | |
94 value: defaults.value, | |
95 nada: { nada: defaults.nada } = { nada: "nothing" } | |
96 } = { value: "BLAH" }) { | |
97 return config; | |
98 } | |
99 var defaults = {}; | |
100 assertEquals({ value: "BLAH" }, fn()); | |
101 assertEquals("BLAH", defaults.value); | |
102 assertEquals("nothing", defaults.nada); | |
103 })(); | |
104 | |
105 | |
106 (function testFunctionInitializers2() { | |
107 function fn(config = [ | |
108 defaults.value, | |
109 { nada: defaults.nada } = { nada: "nothing" } | |
110 ] = ["BLAH"]) { return config; } | |
111 var defaults = {}; | |
112 assertEquals(["BLAH"], fn()); | |
113 assertEquals("BLAH", defaults.value); | |
114 assertEquals("nothing", defaults.nada); | |
115 })(); | |
116 | |
117 | |
118 (function testDeclarationInitializers() { | |
119 var defaults = {}; | |
120 var { value } = { value: defaults.value } = { value: "BLAH" }; | |
121 assertEquals("BLAH", value); | |
122 assertEquals("BLAH", defaults.value); | |
123 })(); | |
124 | |
125 | |
126 (function testDeclarationInitializers2() { | |
127 var defaults = {}; | |
128 var [value] = [defaults.value] = ["BLAH"]; | |
129 assertEquals("BLAH", value); | |
130 assertEquals("BLAH", defaults.value); | |
131 })(); | |
132 | |
133 | |
134 (function testObjectLiteralProperty() { | |
135 var ext = {}; | |
136 var obj = { | |
137 a: { b: ext.b, c: ext["c"], d: { set v(val) { ext.d = val; } }.v } = { | |
138 b: "b", c: "c", d: "d" } | |
139 }; | |
140 assertEquals({ b: "b", c: "c", d: "d" }, ext); | |
141 assertEquals({ a: { b: "b", c: "c", d: "d" } }, obj); | |
142 })(); | |
143 | |
144 | |
145 (function testArrayLiteralProperty() { | |
146 var ext = {}; | |
147 var obj = [ | |
148 ...[ ext.b, ext["c"], { set v(val) { ext.d = val; } }.v ] = [ | |
149 "b", "c", "d" ] | |
150 ]; | |
151 assertEquals({ b: "b", c: "c", d: "d" }, ext); | |
152 assertEquals([ "b", "c", "d" ], obj); | |
153 })(); | |
154 | |
155 | |
156 // TODO(caitp): add similar test for ArrayPatterns, once Proxies support | |
157 // delegating symbol-keyed get/set. | |
158 (function testObjectPatternOperationOrder() { | |
159 var steps = []; | |
160 var store = {}; | |
161 function computePropertyName(name) { | |
162 steps.push("compute name: " + name); | |
163 return name; | |
164 } | |
165 function loadValue(descr, value) { | |
166 steps.push("load: " + descr + " > " + value); | |
167 return value; | |
168 } | |
169 function storeValue(descr, name, value) { | |
170 steps.push("store: " + descr + " = " + value); | |
171 store[name] = value; | |
172 } | |
173 var result = { | |
174 get a() { assertUnreachable(); }, | |
175 set a(value) { storeValue("result.a", "a", value); }, | |
176 get b() { assertUnreachable(); }, | |
177 set b(value) { storeValue("result.b", "b", value); } | |
178 }; | |
179 | |
180 ({ | |
181 obj: { | |
182 x: result.a = 10, | |
183 [computePropertyName("y")]: result.b = false, | |
184 } = {} | |
185 } = { obj: { | |
186 get x() { return loadValue(".temp.obj.x", undefined); }, | |
187 set x(value) { assertUnreachable(); }, | |
188 get y() { return loadValue(".temp.obj.y", undefined); }, | |
189 set y(value) { assertUnreachable(); } | |
190 }}); | |
191 | |
192 assertPropertiesEqual({ | |
193 a: 10, | |
194 b: false | |
195 }, store); | |
196 | |
197 assertArrayEquals([ | |
198 "load: .temp.obj.x > undefined", | |
199 "store: result.a = 10", | |
200 | |
201 "compute name: y", | |
202 "load: .temp.obj.y > undefined", | |
203 "store: result.b = false" | |
204 ], steps); | |
205 | |
206 steps = []; | |
207 | |
208 ({ | |
209 obj: { | |
210 x: result.a = 50, | |
211 [computePropertyName("y")]: result.b = "hello", | |
212 } = {} | |
213 } = { obj: { | |
214 get x() { return loadValue(".temp.obj.x", 20); }, | |
215 set x(value) { assertUnreachable(); }, | |
216 get y() { return loadValue(".temp.obj.y", true); }, | |
217 set y(value) { assertUnreachable(); } | |
218 }}); | |
219 | |
220 assertPropertiesEqual({ | |
221 a: 20, | |
222 b: true | |
223 }, store); | |
224 | |
225 assertArrayEquals([ | |
226 "load: .temp.obj.x > 20", | |
227 "store: result.a = 20", | |
228 "compute name: y", | |
229 "load: .temp.obj.y > true", | |
230 "store: result.b = true", | |
231 ], steps); | |
232 })(); | |
233 | |
234 // Credit to Mike Pennisi and other Test262 contributors for originally writing | |
235 // the testse the following are based on. | |
236 (function testArrayElision() { | |
237 var value = [1, 2, 3, 4, 5, 6, 7, 8, 9]; | |
238 var a, obj = {}; | |
239 var result = [, a, , obj.b, , ...obj["rest"]] = value; | |
240 | |
241 assertEquals(result, value); | |
242 assertEquals(2, a); | |
243 assertEquals(4, obj.b); | |
244 assertArrayEquals([6, 7, 8, 9], obj.rest); | |
245 })(); | |
246 | |
247 (function testArrayElementInitializer() { | |
248 function test(value, initializer, expected) { | |
249 var a, obj = {}; | |
250 var initialized = false; | |
251 var shouldBeInitialized = value[0] === undefined; | |
252 assertEquals(value, [ a = (initialized = true, initializer) ] = value); | |
253 assertEquals(expected, a); | |
254 assertEquals(shouldBeInitialized, initialized); | |
255 | |
256 var initialized2 = false; | |
257 assertEquals(value, [ obj.a = (initialized2 = true, initializer) ] = value); | |
258 assertEquals(expected, obj.a); | |
259 assertEquals(shouldBeInitialized, initialized2); | |
260 } | |
261 | |
262 test([], "BAM!", "BAM!"); | |
263 test([], "BOOP!", "BOOP!"); | |
264 test([null], 123, null); | |
265 test([undefined], 456, 456); | |
266 test([,], "PUPPIES", "PUPPIES"); | |
267 | |
268 (function accept_IN() { | |
269 var value = [], x; | |
270 assertEquals(value, [ x = 'x' in {} ] = value); | |
271 assertEquals(false, x); | |
272 })(); | |
273 | |
274 (function ordering() { | |
275 var x = 0, a, b, value = []; | |
276 assertEquals(value, [ a = x += 1, b = x *= 2 ] = value); | |
277 assertEquals(1, a); | |
278 assertEquals(2, b); | |
279 assertEquals(2, x); | |
280 })(); | |
281 | |
282 (function yieldExpression() { | |
283 var value = [], it, result, x; | |
284 it = (function*() { | |
285 result = [ x = yield ] = value; | |
286 })(); | |
287 var next = it.next(); | |
288 | |
289 assertEquals(undefined, result); | |
290 assertEquals(undefined, next.value); | |
291 assertEquals(false, next.done); | |
292 assertEquals(undefined, x); | |
293 | |
294 next = it.next(86); | |
295 | |
296 assertEquals(value, result); | |
297 assertEquals(undefined, next.value); | |
298 assertEquals(true, next.done); | |
299 assertEquals(86, x); | |
300 })(); | |
301 | |
302 (function yieldIdentifier() { | |
303 var value = [], yield = "BOOP!", x; | |
304 assertEquals(value, [ x = yield ] = value); | |
305 assertEquals("BOOP!", x); | |
306 })(); | |
307 | |
308 assertThrows(function let_TDZ() { | |
309 "use strict"; | |
310 var x; | |
311 [ x = y ] = []; | |
312 let y; | |
313 }, ReferenceError); | |
314 })(); | |
315 | |
316 | |
317 (function testArrayElementNestedPattern() { | |
318 assertThrows(function nestedArrayRequireObjectCoercibleNull() { | |
319 var x; [ [ x ] ] = [ null ]; | |
320 }, TypeError); | |
321 | |
322 assertThrows(function nestedArrayRequireObjectCoercibleUndefined() { | |
323 var x; [ [ x ] ] = [ undefined ]; | |
324 }, TypeError); | |
325 | |
326 assertThrows(function nestedArrayRequireObjectCoercibleUndefined2() { | |
327 var x; [ [ x ] ] = [ ]; | |
328 }, TypeError); | |
329 | |
330 assertThrows(function nestedArrayRequireObjectCoercibleUndefined3() { | |
331 var x; [ [ x ] ] = [ , ]; | |
332 }, TypeError); | |
333 | |
334 assertThrows(function nestedObjectRequireObjectCoercibleNull() { | |
335 var x; [ { x } ] = [ null ]; | |
336 }, TypeError); | |
337 | |
338 assertThrows(function nestedObjectRequireObjectCoercibleUndefined() { | |
339 var x; [ { x } ] = [ undefined ]; | |
340 }, TypeError); | |
341 | |
342 assertThrows(function nestedObjectRequireObjectCoercibleUndefined2() { | |
343 var x; [ { x } ] = [ ]; | |
344 }, TypeError); | |
345 | |
346 assertThrows(function nestedObjectRequireObjectCoercibleUndefined3() { | |
347 var x; [ { x } ] = [ , ]; | |
348 }, TypeError); | |
349 | |
350 (function nestedArray() { | |
351 var x, value = [ [ "zap", "blonk" ] ]; | |
352 assertEquals(value, [ [ , x ] ] = value); | |
353 assertEquals("blonk", x); | |
354 })(); | |
355 | |
356 (function nestedObject() { | |
357 var x, value = [ { a: "zap", b: "blonk" } ]; | |
358 assertEquals(value, [ { b: x } ] = value); | |
359 assertEquals("blonk", x); | |
360 })(); | |
361 })(); | |
362 | |
363 (function testArrayRestElement() { | |
364 (function testBasic() { | |
365 var x, rest, array = [1, 2, 3]; | |
366 assertEquals(array, [x, ...rest] = array); | |
367 assertEquals(1, x); | |
368 assertEquals([2, 3], rest); | |
369 | |
370 array = [4, 5, 6]; | |
371 assertEquals(array, [, ...rest] = array); | |
372 assertEquals([5, 6], rest); | |
373 | |
374 })(); | |
375 | |
376 (function testNestedRestObject() { | |
377 var value = [1, 2, 3], x; | |
378 assertEquals(value, [...{ 1: x }] = value); | |
379 assertEquals(2, x); | |
380 })(); | |
381 | |
382 (function iterable() { | |
383 var count = 0; | |
384 var x, y, z; | |
385 function* g() { | |
386 count++; | |
387 yield; | |
388 count++; | |
389 yield; | |
390 count++; | |
391 yield; | |
392 } | |
393 var it = g(); | |
394 assertEquals(it, [...x] = it); | |
395 assertEquals([undefined, undefined, undefined], x); | |
396 assertEquals(3, count); | |
397 | |
398 it = [g()]; | |
399 assertEquals(it, [ [...y] ] = it); | |
400 assertEquals([undefined, undefined, undefined], y); | |
401 assertEquals(6, count); | |
402 | |
403 it = { a: g() }; | |
404 assertEquals(it, { a: [...z] } = it); | |
405 assertEquals([undefined, undefined, undefined], z); | |
406 assertEquals(9, count); | |
407 })(); | |
408 })(); | |
409 | |
410 (function testRequireObjectCoercible() { | |
411 assertThrows(() => ({} = undefined), TypeError); | |
412 assertThrows(() => ({} = null), TypeError); | |
413 assertThrows(() => [] = undefined, TypeError); | |
414 assertThrows(() => [] = null, TypeError); | |
415 assertEquals("test", ({} = "test")); | |
416 assertEquals("test", [] = "test"); | |
417 assertEquals(123, ({} = 123)); | |
418 })(); | |
419 | |
420 (function testConstReassignment() { | |
421 "use strict"; | |
422 const c = "untouchable"; | |
423 assertThrows(() => { [ c ] = [ "nope!" ]; }, TypeError); | |
424 assertThrows(() => { [ [ c ] ] = [ [ "nope!" ] ]; }, TypeError); | |
425 assertThrows(() => { [ { c } ] = [ { c: "nope!" } ]; }, TypeError); | |
426 assertThrows(() => { ({ c } = { c: "nope!" }); }, TypeError); | |
427 assertThrows(() => { ({ a: { c } } = { a: { c: "nope!" } }); }, TypeError); | |
428 assertThrows(() => { ({ a: [ c ] } = { a: [ "nope!" ] }); }, TypeError); | |
429 assertEquals("untouchable", c); | |
430 })(); | |
431 | |
432 (function testForIn() { | |
433 var log = []; | |
434 var x = {}; | |
435 var object = { | |
436 "Apenguin": 1, | |
437 "\u{1F382}cake": 2, | |
438 "Bpuppy": 3, | |
439 "Cspork": 4 | |
440 }; | |
441 for ([x.firstLetter, ...x.rest] in object) { | |
442 if (x.firstLetter === "A") { | |
443 assertEquals(["p", "e", "n", "g", "u", "i", "n"], x.rest); | |
444 continue; | |
445 } | |
446 if (x.firstLetter === "C") { | |
447 assertEquals(["s", "p", "o", "r", "k"], x.rest); | |
448 break; | |
449 } | |
450 log.push({ firstLetter: x.firstLetter, rest: x.rest }); | |
451 } | |
452 assertEquals([ | |
453 { firstLetter: "\u{1F382}", rest: ["c", "a", "k", "e"] }, | |
454 { firstLetter: "B", rest: ["p", "u", "p", "p", "y"] }, | |
455 ], log); | |
456 })(); | |
457 | |
458 (function testForOf() { | |
459 var log = []; | |
460 var x = {}; | |
461 var names = [ | |
462 "Apenguin", | |
463 "\u{1F382}cake", | |
464 "Bpuppy", | |
465 "Cspork" | |
466 ]; | |
467 for ([x.firstLetter, ...x.rest] of names) { | |
468 if (x.firstLetter === "A") { | |
469 assertEquals(["p", "e", "n", "g", "u", "i", "n"], x.rest); | |
470 continue; | |
471 } | |
472 if (x.firstLetter === "C") { | |
473 assertEquals(["s", "p", "o", "r", "k"], x.rest); | |
474 break; | |
475 } | |
476 log.push({ firstLetter: x.firstLetter, rest: x.rest }); | |
477 } | |
478 assertEquals([ | |
479 { firstLetter: "\u{1F382}", rest: ["c", "a", "k", "e"] }, | |
480 { firstLetter: "B", rest: ["p", "u", "p", "p", "y"] }, | |
481 ], log); | |
482 })(); | |
OLD | NEW |