Skip to content

Commit 4e8df7c

Browse files
jasnelladuh95
authored andcommitted
stream: correct strict pending-write behavior & cancellation
Signed-off-by: James M Snell <jasnell@gmail.com> Assisted-by: Opencode PR-URL: #66079 Reviewed-By: Trivikram Kamat <trivikr.dev@gmail.com>
1 parent b44b865 commit 4e8df7c

5 files changed

Lines changed: 784 additions & 200 deletions

File tree

‎doc/api/stream_iter.md‎

Lines changed: 18 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -1531,8 +1531,9 @@ added: v26.1.0
15311531

15321532
> Stability: 1 - Experimental
15331533
1534-
* `readable` {stream.Readable|Object} A classic Readable stream or any object
1535-
with `read()`, `on()`, and `off()` methods.
1534+
* `readable` {stream.Readable|Object} A classic Readable stream or a compatible
1535+
object with `read()`, `pipe()`, `destroy()`, `on()`, and `removeListener()`
1536+
methods.
15361537
* Returns: {AsyncIterable} whose chunks fulfill with {Uint8Array\[]}
15371538

15381539
Converts a classic Readable stream (or duck-typed equivalent) into a
@@ -1541,8 +1542,8 @@ stream/iter async iterable source that can be passed to [`from()`][],
15411542

15421543
If the object implements the [`toAsyncStreamable`][] protocol (as
15431544
`stream.Readable` does), that protocol is used. Otherwise, the function
1544-
duck-types on `read()`, `on()`, and `off()` (EventEmitter) and wraps the
1545-
stream with a batched async iterator.
1545+
duck-types on `read()`, `pipe()`, `destroy()`, `on()`, and `removeListener()`
1546+
(EventEmitter) and wraps the stream with a batched async iterator.
15461547

15471548
The result is cached per instance -- calling `fromReadable()` twice with the
15481549
same stream returns the same iterable.
@@ -1585,13 +1586,14 @@ added: v26.1.0
15851586

15861587
> Stability: 1 - Experimental
15871588
1588-
* `writable` {stream.Writable|Object} A classic Writable stream or any object
1589-
with `write()` and `on()` methods.
1589+
* `writable` {stream.Writable|Object} A classic Writable stream or a compatible
1590+
object with `write()`, `end()`, `destroy()`, `on()`, and `removeListener()`
1591+
methods.
15901592
* `options` {Object}
15911593
* `backpressure` {string} Backpressure policy. **Default:** `'strict'`.
1592-
* `'strict'` -- writes are rejected when the buffer is full. Catches
1593-
callers that ignore backpressure.
1594-
* `'unbounded'` -- writes wait for drain when the buffer is full. Recommended
1594+
* `'strict'` -- one write may wait while the buffer is full. Further writes
1595+
are rejected until it is accepted or canceled.
1596+
* `'unbounded'` -- writes are queued while the buffer is full. Recommended
15951597
for use with [`pipeTo()`][].
15961598
* `'drop-newest'` -- writes are silently discarded when the buffer is full.
15971599
* `'drop-oldest'` -- **not supported**. Throws `ERR_INVALID_ARG_VALUE`.
@@ -1603,8 +1605,9 @@ destination.
16031605

16041606
Since all writes on a classic Writable are fundamentally asynchronous,
16051607
the synchronous Writer methods (`writeSync`, `writevSync`, `endSync`) always
1606-
return `false` or `-1`, deferring to the async path. The per-write
1607-
`options.signal` parameter from the Writer interface is also ignored.
1608+
return `false` or `-1`, deferring to the async path. A queued `write()` or
1609+
`writev()` can be canceled with its `options.signal` before it reaches the
1610+
classic Writable.
16081611

16091612
If `writer.fail(reason)` receives a non-Error reason, the classic Writable is
16101613
destroyed with an `ERR_FALSY_VALUE_REJECTION` or `ERR_OPERATION_FAILED` error.
@@ -1757,6 +1760,10 @@ non-Error reason is wrapped in an `ERR_FALSY_VALUE_REJECTION` or
17571760
`ERR_OPERATION_FAILED` error before it is passed to the callback. The error's
17581761
`reason` property contains the original value.
17591762

1763+
Destroying the Writable before successful completion calls `writer.fail()`.
1764+
If `fail()` is unavailable, `Symbol.dispose` or `Symbol.asyncDispose` is used
1765+
when implemented by the Writer.
1766+
17601767
The Writable uses the default classic stream `highWaterMark`. Classic stream
17611768
backpressure bounds writes waiting to reach the underlying Writer, while the
17621769
Writer controls completion of the active `_write()` or `_writev()` operation.

0 commit comments

Comments
 (0)