markTestSkipped('Not supported on your platform (outdated HHVM?)'); } $this->loop = LoopFactory::create(); $this->server = new TcpServer(0, $this->loop); $this->server = new SecureServer($this->server, $this->loop, array( 'local_cert' => __DIR__ . '/../examples/localhost.pem' )); $this->address = $this->server->getAddress(); $this->connector = new SecureConnector(new TcpConnector($this->loop), $this->loop, array('verify_peer' => false)); } public function tearDown() { if ($this->server !== null) { $this->server->close(); $this->server = null; } } public function testConnectToServer() { $client = Block\await($this->connector->connect($this->address), $this->loop, self::TIMEOUT); /* @var $client ConnectionInterface */ $client->close(); // if we reach this, then everything is good $this->assertNull(null); } public function testConnectToServerEmitsConnection() { $promiseServer = $this->createPromiseForEvent($this->server, 'connection', $this->expectCallableOnce()); $promiseClient = $this->connector->connect($this->address); list($_, $client) = Block\awaitAll(array($promiseServer, $promiseClient), $this->loop, self::TIMEOUT); /* @var $client ConnectionInterface */ $client->close(); } public function testSendSmallDataToServerReceivesOneChunk() { // server expects one connection which emits one data event $received = new Deferred(); $this->server->on('connection', function (ConnectionInterface $peer) use ($received) { $peer->on('data', function ($chunk) use ($received) { $received->resolve($chunk); }); }); $client = Block\await($this->connector->connect($this->address), $this->loop, self::TIMEOUT); /* @var $client ConnectionInterface */ $client->write('hello'); // await server to report one "data" event $data = Block\await($received->promise(), $this->loop, self::TIMEOUT); $client->close(); $this->assertEquals('hello', $data); } public function testSendDataWithEndToServerReceivesAllData() { $disconnected = new Deferred(); $this->server->on('connection', function (ConnectionInterface $peer) use ($disconnected) { $received = ''; $peer->on('data', function ($chunk) use (&$received) { $received .= $chunk; }); $peer->on('close', function () use (&$received, $disconnected) { $disconnected->resolve($received); }); }); $client = Block\await($this->connector->connect($this->address), $this->loop, self::TIMEOUT); /* @var $client ConnectionInterface */ $data = str_repeat('a', 200000); $client->end($data); // await server to report connection "close" event $received = Block\await($disconnected->promise(), $this->loop, self::TIMEOUT); $this->assertEquals($data, $received); } public function testSendDataWithoutEndingToServerReceivesAllData() { $received = ''; $this->server->on('connection', function (ConnectionInterface $peer) use (&$received) { $peer->on('data', function ($chunk) use (&$received) { $received .= $chunk; }); }); $client = Block\await($this->connector->connect($this->address), $this->loop, self::TIMEOUT); /* @var $client ConnectionInterface */ $data = str_repeat('d', 200000); $client->write($data); // buffer incoming data for 0.1s (should be plenty of time) Block\sleep(0.1, $this->loop); $client->close(); $this->assertEquals($data, $received); } public function testConnectToServerWhichSendsSmallDataReceivesOneChunk() { $this->server->on('connection', function (ConnectionInterface $peer) { $peer->write('hello'); }); $client = Block\await($this->connector->connect($this->address), $this->loop, self::TIMEOUT); /* @var $client ConnectionInterface */ // await client to report one "data" event $receive = $this->createPromiseForEvent($client, 'data', $this->expectCallableOnceWith('hello')); Block\await($receive, $this->loop, self::TIMEOUT); $client->close(); } public function testConnectToServerWhichSendsDataWithEndReceivesAllData() { $data = str_repeat('b', 100000); $this->server->on('connection', function (ConnectionInterface $peer) use ($data) { $peer->end($data); }); $client = Block\await($this->connector->connect($this->address), $this->loop, self::TIMEOUT); /* @var $client ConnectionInterface */ // await data from client until it closes $received = $this->buffer($client, $this->loop, self::TIMEOUT); $this->assertEquals($data, $received); } public function testConnectToServerWhichSendsDataWithoutEndingReceivesAllData() { $data = str_repeat('c', 100000); $this->server->on('connection', function (ConnectionInterface $peer) use ($data) { $peer->write($data); }); $client = Block\await($this->connector->connect($this->address), $this->loop, self::TIMEOUT); /* @var $client ConnectionInterface */ // buffer incoming data for 0.1s (should be plenty of time) $received = ''; $client->on('data', function ($chunk) use (&$received) { $received .= $chunk; }); Block\sleep(0.1, $this->loop); $client->close(); $this->assertEquals($data, $received); } private function createPromiseForEvent(EventEmitterInterface $emitter, $event, $fn) { return new Promise(function ($resolve) use ($emitter, $event, $fn) { $emitter->on($event, function () use ($resolve, $fn) { $resolve(call_user_func_array($fn, func_get_args())); }); }); } }