mirror of
https://github.com/tc39/test262.git
synced 2025-07-24 22:45:10 +02:00
Add initial tests for the "iterator-sequencing" proposal
This commit is contained in:
parent
dad2774b2e
commit
490463d485
@ -88,6 +88,10 @@ Error.isError
|
||||
# https://tc39.es/proposal-defer-import-eval
|
||||
import-defer
|
||||
|
||||
# Iterator Sequencing
|
||||
# https://github.com/tc39/proposal-iterator-sequencing
|
||||
iterator-sequencing
|
||||
|
||||
## Standard language features
|
||||
#
|
||||
# Language features that have been included in a published version of the
|
||||
|
42
test/built-ins/Iterator/concat/arguments-checked-in-order.js
Normal file
42
test/built-ins/Iterator/concat/arguments-checked-in-order.js
Normal file
@ -0,0 +1,42 @@
|
||||
// Copyright (C) 2024 André Bargull. All rights reserved.
|
||||
// This code is governed by the BSD license found in the LICENSE file.
|
||||
|
||||
/*---
|
||||
esid: sec-iterator.concat
|
||||
description: >
|
||||
Arguments are validated in order.
|
||||
info: |
|
||||
Iterator.concat ( ...items )
|
||||
|
||||
1. Let iterables be a new empty List.
|
||||
2. For each element item of items, do
|
||||
a. If item is not an Object, throw a TypeError exception.
|
||||
b. Let method be ? GetMethod(item, %Symbol.iterator%).
|
||||
...
|
||||
features: [iterator-sequencing]
|
||||
---*/
|
||||
|
||||
let getIterator = 0;
|
||||
|
||||
let iterable1 = {
|
||||
get [Symbol.iterator]() {
|
||||
getIterator++;
|
||||
return function() {
|
||||
throw new Test262Error();
|
||||
};
|
||||
}
|
||||
};
|
||||
|
||||
let iterable2 = {
|
||||
get [Symbol.iterator]() {
|
||||
throw new Test262Error();
|
||||
}
|
||||
};
|
||||
|
||||
assert.sameValue(getIterator, 0);
|
||||
|
||||
assert.throws(TypeError, function() {
|
||||
Iterator.concat(iterable1, null, iterable2);
|
||||
});
|
||||
|
||||
assert.sameValue(getIterator, 1);
|
49
test/built-ins/Iterator/concat/fresh-iterator-result.js
Normal file
49
test/built-ins/Iterator/concat/fresh-iterator-result.js
Normal file
@ -0,0 +1,49 @@
|
||||
// Copyright (C) 2024 André Bargull. All rights reserved.
|
||||
// This code is governed by the BSD license found in the LICENSE file.
|
||||
|
||||
/*---
|
||||
esid: sec-iterator.concat
|
||||
description: >
|
||||
Returns a fresh iterator result object
|
||||
info: |
|
||||
Iterator.concat ( ...items )
|
||||
|
||||
...
|
||||
3. Let closure be a new Abstract Closure with no parameters that captures iterables and performs the following steps when called:
|
||||
a. For each Record iterable of iterables, do
|
||||
...
|
||||
v. Repeat, while innerAlive is true,
|
||||
1. Let innerValue be ? IteratorStepValue(iteratorRecord).
|
||||
2. If innerValue is done, then
|
||||
...
|
||||
3. Else,
|
||||
a. Let completion be Completion(Yield(innerValue)).
|
||||
...
|
||||
features: [iterator-sequencing]
|
||||
---*/
|
||||
|
||||
let oldIterResult = {
|
||||
done: false,
|
||||
value: 123,
|
||||
};
|
||||
|
||||
let testIterator = {
|
||||
next() {
|
||||
return oldIterResult;
|
||||
}
|
||||
};
|
||||
|
||||
let iterable = {
|
||||
[Symbol.iterator]() {
|
||||
return testIterator;
|
||||
}
|
||||
};
|
||||
|
||||
let iterator = Iterator.concat(iterable);
|
||||
|
||||
let iterResult = iterator.next();
|
||||
|
||||
assert.sameValue(iterResult.done, false);
|
||||
assert.sameValue(iterResult.value, 123);
|
||||
|
||||
assert.notSameValue(iterResult, oldIterResult);
|
@ -0,0 +1,52 @@
|
||||
// Copyright (C) 2024 André Bargull. All rights reserved.
|
||||
// This code is governed by the BSD license found in the LICENSE file.
|
||||
|
||||
/*---
|
||||
esid: sec-iterator.concat
|
||||
description: >
|
||||
Gets the iterator method from the input iterables only once.
|
||||
info: |
|
||||
Iterator.concat ( ...items )
|
||||
|
||||
1. Let iterables be a new empty List.
|
||||
2. For each element item of items, do
|
||||
a. If item is not an Object, throw a TypeError exception.
|
||||
b. Let method be ? GetMethod(item, %Symbol.iterator%).
|
||||
c. If method is undefined, throw a TypeError exception.
|
||||
d. Append the Record { [[OpenMethod]]: method, [[Iterable]]: item } to iterables.
|
||||
...
|
||||
features: [iterator-sequencing]
|
||||
includes: [compareArray.js]
|
||||
---*/
|
||||
|
||||
let iteratorGets = 0;
|
||||
let iteratorCalls = 0;
|
||||
let array = [1, 2, 3];
|
||||
|
||||
class CountingIterable {
|
||||
get [Symbol.iterator]() {
|
||||
++iteratorGets;
|
||||
|
||||
return function () {
|
||||
++iteratorCalls;
|
||||
return array[Symbol.iterator]();
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
let iterable = new CountingIterable();
|
||||
|
||||
assert.sameValue(iteratorGets, 0);
|
||||
assert.sameValue(iteratorCalls, 0);
|
||||
|
||||
let iter = Iterator.concat(iterable);
|
||||
|
||||
assert.sameValue(iteratorGets, 1);
|
||||
assert.sameValue(iteratorCalls, 0);
|
||||
|
||||
let result = [...iter];
|
||||
|
||||
assert.sameValue(iteratorGets, 1);
|
||||
assert.sameValue(iteratorCalls, 1);
|
||||
|
||||
assert.compareArray(result, array);
|
27
test/built-ins/Iterator/concat/get-iterator-method-throws.js
Normal file
27
test/built-ins/Iterator/concat/get-iterator-method-throws.js
Normal file
@ -0,0 +1,27 @@
|
||||
// Copyright (C) 2024 André Bargull. All rights reserved.
|
||||
// This code is governed by the BSD license found in the LICENSE file.
|
||||
|
||||
/*---
|
||||
esid: sec-iterator.concat
|
||||
description: >
|
||||
Error thrown when retrieving the iterator method.
|
||||
info: |
|
||||
Iterator.concat ( ...items )
|
||||
|
||||
1. Let iterables be a new empty List.
|
||||
2. For each element item of items, do
|
||||
a. If item is not an Object, throw a TypeError exception.
|
||||
b. Let method be ? GetMethod(item, %Symbol.iterator%).
|
||||
...
|
||||
features: [iterator-sequencing]
|
||||
---*/
|
||||
|
||||
var iterable = {
|
||||
get [Symbol.iterator]() {
|
||||
throw new Test262Error();
|
||||
}
|
||||
};
|
||||
|
||||
assert.throws(Test262Error, function() {
|
||||
Iterator.concat(iterable);
|
||||
});
|
@ -0,0 +1,52 @@
|
||||
// Copyright (C) 2024 André Bargull. All rights reserved.
|
||||
// This code is governed by the BSD license found in the LICENSE file.
|
||||
|
||||
/*---
|
||||
esid: sec-iterator.concat
|
||||
description: >
|
||||
Inner iterators created in order
|
||||
info: |
|
||||
Iterator.concat ( ...items )
|
||||
|
||||
...
|
||||
3. Let closure be a new Abstract Closure with no parameters that captures iterables and performs the following steps when called:
|
||||
a. For each Record iterable of iterables, do
|
||||
i. Let iter be ? Call(iterable.[[OpenMethod]], iterable.[[Iterable]]).
|
||||
...
|
||||
v. Repeat, while innerAlive is true,
|
||||
...
|
||||
features: [iterator-sequencing]
|
||||
includes: [compareArray.js]
|
||||
---*/
|
||||
|
||||
let calledIterator = [];
|
||||
|
||||
let iterable1 = {
|
||||
[Symbol.iterator]() {
|
||||
calledIterator.push("iterable1");
|
||||
return [1][Symbol.iterator]();
|
||||
}
|
||||
};
|
||||
|
||||
let iterable2 = {
|
||||
[Symbol.iterator]() {
|
||||
calledIterator.push("iterable2");
|
||||
return [2][Symbol.iterator]();
|
||||
}
|
||||
};
|
||||
|
||||
let iterator = Iterator.concat(iterable1, iterable2);
|
||||
|
||||
assert.compareArray(calledIterator, []);
|
||||
|
||||
let iterResult = iterator.next();
|
||||
assert.sameValue(iterResult.done, false);
|
||||
assert.sameValue(iterResult.value, 1);
|
||||
|
||||
assert.compareArray(calledIterator, ["iterable1"]);
|
||||
|
||||
iterResult = iterator.next();
|
||||
assert.sameValue(iterResult.done, false);
|
||||
assert.sameValue(iterResult.value, 2);
|
||||
|
||||
assert.compareArray(calledIterator, ["iterable1", "iterable2"]);
|
15
test/built-ins/Iterator/concat/is-function.js
Normal file
15
test/built-ins/Iterator/concat/is-function.js
Normal file
@ -0,0 +1,15 @@
|
||||
// Copyright (C) 2024 André Bargull. All rights reserved.
|
||||
// This code is governed by the BSD license found in the LICENSE file.
|
||||
|
||||
/*---
|
||||
esid: sec-iterator.concat
|
||||
description: >
|
||||
Iterator.concat is a built-in function
|
||||
features: [iterator-sequencing]
|
||||
---*/
|
||||
|
||||
assert.sameValue(
|
||||
typeof Iterator.concat,
|
||||
"function",
|
||||
"The value of `typeof Iterator.concat` is 'function'"
|
||||
);
|
23
test/built-ins/Iterator/concat/length.js
Normal file
23
test/built-ins/Iterator/concat/length.js
Normal file
@ -0,0 +1,23 @@
|
||||
// Copyright (C) 2024 André Bargull. All rights reserved.
|
||||
// This code is governed by the BSD license found in the LICENSE file.
|
||||
|
||||
/*---
|
||||
esid: sec-iterator.concat
|
||||
description: >
|
||||
Iterator.concat has a "length" property whose value is 0.
|
||||
info: |
|
||||
ECMAScript Standard Built-in Objects
|
||||
|
||||
Unless otherwise specified, the length property of a built-in
|
||||
Function object has the attributes { [[Writable]]: false, [[Enumerable]]:
|
||||
false, [[Configurable]]: true }.
|
||||
features: [iterator-sequencing]
|
||||
includes: [propertyHelper.js]
|
||||
---*/
|
||||
|
||||
verifyProperty(Iterator.concat, "length", {
|
||||
value: 0,
|
||||
writable: false,
|
||||
enumerable: false,
|
||||
configurable: true,
|
||||
});
|
45
test/built-ins/Iterator/concat/many-arguments.js
Normal file
45
test/built-ins/Iterator/concat/many-arguments.js
Normal file
@ -0,0 +1,45 @@
|
||||
// Copyright (C) 2024 André Bargull. All rights reserved.
|
||||
// This code is governed by the BSD license found in the LICENSE file.
|
||||
|
||||
/*---
|
||||
esid: sec-iterator.concat
|
||||
description: >
|
||||
Iterator.concat when called with many arguments.
|
||||
info: |
|
||||
Iterator.concat ( ...items )
|
||||
|
||||
1. Let iterables be a new empty List.
|
||||
2. For each element item of items, do
|
||||
...
|
||||
3. Let closure be a new Abstract Closure with no parameters that captures iterables and performs the following steps when called:
|
||||
a. For each Record iterable of iterables, do
|
||||
...
|
||||
b. Return ReturnCompletion(undefined).
|
||||
...
|
||||
6. Return gen.
|
||||
features: [iterator-sequencing]
|
||||
---*/
|
||||
|
||||
let iterables = [
|
||||
[/* empty */],
|
||||
[1],
|
||||
[2, 3],
|
||||
[4, 5, 6],
|
||||
[7, 8, 9, 10],
|
||||
];
|
||||
|
||||
let iterator = Iterator.concat(...iterables);
|
||||
|
||||
let array = [].concat(...iterables);
|
||||
|
||||
for (let i = 0; i < array.length; i++) {
|
||||
let iterResult = iterator.next();
|
||||
|
||||
assert.sameValue(iterResult.done, false);
|
||||
assert.sameValue(iterResult.value, array[i]);
|
||||
}
|
||||
|
||||
let iterResult = iterator.next();
|
||||
|
||||
assert.sameValue(iterResult.done, true);
|
||||
assert.sameValue(iterResult.value, undefined);
|
30
test/built-ins/Iterator/concat/name.js
Normal file
30
test/built-ins/Iterator/concat/name.js
Normal file
@ -0,0 +1,30 @@
|
||||
// Copyright (C) 2024 André Bargull. All rights reserved.
|
||||
// This code is governed by the BSD license found in the LICENSE file.
|
||||
|
||||
/*---
|
||||
esid: sec-iterator.concat
|
||||
description: >
|
||||
The "name" property of Iterator.concat
|
||||
info: |
|
||||
17 ECMAScript Standard Built-in Objects
|
||||
|
||||
Every built-in Function object, including constructors, that is not
|
||||
identified as an anonymous function has a name property whose value is a
|
||||
String. Unless otherwise specified, this value is the name that is given to
|
||||
the function in this specification.
|
||||
|
||||
...
|
||||
|
||||
Unless otherwise specified, the name property of a built-in Function
|
||||
object, if it exists, has the attributes { [[Writable]]: false,
|
||||
[[Enumerable]]: false, [[Configurable]]: true }.
|
||||
features: [iterator-sequencing]
|
||||
includes: [propertyHelper.js]
|
||||
---*/
|
||||
|
||||
verifyProperty(Iterator.concat, "name", {
|
||||
value: "concat",
|
||||
writable: false,
|
||||
enumerable: false,
|
||||
configurable: true,
|
||||
});
|
@ -0,0 +1,51 @@
|
||||
// Copyright (C) 2024 André Bargull. All rights reserved.
|
||||
// This code is governed by the BSD license found in the LICENSE file.
|
||||
|
||||
/*---
|
||||
esid: sec-iterator.concat
|
||||
description: >
|
||||
Underlying iterator's next method is called with zero arguments.
|
||||
info: |
|
||||
Iterator.concat ( ...items )
|
||||
|
||||
...
|
||||
3. Let closure be a new Abstract Closure with no parameters that captures iterables and performs the following steps when called:
|
||||
a. For each Record iterable of iterables, do
|
||||
...
|
||||
v. Repeat, while innerAlive is true,
|
||||
1. Let innerValue be ? IteratorStepValue(iteratorRecord).
|
||||
...
|
||||
features: [iterator-sequencing]
|
||||
---*/
|
||||
|
||||
let nextCalled = 0;
|
||||
|
||||
let testIterator = {
|
||||
next() {
|
||||
nextCalled++;
|
||||
assert.sameValue(arguments.length, 0);
|
||||
|
||||
return {
|
||||
done: false,
|
||||
value: 0,
|
||||
};
|
||||
}
|
||||
};
|
||||
|
||||
let iterable = {
|
||||
[Symbol.iterator]() {
|
||||
return testIterator;
|
||||
}
|
||||
};
|
||||
|
||||
let iterator = Iterator.concat(iterable);
|
||||
assert.sameValue(nextCalled, 0);
|
||||
|
||||
iterator.next();
|
||||
assert.sameValue(nextCalled, 1);
|
||||
|
||||
iterator.next(1);
|
||||
assert.sameValue(nextCalled, 2);
|
||||
|
||||
iterator.next(1, 2);
|
||||
assert.sameValue(nextCalled, 3);
|
@ -0,0 +1,37 @@
|
||||
// Copyright (C) 2024 André Bargull. All rights reserved.
|
||||
// This code is governed by the BSD license found in the LICENSE file.
|
||||
|
||||
/*---
|
||||
esid: sec-iterator.concat
|
||||
description: >
|
||||
Underlying iterator next returns non-object
|
||||
info: |
|
||||
Iterator.concat ( ...items )
|
||||
|
||||
...
|
||||
3. Let closure be a new Abstract Closure with no parameters that captures iterables and performs the following steps when called:
|
||||
a. For each Record iterable of iterables, do
|
||||
...
|
||||
v. Repeat, while innerAlive is true,
|
||||
1. Let innerValue be ? IteratorStepValue(iteratorRecord).
|
||||
...
|
||||
features: [iterator-sequencing]
|
||||
---*/
|
||||
|
||||
let nonObjectIterator = {
|
||||
next() {
|
||||
return null;
|
||||
}
|
||||
};
|
||||
|
||||
let iterable = {
|
||||
[Symbol.iterator]() {
|
||||
return nonObjectIterator;
|
||||
}
|
||||
};
|
||||
|
||||
let iterator = Iterator.concat(iterable);
|
||||
|
||||
assert.throws(TypeError, function() {
|
||||
iterator.next();
|
||||
});
|
@ -0,0 +1,45 @@
|
||||
// Copyright (C) 2024 André Bargull. All rights reserved.
|
||||
// This code is governed by the BSD license found in the LICENSE file.
|
||||
|
||||
/*---
|
||||
esid: sec-iterator.concat
|
||||
description: >
|
||||
Underlying iterator next returns object with throwing done getter
|
||||
info: |
|
||||
Iterator.concat ( ...items )
|
||||
|
||||
...
|
||||
3. Let closure be a new Abstract Closure with no parameters that captures iterables and performs the following steps when called:
|
||||
a. For each Record iterable of iterables, do
|
||||
...
|
||||
v. Repeat, while innerAlive is true,
|
||||
1. Let innerValue be ? IteratorStepValue(iteratorRecord).
|
||||
...
|
||||
features: [iterator-sequencing]
|
||||
---*/
|
||||
|
||||
let throwingIterator = {
|
||||
next() {
|
||||
return {
|
||||
get done() {
|
||||
throw new Test262Error();
|
||||
},
|
||||
value: 1,
|
||||
};
|
||||
},
|
||||
return() {
|
||||
throw new Error();
|
||||
}
|
||||
};
|
||||
|
||||
let iterable = {
|
||||
[Symbol.iterator]() {
|
||||
return throwingIterator;
|
||||
}
|
||||
};
|
||||
|
||||
let iterator = Iterator.concat(iterable);
|
||||
|
||||
assert.throws(Test262Error, function() {
|
||||
iterator.next();
|
||||
});
|
@ -0,0 +1,49 @@
|
||||
// Copyright (C) 2024 André Bargull. All rights reserved.
|
||||
// This code is governed by the BSD license found in the LICENSE file.
|
||||
|
||||
/*---
|
||||
esid: sec-iterator.concat
|
||||
description: >
|
||||
Underlying iterator next returns object with throwing value getter, but is already done
|
||||
info: |
|
||||
Iterator.concat ( ...items )
|
||||
|
||||
...
|
||||
3. Let closure be a new Abstract Closure with no parameters that captures iterables and performs the following steps when called:
|
||||
a. For each Record iterable of iterables, do
|
||||
...
|
||||
v. Repeat, while innerAlive is true,
|
||||
1. Let innerValue be ? IteratorStepValue(iteratorRecord).
|
||||
...
|
||||
features: [iterator-sequencing]
|
||||
---*/
|
||||
|
||||
class ReturnCalledError extends Error {}
|
||||
class ValueGetterError extends Error {}
|
||||
|
||||
let throwingIterator = {
|
||||
next() {
|
||||
return {
|
||||
get value() {
|
||||
throw new ValueGetterError();
|
||||
},
|
||||
done: true,
|
||||
};
|
||||
},
|
||||
return() {
|
||||
throw new ReturnCalledError();
|
||||
}
|
||||
};
|
||||
|
||||
let iterable = {
|
||||
[Symbol.iterator]() {
|
||||
return throwingIterator;
|
||||
}
|
||||
};
|
||||
|
||||
let iterator = Iterator.concat(iterable);
|
||||
|
||||
let iterResult = iterator.next();
|
||||
|
||||
assert.sameValue(iterResult.done, true);
|
||||
assert.sameValue(iterResult.value, undefined);
|
@ -0,0 +1,45 @@
|
||||
// Copyright (C) 2024 André Bargull. All rights reserved.
|
||||
// This code is governed by the BSD license found in the LICENSE file.
|
||||
|
||||
/*---
|
||||
esid: sec-iterator.concat
|
||||
description: >
|
||||
Underlying iterator next returns object with throwing value getter
|
||||
info: |
|
||||
Iterator.concat ( ...items )
|
||||
|
||||
...
|
||||
3. Let closure be a new Abstract Closure with no parameters that captures iterables and performs the following steps when called:
|
||||
a. For each Record iterable of iterables, do
|
||||
...
|
||||
v. Repeat, while innerAlive is true,
|
||||
1. Let innerValue be ? IteratorStepValue(iteratorRecord).
|
||||
...
|
||||
features: [iterator-sequencing]
|
||||
---*/
|
||||
|
||||
let throwingIterator = {
|
||||
next() {
|
||||
return {
|
||||
get value() {
|
||||
throw new Test262Error();
|
||||
},
|
||||
done: false,
|
||||
};
|
||||
},
|
||||
return() {
|
||||
throw new Error();
|
||||
}
|
||||
};
|
||||
|
||||
let iterable = {
|
||||
[Symbol.iterator]() {
|
||||
return throwingIterator;
|
||||
}
|
||||
};
|
||||
|
||||
let iterator = Iterator.concat(iterable);
|
||||
|
||||
assert.throws(Test262Error, function() {
|
||||
iterator.next();
|
||||
});
|
37
test/built-ins/Iterator/concat/next-method-throws.js
Normal file
37
test/built-ins/Iterator/concat/next-method-throws.js
Normal file
@ -0,0 +1,37 @@
|
||||
// Copyright (C) 2024 André Bargull. All rights reserved.
|
||||
// This code is governed by the BSD license found in the LICENSE file.
|
||||
|
||||
/*---
|
||||
esid: sec-iterator.concat
|
||||
description: >
|
||||
Underlying iterator has throwing next method
|
||||
info: |
|
||||
Iterator.concat ( ...items )
|
||||
|
||||
...
|
||||
3. Let closure be a new Abstract Closure with no parameters that captures iterables and performs the following steps when called:
|
||||
a. For each Record iterable of iterables, do
|
||||
...
|
||||
v. Repeat, while innerAlive is true,
|
||||
1. Let innerValue be ? IteratorStepValue(iteratorRecord).
|
||||
...
|
||||
features: [iterator-sequencing]
|
||||
---*/
|
||||
|
||||
let throwingIterator = {
|
||||
next() {
|
||||
throw new Test262Error();
|
||||
}
|
||||
};
|
||||
|
||||
let iterable = {
|
||||
[Symbol.iterator]() {
|
||||
return throwingIterator;
|
||||
}
|
||||
};
|
||||
|
||||
let iterator = Iterator.concat(iterable);
|
||||
|
||||
assert.throws(Test262Error, function() {
|
||||
iterator.next();
|
||||
});
|
17
test/built-ins/Iterator/concat/non-constructible.js
Normal file
17
test/built-ins/Iterator/concat/non-constructible.js
Normal file
@ -0,0 +1,17 @@
|
||||
// Copyright (C) 2024 André Bargull. All rights reserved.
|
||||
// This code is governed by the BSD license found in the LICENSE file.
|
||||
|
||||
/*---
|
||||
esid: sec-iterator.concat
|
||||
description: >
|
||||
Iterator.concat is not constructible.
|
||||
|
||||
Built-in function objects that are not identified as constructors do not
|
||||
implement the [[Construct]] internal method unless otherwise specified in the
|
||||
description of a particular function.
|
||||
features: [iterator-sequencing]
|
||||
---*/
|
||||
|
||||
assert.throws(TypeError, () => {
|
||||
new Iterator.concat();
|
||||
});
|
27
test/built-ins/Iterator/concat/prop-desc.js
Normal file
27
test/built-ins/Iterator/concat/prop-desc.js
Normal file
@ -0,0 +1,27 @@
|
||||
// Copyright (C) 2024 André Bargull. All rights reserved.
|
||||
// This code is governed by the BSD license found in the LICENSE file.
|
||||
|
||||
/*---
|
||||
esid: sec-iterator.concat
|
||||
description: >
|
||||
Property descriptor of Iterator.concat
|
||||
info: |
|
||||
Iterator.concat
|
||||
|
||||
* is the initial value of the Iterator.concat property of the global object.
|
||||
|
||||
17 ECMAScript Standard Built-in Objects
|
||||
|
||||
Every other data property described in clauses 18 through 26 and in Annex B.2
|
||||
has the attributes { [[Writable]]: true, [[Enumerable]]: false,
|
||||
[[Configurable]]: true } unless otherwise specified.
|
||||
features: [iterator-sequencing]
|
||||
includes: [propertyHelper.js]
|
||||
---*/
|
||||
|
||||
verifyProperty(Iterator, "concat", {
|
||||
value: Iterator.concat,
|
||||
writable: true,
|
||||
enumerable: false,
|
||||
configurable: true,
|
||||
});
|
16
test/built-ins/Iterator/concat/proto.js
Normal file
16
test/built-ins/Iterator/concat/proto.js
Normal file
@ -0,0 +1,16 @@
|
||||
// Copyright (C) 2024 André Bargull. All rights reserved.
|
||||
// This code is governed by the BSD license found in the LICENSE file.
|
||||
|
||||
/*---
|
||||
esid: sec-iterator.concat
|
||||
description: >
|
||||
The value of the [[Prototype]] internal slot of Iterator.concat is the
|
||||
intrinsic object %FunctionPrototype%.
|
||||
features: [iterator-sequencing]
|
||||
---*/
|
||||
|
||||
assert.sameValue(
|
||||
Object.getPrototypeOf(Iterator.concat),
|
||||
Function.prototype,
|
||||
"Object.getPrototypeOf(Iterator.concat) must return the value of Function.prototype"
|
||||
);
|
13
test/built-ins/Iterator/concat/result-is-iterator.js
Normal file
13
test/built-ins/Iterator/concat/result-is-iterator.js
Normal file
@ -0,0 +1,13 @@
|
||||
// Copyright (C) 2024 André Bargull. All rights reserved.
|
||||
// This code is governed by the BSD license found in the LICENSE file.
|
||||
|
||||
/*---
|
||||
esid: sec-iterator.concat
|
||||
description: >
|
||||
The value of the [[Prototype]] internal slot of the return value of Iterator.concat
|
||||
is the intrinsic object %IteratorHelperPrototype%.
|
||||
features: [iterator-sequencing]
|
||||
---*/
|
||||
|
||||
var iter = Iterator.concat();
|
||||
assert(iter instanceof Iterator, "Iterator.concat() must return an Iterator");
|
58
test/built-ins/Iterator/concat/return-is-forwarded.js
Normal file
58
test/built-ins/Iterator/concat/return-is-forwarded.js
Normal file
@ -0,0 +1,58 @@
|
||||
// Copyright (C) 2024 André Bargull. All rights reserved.
|
||||
// This code is governed by the BSD license found in the LICENSE file.
|
||||
|
||||
/*---
|
||||
esid: sec-iterator.concat
|
||||
description: >
|
||||
Underlying iterator return is called when result iterator is closed
|
||||
info: |
|
||||
Iterator.concat ( ...items )
|
||||
|
||||
...
|
||||
3. Let closure be a new Abstract Closure with no parameters that captures iterables and performs the following steps when called:
|
||||
a. For each Record iterable of iterables, do
|
||||
...
|
||||
v. Repeat, while innerAlive is true,
|
||||
...
|
||||
3. Else,
|
||||
a. Let completion be Completion(Yield(innerValue)).
|
||||
b. If completion is an abrupt completion, then
|
||||
i. Return ? IteratorClose(iteratorRecord, completion).
|
||||
...
|
||||
features: [iterator-sequencing]
|
||||
---*/
|
||||
|
||||
let returnCount = 0;
|
||||
|
||||
let testIterator = {
|
||||
next() {
|
||||
return {
|
||||
done: false,
|
||||
value: 1,
|
||||
};
|
||||
},
|
||||
return() {
|
||||
++returnCount;
|
||||
return {};
|
||||
}
|
||||
};
|
||||
|
||||
let iterable = {
|
||||
[Symbol.iterator]() {
|
||||
return testIterator;
|
||||
}
|
||||
};
|
||||
|
||||
let iterator = Iterator.concat(iterable);
|
||||
assert.sameValue(returnCount, 0);
|
||||
|
||||
let iterResult = iterator.next();
|
||||
assert.sameValue(returnCount, 0);
|
||||
assert.sameValue(iterResult.done, false);
|
||||
assert.sameValue(iterResult.value, 1);
|
||||
|
||||
iterator.return();
|
||||
assert.sameValue(returnCount, 1);
|
||||
|
||||
iterator.return();
|
||||
assert.sameValue(returnCount, 1);
|
@ -0,0 +1,43 @@
|
||||
// Copyright (C) 2024 André Bargull. All rights reserved.
|
||||
// This code is governed by the BSD license found in the LICENSE file.
|
||||
|
||||
/*---
|
||||
esid: sec-iterator.concat
|
||||
description: >
|
||||
Underlying iterator return is not called after result iterator observes that underlying iterator is exhausted
|
||||
info: |
|
||||
Iterator.concat ( ...items )
|
||||
|
||||
...
|
||||
3. Let closure be a new Abstract Closure with no parameters that captures iterables and performs the following steps when called:
|
||||
a. For each Record iterable of iterables, do
|
||||
...
|
||||
v. Repeat, while innerAlive is true,
|
||||
...
|
||||
2. If innerValue is done, then
|
||||
a. Set innerAlive to false.
|
||||
...
|
||||
features: [iterator-sequencing]
|
||||
---*/
|
||||
|
||||
let testIterator = {
|
||||
next() {
|
||||
return {
|
||||
done: true,
|
||||
value: undefined,
|
||||
};
|
||||
},
|
||||
return() {
|
||||
throw new Test262Error();
|
||||
}
|
||||
};
|
||||
|
||||
let iterable = {
|
||||
[Symbol.iterator]() {
|
||||
return testIterator;
|
||||
}
|
||||
};
|
||||
|
||||
let iterator = Iterator.concat(iterable);
|
||||
iterator.next();
|
||||
iterator.return();
|
@ -0,0 +1,32 @@
|
||||
// Copyright (C) 2024 André Bargull. All rights reserved.
|
||||
// This code is governed by the BSD license found in the LICENSE file.
|
||||
|
||||
/*---
|
||||
esid: sec-iterator.concat
|
||||
description: >
|
||||
Underlying iterator return is not called before initial call to next method
|
||||
features: [iterator-sequencing]
|
||||
---*/
|
||||
|
||||
let testIterator = {
|
||||
next() {
|
||||
return {
|
||||
done: false,
|
||||
value: 1,
|
||||
};
|
||||
},
|
||||
return() {
|
||||
throw new Test262Error();
|
||||
}
|
||||
};
|
||||
|
||||
let iterable = {
|
||||
[Symbol.iterator]() {
|
||||
return testIterator;
|
||||
}
|
||||
};
|
||||
|
||||
let iterator = Iterator.concat(iterable);
|
||||
iterator.return();
|
||||
iterator.next();
|
||||
iterator.return();
|
@ -0,0 +1,67 @@
|
||||
// Copyright (C) 2024 André Bargull. All rights reserved.
|
||||
// This code is governed by the BSD license found in the LICENSE file.
|
||||
|
||||
/*---
|
||||
esid: sec-iterator.concat
|
||||
description: >
|
||||
Underlying iterator's return method is called with zero arguments.
|
||||
info: |
|
||||
Iterator.concat ( ...items )
|
||||
|
||||
...
|
||||
3. Let closure be a new Abstract Closure with no parameters that captures iterables and performs the following steps when called:
|
||||
a. For each Record iterable of iterables, do
|
||||
...
|
||||
v. Repeat, while innerAlive is true,
|
||||
...
|
||||
3. Else,
|
||||
...
|
||||
b. If completion is an abrupt completion, then
|
||||
i. Return ? IteratorClose(iteratorRecord, completion).
|
||||
features: [iterator-sequencing]
|
||||
---*/
|
||||
|
||||
let returnCalled = 0;
|
||||
|
||||
let testIterator = {
|
||||
next() {
|
||||
return {done: false};
|
||||
},
|
||||
return() {
|
||||
returnCalled++;
|
||||
assert.sameValue(arguments.length, 0);
|
||||
return {done: true};
|
||||
}
|
||||
};
|
||||
|
||||
let iterable = {
|
||||
[Symbol.iterator]() {
|
||||
return testIterator;
|
||||
}
|
||||
};
|
||||
|
||||
let iterator;
|
||||
|
||||
// Call with zero arguments.
|
||||
iterator = Iterator.concat(iterable);
|
||||
iterator.next();
|
||||
assert.sameValue(returnCalled, 0);
|
||||
|
||||
iterator.return();
|
||||
assert.sameValue(returnCalled, 1);
|
||||
|
||||
// Call with one argument.
|
||||
iterator = Iterator.concat(iterable);
|
||||
iterator.next();
|
||||
assert.sameValue(returnCalled, 1);
|
||||
|
||||
iterator.return(1);
|
||||
assert.sameValue(returnCalled, 2);
|
||||
|
||||
// Call with two arguments.
|
||||
iterator = Iterator.concat(iterable);
|
||||
iterator.next();
|
||||
assert.sameValue(returnCalled, 2);
|
||||
|
||||
iterator.return(1, 2);
|
||||
assert.sameValue(returnCalled, 3);
|
37
test/built-ins/Iterator/concat/single-argument.js
Normal file
37
test/built-ins/Iterator/concat/single-argument.js
Normal file
@ -0,0 +1,37 @@
|
||||
// Copyright (C) 2024 André Bargull. All rights reserved.
|
||||
// This code is governed by the BSD license found in the LICENSE file.
|
||||
|
||||
/*---
|
||||
esid: sec-iterator.concat
|
||||
description: >
|
||||
Iterator.concat when called with a single argument.
|
||||
info: |
|
||||
Iterator.concat ( ...items )
|
||||
|
||||
1. Let iterables be a new empty List.
|
||||
2. For each element item of items, do
|
||||
...
|
||||
3. Let closure be a new Abstract Closure with no parameters that captures iterables and performs the following steps when called:
|
||||
a. For each Record iterable of iterables, do
|
||||
...
|
||||
b. Return ReturnCompletion(undefined).
|
||||
...
|
||||
6. Return gen.
|
||||
features: [iterator-sequencing]
|
||||
---*/
|
||||
|
||||
let array = [1, 2, 3];
|
||||
|
||||
let iterator = Iterator.concat(array);
|
||||
|
||||
for (let i = 0; i < array.length; i++) {
|
||||
let iterResult = iterator.next();
|
||||
|
||||
assert.sameValue(iterResult.done, false);
|
||||
assert.sameValue(iterResult.value, array[i]);
|
||||
}
|
||||
|
||||
let iterResult = iterator.next();
|
||||
|
||||
assert.sameValue(iterResult.done, true);
|
||||
assert.sameValue(iterResult.value, undefined);
|
@ -0,0 +1,47 @@
|
||||
// Copyright (C) 2024 André Bargull. All rights reserved.
|
||||
// This code is governed by the BSD license found in the LICENSE file.
|
||||
|
||||
/*---
|
||||
esid: sec-iterator.concat
|
||||
description: >
|
||||
Throws a TypeError when the closure generator is already running.
|
||||
info: |
|
||||
27.1.2.1.1 %IteratorHelperPrototype%.next ( )
|
||||
1. Return ? GeneratorResume(this value, undefined, "Iterator Helper").
|
||||
|
||||
27.5.3.3 GeneratorResume ( generator, value, generatorBrand )
|
||||
1. Let state be ? GeneratorValidate(generator, generatorBrand).
|
||||
...
|
||||
|
||||
27.5.3.2 GeneratorValidate ( generator, generatorBrand )
|
||||
...
|
||||
6. If state is executing, throw a TypeError exception.
|
||||
...
|
||||
features: [iterator-sequencing]
|
||||
---*/
|
||||
|
||||
let enterCount = 0;
|
||||
|
||||
let testIterator = {
|
||||
next() {
|
||||
enterCount++;
|
||||
iterator.next();
|
||||
return {done: false};
|
||||
}
|
||||
}
|
||||
|
||||
let iterable = {
|
||||
[Symbol.iterator]() {
|
||||
return testIterator;
|
||||
}
|
||||
};
|
||||
|
||||
let iterator = Iterator.concat(iterable);
|
||||
|
||||
assert.sameValue(enterCount, 0);
|
||||
|
||||
assert.throws(TypeError, function() {
|
||||
iterator.next();
|
||||
});
|
||||
|
||||
assert.sameValue(enterCount, 1);
|
@ -0,0 +1,53 @@
|
||||
// Copyright (C) 2024 André Bargull. All rights reserved.
|
||||
// This code is governed by the BSD license found in the LICENSE file.
|
||||
|
||||
/*---
|
||||
esid: sec-iterator.concat
|
||||
description: >
|
||||
Throws a TypeError when the closure generator is already running.
|
||||
info: |
|
||||
27.1.2.1.2 %IteratorHelperPrototype%.return ( )
|
||||
...
|
||||
6. Return ? GeneratorResumeAbrupt(O, C, "Iterator Helper").
|
||||
|
||||
27.5.3.4 GeneratorResumeAbrupt ( generator, abruptCompletion, generatorBrand )
|
||||
1. Let state be ? GeneratorValidate(generator, generatorBrand).
|
||||
...
|
||||
|
||||
27.5.3.2 GeneratorValidate ( generator, generatorBrand )
|
||||
...
|
||||
6. If state is executing, throw a TypeError exception.
|
||||
...
|
||||
features: [iterator-sequencing]
|
||||
---*/
|
||||
|
||||
let enterCount = 0;
|
||||
|
||||
let testIterator = {
|
||||
next() {
|
||||
return {done: false};
|
||||
},
|
||||
return() {
|
||||
enterCount++;
|
||||
iterator.return();
|
||||
return {done: false};
|
||||
}
|
||||
}
|
||||
|
||||
let iterable = {
|
||||
[Symbol.iterator]() {
|
||||
return testIterator;
|
||||
}
|
||||
};
|
||||
|
||||
let iterator = Iterator.concat(iterable);
|
||||
|
||||
iterator.next();
|
||||
|
||||
assert.sameValue(enterCount, 0);
|
||||
|
||||
assert.throws(TypeError, function() {
|
||||
iterator.return();
|
||||
});
|
||||
|
||||
assert.sameValue(enterCount, 1);
|
@ -0,0 +1,44 @@
|
||||
// Copyright (C) 2024 André Bargull. All rights reserved.
|
||||
// This code is governed by the BSD license found in the LICENSE file.
|
||||
|
||||
/*---
|
||||
esid: sec-iterator.concat
|
||||
description: >
|
||||
Throws a TypeError when the iterable is not an object.
|
||||
info: |
|
||||
Iterator.concat ( ...items )
|
||||
|
||||
1. Let iterables be a new empty List.
|
||||
2. For each element item of items, do
|
||||
a. If item is not an Object, throw a TypeError exception.
|
||||
...
|
||||
features: [iterator-sequencing]
|
||||
---*/
|
||||
|
||||
assert.throws(TypeError, function() {
|
||||
Iterator.concat(undefined);
|
||||
}, "iterable is undefined");
|
||||
|
||||
assert.throws(TypeError, function() {
|
||||
Iterator.concat(null);
|
||||
}, "iterable is null");
|
||||
|
||||
assert.throws(TypeError, function() {
|
||||
Iterator.concat(true);
|
||||
}, "iterable is boolean");
|
||||
|
||||
assert.throws(TypeError, function() {
|
||||
Iterator.concat(123);
|
||||
}, "iterable is number");
|
||||
|
||||
assert.throws(TypeError, function() {
|
||||
Iterator.concat(123n);
|
||||
}, "iterable is bigint");
|
||||
|
||||
assert.throws(TypeError, function() {
|
||||
Iterator.concat("test");
|
||||
}, "iterable is string");
|
||||
|
||||
assert.throws(TypeError, function() {
|
||||
Iterator.concat(Symbol());
|
||||
}, "iterable is symbol");
|
@ -0,0 +1,50 @@
|
||||
// Copyright (C) 2024 André Bargull. All rights reserved.
|
||||
// This code is governed by the BSD license found in the LICENSE file.
|
||||
|
||||
/*---
|
||||
esid: sec-iterator.concat
|
||||
description: >
|
||||
Throws a TypeError when the iterator method is not callable.
|
||||
info: |
|
||||
Iterator.concat ( ...items )
|
||||
|
||||
1. Let iterables be a new empty List.
|
||||
2. For each element item of items, do
|
||||
a. If item is not an Object, throw a TypeError exception.
|
||||
b. Let method be ? GetMethod(item, %Symbol.iterator%).
|
||||
c. If method is undefined, throw a TypeError exception.
|
||||
...
|
||||
features: [iterator-sequencing]
|
||||
---*/
|
||||
|
||||
assert.throws(TypeError, function() {
|
||||
Iterator.concat({});
|
||||
}, "iterable has no iterator method");
|
||||
|
||||
assert.throws(TypeError, function() {
|
||||
Iterator.concat({[Symbol.iterator]: undefined});
|
||||
}, "iterator method is undefined");
|
||||
|
||||
assert.throws(TypeError, function() {
|
||||
Iterator.concat({[Symbol.iterator]: null});
|
||||
}, "iterator method is null");
|
||||
|
||||
assert.throws(TypeError, function() {
|
||||
Iterator.concat({[Symbol.iterator]: true});
|
||||
}, "iterator method is boolean");
|
||||
|
||||
assert.throws(TypeError, function() {
|
||||
Iterator.concat({[Symbol.iterator]: 123});
|
||||
}, "iterator method is number");
|
||||
|
||||
assert.throws(TypeError, function() {
|
||||
Iterator.concat({[Symbol.iterator]: 123n});
|
||||
}, "iterator method is bigint");
|
||||
|
||||
assert.throws(TypeError, function() {
|
||||
Iterator.concat({[Symbol.iterator]: "abc"});
|
||||
}, "iterator method is string");
|
||||
|
||||
assert.throws(TypeError, function() {
|
||||
Iterator.concat({[Symbol.iterator]: Symbol()});
|
||||
}, "iterator method is symbol");
|
@ -0,0 +1,49 @@
|
||||
// Copyright (C) 2024 André Bargull. All rights reserved.
|
||||
// This code is governed by the BSD license found in the LICENSE file.
|
||||
|
||||
/*---
|
||||
esid: sec-iterator.concat
|
||||
description: >
|
||||
Throws a TypeError when the iterator is not an object.
|
||||
info: |
|
||||
Iterator.concat ( ...items )
|
||||
|
||||
...
|
||||
3. Let closure be a new Abstract Closure with no parameters that captures iterables and performs the following steps when called:
|
||||
a. For each Record iterable of iterables, do
|
||||
i. Let iter be ? Call(iterable.[[OpenMethod]], iterable.[[Iterable]]).
|
||||
ii. If iter is not an Object, throw a TypeError exception.
|
||||
...
|
||||
features: [iterator-sequencing]
|
||||
---*/
|
||||
|
||||
function MakeIterable(iterator) {
|
||||
return {
|
||||
[Symbol.iterator]() {
|
||||
return iterator;
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
var iterator;
|
||||
|
||||
iterator = Iterator.concat(MakeIterable(undefined));
|
||||
assert.throws(TypeError, function() { iterator.next(); }, "iterator is undefined");
|
||||
|
||||
iterator = Iterator.concat(MakeIterable(null));
|
||||
assert.throws(TypeError, function() { iterator.next(); }, "iterator is null");
|
||||
|
||||
iterator = Iterator.concat(MakeIterable(true));
|
||||
assert.throws(TypeError, function() { iterator.next(); }, "iterator is boolean");
|
||||
|
||||
iterator = Iterator.concat(MakeIterable(123));
|
||||
assert.throws(TypeError, function() { iterator.next(); }, "iterator is number");
|
||||
|
||||
iterator = Iterator.concat(MakeIterable(123n));
|
||||
assert.throws(TypeError, function() { iterator.next(); }, "iterator is bigint");
|
||||
|
||||
iterator = Iterator.concat(MakeIterable("abc"));
|
||||
assert.throws(TypeError, function() { iterator.next(); }, "iterator is string");
|
||||
|
||||
iterator = Iterator.concat(MakeIterable(Symbol()));
|
||||
assert.throws(TypeError, function() { iterator.next(); }, "iterator is symbol");
|
28
test/built-ins/Iterator/concat/zero-arguments.js
Normal file
28
test/built-ins/Iterator/concat/zero-arguments.js
Normal file
@ -0,0 +1,28 @@
|
||||
// Copyright (C) 2024 André Bargull. All rights reserved.
|
||||
// This code is governed by the BSD license found in the LICENSE file.
|
||||
|
||||
/*---
|
||||
esid: sec-iterator.concat
|
||||
description: >
|
||||
Iterator.concat when called with zero arguments.
|
||||
info: |
|
||||
Iterator.concat ( ...items )
|
||||
|
||||
1. Let iterables be a new empty List.
|
||||
2. For each element item of items, do
|
||||
...
|
||||
3. Let closure be a new Abstract Closure with no parameters that captures iterables and performs the following steps when called:
|
||||
a. For each Record iterable of iterables, do
|
||||
...
|
||||
b. Return ReturnCompletion(undefined).
|
||||
...
|
||||
6. Return gen.
|
||||
features: [iterator-sequencing]
|
||||
---*/
|
||||
|
||||
let iterator = Iterator.concat();
|
||||
|
||||
let iterResult = iterator.next();
|
||||
|
||||
assert.sameValue(iterResult.done, true);
|
||||
assert.sameValue(iterResult.value, undefined);
|
Loading…
x
Reference in New Issue
Block a user