Потрясающий новый фасад RateLimiter делает управление скоростью обработки запросов простым, масштабируемым и приятным в использовании. Подумайте о рефакторинге ваших ограничителей, если переходите на Laravel 8.
В предыдущих версиях Laravel, вплоть до 7-ой, когда нужно было ограничить скорость обработки запросов на определенных маршрутов, то это можно было сделать применив мидлвар throttle:
Route::get('admin/profile', function () {
//
})->middleware('auth', 'throttle:30,1');
Параметр 30,1 в этой конфигурации означает, что аутентифицированный пользователь может получить доступ к маршруту 30 раз в минуту. Если пользователь превысит этот лимит в течение указанного периода, то Laravel вернет ошибку 429 Too Many Requests.
Числа захардкожены и невозможно настроить их динамическое изменение или повторное использование этой настроенной конфигурации для других маршрутов.
Laravel 8 решает эти проблемы вводя фасад RateLimiter. Давайте рассмотрим его более подробно.
Фасад RateLimiter
С помощью фасада Illuminate\Support\Facades\RateLimiter вы можете задавать «именованные» ограничители скорости различных конфигураций. Поскольку у них теперь есть имена, то вы можете использовать их для разных маршрутов и их групп.
Кроме того, вы можете создать несколько ограничителей скорости для разных вариантов использования.
Ограничители прописываются в методе boot в AppServiceProvider. Например, если вам нужен ограничитель limitadmin, то вы можете сделать это так:
namespace App\Providers;
use Illuminate\Cache\RateLimiting\Limit;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\RateLimiter;
use Illuminate\Support\ServiceProvider;
class AppServiceProvider extends ServiceProvider
{
public function boot()
{
RateLimiter::for('limitadmin', function (Request $request) {
return Limit::perMinute(3);
});
}
}
Метод for в RateLimiter принимает два параметра:
- Название ограничителя скорости
- Замыкание, которое возвращает конфигурацию ограничения для маршрутов
В Замыкании вы можете вернуть фактическое ограничение скорости запросов, используя метод perMinute из Illuminate\Cache\RateLimiting\Limit, в котором вы указывается, сколько раз в минуту пользователю разрешен доступ к маршруту.
Использование именованного ограничителя скорости
После того, как вы создадите ограничитель скорости — его можно назначить маршруту:
Route::get('profile', function () {
//
})->middleware(['throttle:limitadmin']);
Как видите, вместо закардкоженной конфигурации, вы просто используете имя ограничителя. Это читабельно и доступно для многоразового использования.
Динамические ограничители
Можно создавать ограничители скорости запросов, основанные на определенных условиях.
Замыкание метода for получает объект Illuminate\Http\Request и мы можем его использовать. Например, если нужно ограничивать только обычных пользователей и не применяться к администраторам, то мы можем сделать это так:
RateLimiter::for('limitadmin', function (Request $request) {
return $request->user()->type == 'admin'
? Limit::none()
: Limit::perMinute(3);
});
Как видите, с помощью метода none() можно задать неограниченную скорость обработки запросов.
Кастомный ответ
Также, вместо стандартного 429 Too Many Requests, можно вернуть свой собственный ответ используя метод response:
RateLimiter::for('book', function (Request $request) {
return Limit::perMinute(3)->response(function() {
return new Response('Beep! Beep! Too many attempts');
});
});
Автор: Amit Merchant
Перевод: Алексей Широков
Наш Телеграм-канал — следите за новостями о Laravel.
