@@ -184,6 +184,83 @@ public function testRemoveStreamForWriteOnly()
184
184
$ this ->tickLoop ($ this ->loop );
185
185
}
186
186
187
+ public function testRemoveReadAndWriteStreamFromLoopOnceResourceClosesEndsLoop ()
188
+ {
189
+ list ($ stream , $ other ) = $ this ->createSocketPair ();
190
+ stream_set_blocking ($ stream , false );
191
+ stream_set_blocking ($ other , false );
192
+
193
+ // dummy writable handler
194
+ $ this ->loop ->addWriteStream ($ stream , function () { });
195
+
196
+ // remove stream when the stream is readable (closes)
197
+ $ this ->loop ->addReadStream ($ stream , function ($ stream ) {
198
+ $ this ->loop ->removeReadStream ($ stream );
199
+ $ this ->loop ->removeWriteStream ($ stream );
200
+ fclose ($ stream );
201
+ });
202
+
203
+ // close other side
204
+ fclose ($ other );
205
+
206
+ $ this ->assertRunFasterThan ($ this ->tickTimeout );
207
+ }
208
+
209
+ public function testRemoveReadAndWriteStreamFromLoopOnceResourceClosesOnEndOfFileEndsLoop ()
210
+ {
211
+ list ($ stream , $ other ) = $ this ->createSocketPair ();
212
+ stream_set_blocking ($ stream , false );
213
+ stream_set_blocking ($ other , false );
214
+
215
+ // dummy writable handler to fill outgoing buffer
216
+ fwrite ($ stream , str_repeat ('. ' , 60000 ));
217
+ $ this ->loop ->addWriteStream ($ stream , function ($ stream ) use ($ other ) {
218
+ fwrite ($ stream , '. ' );
219
+
220
+ // close other side once outgoing buffer is filled
221
+ fclose ($ other );
222
+ });
223
+
224
+ // remove stream when the stream is readable (closes)
225
+ $ never = $ this ->expectCallableNever ();
226
+ $ this ->loop ->addReadStream ($ stream , function ($ stream ) use ($ never ) {
227
+ $ data = fread ($ stream , 1024 );
228
+ if ($ data !== '' ) {
229
+ // we expect to read an empty string => stream closed
230
+ return $ never ();
231
+ }
232
+
233
+ $ this ->loop ->removeReadStream ($ stream );
234
+ $ this ->loop ->removeWriteStream ($ stream );
235
+ fclose ($ stream );
236
+ });
237
+
238
+ $ this ->loop ->addTimer (0.01 , function () use ($ other ) {
239
+ fclose ($ other );
240
+ });
241
+
242
+ $ this ->assertRunFasterThan (0.1 );
243
+ }
244
+
245
+ public function testRemoveReadAndWriteStreamFromLoopWithClosingResourceEndsLoop ()
246
+ {
247
+ // get only one part of the pair to ensure the other side will close immediately
248
+ list ($ stream ) = $ this ->createSocketPair ();
249
+ stream_set_blocking ($ stream , false );
250
+
251
+ // dummy writable handler
252
+ $ this ->loop ->addWriteStream ($ stream , function () { });
253
+
254
+ // remove stream when the stream is readable (closes)
255
+ $ this ->loop ->addReadStream ($ stream , function ($ stream ) {
256
+ $ this ->loop ->removeReadStream ($ stream );
257
+ $ this ->loop ->removeWriteStream ($ stream );
258
+ fclose ($ stream );
259
+ });
260
+
261
+ $ this ->assertRunFasterThan ($ this ->tickTimeout );
262
+ }
263
+
187
264
public function testRemoveInvalid ()
188
265
{
189
266
list ($ stream ) = $ this ->createSocketPair ();
0 commit comments