Skip to content

Commit 6090eb7

Browse files
authored
Merge pull request #110 from clue-labs/streams
Documentation for advanced stream API
2 parents ddee079 + 8047bce commit 6090eb7

7 files changed

+218
-12
lines changed

README.md

+119
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,7 @@ For the code of the current stable 0.4.x release, checkout the
2222
* [Install](#install)
2323
* [Tests](#tests)
2424
* [License](#license)
25+
* [More](#more)
2526

2627
## Quickstart example
2728

@@ -291,6 +292,116 @@ echo 'a';
291292

292293
See also [example #3](examples).
293294

295+
### addReadStream()
296+
297+
> Advanced! Note that this low-level API is considered advanced usage.
298+
Most use cases should probably use the higher-level
299+
[readable Stream API](https://github.com/reactphp/stream#readablestreaminterface)
300+
instead.
301+
302+
The `addReadStream(resource $stream, callable $callback): void` method can be used to
303+
register a listener to be notified when a stream is ready to read.
304+
305+
The first parameter MUST be a valid stream resource that supports
306+
checking whether it is ready to read by this loop implementation.
307+
A single stream resource MUST NOT be added more than once.
308+
Instead, either call [`removeReadStream()`](#removereadstream) first or
309+
react to this event with a single listener and then dispatch from this
310+
listener.
311+
312+
The listener callback function MUST be able to accept a single parameter,
313+
the stream resource added by this method or you MAY use a function which
314+
has no parameters at all.
315+
316+
The listener callback function MUST NOT throw an `Exception`.
317+
The return value of the listener callback function will be ignored and has
318+
no effect, so for performance reasons you're recommended to not return
319+
any excessive data structures.
320+
321+
If you want to access any variables within your callback function, you
322+
can bind arbitrary data to a callback closure like this:
323+
324+
```php
325+
$loop->addReadStream($stream, function ($stream) use ($name) {
326+
echo $name . ' said: ' . fread($stream);
327+
});
328+
```
329+
330+
See also [example #11](examples).
331+
332+
You can invoke [`removeReadStream()`](#removereadstream) to remove the
333+
read event listener for this stream.
334+
335+
The execution order of listeners when multiple streams become ready at
336+
the same time is not guaranteed.
337+
338+
### addWriteStream()
339+
340+
> Advanced! Note that this low-level API is considered advanced usage.
341+
Most use cases should probably use the higher-level
342+
[writable Stream API](https://github.com/reactphp/stream#writablestreaminterface)
343+
instead.
344+
345+
The `addWriteStream(resource $stream, callable $callback): void` method can be used to
346+
register a listener to be notified when a stream is ready to write.
347+
348+
The first parameter MUST be a valid stream resource that supports
349+
checking whether it is ready to write by this loop implementation.
350+
A single stream resource MUST NOT be added more than once.
351+
Instead, either call [`removeWriteStream()`](#removewritestream) first or
352+
react to this event with a single listener and then dispatch from this
353+
listener.
354+
355+
The listener callback function MUST be able to accept a single parameter,
356+
the stream resource added by this method or you MAY use a function which
357+
has no parameters at all.
358+
359+
The listener callback function MUST NOT throw an `Exception`.
360+
The return value of the listener callback function will be ignored and has
361+
no effect, so for performance reasons you're recommended to not return
362+
any excessive data structures.
363+
364+
If you want to access any variables within your callback function, you
365+
can bind arbitrary data to a callback closure like this:
366+
367+
```php
368+
$loop->addWriteStream($stream, function ($stream) use ($name) {
369+
fwrite($stream, 'Hello ' . $name);
370+
});
371+
```
372+
373+
See also [example #12](examples).
374+
375+
You can invoke [`removeWriteStream()`](#removewritestream) to remove the
376+
write event listener for this stream.
377+
378+
The execution order of listeners when multiple streams become ready at
379+
the same time is not guaranteed.
380+
381+
### removeReadStream()
382+
383+
The `removeReadStream(resource $stream): void` method can be used to
384+
remove the read event listener for the given stream.
385+
386+
Removing a stream from the loop that has already been removed or trying
387+
to remove a stream that was never added or is invalid has no effect.
388+
389+
### removeWriteStream()
390+
391+
The `removeWriteStream(resource $stream): void` method can be used to
392+
remove the write event listener for the given stream.
393+
394+
Removing a stream from the loop that has already been removed or trying
395+
to remove a stream that was never added or is invalid has no effect.
396+
397+
### removeStream()
398+
399+
The `removeStream(resource $stream): void` method can be used to
400+
remove all listeners for the given stream.
401+
402+
Removing a stream from the loop that has already been removed or trying
403+
to remove a stream that was never added or is invalid has no effect.
404+
294405
## Install
295406

296407
The recommended way to install this library is [through Composer](http://getcomposer.org).
@@ -320,3 +431,11 @@ $ php vendor/bin/phpunit
320431
## License
321432

322433
MIT, see [LICENSE file](LICENSE).
434+
435+
## More
436+
437+
* See our [Stream component](https://github.com/reactphp/stream) for more
438+
information on how streams are used in real-world applications.
439+
* See our [users wiki](https://github.com/reactphp/react/wiki/Users) and the
440+
[dependents on Packagist](https://packagist.org/packages/react/event-loop/dependents)
441+
for a list of packages that use the EventLoop in real-world applications.

src/ExtEventLoop.php

+2-2
Original file line numberDiff line numberDiff line change
@@ -289,11 +289,11 @@ private function createStreamCallback()
289289
$key = (int) $stream;
290290

291291
if (Event::READ === (Event::READ & $flags) && isset($this->readListeners[$key])) {
292-
call_user_func($this->readListeners[$key], $stream, $this);
292+
call_user_func($this->readListeners[$key], $stream);
293293
}
294294

295295
if (Event::WRITE === (Event::WRITE & $flags) && isset($this->writeListeners[$key])) {
296-
call_user_func($this->writeListeners[$key], $stream, $this);
296+
call_user_func($this->writeListeners[$key], $stream);
297297
}
298298
};
299299
}

src/LibEvLoop.php

+2-2
Original file line numberDiff line numberDiff line change
@@ -40,7 +40,7 @@ public function addReadStream($stream, callable $listener)
4040
}
4141

4242
$callback = function () use ($stream, $listener) {
43-
call_user_func($listener, $stream, $this);
43+
call_user_func($listener, $stream);
4444
};
4545

4646
$event = new IOEvent($callback, $stream, IOEvent::READ);
@@ -59,7 +59,7 @@ public function addWriteStream($stream, callable $listener)
5959
}
6060

6161
$callback = function () use ($stream, $listener) {
62-
call_user_func($listener, $stream, $this);
62+
call_user_func($listener, $stream);
6363
};
6464

6565
$event = new IOEvent($callback, $stream, IOEvent::WRITE);

src/LibEventLoop.php

+2-2
Original file line numberDiff line numberDiff line change
@@ -307,11 +307,11 @@ private function createStreamCallback()
307307
$key = (int) $stream;
308308

309309
if (EV_READ === (EV_READ & $flags) && isset($this->readListeners[$key])) {
310-
call_user_func($this->readListeners[$key], $stream, $this);
310+
call_user_func($this->readListeners[$key], $stream);
311311
}
312312

313313
if (EV_WRITE === (EV_WRITE & $flags) && isset($this->writeListeners[$key])) {
314-
call_user_func($this->writeListeners[$key], $stream, $this);
314+
call_user_func($this->writeListeners[$key], $stream);
315315
}
316316
};
317317
}

src/LoopInterface.php

+89-2
Original file line numberDiff line numberDiff line change
@@ -7,38 +7,125 @@
77
interface LoopInterface
88
{
99
/**
10-
* Register a listener to be notified when a stream is ready to read.
10+
* [Advanced] Register a listener to be notified when a stream is ready to read.
11+
*
12+
* Note that this low-level API is considered advanced usage.
13+
* Most use cases should probably use the higher-level
14+
* [readable Stream API](https://github.com/reactphp/stream#readablestreaminterface)
15+
* instead.
16+
*
17+
* The first parameter MUST be a valid stream resource that supports
18+
* checking whether it is ready to read by this loop implementation.
19+
* A single stream resource MUST NOT be added more than once.
20+
* Instead, either call [`removeReadStream()`](#removereadstream) first or
21+
* react to this event with a single listener and then dispatch from this
22+
* listener.
23+
*
24+
* The listener callback function MUST be able to accept a single parameter,
25+
* the stream resource added by this method or you MAY use a function which
26+
* has no parameters at all.
27+
*
28+
* The listener callback function MUST NOT throw an `Exception`.
29+
* The return value of the listener callback function will be ignored and has
30+
* no effect, so for performance reasons you're recommended to not return
31+
* any excessive data structures.
32+
*
33+
* If you want to access any variables within your callback function, you
34+
* can bind arbitrary data to a callback closure like this:
35+
*
36+
* ```php
37+
* $loop->addReadStream($stream, function ($stream) use ($name) {
38+
* echo $name . ' said: ' . fread($stream);
39+
* });
40+
* ```
41+
*
42+
* See also [example #11](examples).
43+
*
44+
* You can invoke [`removeReadStream()`](#removereadstream) to remove the
45+
* read event listener for this stream.
46+
*
47+
* The execution order of listeners when multiple streams become ready at
48+
* the same time is not guaranteed.
1149
*
1250
* @param resource $stream The PHP stream resource to check.
1351
* @param callable $listener Invoked when the stream is ready.
52+
* @see self::removeReadStream()
1453
*/
1554
public function addReadStream($stream, callable $listener);
1655

1756
/**
18-
* Register a listener to be notified when a stream is ready to write.
57+
* [Advanced] Register a listener to be notified when a stream is ready to write.
58+
*
59+
* Note that this low-level API is considered advanced usage.
60+
* Most use cases should probably use the higher-level
61+
* [writable Stream API](https://github.com/reactphp/stream#writablestreaminterface)
62+
* instead.
63+
*
64+
* The first parameter MUST be a valid stream resource that supports
65+
* checking whether it is ready to write by this loop implementation.
66+
* A single stream resource MUST NOT be added more than once.
67+
* Instead, either call [`removeWriteStream()`](#removewritestream) first or
68+
* react to this event with a single listener and then dispatch from this
69+
* listener.
70+
*
71+
* The listener callback function MUST be able to accept a single parameter,
72+
* the stream resource added by this method or you MAY use a function which
73+
* has no parameters at all.
74+
*
75+
* The listener callback function MUST NOT throw an `Exception`.
76+
* The return value of the listener callback function will be ignored and has
77+
* no effect, so for performance reasons you're recommended to not return
78+
* any excessive data structures.
79+
*
80+
* If you want to access any variables within your callback function, you
81+
* can bind arbitrary data to a callback closure like this:
82+
*
83+
* ```php
84+
* $loop->addWriteStream($stream, function ($stream) use ($name) {
85+
* fwrite($stream, 'Hello ' . $name);
86+
* });
87+
* ```
88+
*
89+
* See also [example #12](examples).
90+
*
91+
* You can invoke [`removeWriteStream()`](#removewritestream) to remove the
92+
* write event listener for this stream.
93+
*
94+
* The execution order of listeners when multiple streams become ready at
95+
* the same time is not guaranteed.
1996
*
2097
* @param resource $stream The PHP stream resource to check.
2198
* @param callable $listener Invoked when the stream is ready.
99+
* @see self::removeWriteStream()
22100
*/
23101
public function addWriteStream($stream, callable $listener);
24102

25103
/**
26104
* Remove the read event listener for the given stream.
27105
*
106+
* Removing a stream from the loop that has already been removed or trying
107+
* to remove a stream that was never added or is invalid has no effect.
108+
*
28109
* @param resource $stream The PHP stream resource.
29110
*/
30111
public function removeReadStream($stream);
31112

32113
/**
33114
* Remove the write event listener for the given stream.
34115
*
116+
* Removing a stream from the loop that has already been removed or trying
117+
* to remove a stream that was never added or is invalid has no effect.
118+
*
35119
* @param resource $stream The PHP stream resource.
36120
*/
37121
public function removeWriteStream($stream);
38122

39123
/**
40124
* Remove all listeners for the given stream.
41125
*
126+
* Removing a stream from the loop that has already been removed or trying
127+
* to remove a stream that was never added or is invalid has no effect.
128+
*
42129
* @param resource $stream The PHP stream resource.
43130
*/
44131
public function removeStream($stream);

src/StreamSelectLoop.php

+2-2
Original file line numberDiff line numberDiff line change
@@ -206,15 +206,15 @@ private function waitForStreamActivity($timeout)
206206
$key = (int) $stream;
207207

208208
if (isset($this->readListeners[$key])) {
209-
call_user_func($this->readListeners[$key], $stream, $this);
209+
call_user_func($this->readListeners[$key], $stream);
210210
}
211211
}
212212

213213
foreach ($write as $stream) {
214214
$key = (int) $stream;
215215

216216
if (isset($this->writeListeners[$key])) {
217-
call_user_func($this->writeListeners[$key], $stream, $this);
217+
call_user_func($this->writeListeners[$key], $stream);
218218
}
219219
}
220220
}

tests/StreamSelectLoopTest.php

+2-2
Original file line numberDiff line numberDiff line change
@@ -94,11 +94,11 @@ public function testSignalInterruptWithStream($signal)
9494

9595
// add stream to the loop
9696
list($writeStream, $readStream) = $this->createSocketPair();
97-
$this->loop->addReadStream($readStream, function($stream, $loop) {
97+
$this->loop->addReadStream($readStream, function ($stream) {
9898
/** @var $loop LoopInterface */
9999
$read = fgets($stream);
100100
if ($read === "end loop\n") {
101-
$loop->stop();
101+
$this->loop->stop();
102102
}
103103
});
104104
$this->loop->addTimer(0.1, function() use ($writeStream) {

0 commit comments

Comments
 (0)