@@ -28,6 +28,7 @@ const {
28
28
NumberParseInt,
29
29
ObjectDefineProperties,
30
30
ObjectSetPrototypeOf,
31
+ Promise,
31
32
Set,
32
33
SymbolAsyncIterator,
33
34
Symbol
@@ -60,11 +61,11 @@ const kPaused = Symbol('kPaused');
60
61
61
62
// Lazy loaded to improve the startup performance.
62
63
let StringDecoder ;
63
- let createReadableStreamAsyncIterator ;
64
64
let from ;
65
65
66
66
ObjectSetPrototypeOf ( Readable . prototype , Stream . prototype ) ;
67
67
ObjectSetPrototypeOf ( Readable , Stream ) ;
68
+ function nop ( ) { }
68
69
69
70
const { errorOrDestroy } = destroyImpl ;
70
71
@@ -1076,13 +1077,86 @@ Readable.prototype.wrap = function(stream) {
1076
1077
} ;
1077
1078
1078
1079
Readable . prototype [ SymbolAsyncIterator ] = function ( ) {
1079
- if ( createReadableStreamAsyncIterator === undefined ) {
1080
- createReadableStreamAsyncIterator =
1081
- require ( 'internal/streams/async_iterator' ) ;
1080
+ let stream = this ;
1081
+
1082
+ if ( typeof stream . read !== 'function' ) {
1083
+ // v1 stream
1084
+ const src = stream ;
1085
+ stream = new Readable ( {
1086
+ objectMode : true ,
1087
+ destroy ( err , callback ) {
1088
+ destroyImpl . destroyer ( src , err ) ;
1089
+ callback ( err ) ;
1090
+ }
1091
+ } ) . wrap ( src ) ;
1082
1092
}
1083
- return createReadableStreamAsyncIterator ( this ) ;
1093
+
1094
+ const iter = createAsyncIterator ( stream ) ;
1095
+ iter . stream = stream ;
1096
+ return iter ;
1084
1097
} ;
1085
1098
1099
+ async function * createAsyncIterator ( stream ) {
1100
+ let callback = nop ;
1101
+
1102
+ function next ( resolve ) {
1103
+ if ( this === stream ) {
1104
+ callback ( ) ;
1105
+ callback = nop ;
1106
+ } else {
1107
+ callback = resolve ;
1108
+ }
1109
+ }
1110
+
1111
+ const state = stream . _readableState ;
1112
+
1113
+ let error = state . errored ;
1114
+ let errorEmitted = state . errorEmitted ;
1115
+ let endEmitted = state . endEmitted ;
1116
+ let closeEmitted = state . closeEmitted ;
1117
+
1118
+ stream
1119
+ . on ( 'readable' , next )
1120
+ . on ( 'error' , function ( err ) {
1121
+ error = err ;
1122
+ errorEmitted = true ;
1123
+ next . call ( this ) ;
1124
+ } )
1125
+ . on ( 'end' , function ( ) {
1126
+ endEmitted = true ;
1127
+ next . call ( this ) ;
1128
+ } )
1129
+ . on ( 'close' , function ( ) {
1130
+ closeEmitted = true ;
1131
+ next . call ( this ) ;
1132
+ } ) ;
1133
+
1134
+ try {
1135
+ while ( true ) {
1136
+ const chunk = stream . destroyed ? null : stream . read ( ) ;
1137
+ if ( chunk !== null ) {
1138
+ yield chunk ;
1139
+ } else if ( errorEmitted ) {
1140
+ throw error ;
1141
+ } else if ( endEmitted ) {
1142
+ break ;
1143
+ } else if ( closeEmitted ) {
1144
+ break ;
1145
+ } else {
1146
+ await new Promise ( next ) ;
1147
+ }
1148
+ }
1149
+ } catch ( err ) {
1150
+ destroyImpl . destroyer ( stream , err ) ;
1151
+ throw err ;
1152
+ } finally {
1153
+ if ( state . autoDestroy || ! endEmitted ) {
1154
+ // TODO(ronag): ERR_PREMATURE_CLOSE?
1155
+ destroyImpl . destroyer ( stream , null ) ;
1156
+ }
1157
+ }
1158
+ }
1159
+
1086
1160
// Making it explicit these properties are not enumerable
1087
1161
// because otherwise some prototype manipulation in
1088
1162
// userland will fail.
0 commit comments