2016-08-10 23:48:42 +02:00
|
|
|
<?php
|
|
|
|
|
|
|
|
namespace Amp\Stream;
|
|
|
|
|
|
|
|
use Amp\Coroutine;
|
2016-08-16 00:19:32 +02:00
|
|
|
use Interop\Async\Awaitable;
|
2016-08-10 23:48:42 +02:00
|
|
|
|
|
|
|
// @codeCoverageIgnoreStart
|
|
|
|
if (\strlen('…') !== 3) {
|
2016-08-16 00:19:32 +02:00
|
|
|
throw new \Error(
|
2016-08-10 23:48:42 +02:00
|
|
|
'The mbstring.func_overload ini setting is enabled. It must be disable to use the stream package.'
|
|
|
|
);
|
|
|
|
} // @codeCoverageIgnoreEnd
|
|
|
|
|
|
|
|
/**
|
|
|
|
* @param \Amp\Stream\Stream $source
|
|
|
|
* @param \Amp\Stream\Stream $destination
|
|
|
|
* @param int|null $bytes
|
|
|
|
*
|
|
|
|
* @return \Interop\Async\Awaitable
|
|
|
|
*/
|
2016-08-16 00:19:32 +02:00
|
|
|
function pipe(Stream $source, Stream $destination, int $bytes = null): Awaitable {
|
2016-08-10 23:48:42 +02:00
|
|
|
return new Coroutine(__doPipe($source, $destination, $bytes));
|
|
|
|
}
|
|
|
|
|
2016-08-16 00:19:32 +02:00
|
|
|
function __doPipe(Stream $source, Stream $destination, int $bytes = null): \Generator {
|
2016-08-10 23:48:42 +02:00
|
|
|
if (!$destination->isWritable()) {
|
|
|
|
throw new \LogicException("The destination is not writable");
|
|
|
|
}
|
|
|
|
|
|
|
|
if (null !== $bytes) {
|
2016-08-16 00:19:32 +02:00
|
|
|
return yield $destination->write(
|
|
|
|
yield $source->read($bytes)
|
2016-08-10 23:48:42 +02:00
|
|
|
);
|
|
|
|
}
|
|
|
|
|
|
|
|
$written = 0;
|
|
|
|
|
|
|
|
do {
|
2016-08-16 00:19:32 +02:00
|
|
|
$written += yield $destination->write(
|
2016-08-10 23:48:42 +02:00
|
|
|
yield $source->read()
|
2016-08-16 00:19:32 +02:00
|
|
|
);
|
2016-08-10 23:48:42 +02:00
|
|
|
} while ($source->isReadable() && $destination->isWritable());
|
|
|
|
|
2016-08-16 00:19:32 +02:00
|
|
|
return $written;
|
2016-08-10 23:48:42 +02:00
|
|
|
}
|