Skip to content

Commit 0e01d1a

Browse files
author
ahmard
committed
ReactPHP implementation added
Code refactored
1 parent f55b73a commit 0e01d1a

19 files changed

+556
-110
lines changed

README.md

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ composer require ahmard/php-server
77

88
## Usage
99
### PHP Built-In Server
10+
An implementation of [Built-In Server](https://www.php.net/manual/en/features.commandline.webserver.php)
1011

1112
- With document root
1213
```php
@@ -33,4 +34,27 @@ use PHPServer\BuiltIn\Server;
3334
Server::create('127.0.0.1', '9900')
3435
->onRequest(fn() => var_dump('Request Received'))
3536
->start();
37+
```
38+
39+
40+
### ReactPHP
41+
An implementation of [ReactPHP](https://reactphp.org)
42+
43+
```php
44+
use PHPServer\React\Server;
45+
use Psr\Http\Message\RequestInterface;
46+
use React\Http\Message\Response;
47+
48+
require 'vendor/autoload.php';
49+
50+
$handler = function (RequestInterface $request) {
51+
$html = 'Welcome,<br/>';
52+
$html .= "Method: {$request->getMethod()}<br/>";
53+
$html .= "Route: {$request->getUri()->getPath()}";
54+
return new Response(200, ['Content-Type' => 'text/html'], $html);
55+
};
56+
57+
Server::create('127.0.0.1', 9001)
58+
->onRequest($handler)
59+
->start();
3660
```

bin/built-in.php

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
<?php
2+
3+
use PHPServer\ServerInfo;
4+
use PHPServer\Terminal;
5+
6+
require 'vendor/autoload.php';
7+
8+
$arguments = Terminal::performServerChecks(true);
9+
10+
/**@var ServerInfo $serverInfo * */
11+
$serverInfo = $arguments['info'];
12+
13+
14+
if (null !== $serverInfo->getRequestCallback()) {
15+
$serverInfo->getRequestCallback()();
16+
}

bin/react.php

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
<?php
2+
3+
use PHPServer\ServerInfo;
4+
use PHPServer\Terminal;
5+
use React\Http\HttpServer;
6+
use React\Socket\SocketServer;
7+
8+
require 'vendor/autoload.php';
9+
10+
$arguments = Terminal::performServerChecks();
11+
12+
/**@var ServerInfo $serverInfo * */
13+
$serverInfo = $arguments['info'];
14+
15+
$socket = new SocketServer("{$serverInfo->getHost()}:{$serverInfo->getPort()}");
16+
$http = new HttpServer($serverInfo->getRequestCallback());
17+
$http->listen($socket);

composer.json

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,9 @@
55
"license": "MIT",
66
"require": {
77
"php": "^8.0",
8-
"react/child-process": "^0.6.3"
8+
"react/child-process": "^0.6.3",
9+
"react/http": "^1.5",
10+
"opis/closure": "^3.6"
911
},
1012
"require-dev": {
1113
"phpstan/phpstan": "^0.12.98",
@@ -14,7 +16,8 @@
1416
"autoload": {
1517
"psr-4": {
1618
"PHPServer\\": "src/"
17-
}
19+
},
20+
"files": ["src/functions.php"]
1821
},
1922
"authors": [
2023
{

requests.http

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,4 @@
1+
GET http://localhost:9001/
2+
Accept: application/json
3+
4+
###

src/BuiltIn/Factory.php

Lines changed: 0 additions & 33 deletions
This file was deleted.

src/BuiltIn/Server.php

Lines changed: 56 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -3,60 +3,93 @@
33
namespace PHPServer\BuiltIn;
44

55
use Closure;
6-
use JetBrains\PhpStorm\ArrayShape;
76
use JetBrains\PhpStorm\Pure;
7+
use PHPServer\ServerCommand;
8+
use PHPServer\ServerInfo;
9+
use PHPServer\ServerInterface;
10+
use PHPServer\ServerProcess;
11+
use PHPServer\StartedServer;
12+
use PHPServer\StartedServerInterface;
13+
use PHPServer\Terminal;
14+
use function PHPServer\base_path;
815

9-
class Server
16+
class Server implements ServerInterface
1017
{
18+
protected static array $filledInfo = [];
1119
protected string|null $documentRoot = null;
1220
protected string|null $routerScript = null;
1321
protected Closure|null $requestCallback = null;
1422

23+
public function __construct(
24+
protected string $host,
25+
protected int $port
26+
)
27+
{
28+
}
1529

16-
#[Pure] public static function create(float|string $host, int $port): Server
30+
#[Pure] public static function create(string $host, int $port): static
1731
{
1832
return new Server($host, $port);
1933
}
2034

21-
public function __construct(
22-
protected float|string $host,
23-
protected int $port
24-
)
35+
public function getCommand(): ServerCommand
2536
{
37+
$config = $this->getInfo();
38+
$command = "php -S {$config->getHost()}:{$config->getPort()}";
39+
40+
if (null == $config->getDocumentRoot()) {
41+
42+
if (null !== $config->getRouterScript()) {
43+
$command .= " {$config->getRouterScript()}";
44+
}
45+
46+
if (null !== $config->getRequestCallback()) {
47+
$s = Terminal::encodeArgument($this->getInfo()->toArray());
48+
$command = 'PHP_SERVER_INFO="' . $s . '" ' . $command;
49+
$command .= ' ' . base_path('bin/built-in.php');
50+
}
51+
52+
}
53+
54+
$serverCommand = ServerCommand::create($command);
55+
56+
if (null !== $config->getDocumentRoot()) {
57+
$serverCommand->addArgument('-t', $config->getDocumentRoot());
58+
}
59+
60+
return $serverCommand;
2661
}
2762

28-
public function setDocumentRoot(string $path): Server
63+
public function getInfo(): ServerInfo
64+
{
65+
return ServerInfo::create()
66+
->setHost($this->host)
67+
->setPort($this->port)
68+
->setDocumentRoot($this->documentRoot)
69+
->setRequestCallback($this->requestCallback)
70+
->setRouterScript($this->routerScript);
71+
}
72+
73+
public function setDocumentRoot(string $path): static
2974
{
3075
$this->documentRoot = $path;
3176
return $this;
3277
}
3378

34-
public function setRouterScript(string $filePath): Server
79+
public function setRouterScript(string $filePath): static
3580
{
3681
$this->routerScript = $filePath;
3782
return $this;
3883
}
3984

40-
public function onRequest(callable $callback): Server
85+
public function onRequest(callable $callback): static
4186
{
4287
$this->requestCallback = $callback;
4388
return $this;
4489
}
4590

46-
public function start(): StartedServer
91+
public function start(): StartedServerInterface
4792
{
4893
return new StartedServer($this, ServerProcess::create($this));
4994
}
50-
51-
#[ArrayShape(['host' => "int|string", 'port' => "int", 'document_root' => "null|string", 'router_script' => "null|string", 'request_callback' => "\Closure|null"])]
52-
public function getInfo(): array
53-
{
54-
return [
55-
'host' => $this->host,
56-
'port' => $this->port,
57-
'document_root' => $this->documentRoot,
58-
'router_script' => $this->routerScript,
59-
'request_callback' => $this->requestCallback,
60-
];
61-
}
6295
}

src/BuiltIn/ServerProcess.php

Lines changed: 0 additions & 42 deletions
This file was deleted.

src/React/Server.php

Lines changed: 68 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,68 @@
1+
<?php
2+
3+
namespace PHPServer\React;
4+
5+
use Closure;
6+
use JetBrains\PhpStorm\Pure;
7+
use PHPServer\ServerCommand;
8+
use PHPServer\ServerInfo;
9+
use PHPServer\ServerInterface;
10+
use PHPServer\ServerProcess;
11+
use PHPServer\StartedServer;
12+
use PHPServer\StartedServerInterface;
13+
use PHPServer\Terminal;
14+
use function PHPServer\base_path;
15+
16+
class Server implements ServerInterface
17+
{
18+
protected string|null $documentRoot = null;
19+
protected string|null $routerScript = null;
20+
protected Closure|null $requestCallback = null;
21+
22+
public function __construct(
23+
protected string $host,
24+
protected int $port
25+
)
26+
{
27+
}
28+
29+
#[Pure] public static function create(string $host, int $port): static
30+
{
31+
return new Server($host, $port);
32+
}
33+
34+
public function setDocumentRoot(string $path): static
35+
{
36+
$this->documentRoot = $path;
37+
return $this;
38+
}
39+
40+
public function onRequest(callable $callback): static
41+
{
42+
$this->requestCallback = $callback;
43+
return $this;
44+
}
45+
46+
public function start(): StartedServerInterface
47+
{
48+
return new StartedServer($this, ServerProcess::create($this));
49+
}
50+
51+
public function getCommand(): ServerCommand
52+
{
53+
$serverInfo = Terminal::encodeArgument($this->getInfo()->toArray());
54+
55+
return ServerCommand::create('php ' . base_path('bin/react.php'))
56+
->addArgument('-s', $serverInfo);
57+
}
58+
59+
public function getInfo(): ServerInfo
60+
{
61+
return ServerInfo::create()
62+
->setHost($this->host)
63+
->setPort($this->port)
64+
->setDocumentRoot($this->documentRoot)
65+
->setRequestCallback($this->requestCallback)
66+
->setRouterScript($this->routerScript);
67+
}
68+
}

0 commit comments

Comments
 (0)