Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 4 additions & 3 deletions src/Connection.php
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
namespace React\Socket;

use Evenement\EventEmitter;
use React\EventLoop\Loop;
use React\EventLoop\LoopInterface;
use React\Stream\DuplexResourceStream;
use React\Stream\Util;
Expand Down Expand Up @@ -41,7 +42,7 @@ class Connection extends EventEmitter implements ConnectionInterface

private $input;

public function __construct($resource, LoopInterface $loop)
public function __construct($resource)
{
// Legacy PHP < 7.3.3 (and PHP < 7.2.15) suffers from a bug where feof()
// might block with 100% CPU usage on fragmented TLS records.
Expand All @@ -66,9 +67,9 @@ public function __construct($resource, LoopInterface $loop)

$this->input = new DuplexResourceStream(
$resource,
$loop,
Loop::get(),
$clearCompleteBuffer ? -1 : null,
new WritableResourceStream($resource, $loop, null, $limitWriteChunks ? 8192 : null)
new WritableResourceStream($resource, Loop::get(), null, $limitWriteChunks ? 8192 : null)
);

$this->stream = $resource;
Expand Down
26 changes: 8 additions & 18 deletions src/Connector.php
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
use React\Dns\Config\Config as DnsConfig;
use React\Dns\Resolver\Factory as DnsFactory;
use React\Dns\Resolver\ResolverInterface;
use React\EventLoop\Loop;
use React\EventLoop\LoopInterface;
use function React\Promise\reject;

Expand Down Expand Up @@ -37,20 +38,13 @@ final class Connector implements ConnectorInterface
* This class takes two optional arguments for more advanced usage:
*
* ```php
* $connector = new React\Socket\Connector(array $context = [], ?LoopInterface $loop = null);
* $connector = new React\Socket\Connector(array $context = []);
* ```
*
* This class takes an optional `LoopInterface|null $loop` parameter that can be used to
* pass the event loop instance to use for this object. You can use a `null` value
* here in order to use the [default loop](https://github.com/reactphp/event-loop#loop).
* This value SHOULD NOT be given unless you're sure you want to explicitly use a
* given event loop instance.
*
* @param array $context
* @param ?LoopInterface $loop
* @throws \InvalidArgumentException for invalid arguments
*/
public function __construct(array $context = [], ?LoopInterface $loop = null)
public function __construct(array $context = [])
{
// apply default options if not explicitly given
$context += [
Expand All @@ -71,7 +65,6 @@ public function __construct(array $context = [], ?LoopInterface $loop = null)
$tcp = $context['tcp'];
} else {
$tcp = new TcpConnector(
$loop,
\is_array($context['tcp']) ? $context['tcp'] : []
);
}
Expand All @@ -93,12 +86,12 @@ public function __construct(array $context = [], ?LoopInterface $loop = null)
$factory = new DnsFactory();
$resolver = $factory->createCached(
$config,
$loop
Loop::get()
);
}

if ($context['happy_eyeballs'] === true) {
$tcp = new HappyEyeBallsConnector($loop, $tcp, $resolver);
$tcp = new HappyEyeBallsConnector($tcp, $resolver);
} else {
$tcp = new DnsConnector($tcp, $resolver);
}
Expand All @@ -110,8 +103,7 @@ public function __construct(array $context = [], ?LoopInterface $loop = null)
if ($context['timeout'] !== false) {
$context['tcp'] = new TimeoutConnector(
$context['tcp'],
$context['timeout'],
$loop
$context['timeout']
);
}

Expand All @@ -122,16 +114,14 @@ public function __construct(array $context = [], ?LoopInterface $loop = null)
if (!$context['tls'] instanceof ConnectorInterface) {
$context['tls'] = new SecureConnector(
$tcp,
$loop,
\is_array($context['tls']) ? $context['tls'] : []
);
}

if ($context['timeout'] !== false) {
$context['tls'] = new TimeoutConnector(
$context['tls'],
$context['timeout'],
$loop
$context['timeout']
);
}

Expand All @@ -140,7 +130,7 @@ public function __construct(array $context = [], ?LoopInterface $loop = null)

if ($context['unix'] !== false) {
if (!$context['unix'] instanceof ConnectorInterface) {
$context['unix'] = new UnixConnector($loop);
$context['unix'] = new UnixConnector();
}
$this->connectors['unix'] = $context['unix'];
}
Expand Down
11 changes: 4 additions & 7 deletions src/FdServer.php
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,6 @@
final class FdServer extends EventEmitter implements ServerInterface
{
private $master;
private $loop;
private $unix = false;
private $listening = false;

Expand Down Expand Up @@ -75,7 +74,7 @@ final class FdServer extends EventEmitter implements ServerInterface
* @throws \InvalidArgumentException if the listening address is invalid
* @throws \RuntimeException if listening on this address fails (already in use etc.)
*/
public function __construct($fd, ?LoopInterface $loop = null)
public function __construct($fd)
{
if (\preg_match('#^php://fd/(\d+)$#', $fd, $m)) {
$fd = (int) $m[1];
Expand All @@ -87,8 +86,6 @@ public function __construct($fd, ?LoopInterface $loop = null)
);
}

$this->loop = $loop ?? Loop::get();

$errno = 0;
$errstr = '';
\set_error_handler(function ($_, $error) use (&$errno, &$errstr) {
Expand Down Expand Up @@ -173,7 +170,7 @@ public function pause()
return;
}

$this->loop->removeReadStream($this->master);
Loop::removeReadStream($this->master);
$this->listening = false;
}

Expand All @@ -183,7 +180,7 @@ public function resume()
return;
}

$this->loop->addReadStream($this->master, function ($master) {
Loop::addReadStream($this->master, function ($master) {
try {
$newSocket = SocketServer::accept($master);
} catch (\RuntimeException $e) {
Expand All @@ -209,7 +206,7 @@ public function close()
/** @internal */
public function handleConnection($socket)
{
$connection = new Connection($socket, $this->loop);
$connection = new Connection($socket);
$connection->unix = $this->unix;

$this->emit('connection', [$connection]);
Expand Down
17 changes: 8 additions & 9 deletions src/HappyEyeBallsConnectionBuilder.php
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@

use React\Dns\Model\Message;
use React\Dns\Resolver\ResolverInterface;
use React\EventLoop\Loop;
use React\EventLoop\LoopInterface;
use React\EventLoop\TimerInterface;
use React\Promise\Deferred;
Expand Down Expand Up @@ -31,7 +32,6 @@ final class HappyEyeBallsConnectionBuilder
*/
const RESOLUTION_DELAY = 0.05;

public $loop;
public $connector;
public $resolver;
public $uri;
Expand All @@ -54,9 +54,8 @@ final class HappyEyeBallsConnectionBuilder
public $lastError6;
public $lastError4;

public function __construct(LoopInterface $loop, ConnectorInterface $connector, ResolverInterface $resolver, $uri, $host, $parts)
public function __construct(ConnectorInterface $connector, ResolverInterface $resolver, $uri, $host, $parts)
{
$this->loop = $loop;
$this->connector = $connector;
$this->resolver = $resolver;
$this->uri = $uri;
Expand Down Expand Up @@ -93,12 +92,12 @@ public function connect()
// discard all IPv4 addresses if cancelled
$ips = [];
});
$timer = $this->loop->addTimer($this::RESOLUTION_DELAY, function () use ($deferred, $ips) {
$timer = Loop::addTimer($this::RESOLUTION_DELAY, function () use ($deferred, $ips) {
$deferred->resolve($ips);
});

$this->resolverPromises[Message::TYPE_AAAA]->then(function () use ($timer, $deferred, &$ips) {
$this->loop->cancelTimer($timer);
Loop::cancelTimer($timer);
$deferred->resolve($ips);
});

Expand Down Expand Up @@ -139,7 +138,7 @@ public function resolve($type, $reject)

// cancel next attempt timer when there are no more IPs to connect to anymore
if ($this->nextAttemptTimer !== null && !$this->connectQueue) {
$this->loop->cancelTimer($this->nextAttemptTimer);
Loop::cancelTimer($this->nextAttemptTimer);
$this->nextAttemptTimer = null;
}

Expand Down Expand Up @@ -191,7 +190,7 @@ public function check($resolve, $reject)
// start next connection attempt immediately on error
if ($this->connectQueue) {
if ($this->nextAttemptTimer !== null) {
$this->loop->cancelTimer($this->nextAttemptTimer);
Loop::cancelTimer($this->nextAttemptTimer);
$this->nextAttemptTimer = null;
}

Expand All @@ -216,7 +215,7 @@ public function check($resolve, $reject)
// Allow next connection attempt in 100ms: https://tools.ietf.org/html/rfc8305#section-5
// Only start timer when more IPs are queued or when DNS query is still pending (might add more IPs)
if ($this->nextAttemptTimer === null && (\count($this->connectQueue) > 0 || $this->resolved[Message::TYPE_A] === false || $this->resolved[Message::TYPE_AAAA] === false)) {
$this->nextAttemptTimer = $this->loop->addTimer(self::CONNECTION_ATTEMPT_DELAY, function () use ($resolve, $reject) {
$this->nextAttemptTimer = Loop::addTimer(self::CONNECTION_ATTEMPT_DELAY, function () use ($resolve, $reject) {
$this->nextAttemptTimer = null;

if ($this->connectQueue) {
Expand Down Expand Up @@ -259,7 +258,7 @@ public function cleanUp()
}

if ($this->nextAttemptTimer instanceof TimerInterface) {
$this->loop->cancelTimer($this->nextAttemptTimer);
Loop::cancelTimer($this->nextAttemptTimer);
$this->nextAttemptTimer = null;
}
}
Expand Down
5 changes: 1 addition & 4 deletions src/HappyEyeBallsConnector.php
Original file line number Diff line number Diff line change
Expand Up @@ -9,13 +9,11 @@

final class HappyEyeBallsConnector implements ConnectorInterface
{
private $loop;
private $connector;
private $resolver;

public function __construct(?LoopInterface $loop, ConnectorInterface $connector, ResolverInterface $resolver)
public function __construct(ConnectorInterface $connector, ResolverInterface $resolver)
{
$this->loop = $loop ?? Loop::get();
$this->connector = $connector;
$this->resolver = $resolver;
}
Expand Down Expand Up @@ -48,7 +46,6 @@ public function connect($uri)
}

$builder = new HappyEyeBallsConnectionBuilder(
$this->loop,
$this->connector,
$this->resolver,
$uri,
Expand Down
4 changes: 2 additions & 2 deletions src/SecureConnector.php
Original file line number Diff line number Diff line change
Expand Up @@ -13,10 +13,10 @@ final class SecureConnector implements ConnectorInterface
private $streamEncryption;
private $context;

public function __construct(ConnectorInterface $connector, ?LoopInterface $loop = null, array $context = [])
public function __construct(ConnectorInterface $connector, array $context = [])
{
$this->connector = $connector;
$this->streamEncryption = new StreamEncryption($loop ?? Loop::get(), false);
$this->streamEncryption = new StreamEncryption(false);
$this->context = $context;
}

Expand Down
5 changes: 2 additions & 3 deletions src/SecureServer.php
Original file line number Diff line number Diff line change
Expand Up @@ -114,20 +114,19 @@ final class SecureServer extends EventEmitter implements ServerInterface
* then close the underlying connection.
*
* @param ServerInterface|TcpServer $tcp
* @param ?LoopInterface $loop
* @param array $context
* @see TcpServer
* @link https://www.php.net/manual/en/context.ssl.php for TLS context options
*/
public function __construct(ServerInterface $tcp, ?LoopInterface $loop = null, array $context = [])
public function __construct(ServerInterface $tcp, array $context = [])
{
// default to empty passphrase to suppress blocking passphrase prompt
$context += [
'passphrase' => ''
];

$this->tcp = $tcp;
$this->encryption = new StreamEncryption($loop ?? Loop::get());
$this->encryption = new StreamEncryption();
$this->context = $context;

$this->tcp->on('connection', function ($connection) {
Expand Down
11 changes: 5 additions & 6 deletions src/SocketServer.php
Original file line number Diff line number Diff line change
Expand Up @@ -27,11 +27,10 @@ final class SocketServer extends EventEmitter implements ServerInterface
*
* @param string $uri
* @param array $context
* @param ?LoopInterface $loop
* @throws \InvalidArgumentException if the listening address is invalid
* @throws \RuntimeException if listening on this address fails (already in use etc.)
*/
public function __construct($uri, array $context = [], ?LoopInterface $loop = null)
public function __construct($uri, array $context = [])
{
// apply default options if not explicitly given
$context += [
Expand All @@ -47,9 +46,9 @@ public function __construct($uri, array $context = [], ?LoopInterface $loop = nu
}

if ($scheme === 'unix') {
$server = new UnixServer($uri, $loop, $context['unix']);
$server = new UnixServer($uri, $context['unix']);
} elseif ($scheme === 'php') {
$server = new FdServer($uri, $loop);
$server = new FdServer($uri);
} else {
if (preg_match('#^(?:\w+://)?\d+$#', $uri)) {
throw new \InvalidArgumentException(
Expand All @@ -58,10 +57,10 @@ public function __construct($uri, array $context = [], ?LoopInterface $loop = nu
);
}

$server = new TcpServer(str_replace('tls://', '', $uri), $loop, $context['tcp']);
$server = new TcpServer(str_replace('tls://', '', $uri), $context['tcp']);

if ($scheme === 'tls') {
$server = new SecureServer($server, $loop, $context['tls']);
$server = new SecureServer($server, $context['tls']);
}
}

Expand Down
11 changes: 5 additions & 6 deletions src/StreamEncryption.php
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@

namespace React\Socket;

use React\EventLoop\Loop;
use React\EventLoop\LoopInterface;
use React\Promise\Deferred;

Expand All @@ -13,13 +14,11 @@
*/
class StreamEncryption
{
private $loop;
private $method;
private $server;

public function __construct(LoopInterface $loop, $server = true)
public function __construct($server = true)
{
$this->loop = $loop;
$this->server = $server;

// support TLSv1.0+ by default and exclude legacy SSLv2/SSLv3.
Expand Down Expand Up @@ -78,21 +77,21 @@ public function toggle(Connection $stream, $toggle)
$this->toggleCrypto($socket, $deferred, $toggle, $method);
};

$this->loop->addReadStream($socket, $toggleCrypto);
Loop::addReadStream($socket, $toggleCrypto);

if (!$this->server) {
$toggleCrypto();
}

return $deferred->promise()->then(function () use ($stream, $socket, $toggle) {
$this->loop->removeReadStream($socket);
Loop::removeReadStream($socket);

$stream->encryptionEnabled = $toggle;
$stream->resume();

return $stream;
}, function($error) use ($stream, $socket) {
$this->loop->removeReadStream($socket);
Loop::removeReadStream($socket);
$stream->resume();
throw $error;
});
Expand Down
Loading
Loading