Skip to content

Commit e518c0f

Browse files
committed
Merge branch 'development'
2 parents 5922ee7 + f2b0403 commit e518c0f

File tree

8 files changed

+225
-17
lines changed

8 files changed

+225
-17
lines changed

CHANGELOG.md

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,21 @@
33
All notable changes to this project will be documented in this file.
44
This project adheres to [Semantic Versioning](http://semver.org/) and [Keep a CHANGELOG](http://keepachangelog.com).
55

6+
## [3.0.0] - 2019-07-29
7+
8+
**Please take notice of the backwards incompatible changes (BC breaks) documented below
9+
in the changelog of [3.0.0-alpha](#300-alpha---2019-04-30) & [3.0.0-beta](#300-beta---2019-06-24).**
10+
11+
### Added
12+
13+
* Reserved private constant for ABORT_REQUEST instruction for future use
14+
* Socket ID is now represented and generated by a proper type class
15+
16+
### Improved
17+
18+
* Import of root namespace functions
19+
* Dependency injection for socket implementation
20+
621
## [3.0.0-beta] - 2019-06-24
722

823
### Backwards incompatible changes (BC breaks)
@@ -276,6 +291,7 @@ Based on [Pierrick Charron](https://github.com/adoy)'s [PHP-FastCGI-Client](http
276291
* Getters/Setters for connect timeout, read/write timeout, keep alive, socket persistence from `Client` (now part of the socket connection)
277292
* Method `Client->getValues()`
278293

294+
[3.0.0]: https://github.com/hollodotme/fast-cgi-client/compare/v3.0.0-beta...v3.0.0
279295
[3.0.0-beta]: https://github.com/hollodotme/fast-cgi-client/compare/v3.0.0-alpha...v3.0.0-beta
280296
[3.0.0-alpha]: https://github.com/hollodotme/fast-cgi-client/compare/v2.7.2...v3.0.0-alpha
281297
[2.7.2]: https://github.com/hollodotme/fast-cgi-client/compare/v2.7.1...v2.7.2

README.md

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,7 @@ Please see the following links for earlier releases:
2020

2121
* PHP >= 7.0 (EOL) [v1.0.0], [v1.0.1], [v1.1.0], [v1.2.0], [v1.3.0], [v1.4.0], [v1.4.1], [v1.4.2]
2222
* PHP >= 7.1 [v2.0.0], [v2.0.1], [v2.1.0], [v2.2.0], [v2.3.0], [v2.4.0], [v2.4.1], [v2.4.2], [v2.4.3], [v2.5.0], [v2.6.0], [v2.7.0], [v2.7.1],
23-
[v2.7.2], [v3.0.0-alpha]
23+
[v2.7.2], [v3.0.0-alpha], [v3.0.0-beta]
2424

2525
Read more about the journey to and changes in `v2.6.0` in [this blog post](https://hollo.me/php/background-info-fast-cgi-client-v2.6.0.html).
2626

@@ -777,6 +777,7 @@ Run a call through a Unix Domain Socket
777777
This shows the response of the php-fpm status page.
778778

779779

780+
[v3.0.0-beta]: https://github.com/hollodotme/fast-cgi-client/blob/v3.0.0-beta/README.md
780781
[v3.0.0-alpha]: https://github.com/hollodotme/fast-cgi-client/blob/v3.0.0-alpha/README.md
781782
[v2.7.2]: https://github.com/hollodotme/fast-cgi-client/blob/v2.7.2/README.md
782783
[v2.7.1]: https://github.com/hollodotme/fast-cgi-client/blob/v2.7.1/README.md

src/Sockets/Socket.php

Lines changed: 18 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -46,7 +46,6 @@
4646
use function is_resource;
4747
use function microtime;
4848
use function ord;
49-
use function random_int;
5049
use function str_repeat;
5150
use function stream_get_meta_data;
5251
use function stream_select;
@@ -61,6 +60,8 @@ final class Socket
6160
{
6261
private const BEGIN_REQUEST = 1;
6362

63+
private const ABORT_REQUEST = 2;
64+
6465
private const END_REQUEST = 3;
6566

6667
private const PARAMS = 4;
@@ -93,7 +94,7 @@ final class Socket
9394

9495
public const STREAM_SELECT_USEC = 200000;
9596

96-
/** @var int */
97+
/** @var SocketId */
9798
private $id;
9899

99100
/** @var ConfiguresSocketConnection */
@@ -127,19 +128,21 @@ final class Socket
127128
private $status;
128129

129130
/**
131+
* @param SocketId $socketId
130132
* @param ConfiguresSocketConnection $connection
131133
* @param EncodesPacket $packetEncoder
132134
* @param EncodesNameValuePair $nameValuePairEncoder
133135
*
134136
* @throws Exception
135137
*/
136138
public function __construct(
139+
SocketId $socketId,
137140
ConfiguresSocketConnection $connection,
138141
EncodesPacket $packetEncoder,
139142
EncodesNameValuePair $nameValuePairEncoder
140143
)
141144
{
142-
$this->id = random_int( 1, (1 << 16) - 1 );
145+
$this->id = $socketId;
143146
$this->connection = $connection;
144147
$this->packetEncoder = $packetEncoder;
145148
$this->nameValuePairEncoder = $nameValuePairEncoder;
@@ -151,7 +154,7 @@ public function __construct(
151154

152155
public function getId() : int
153156
{
154-
return $this->id;
157+
return $this->id->getValue();
155158
}
156159

157160
public function usesConnection( ConfiguresSocketConnection $connection ) : bool
@@ -331,17 +334,21 @@ private function getRequestPackets( ProvidesRequestData $request ) : string
331334
$requestPackets = $this->packetEncoder->encodePacket(
332335
self::BEGIN_REQUEST,
333336
chr( 0 ) . chr( self::RESPONDER ) . chr( 1 ) . str_repeat( chr( 0 ), 5 ),
334-
$this->id
337+
$this->id->getValue()
335338
);
336339

337340
$paramsRequest = $this->nameValuePairEncoder->encodePairs( $request->getParams() );
338341

339342
if ( $paramsRequest )
340343
{
341-
$requestPackets .= $this->packetEncoder->encodePacket( self::PARAMS, $paramsRequest, $this->id );
344+
$requestPackets .= $this->packetEncoder->encodePacket(
345+
self::PARAMS,
346+
$paramsRequest,
347+
$this->id->getValue()
348+
);
342349
}
343350

344-
$requestPackets .= $this->packetEncoder->encodePacket( self::PARAMS, '', $this->id );
351+
$requestPackets .= $this->packetEncoder->encodePacket( self::PARAMS, '', $this->id->getValue() );
345352

346353
if ( $request->getContent() )
347354
{
@@ -355,14 +362,14 @@ private function getRequestPackets( ProvidesRequestData $request ) : string
355362
$offset,
356363
self::REQ_MAX_CONTENT_SIZE
357364
),
358-
$this->id
365+
$this->id->getValue()
359366
);
360367
$offset += self::REQ_MAX_CONTENT_SIZE;
361368
}
362369
while ( $offset < $request->getContentLength() );
363370
}
364371

365-
$requestPackets .= $this->packetEncoder->encodePacket( self::STDIN, '', $this->id );
372+
$requestPackets .= $this->packetEncoder->encodePacket( self::STDIN, '', $this->id->getValue() );
366373

367374
return $requestPackets;
368375
}
@@ -429,7 +436,7 @@ public function fetchResponse( ?int $timeoutMs = null ) : ProvidesResponseData
429436
continue;
430437
}
431438

432-
if ( self::END_REQUEST === $packetType && $packet['requestId'] === $this->id )
439+
if ( self::END_REQUEST === $packetType && $packet['requestId'] === $this->id->getValue() )
433440
{
434441
break;
435442
}
@@ -577,7 +584,7 @@ public function collectResource( array &$resources ) : void
577584
{
578585
if ( null !== $this->resource )
579586
{
580-
$resources[ (string)$this->id ] = $this->resource;
587+
$resources[ (string)$this->id->getValue() ] = $this->resource;
581588
}
582589
}
583590
}

src/Sockets/SocketCollection.php

Lines changed: 9 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -34,16 +34,21 @@ public function new(
3434
{
3535
for ( $i = 0; $i < 10; $i++ )
3636
{
37-
$socket = new Socket( $connection, $packetEncoder, $nameValuePairEncoder );
37+
$socketId = SocketId::new();
3838

39-
if ( $this->exists( $socket->getId() ) )
39+
if ( $this->exists( $socketId->getValue() ) )
4040
{
4141
continue;
4242
}
4343

44-
$this->sockets[ $socket->getId() ] = $socket;
44+
$this->sockets[ $socketId->getValue() ] = new Socket(
45+
$socketId,
46+
$connection,
47+
$packetEncoder,
48+
$nameValuePairEncoder
49+
);
4550

46-
return $socket;
51+
return $this->sockets[ $socketId->getValue() ];
4752
}
4853

4954
throw new WriteFailedException( 'Could not allocate a new socket ID' );

src/Sockets/SocketId.php

Lines changed: 69 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,69 @@
1+
<?php declare(strict_types=1);
2+
3+
namespace hollodotme\FastCGI\Sockets;
4+
5+
use Exception;
6+
use InvalidArgumentException;
7+
use function random_int;
8+
9+
final class SocketId
10+
{
11+
/** @var int */
12+
private $id;
13+
14+
/**
15+
* @param int $id
16+
*
17+
* @throws InvalidArgumentException
18+
*/
19+
private function __construct( int $id )
20+
{
21+
$this->guardValueIsValid( $id );
22+
23+
$this->id = $id;
24+
}
25+
26+
/**
27+
* @param int $value
28+
*
29+
* @throws InvalidArgumentException
30+
*/
31+
private function guardValueIsValid( int $value ) : void
32+
{
33+
if ( $value < 1 || $value > ((1 << 16) - 1) )
34+
{
35+
throw new InvalidArgumentException( 'Invalid socket ID (out of range): ' . $value );
36+
}
37+
}
38+
39+
/**
40+
* @return SocketId
41+
* @throws InvalidArgumentException
42+
* @throws Exception
43+
*/
44+
public static function new() : self
45+
{
46+
return new self( random_int( 1, (1 << 16) - 1 ) );
47+
}
48+
49+
/**
50+
* @param int $id
51+
*
52+
* @return SocketId
53+
* @throws InvalidArgumentException
54+
*/
55+
public static function fromInt( int $id ) : self
56+
{
57+
return new self( $id );
58+
}
59+
60+
public function getValue() : int
61+
{
62+
return $this->id;
63+
}
64+
65+
public function equals( SocketId $other ) : bool
66+
{
67+
return $this->id === $other->id;
68+
}
69+
}

tests/Integration/NetworkSocketTest.php

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -43,6 +43,7 @@
4343
use RuntimeException;
4444
use SebastianBergmann\RecursionContext\InvalidArgumentException;
4545
use Throwable;
46+
use function http_build_query;
4647

4748
final class NetworkSocketTest extends TestCase
4849
{

tests/Unit/Sockets/SocketIdTest.php

Lines changed: 106 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,106 @@
1+
<?php declare(strict_types=1);
2+
3+
namespace hollodotme\FastCGI\Tests\Unit\Sockets;
4+
5+
use hollodotme\FastCGI\Sockets\SocketId;
6+
use PHPUnit\Framework\ExpectationFailedException;
7+
use PHPUnit\Framework\TestCase;
8+
use SebastianBergmann\RecursionContext\InvalidArgumentException;
9+
10+
final class SocketIdTest extends TestCase
11+
{
12+
/**
13+
* @throws \InvalidArgumentException
14+
* @throws ExpectationFailedException
15+
* @throws InvalidArgumentException
16+
*/
17+
public function testCanGetNewInstance() : void
18+
{
19+
for ( $i = 0; $i < 100; $i++ )
20+
{
21+
$socketId = SocketId::new();
22+
23+
$this->assertGreaterThanOrEqual( 1, $socketId->getValue() );
24+
$this->assertLessThanOrEqual( (1 << 16) - 1, $socketId->getValue() );
25+
}
26+
}
27+
28+
/**
29+
* @throws ExpectationFailedException
30+
* @throws InvalidArgumentException
31+
* @throws \InvalidArgumentException
32+
*/
33+
public function testGetValue() : void
34+
{
35+
$socketId = SocketId::new();
36+
37+
$this->assertGreaterThanOrEqual( 1, $socketId->getValue() );
38+
$this->assertLessThanOrEqual( (1 << 16) - 1, $socketId->getValue() );
39+
}
40+
41+
/**
42+
* @throws ExpectationFailedException
43+
* @throws InvalidArgumentException
44+
* @throws \InvalidArgumentException
45+
*/
46+
public function testCanGetNewInstanceFromInt() : void
47+
{
48+
for ( $i = 1; $i < 10; $i++ )
49+
{
50+
$socketId = SocketId::fromInt( $i );
51+
52+
$this->assertSame( $i, $socketId->getValue() );
53+
}
54+
}
55+
56+
/**
57+
* @param int $socketIdValue
58+
*
59+
* @throws \InvalidArgumentException
60+
* @dataProvider outOfRangeSocketIdValueProvider
61+
*/
62+
public function testThrowsExceptionIfSocketIdValueIsOutOfRange( int $socketIdValue ) : void
63+
{
64+
$this->expectException( \InvalidArgumentException::class );
65+
$this->expectExceptionMessage( 'Invalid socket ID (out of range): ' . $socketIdValue );
66+
67+
SocketId::fromInt( $socketIdValue );
68+
}
69+
70+
public function outOfRangeSocketIdValueProvider() : array
71+
{
72+
return [
73+
[
74+
'socketIdValue' => 0,
75+
],
76+
[
77+
'socketIdValue' => 1 << 16,
78+
],
79+
];
80+
}
81+
82+
/**
83+
* @throws ExpectationFailedException
84+
* @throws InvalidArgumentException
85+
* @throws \InvalidArgumentException
86+
*/
87+
public function testEquals() : void
88+
{
89+
$socketId = SocketId::fromInt( 123 );
90+
$otherEquals = SocketId::fromInt( 123 );
91+
$otherEqualsNot = SocketId::fromInt( 321 );
92+
93+
$this->assertNotSame( $socketId, $otherEquals );
94+
$this->assertNotSame( $socketId, $otherEqualsNot );
95+
$this->assertNotSame( $otherEquals, $otherEqualsNot );
96+
97+
$this->assertTrue( $socketId->equals( $otherEquals ) );
98+
$this->assertTrue( $otherEquals->equals( $socketId ) );
99+
100+
$this->assertFalse( $socketId->equals( $otherEqualsNot ) );
101+
$this->assertFalse( $otherEqualsNot->equals( $socketId ) );
102+
103+
$this->assertFalse( $otherEquals->equals( $otherEqualsNot ) );
104+
$this->assertFalse( $otherEqualsNot->equals( $otherEquals ) );
105+
}
106+
}

0 commit comments

Comments
 (0)