Задать вопрос

Правильный ли пример реализации middleware?

Правильный ли пример реализации middleware?

Тестовый класс middleware
spoiler

namespace App\Middleware;

use Engine\Core\Middleware\MiddlewareInterface;
use Psr\Http\Message\ResponseInterface;
use Psr\Http\Message\ServerRequestInterface;

class Test implements MiddlewareInterface
{
    public function handle(ServerRequestInterface $request, $params)
    {
        die('OK');
    }
}



Он реализует интерфейс
spoiler

namespace Engine\Core\Middleware;

use Psr\Http\Message\ResponseInterface;
use Psr\Http\Message\ServerRequestInterface;

interface MiddlewareInterface
{
    public function handle(ServerRequestInterface $request, $params);
}



Кратко о жизненном цикле
5d1c85e98491a004295980.jpeg
Предположим, я создал контроллер Для получения некой секретной информации о пользователе.
Параллельно я создал отдельный класс для проверки JWT в специальной папке с Middleware классами.

В конструкторе контроллера, я прописываю следующее:
public function __construct(DI $di)
    {
        $this->middleware->execute( Verification::class, []);
    }

Далее
namespace App\Middleware;

use Engine\Core\Middleware\MiddlewareInterface;
use Psr\Http\Message\ResponseInterface;
use Psr\Http\Message\ServerRequestInterface;

class Verification implements MiddlewareInterface
{
    public function handle(ServerRequestInterface $request, $params)
    {
        die('Не прошёл проверку'); // die для демонстрации (защита от хейтеров)
    }
}

Некоторые детали.
При регистрации классов Middleware, не происходит инициализация и создание объекта.
Инициализация происходит в момент вызова контроллера.

А вот основной класс, который занимается инициализацией Middleware
spoiler

namespace Engine\Core\Middleware;

class Middleware
{
    private $container = [];

    public function registration(string $class)
    {
        if (!$this->has($class)) {
            $this->container[] = $class;
        }
    }

    public function has(string $class): bool
    {
        return in_array($class, $this->container);
    }

    public function execute(string $class, $arg = [])
    {
        if ($this->has($class)) {
            if (class_exists($class)) {
                $ObjectMiddleware = new $class();
            }

            /** @var MiddlewareInterface $ObjectMiddleware */
            $ObjectMiddleware->handle(new ServerRequest(), $arg);
        }
    }
}


Хоть отдалённо похоже на некое решение промежуточного ПО.
  • Вопрос задан
  • 992 просмотра
Подписаться 9 Простой 16 комментариев
Пригласить эксперта
Ответы на вопрос 1
@EvgeniiR
https://github.com/EvgeniiR
Мало что можно сказать по паре десятков строчек кода, даже без гитхаба с проектом. Пара примечаний:

1. Очень смущает парметр $args в методе execute(). Массив, типы и элементы внутри которого не определены, потенциальный источник многих проблем.
2. Зачем прокидывать DI в контроллер?

И совет - попробуйте psalm. Ставится и запускается на дефолтных настройках в два клика, позволит избегать огромного количества проблем с типами, и понимать где проблемы, никакие обращения к необъявленным явно элементам в массиве там уже не прокатят
Ответ написан
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Похожие вопросы