amphp/http-server-router

基于HTTP方法和路径将路由映射到请求处理程序,适用于amphp/http-server。

资助包维护!
amphp

v2.0.0 2023-08-05 19:16 UTC

README

AMPHP是一组为PHP设计的事件驱动库集合,考虑到纤程和并发。此包提供了一个基于请求路径和方法的amphp/http-server路由请求处理程序,使用FastRoute

安装

此包可以作为Composer依赖项安装。您应将amphp/http-server指定为单独的依赖项。

composer require amphp/http-server-router

用法

Router实现RequestHandler,由HttpServer使用以处理传入的请求。传入请求通过Router根据请求路径路由到其他RequestHandler

可以使用addRoute($method, $uri, $requestHandler)方法定义路由。

public function addRoute(
    string $method,
    string $uri,
    RequestHandler $requestHandler
): void

匹配的路由参数作为关联数组在请求属性中的Amp\Http\Server\Router键中可用。请阅读FastRoute关于如何定义占位符的文档

中间件

您可以使用addMiddleware($middleware)将所有路由堆叠在具有公共中间件集的中间件上。每个中间件按照addMiddleware()调用的顺序调用。对于后备处理程序,路由器将不会调用任何中间件。

public function addMiddleware(Middleware $middleware): void

注意可以通过在将RequestHandler传递给addRoute()之前使用Amp\Http\Server\Middleware\stackMiddleware()来添加按路由中间件。

后备

如果没有路由匹配请求路径,您可以指定另一个RequestHandler实例来处理任何不匹配的路由。如果没有提供后备处理程序,将使用提供给Router构造函数的ErrorHandler实例返回404响应。

public function setFallback(RequestHandler $requestHandler): void

注意当请求转发到后备处理程序时,由Router::addMiddleware()定义的中间件将不会调用。请使用Amp\Http\Server\Middleware\stackMiddleware()来包裹后备请求处理程序所需的任何中间件。

示例

use Amp\Http\HttpStatus;
use Amp\Http\Server\DefaultErrorHandler;
use Amp\Http\Server\Request;
use Amp\Http\Server\RequestHandler\ClosureRequestHandler;
use Amp\Http\Server\Response;
use Amp\Http\Server\Router;
use Amp\Http\Server\SocketHttpServer;

// $logger is an instance of a PSR-3 logger.
$server = SocketHttpServer::createForDirectAccess($logger);
$errorHandler = new DefaultErrorHandler();

$router = new Router($server, $logger, $errorHandler);

$router->addRoute('GET', '/', new ClosureRequestHandler(
    function () {
        return new Response(
            status: HttpStatus::OK,
            headers: ['content-type' => 'text/plain'],
            body: 'Hello, world!',
        );
    },
));

$router->addRoute('GET', '/{name}', new ClosureRequestHandler(
    function (Request $request) {
        $args = $request->getAttribute(Router::class);
        return new Response(
            status: HttpStatus::OK,
            headers: ['content-type' => 'text/plain'],
            body: "Hello, {$args['name']}!",
        );
    },
));

$server->expose('0.0.0.0:1337');

$server->start($router, $errorHandler);

// Serve requests until SIGINT or SIGTERM is received by the process.
Amp\trapSignal([SIGINT, SIGTERM]);

$server->stop();

完整的示例可以在examples/hello-world.php中找到。

php examples/hello-world.php

限制

Router会在匹配之前解码URI路径。这也会解码任何正斜杠(/),这可能导致对编码斜杠的URI的意外匹配。默认情况下,FastRoute占位符通过斜杠分隔路径段进行匹配。这意味着类似于/token/{token}的路由不会匹配,如果token包含编码斜杠。您可以通过使用自定义正则表达式来绕过此限制,例如/token/{token:.+}

安全

如果您发现任何与安全相关的漏洞,请使用私人安全漏洞报告员而不是公共问题跟踪器。

许可证

MIT许可证(MIT)。更多信息请参阅许可证