Skip to content

Commit 80b01b4

Browse files
committed
Initial version
0 parents  commit 80b01b4

File tree

3 files changed

+158
-0
lines changed

3 files changed

+158
-0
lines changed

LICENSE

+21
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
The MIT License (MIT)
2+
3+
Copyright (c) 2018 Niels Theen
4+
5+
Permission is hereby granted, free of charge, to any person obtaining a copy
6+
of this software and associated documentation files (the "Software"), to deal
7+
in the Software without restriction, including without limitation the rights
8+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9+
copies of the Software, and to permit persons to whom the Software is furnished
10+
to do so, subject to the following conditions:
11+
12+
The above copyright notice and this permission notice shall be included in all
13+
copies or substantial portions of the Software.
14+
15+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
21+
THE SOFTWARE.

examples/01-define-api.php

+25
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
<?php
2+
3+
require_once '../vendor/autoload.php';
4+
5+
$loop = \React\EventLoop\Factory::create();
6+
7+
$server = new \Legionth\React\Http\Rest\Server();
8+
9+
$server->get('/say/hello', function (\Psr\Http\Message\ServerRequestInterface $request, callable $next) {
10+
return new \React\Http\Response(200, array(), 'hello');
11+
});
12+
13+
$server->post('/say/:word', function (\Psr\Http\Message\ServerRequestInterface $request, callable $next) {
14+
$word = $request->getQueryParams()['word'];
15+
16+
return new \React\Http\Response(200, array(), 'You said: ' . $word);
17+
});
18+
19+
$socket = new \React\Socket\Server(isset($argv[1]) ? $argv[1] : '0.0.0.0:0', $loop);
20+
21+
$server->listen($socket);
22+
23+
echo 'Listening on ' . str_replace('tcp:', 'http:', $socket->getAddress()) . PHP_EOL;
24+
25+
$loop->run();

src/Server.php

+112
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,112 @@
1+
<?php
2+
3+
namespace Legionth\React\Http\Rest;
4+
5+
use Psr\Http\Message\RequestInterface;
6+
use Psr\Http\Message\ServerRequestInterface;
7+
use RingCentral\Psr7\Response;
8+
9+
class Server
10+
{
11+
/**
12+
* @var array
13+
*/
14+
private $functions;
15+
16+
public function listen(\React\Socket\Server $socket)
17+
{
18+
$middleWareFunctions = array();
19+
20+
foreach ($this->functions as $httpMethod => $pathFunctionArray) {
21+
foreach ($pathFunctionArray as $path => $function) {
22+
$middleWareFunctions[] = $this->createRestfulFunction($httpMethod, $path, $function);
23+
}
24+
}
25+
26+
$middleWareFunctions[] = function (ServerRequestInterface $request) {
27+
return new Response(404);
28+
};
29+
30+
$httpServer = new \React\Http\Server($middleWareFunctions);
31+
32+
$httpServer->listen($socket);
33+
}
34+
35+
public function get(string $path, callable $callable)
36+
{
37+
$this->functions['get'][$path] = $callable;
38+
}
39+
40+
public function post(string $path, callable $callable)
41+
{
42+
$this->functions['post'][$path] = $callable;
43+
}
44+
45+
public function put(string $path, callable $callable)
46+
{
47+
$this->functions['put'][$path] = $callable;
48+
}
49+
50+
public function delete(string $path, callable $callable)
51+
{
52+
$this->functions['delete'][$path] = $callable;
53+
}
54+
55+
public function head(string $path, callable $callable)
56+
{
57+
$this->functions['head'][$path] = $callable;
58+
}
59+
60+
public function options(string $path, callable $callable)
61+
{
62+
$this->functions['options'][$path] = $callable;
63+
}
64+
65+
public function connect(string $path, callable $callable)
66+
{
67+
$this->functions['connect'][$path] = $callable;
68+
}
69+
70+
public function trace(string $path, callable $callable)
71+
{
72+
$this->functions['trace'][$path] = $callable;
73+
}
74+
75+
/**
76+
* @param $httpMethod
77+
* @param $path
78+
* @param $function
79+
* @return \Closure
80+
*/
81+
private function createRestfulFunction($httpMethod, $path, $function)
82+
{
83+
return function (RequestInterface $request, callable $next) use ($httpMethod, $path, $function) {
84+
if ($request->getMethod() === strtoupper($httpMethod)) {
85+
$requestPath = $request->getUri()->getPath();
86+
$requestPathArray = explode('/', $requestPath);
87+
$pathArray = explode('/', $path);
88+
89+
if (count($requestPathArray) !== count($pathArray)) {
90+
return $next($request);
91+
}
92+
93+
$queryParams = $request->getQueryParams();
94+
95+
foreach ($pathArray as $id => $valueName) {
96+
$position = strpos($valueName, ':');
97+
if (0 === $position) {
98+
$valueName = substr($valueName, 1);
99+
$queryParams[$valueName] = $requestPathArray[$id];
100+
}
101+
}
102+
103+
$request = $request->withQueryParams($queryParams);
104+
105+
return $function($request, $next);
106+
}
107+
108+
return $next($request);
109+
};
110+
}
111+
}
112+

0 commit comments

Comments
 (0)