Middleware IO7
Внимание
Данная статья документации написана нейросетью. Возможны некоторые расхождения и неточность информации!
Middleware выполняется до и после обработчика маршрута. Каждый middleware реализует интерфейс IO\Middleware.
Интерфейс IO\Middleware
namespace IO;
interface Middleware
{
public function handle(App $app, ?Route $route, array $params = []): mixed;
public function terminate(App $app, ?Route $route, mixed $response, array $params = []): void;
}
handle()
Вызывается до обработчика маршрута.
| Параметр | Тип | Значение по умолчанию | Обязателен | Описание |
|---|---|---|---|---|
$app | App | — | Да | Экземпляр приложения |
$route | ?Route | null | Нет | Экземпляр маршрута (null при вызове из конфигурации) |
$params | array | [] | Нет | Параметры middleware |
Возвращает: null (продолжить) или array|string (прервать выполнение).
terminate()
Вызывается после обработчика маршрута.
| Параметр | Тип | Значение по умолчанию | Обязателен | Описание |
|---|---|---|---|---|
$app | App | — | Да | Экземпляр приложения |
$route | ?Route | null | Нет | Экземпляр маршрута |
$response | mixed | — | Да | Ответ маршрута |
$params | array | [] | Нет | Параметры middleware |
Создание middleware
namespace App\Middlewares;
use IO\App;
use IO\Middleware;
use IO\Route;
class MyMiddleware implements Middleware
{
public function handle(App $app, ?Route $route, array $params = []): mixed
{
$token = $params['token'] ?? '';
if ($token !== 'valid') {
return ['error_code' => 403, 'error_str' => 'Forbidden'];
}
$route->set('authorized', true);
return null;
}
public function terminate(App $app, ?Route $route, mixed $response, array $params = []): void
{
// Логирование, очистка кеша и т.д.
}
}
Подключение middleware
В конфигурации маршрута
$app->add_route([
'url' => '/admin/dashboard',
'type' => ['get'],
'class_name' => \App\Routes\AdminRoute::class,
'method' => 'index',
'middleware' => [
\IO\Middlewares\AuthMiddleware::class,
\App\Middlewares\AdminCheck::class,
],
]);
С параметрами:
$app->add_route([
'url' => '/api/data',
'type' => ['get'],
'class_name' => \App\Routes\ApiRoute::class,
'method' => 'getData',
'middleware' => [
\IO\Middlewares\ThrottleMiddleware::class => ['requests' => 100, 'window' => 3600],
],
]);
Через Route::addMiddleware()
class AdminRoute extends \IO\Route
{
public function init(): void
{
$this->addMiddleware(\App\Middlewares\AuditMiddleware::class, [
'log_level' => 'info',
]);
parent::init();
}
public function dashboard(): \IO\Response
{
// ...
}
}
Встроенные middleware
AuthMiddleware
Проверка авторизации.
use IO\Middlewares\AuthMiddleware;
// С редиректом на страницу логина
$middleware = new AuthMiddleware('/login');
// С JSON-ответом (для API)
$middleware = new AuthMiddleware('/login', true);
Данные в контексте маршрута:
| Ключ | Описание |
|---|---|
user | Данные пользователя |
user_id | ID пользователя |
user_login | Логин пользователя |
permissions | Разрешения (кабинеты) |
current_account | Текущий аккаунт |
current_cabinet | Текущий кабинет |
class AdminRoute extends \IO\Route
{
public function index(): \IO\Response
{
$user_id = $this->get('user_id');
$user = $this->get('user');
// ...
}
}
ThrottleMiddleware
Троттлинг запросов по пользователям/IP.
use IO\Middlewares\ThrottleMiddleware;
$middleware = new ThrottleMiddleware([
'default' => ['requests' => 100, 'window' => 3600], // 100/час
'auth' => ['requests' => 20, 'window' => 60], // 20/мин
'api' => ['requests' => 500, 'window' => 3600], // 500/час
]);
Заголовки ответа:
| Заголовок | Описание |
|---|---|
X-RateLimit-Limit | Максимум запросов |
X-RateLimit-Remaining | Оставшиеся запросы |
X-RateLimit-Reset | Время сброса лимита |
CorsMiddleware
Обработка CORS-запросов.
use IO\Middlewares\CorsMiddleware;
$middleware = new CorsMiddleware('myproject', ['https://example.com']);
Другие встроенные middleware
| Класс | Описание |
|---|---|
SecurityHeadersMiddleware | Безопасные HTTP-заголовки |
CacheMiddleware | HTTP-кэширование |
CsrfMiddleware | Защита от CSRF |
LoggingMiddleware | Логирование запросов |
PerformanceMiddleware | Замер производительности |
RequestIdMiddleware | Уникальный ID запроса |
RateLimitMiddleware | Общий троттлинг |
SanitizeMiddleware | Очистка данных |
CompressionMiddleware | Сжатие ответа |
IpWhitelistMiddleware | Белый список IP |
MaintenanceMiddleware | Режим обслуживания |
DebugBarMiddleware | Панель отладки |
ValidationMiddleware | Валидация запросов |
Цепочка middleware
Middleware выполняются последовательно:
请求 → Middleware1::handle() → Middleware2::handle() → Маршрут → Middleware2::terminate() → Middleware1::terminate() → Ответ
Если любой middleware возвращает не-null, выполнение прерывается:
public function handle(App $app, ?Route $route, array $params = []): mixed
{
if (!$this->checkAccess()) {
return ['error_code' => 403, 'error_str' => 'Forbidden'];
}
return null;
}
Пример: полная конфигурация
$app->add_route([
'url' => '/api/admin/users',
'type' => ['get', 'post'],
'class_name' => \App\Routes\AdminRoute::class,
'method' => 'handle',
'middleware' => [
\IO\Middlewares\CorsMiddleware::class,
\IO\Middlewares\AuthMiddleware::class,
\IO\Middlewares\ThrottleMiddleware::class,
\App\Middlewares\AdminCheck::class,
],
]);
Запрос → CorsMiddleware → AuthMiddleware → ThrottleMiddleware → AdminCheck → AdminRoute::handle()