-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathSwooleRunner.php
More file actions
138 lines (120 loc) · 3.77 KB
/
SwooleRunner.php
File metadata and controls
138 lines (120 loc) · 3.77 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
<?php
declare(strict_types=1);
namespace Lit\Runner\Swoole;
use Lit\Bolt\BoltContainerConfiguration;
use Psr\Container\ContainerInterface;
use Psr\Http\Message\ResponseInterface;
use Psr\Http\Server\RequestHandlerInterface;
use Swoole\Http\Request;
use Swoole\Http\Response;
use Swoole\Http\Server;
use Zend\Diactoros\ServerRequest;
use Zend\Diactoros\Stream;
use function Zend\Diactoros\marshalHeadersFromSapi;
use function Zend\Diactoros\marshalUriFromSapi;
use function Zend\Diactoros\normalizeServer;
use function Zend\Diactoros\normalizeUploadedFiles;
/**
* swoole runner
*/
class SwooleRunner
{
protected const CHUNK_SIZE = 1048576;//1M
/**
* @var Server
*/
protected $swooleServer;
/**
* @var RequestHandlerInterface
*/
protected $requestHandler;
/**
* SwooleRunner constructor.
*
* @param Server $swooleServer The swoole server object.
* @param RequestHandlerInterface $requestHandler The request handler.
*/
public function __construct(Server $swooleServer, RequestHandlerInterface $requestHandler)
{
$this->swooleServer = $swooleServer;
$this->requestHandler = $requestHandler;
}
/**
* run a bolt app with swoole.
*
* @param array $config The application configuration.
*/
public static function run($config = [])
{
$container = $config instanceof ContainerInterface
? $config
: BoltContainerConfiguration::createContainer($config + SwooleConfiguration::default());
$container->get(static::class)->work();
}
protected static function emitResponse(Response $res, ResponseInterface $psrRes)
{
$res->status($psrRes->getStatusCode());
foreach ($psrRes->getHeaders() as $name => $values) {
foreach ($values as $value) {
$res->header($name, $value);
}
}
$body = $psrRes->getBody();
$body->rewind();
if ($body->getSize() > static::CHUNK_SIZE) {
while (!$body->eof()) {
$res->write($body->read(static::CHUNK_SIZE));
}
$res->end();
} else {
$res->end($body->getContents());
}
}
protected static function makePsrRequest(Request $req)
{
$server = [];
foreach ($req->server as $key => $value) {
$server[strtoupper($key)] = $value;
}
$server = normalizeServer($server);
$files = isset($req->files)
? normalizeUploadedFiles($req->files)
: [];
$cookies = isset($req->cookie) ? $req->cookie : [];
$query = isset($req->get) ? $req->get : [];
$body = isset($req->post) ? $req->post : [];
$stream = new Stream('php://memory', 'wb+');
$stream->write($req->rawContent());
$stream->rewind();
$headers = marshalHeadersFromSapi($server);
$request = new ServerRequest(
$server,
$files,
marshalUriFromSapi($server, $headers),
$server['REQUEST_METHOD'] ?? 'GET',
$stream,
$headers
);
return $request
->withCookieParams($cookies)
->withQueryParams($query)
->withParsedBody($body);
}
protected function work()
{
$this->swooleServer->on('request', [$this, 'onRequest']);
$this->swooleServer->start();
}
/**
* swoole request event handler
*
* @param Request $req The swoole reqeust.
* @param Response $res The swoole response
*/
public function onRequest(Request $req, Response $res)
{
$psrReq = static::makePsrRequest($req);
$psrRes = $this->requestHandler->handle($psrReq);
static::emitResponse($res, $psrRes);
}
}