This repository was archived by the owner on Jan 26, 2022. It is now read-only.
-
Notifications
You must be signed in to change notification settings - Fork 37
/
Copy pathiteration.html
262 lines (241 loc) · 16.6 KB
/
iteration.html
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
<emu-clause id="sec-common-iteration-interfaces">
<h1>Common Iteration Interfaces</h1>
<emu-clause id="sec-asynciterable-interface">
<h1><ins>The <i>AsyncIterable</i> Interface</ins></h1>
<p>The <i>AsyncIterable</i> interface includes the properties described in <emu-xref href="#table-async-iterable"></emu-xref>:</p>
<emu-table id="table-async-iterable" caption="<i>AsyncIterable</i> Interface Required Properties">
<table>
<tbody>
<tr>
<th>Property</th>
<th>Value</th>
<th>Requirements</th>
</tr>
<tr>
<td>`@@asyncIterator`</td>
<td>A function that returns an <i>AsyncIterator</i> object.</td>
<td>The returned object must conform to the <i>AsyncIterator</i> interface.</td>
</tr>
</tbody>
</table>
</emu-table>
</emu-clause>
<emu-clause id="sec-asynciterator-interface">
<h1><ins>The <i>AsyncIterator</i> Interface</ins></h1>
<p>An object that implements the <i>AsyncIterator</i> interface must include the properties in <emu-xref href="#table-async-iterator-required"></emu-xref>. Such objects may also implement the properties in <emu-xref href="#table-async-iterator-optional"></emu-xref>.</p>
<emu-table id="table-async-iterator-required" caption="<i>AsyncIterator</i> Interface Required Properties">
<table>
<tbody>
<tr>
<th>Property</th>
<th>Value</th>
<th>Requirements</th>
</tr>
<tr>
<td>`next`</td>
<td>A function that returns a promise for an <i>IteratorResult</i> object.</td>
<td>
<p>The returned promise, when fulfilled, must fulfill with an object which conforms to the <i>IteratorResult</i> interface. If a previous call to the `next` method of an <i>AsyncIterator</i> has returned a promise for an <i>IteratorResult</i> object whose `done` property is *true*, then all subsequent calls to the `next` method of that object should also return a promise for an <i>IteratorResult</i> object whose `done` property is *true*. However, this requirement is not enforced.</p>
<p>Additionally, the <i>IteratorResult</i> object that serves as a fulfillment value should have a `value` property whose value is not a promise (or "thenable"). However, this requirement is also not enforced.</p>
</td>
</tr>
</tbody>
</table>
</emu-table>
<emu-note>
<p>Arguments may be passed to the next function but their interpretation and validity is dependent upon the target <i>AsyncIterator</i>. The `for`-`await`-`of` statement and other common users of <em>AsyncIterators</em> do not pass any arguments, so <i>AsyncIterator</i> objects that expect to be used in such a manner must be prepared to deal with being called with no arguments.</p>
</emu-note>
<emu-table id="table-async-iterator-optional" caption="<i>AsyncIterator</i> Interface Optional Properties">
<table>
<tbody>
<tr>
<th>Property</th>
<th>Value</th>
<th>Requirements</th>
</tr>
<tr>
<td>`return`</td>
<td>A function that returns a promise for an <i>IteratorResult</i> object.</td>
<td>
<p>The returned promise, when fulfilled, must fulfill with an object which conforms to the <i>IteratorResult</i> interface. Invoking this method notifies the <i>AsyncIterator</i> object that the caller does not intend to make any more `next` method calls to the <i>AsyncIterator</i>. The returned promise will fulfill with an <i>IteratorResult</i> object which will typically have a `done` property whose value is *true*, and a `value` property with the value passed as the argument of the `return` method. However, this requirement is not enforced.</p>
<p>Additionally, the <i>IteratorResult</i> object that serves as a fulfillment value should have a `value` property whose value is not a promise (or "thenable"). If the argument value is used in the typical manner, then if it is a rejected promise, a promise rejected with the same reason should be returned; if it is a fulfilled promise, then its fulfillment value should be used as the `value` property of the returned promise's <i>IteratorResult</i> object fulfillment value. However, these requirements are also not enforced.</p>
</td>
</tr>
<tr>
<td>`throw`</td>
<td>A function that returns a promise for an <i>IteratorResult</i> object.</td>
<td>
<p>The returned promise, when fulfilled, must fulfill with an object which conforms to the <i>IteratorResult</i> interface. Invoking this method notifies the <i>AsyncIterator</i> object that the caller has detected an error condition. The argument may be used to identify the error condition and typically will be an exception object. A typical response is to return a rejected promise which rejects with the value passed as the argument.</p>
<p>If the returned promise is fulfilled, the <i>IteratorResult</i> fulfillment value will typically have a `done` property whose value is *true*. Additionally, it should have a `value` property whose value is not a promise (or "thenable"), but this requirement is not enforced.</p>
</td>
</tr>
</tbody>
</table>
</emu-table>
<emu-note>
<p>Typically callers of these methods should check for their existence before invoking them. Certain ECMAScript language features including `for`-`await`-`of` and `yield*` call these methods after performing an existence check.</p>
</emu-note>
</emu-clause>
</emu-clause>
<emu-clause id="sec-asynciteratorprototype">
<h1><ins>The %AsyncIteratorPrototype% Object</ins></h1>
<p>The value of the [[Prototype]] internal slot of the <dfn>%AsyncIteratorPrototype%</dfn> object is the intrinsic object %ObjectPrototype%. The %AsyncIteratorPrototype% object is an ordinary object. The initial value of the [[Extensible]] internal slot of the %AsyncIteratorPrototype% object is *true*.</p>
<emu-note>
<p>All objects defined in this specification that implement the AsyncIterator interface also inherit from %AsyncIteratorPrototype%. ECMAScript code may also define objects that inherit from %AsyncIteratorPrototype%.The %AsyncIteratorPrototype% object provides a place where additional methods that are applicable to all async iterator objects may be added.</p>
</emu-note>
<emu-clause id="sec-asynciteratorprototype-asynciterator">
<h1>%AsyncIteratorPrototype% [ @@asyncIterator ] ( )</h1>
<p>The following steps are taken:</p>
<emu-alg>
1. Return the *this* value.
</emu-alg>
<p>The value of the `name` property of this function is `"[Symbol.asyncIterator]"`.</p>
</emu-clause>
</emu-clause>
<emu-clause id="sec-async-from-sync-iterator-objects">
<h1><ins>Async-from-Sync Iterator Objects</ins></h1>
<p>An Async-from-Sync Iterator object is an async iterator that adapts a specific synchronous iterator. There is not a named constructor for Async-from-Sync Iterator objects. Instead, Async-from-Sync iterator objects are created by the CreateAsyncFromSyncIterator abstract operation as needed.</p>
<emu-clause id="sec-createasyncfromsynciterator" aoid="CreateAsyncFromSyncIterator">
<h1>CreateAsyncFromSyncIterator(_syncIteratorRecord_) Abstract Operation</h1>
<p>The abstract operation CreateAsyncFromSyncIterator is used to create an async iterator Record from a synchronous iterator Record. It performs the following steps:</p>
<emu-alg>
1. Let _asyncIterator_ be ! ObjectCreate(%AsyncFromSyncIteratorPrototype%, « [[SyncIteratorRecord]] »).
1. Set _asyncIterator_.[[SyncIteratorRecord]] to _syncIteratorRecord_.
1. Return ? GetIterator(_asyncIterator_, ~async~).
</emu-alg>
</emu-clause>
<emu-clause id="sec-%asyncfromsynciteratorprototype%-object">
<h1>The %AsyncFromSyncIteratorPrototype% Object</h1>
<p>All Async-from-Sync Iterator Objects inherit properties from the <dfn>%AsyncFromSyncIteratorPrototype%</dfn> intrinsic object. The %AsyncFromSyncIteratorPrototype% object is an ordinary object and its [[Prototype]] internal slot is the %AsyncIteratorPrototype% intrinsic object. In addition, %AsyncFromSyncIteratorPrototype% has the following properties:</p>
<emu-clause id="sec-%asyncfromsynciteratorprototype%.next">
<h1>%AsyncFromSyncIteratorPrototype%.next ( _value_ )</h1>
<emu-alg>
1. Let _O_ be the *this* value.
1. Let _promiseCapability_ be ! NewPromiseCapability(%Promise%).
1. If Type(_O_) is not Object, or if _O_ does not have a [[SyncIteratorRecord]] internal slot, then
1. Let _badIteratorError_ be a new *TypeError* exception.
1. Perform ! Call(_promiseCapability_.[[Reject]], *undefined*, « _badIteratorError_ »).
1. Return _promiseCapability_.[[Promise]].
1. Let _syncIteratorRecord_ be _O_.[[SyncIteratorRecord]].
1. Let _nextResult_ be IteratorNext(_syncIteratorRecord_, _value_).
1. IfAbruptRejectPromise(_nextResult_, _promiseCapability_).
1. Let _nextDone_ be IteratorComplete(_nextResult_).
1. IfAbruptRejectPromise(_nextDone_, _promiseCapability_).
1. Let _nextValue_ be IteratorValue(_nextResult_).
1. IfAbruptRejectPromise(_nextValue_, _promiseCapability_).
1. Let _valueWrapperCapability_ be ! NewPromiseCapability(%Promise%).
1. Perform ! Call(_valueWrapperCapability_.[[Resolve]], *undefined*, « _nextValue_ »).
1. Let _onFulfilled_ be a new built-in function object as defined in <emu-xref href="#sec-async-from-sync-iterator-value-unwrap-functions" title></emu-xref>.
1. Set _onFulfilled_.[[Done]] to _nextDone_.
1. Perform ! PerformPromiseThen(_valueWrapperCapability_.[[Promise]], _onFulfilled_, *undefined*, _promiseCapability_).
1. Return _promiseCapability_.[[Promise]].
</emu-alg>
</emu-clause>
<emu-clause id="sec-%asyncfromsynciteratorprototype%.return">
<h1>%AsyncFromSyncIteratorPrototype%.return ( _value_ )</h1>
<emu-alg>
1. Let _O_ be the *this* value.
1. Let _promiseCapability_ be ! NewPromiseCapability(%Promise%).
1. If Type(_O_) is not Object, or if _O_ does not have a [[SyncIteratorRecord]] internal slot, then
1. Let _badIteratorError_ be a new *TypeError* exception.
1. Perform ! Call(_promiseCapability_.[[Reject]], *undefined*, « _badIteratorError_ »).
1. Return _promiseCapability_.[[Promise]].
1. Let _syncIterator_ be _O_.[[SyncIteratorRecord]].[[Iterator]].
1. Let _return_ be GetMethod(_syncIterator_, `"return"`).
1. IfAbruptRejectPromise(_return_, _promiseCapability_).
1. If _return_ is *undefined*, then
1. Let _iterResult_ be ! CreateIterResultObject(_value_, *true*).
1. Perform ! Call(_promiseCapability_.[[Resolve]], *undefined*, « _iterResult_ »).
1. Return _promiseCapability_.[[Promise]].
1. Let _returnResult_ be Call(_return_, _syncIterator_, « _value_ »).
1. IfAbruptRejectPromise(_returnResult_, _promiseCapability_).
1. If Type(_returnResult_) is not *Object*,
1. Perform ! Call(_promiseCapability_.[[Reject]], *undefined*, « a *TypeError* exception »).
1. Return _promiseCapability_.[[Promise]].
1. Let _returnDone_ be IteratorComplete(_returnResult_).
1. IfAbruptRejectPromise(_returnDone_, _promiseCapability_).
1. Let _returnValue_ be IteratorValue(_returnResult_).
1. IfAbruptRejectPromise(_returnValue_, _promiseCapability_).
1. Let _valueWrapperCapability_ be ! NewPromiseCapability(%Promise%).
1. Perform ! Call(_valueWrapperCapability_.[[Resolve]], *undefined*, « _returnValue_ »).
1. Let _onFulfilled_ be a new built-in function object as defined in <emu-xref href="#sec-async-from-sync-iterator-value-unwrap-functions" title></emu-xref>.
1. Set _onFulfilled_.[[Done]] to _returnDone_.
1. Perform ! PerformPromiseThen(_valueWrapperCapability_.[[Promise]], _onFulfilled_, *undefined*, _promiseCapability_).
1. Return _promiseCapability_.[[Promise]].
</emu-alg>
</emu-clause>
<emu-clause id="sec-%asyncfromsynciteratorprototype%.throw">
<h1>%AsyncFromSyncIteratorPrototype%.throw ( _value_ )</h1>
<emu-alg>
1. Let _O_ be the *this* value.
1. Let _promiseCapability_ be ! NewPromiseCapability(%Promise%).
1. If Type(_O_) is not Object, or if _O_ does not have a [[SyncIteratorRecord]] internal slot, then
1. Let _badIteratorError_ be a new *TypeError* exception.
1. Perform ! Call(_promiseCapability_.[[Reject]], *undefined*, « _badIteratorError_ »).
1. Return _promiseCapability_.[[Promise]].
1. Let _syncIterator_ be _O_.[[SyncIteratorRecord]].[[Iterator]].
1. Let _throw_ be GetMethod(_syncIterator_, `"throw"`).
1. IfAbruptRejectPromise(_throw_, _promiseCapability_).
1. If _throw_ is *undefined*, then
1. Perform ! Call(_promiseCapability_.[[Reject]], *undefined*, « _value_ »).
1. Return _promiseCapability_.[[Promise]].
1. Let _throwResult_ be Call(_throw_, _syncIterator_, « _value_ »).
1. IfAbruptRejectPromise(_throwResult_, _promiseCapability_).
1. If Type(_throwResult_) is not *Object*,
1. Perform ! Call(_promiseCapability_.[[Reject]], *undefined*, « a *TypeError* exception »).
1. Return _promiseCapability_.[[Promise]].
1. Let _throwDone_ be IteratorComplete(_throwResult_).
1. IfAbruptRejectPromise(_throwDone_, _promiseCapability_).
1. Let _throwValue_ be IteratorValue(_throwResult_).
1. IfAbruptRejectPromise(_throwValue_, _promiseCapability_).
1. Let _valueWrapperCapability_ be ! NewPromiseCapability(%Promise%).
1. Perform ! Call(_valueWrapperCapability_.[[Resolve]], *undefined*, « _throwValue_ »).
1. Let _onFulfilled_ be a new built-in function object as defined in <emu-xref href="#sec-async-from-sync-iterator-value-unwrap-functions" title></emu-xref>.
1. Set _onFulfilled_.[[Done]] to _throwDone_.
1. Perform ! PerformPromiseThen(_valueWrapperCapability_.[[Promise]], _onFulfilled_, *undefined*, _promiseCapability_).
1. Return _promiseCapability_.[[Promise]].
</emu-alg>
</emu-clause>
<emu-clause id="sec-%asyncfromsynciteratorprototype%-@@tostringtag">
<h1>%AsyncFromSyncIteratorPrototype% [ @@toStringTag ]</h1>
<p>The initial value of the @@toStringTag property is the String value `"Async-from-Sync Iterator"`.</p>
<p>This property has the attributes { [[Writable]]: *false*, [[Enumerable]]: *false*, [[Configurable]]: *true* }.</p>
</emu-clause>
<emu-clause id="sec-async-from-sync-iterator-value-unwrap-functions">
<h1>Async-from-Sync Iterator Value Unwrap Functions</h1>
<p>An async-from-sync iterator value unwrap function is an anonymous built-in function that is used by methods of %AsyncFromSyncIteratorPrototype% when processing the `value` field of an <i>IteratorResult</i> object, in order to wait for its value if it is a promise and re-package the result in a new "unwrapped" <i>IteratorResult</i> object. Each async iterator value unwrap function has a [[Done]] internal slot.</p>
<p>When an async-from-sync iterator value unwrap function _F_ is called with argument _value_, the following steps are taken:</p>
<emu-alg>
1. Return ! CreateIterResultObject(_value_, _F_.[[Done]]).
</emu-alg>
</emu-clause>
</emu-clause>
<emu-clause id="sec-properties-of-async-from-sync-iterator-instances">
<h1>Properties of Async-from-Sync Iterator Instances</h1>
<p>Async-from-Sync Iterator instances are ordinary objects that inherit properties from the %AsyncFromSyncIteratorPrototype% intrinsic object. Async-from-Sync Iterator instances are initially created with the internal slots listed in <emu-xref href="#table-async-from-sync-iterator-internal-slots"></emu-xref>.</p>
<emu-table id="table-async-from-sync-iterator-internal-slots" caption="Internal Slots of Async-from-Sync Iterator Instances">
<table>
<thead>
<tr>
<th>
Internal Slot
</th>
<th>
Description
</th>
</tr>
</thead>
<tbody>
<tr>
<td>
[[SyncIteratorRecord]]
</td>
<td>
A Record, of the type returned by GetIterator, representing the original synchronous iterator which is being adapted.
</td>
</tr>
</tbody>
</table>
</emu-table>
</emu-clause>
</emu-clause>