ircmaxell / tari-php
A Middleware Proof-Of-Concept Library For PHP
Installs: 1 185
Dependents: 0
Suggesters: 0
Security: 0
Stars: 78
Watchers: 12
Forks: 3
Open Issues: 1
Requires
- php: ^7
- psr/http-message: ^1.0
Requires (Dev)
- guzzlehttp/psr7: ^1.3
- phpunit/phpunit: ^5.3
This package is auto-updated.
Last update: 2024-09-20 00:56:27 UTC
README
A PSR-7 Middleware Interface proof-of-concept for PHP.
Requirements
- PHP 7.0
Yes, that's the only hard requirement
Usage As An End User
To use this runner, you need to pick a PSR-7 Library. We'll use Guzzle's.
First, install it: composer require guzzle/psr7
Now, we need a factory instance for the PSR-7 Library;
$factory = new Tari\Adapter\Guzzle\Factory;
Next, we boot up the "Server":
$server = new Tari\Server($factory);
Next, append whatever middleware we want to. In this case, let's add the error handler and the HSTS middleware:
$server->append(new Tari\ServerMiddleware\ErrorHandler); $server->append(new Tari\ServerMiddleware\HSTS(300 /* Max-age in seconds */));
We can also add middleware as closures (Notice we don't need types):
$server->append(function($request, $frame) { $response = $frame->next($request); return $response->withHeader('X-Powered-By', 'Tari-PHP'); });
We also need a "default" action to take:
$default = function($request) use ($factory) { // Default to a 404 NOT FOUND response return $factory->createResponse("Not Found", 404); };
Finally, we can run out stack:
$request = new Guzzle\Psr7\ServerRequest("http://www.example.com/foo", "GET"); $response = $server->run($request, $default);
And that's all there is to it...
Usage As A Library Builder (Server Mode)
To use this middleware as a library author, simply implement the Tari\MiddlewareInterface
interface. It's as easy as that:
use Tari\ServerMiddlewareInterface; use Tari\ServerFrameInterface; use Psr\Http\Message\ServerRequestInterface; use Psr\Http\Message\ResponseInterface; class Foo implements ServerMiddlewareInterface { public function handle(ServerRequestInterface $request, ServerFrameInterface $frame): ResponseInterface { // Do your modifications to the request here $response = $frame->next($request); // Do your modifications to the response here return $response; } }
It's as simple as that.
Aborting a request
Sometimes, you don't want to continue with a request. If you detect that situation in your middleware, simply create a new response:
use Tari\ServerMiddlewareInterface; use Tari\ServerFrameInterface; use Psr\Http\Message\ServerRequestInterface; use Psr\Http\Message\ResponseInterface; class Foo implements ServerMiddlewareInterface { public function handle(ServerRequestInterface $request, ServerFrameInterface $frame): ResponseInterface { if ($this->isBadRequest($request)) { return $frame->factory()->createResponse("Bad Request", 400); } return $frame->next($request); } }
Interfaces
Tari defines 3 consumable interfaces:
ServerMiddlewareInterface
interface ServerMiddlewareInterface { public function handle(ServerRequestInterface $request, ServerFrameInterface $frame): ResponseInterface; }
Used for Server request processing
ServerFrameInterface
interface ServerFrameInterface { public function next(ServerRequestInterface $request): ResponseInterface; public function factory(): FactoryInterface; }
This is used for processing server requests
FactoryInterface
interface FactoryInterface { public function createRequest( UriInterface $uri = null, string $method = '', array $headers = [], $body = null ): RequestInterface; public function createServerRequest( UriInterface $uri = null, string $method = '', array $headers = [], $body = null ): ServerRequestInterface; public function createResponse( int $status = 200, array $headers = [], $body = null ): ResponseInterface; public function createStream($data = null): StreamInterface; public function createUri(string $uri = ''): UriInterface; public function createUploadedFile( $data, int $size, int $error, string $clientFile = '', string $clientMediaType = '' ): UploadedFileInterface; }
There's a lot more going on here, but it's still extremely straight forward and simple.
Each method creates a PSR-7 object, and initializes it.
License
MIT