22
33namespace React \Tests \EventLoop ;
44
5+ use React \EventLoop \StreamSelectLoop ;
6+ use React \EventLoop \ExtUvLoop ;
7+
58abstract class AbstractLoopTest extends TestCase
69{
710 /**
@@ -36,8 +39,116 @@ public function createSocketPair()
3639 return $ sockets ;
3740 }
3841
42+ public function testAddReadStreamTriggersWhenSocketReceivesData ()
43+ {
44+ list ($ input , $ output ) = $ this ->createSocketPair ();
45+
46+ $ loop = $ this ->loop ;
47+ $ timeout = $ loop ->addTimer (0.1 , function () use ($ input , $ loop ) {
48+ $ loop ->removeReadStream ($ input );
49+ });
50+
51+ $ called = 0 ;
52+ $ this ->loop ->addReadStream ($ input , function () use (&$ called , $ loop , $ input , $ timeout ) {
53+ ++$ called ;
54+ $ loop ->removeReadStream ($ input );
55+ $ loop ->cancelTimer ($ timeout );
56+ });
57+
58+ fwrite ($ output , "foo \n" );
59+
60+ $ this ->loop ->run ();
61+
62+ $ this ->assertEquals (1 , $ called );
63+ }
64+
65+ public function testAddReadStreamTriggersWhenSocketCloses ()
66+ {
67+ list ($ input , $ output ) = $ this ->createSocketPair ();
68+
69+ $ loop = $ this ->loop ;
70+ $ timeout = $ loop ->addTimer (0.1 , function () use ($ input , $ loop ) {
71+ $ loop ->removeReadStream ($ input );
72+ });
73+
74+ $ called = 0 ;
75+ $ this ->loop ->addReadStream ($ input , function () use (&$ called , $ loop , $ input , $ timeout ) {
76+ ++$ called ;
77+ $ loop ->removeReadStream ($ input );
78+ $ loop ->cancelTimer ($ timeout );
79+ });
80+
81+ fclose ($ output );
82+
83+ $ this ->loop ->run ();
84+
85+ $ this ->assertEquals (1 , $ called );
86+ }
87+
88+ public function testAddWriteStreamTriggersWhenSocketConnectionSucceeds ()
89+ {
90+ $ server = stream_socket_server ('127.0.0.1:0 ' );
91+
92+ $ errno = $ errstr = null ;
93+ $ connecting = stream_socket_client (stream_socket_get_name ($ server , false ), $ errno , $ errstr , 0 , STREAM_CLIENT_CONNECT | STREAM_CLIENT_ASYNC_CONNECT );
94+
95+ $ loop = $ this ->loop ;
96+ $ timeout = $ loop ->addTimer (0.1 , function () use ($ connecting , $ loop ) {
97+ $ loop ->removeWriteStream ($ connecting );
98+ });
99+
100+ $ called = 0 ;
101+ $ this ->loop ->addWriteStream ($ connecting , function () use (&$ called , $ loop , $ connecting , $ timeout ) {
102+ ++$ called ;
103+ $ loop ->removeWriteStream ($ connecting );
104+ $ loop ->cancelTimer ($ timeout );
105+ });
106+
107+ $ this ->loop ->run ();
108+
109+ $ this ->assertEquals (1 , $ called );
110+ }
111+
112+ public function testAddWriteStreamTriggersWhenSocketConnectionRefused ()
113+ {
114+ // @link https://github.com/reactphp/event-loop/issues/206
115+ if ($ this ->loop instanceof StreamSelectLoop && DIRECTORY_SEPARATOR === '\\' ) {
116+ $ this ->markTestIncomplete ('StreamSelectLoop does not currently support detecting connection refused errors on Windows ' );
117+ }
118+
119+ // first verify the operating system actually refuses the connection and no firewall is in place
120+ // use higher timeout because Windows retires multiple times and has a noticeable delay
121+ // @link https://stackoverflow.com/questions/19440364/why-do-failed-attempts-of-socket-connect-take-1-sec-on-windows
122+ $ errno = $ errstr = null ;
123+ if (@stream_socket_client ('127.0.0.1:1 ' , $ errno , $ errstr , 10.0 ) !== false || $ errno !== SOCKET_ECONNREFUSED ) {
124+ $ this ->markTestSkipped ('Expected host to refuse connection, but got error ' . $ errno . ': ' . $ errstr );
125+ }
126+
127+ $ connecting = stream_socket_client ('127.0.0.1:1 ' , $ errno , $ errstr , 0 , STREAM_CLIENT_CONNECT | STREAM_CLIENT_ASYNC_CONNECT );
128+
129+ $ loop = $ this ->loop ;
130+ $ timeout = $ loop ->addTimer (10.0 , function () use ($ connecting , $ loop ) {
131+ $ loop ->removeWriteStream ($ connecting );
132+ });
133+
134+ $ called = 0 ;
135+ $ this ->loop ->addWriteStream ($ connecting , function () use (&$ called , $ loop , $ connecting , $ timeout ) {
136+ ++$ called ;
137+ $ loop ->removeWriteStream ($ connecting );
138+ $ loop ->cancelTimer ($ timeout );
139+ });
140+
141+ $ this ->loop ->run ();
142+
143+ $ this ->assertEquals (1 , $ called );
144+ }
145+
39146 public function testAddReadStream ()
40147 {
148+ if ($ this ->loop instanceof ExtUvLoop && DIRECTORY_SEPARATOR === '\\' ) {
149+ $ this ->markTestIncomplete ('Ticking ExtUvLoop not supported on Windows ' );
150+ }
151+
41152 list ($ input , $ output ) = $ this ->createSocketPair ();
42153
43154 $ this ->loop ->addReadStream ($ input , $ this ->expectCallableExactly (2 ));
@@ -51,6 +162,10 @@ public function testAddReadStream()
51162
52163 public function testAddReadStreamIgnoresSecondCallable ()
53164 {
165+ if ($ this ->loop instanceof ExtUvLoop && DIRECTORY_SEPARATOR === '\\' ) {
166+ $ this ->markTestIncomplete ('Ticking ExtUvLoop not supported on Windows ' );
167+ }
168+
54169 list ($ input , $ output ) = $ this ->createSocketPair ();
55170
56171 $ this ->loop ->addReadStream ($ input , $ this ->expectCallableExactly (2 ));
@@ -100,6 +215,10 @@ private function subAddReadStreamReceivesDataFromStreamReference()
100215
101216 public function testAddWriteStream ()
102217 {
218+ if ($ this ->loop instanceof ExtUvLoop && DIRECTORY_SEPARATOR === '\\' ) {
219+ $ this ->markTestIncomplete ('Ticking ExtUvLoop not supported on Windows ' );
220+ }
221+
103222 list ($ input ) = $ this ->createSocketPair ();
104223
105224 $ this ->loop ->addWriteStream ($ input , $ this ->expectCallableExactly (2 ));
@@ -109,6 +228,10 @@ public function testAddWriteStream()
109228
110229 public function testAddWriteStreamIgnoresSecondCallable ()
111230 {
231+ if ($ this ->loop instanceof ExtUvLoop && DIRECTORY_SEPARATOR === '\\' ) {
232+ $ this ->markTestIncomplete ('Ticking ExtUvLoop not supported on Windows ' );
233+ }
234+
112235 list ($ input ) = $ this ->createSocketPair ();
113236
114237 $ this ->loop ->addWriteStream ($ input , $ this ->expectCallableExactly (2 ));
@@ -119,6 +242,10 @@ public function testAddWriteStreamIgnoresSecondCallable()
119242
120243 public function testRemoveReadStreamInstantly ()
121244 {
245+ if ($ this ->loop instanceof ExtUvLoop && DIRECTORY_SEPARATOR === '\\' ) {
246+ $ this ->markTestIncomplete ('Ticking ExtUvLoop not supported on Windows ' );
247+ }
248+
122249 list ($ input , $ output ) = $ this ->createSocketPair ();
123250
124251 $ this ->loop ->addReadStream ($ input , $ this ->expectCallableNever ());
@@ -130,6 +257,10 @@ public function testRemoveReadStreamInstantly()
130257
131258 public function testRemoveReadStreamAfterReading ()
132259 {
260+ if ($ this ->loop instanceof ExtUvLoop && DIRECTORY_SEPARATOR === '\\' ) {
261+ $ this ->markTestIncomplete ('Ticking ExtUvLoop not supported on Windows ' );
262+ }
263+
133264 list ($ input , $ output ) = $ this ->createSocketPair ();
134265
135266 $ this ->loop ->addReadStream ($ input , $ this ->expectCallableOnce ());
@@ -145,6 +276,10 @@ public function testRemoveReadStreamAfterReading()
145276
146277 public function testRemoveWriteStreamInstantly ()
147278 {
279+ if ($ this ->loop instanceof ExtUvLoop && DIRECTORY_SEPARATOR === '\\' ) {
280+ $ this ->markTestIncomplete ('Ticking ExtUvLoop not supported on Windows ' );
281+ }
282+
148283 list ($ input ) = $ this ->createSocketPair ();
149284
150285 $ this ->loop ->addWriteStream ($ input , $ this ->expectCallableNever ());
@@ -154,6 +289,10 @@ public function testRemoveWriteStreamInstantly()
154289
155290 public function testRemoveWriteStreamAfterWriting ()
156291 {
292+ if ($ this ->loop instanceof ExtUvLoop && DIRECTORY_SEPARATOR === '\\' ) {
293+ $ this ->markTestIncomplete ('Ticking ExtUvLoop not supported on Windows ' );
294+ }
295+
157296 list ($ input ) = $ this ->createSocketPair ();
158297
159298 $ this ->loop ->addWriteStream ($ input , $ this ->expectCallableOnce ());
@@ -165,6 +304,10 @@ public function testRemoveWriteStreamAfterWriting()
165304
166305 public function testRemoveStreamForReadOnly ()
167306 {
307+ if ($ this ->loop instanceof ExtUvLoop && DIRECTORY_SEPARATOR === '\\' ) {
308+ $ this ->markTestIncomplete ('Ticking ExtUvLoop not supported on Windows ' );
309+ }
310+
168311 list ($ input , $ output ) = $ this ->createSocketPair ();
169312
170313 $ this ->loop ->addReadStream ($ input , $ this ->expectCallableNever ());
@@ -177,6 +320,10 @@ public function testRemoveStreamForReadOnly()
177320
178321 public function testRemoveStreamForWriteOnly ()
179322 {
323+ if ($ this ->loop instanceof ExtUvLoop && DIRECTORY_SEPARATOR === '\\' ) {
324+ $ this ->markTestIncomplete ('Ticking ExtUvLoop not supported on Windows ' );
325+ }
326+
180327 list ($ input , $ output ) = $ this ->createSocketPair ();
181328
182329 fwrite ($ output , "foo \n" );
@@ -399,6 +546,10 @@ public function testFutureTick()
399546
400547 public function testFutureTickFiresBeforeIO ()
401548 {
549+ if ($ this ->loop instanceof ExtUvLoop && DIRECTORY_SEPARATOR === '\\' ) {
550+ $ this ->markTestIncomplete ('Ticking ExtUvLoop not supported on Windows ' );
551+ }
552+
402553 list ($ stream ) = $ this ->createSocketPair ();
403554
404555 $ this ->loop ->addWriteStream (
@@ -419,6 +570,9 @@ function () {
419570 $ this ->tickLoop ($ this ->loop );
420571 }
421572
573+ /**
574+ * @depends testFutureTickFiresBeforeIO
575+ */
422576 public function testRecursiveFutureTick ()
423577 {
424578 list ($ stream ) = $ this ->createSocketPair ();
0 commit comments