Laravel: Lead
20 питань · ~25 хв · Версія v3.0
Увійдіть, щоб продовжити
Сценарні питання: архітектурні рішення, узгодженість, деплой без простою, trade-offs.
- За спробу
- 20
- У пулі
- 100
- Проходжень
- 2
- Середній бал
- 63%
- Пройшли на 70%+
- 0%
Питання для підготовки
130 питаньОптимізація йде кількома шарами:
База даних
- Усунення N+1 (eager loading
with()), правильні індекси, аналіз черезEXPLAIN. - Read/write репліки, кешування важких запитів.
Кешування
Cache::remember()для дорогих обчислень; повне кешування сторінок/фрагментів.php artisan optimize(config/route/view/event cache), OPcache.
Фонова робота
- Винесення повільних завдань (email, обробка медіа, виклики API) у черги.
Інфраструктура
- Laravel Octane (Swoole/FrankenPHP) тримає застосунок у пам'яті.
- CDN для статики, горизонтальне масштабування за load balancer, спільні сесії/кеш у Redis.
Перед оптимізацією - профілювання (Telescope, Clockwork, Debugbar), щоб бити по реальних вузьких місцях.
- CQRS (Command Query Responsibility Segregation) розділяє запис (Commands, що змінюють стан) і читання (Queries). Read-модель можна оптимізувати окремо (денормалізовані проєкції, окрема БД).
- Event Sourcing зберігає не поточний стан, а послідовність подій; поточний стан відновлюється їх відтворенням. Дає повний аудит і «подорож у часі».
// концептуально
$aggregate->retrieve($uuid)
->placeOrder($data) // emit OrderPlaced
->persist(); // зберегти подію
У Laravel зазвичай через пакет spatie/laravel-event-sourcing (aggregates, projectors, reactors). Застосовувати варто там, де критичні аудит і складна доменна логіка - це додає суттєву складність, тож не для типового CRUD.
Шлях запиту:
public/index.php- єдина точка входу; підключає автозавантажувач Composer.- Створюється екземпляр застосунку (Service Container) із
bootstrap/app.php. - HTTP Kernel обробляє запит, завантажує Service Providers (
register→boot). - Запит проходить глобальні middleware (наприклад, обробка сесій, CSRF).
- Router зіставляє URL із маршрутом, виконуються middleware маршруту.
- Викликається контролер/замикання, формується Response.
- Відповідь проходить middleware у зворотному порядку й повертається клієнту; виконується
terminate().
Ключова ідея: контейнер і провайдери бутстрапять застосунок, а middleware утворюють «цибулю» навколо обробки запиту.
Octane запускає застосунок через high-performance сервери (Swoole, FrankenPHP, RoadRunner): фреймворк бутстрапиться один раз і тримається в пам'яті, обслуговуючи наступні запити без повторної ініціалізації.
php artisan octane:start --server=frankenphp
Це усуває оверхед завантаження на кожному запиті й дає кратний приріст RPS.
Підводні камені: оскільки процес довготривалий, треба уникати витоків стану між запитами - статичні властивості, синглтони з накопиченим станом, глобальні змінні можуть «протікати» від запиту до запиту. Octane надає хуки flush і перезапускає воркери для безпеки.
Idempotency (ідемпотентність) - багаторазове виконання операції дає той самий результат, що й однократне. Критично для платежів і повторів завдань у чергах (де доставка «at least once»).
Реалізація для API - idempotency key:
$key = $request->header('Idempotency-Key');
return Cache::lock("idem:$key")->block(5, function () use ($key) {
if ($cached = Cache::get("idem:result:$key")) {
return $cached; // повернути попередній результат
}
$result = $this->charge(); // виконати один раз
Cache::put("idem:result:$key", $result, now()->addDay());
return $result;
});
Для завдань: перевірка «вже оброблено» за унікальним ключем, ShouldBeUnique, або БД-обмеження, що відсікають дублі.
Прочитати - ще не значить знати
20 питань, по одному на екран, ~25 хв. Після завершення - розбір кожної помилки з посиланням на питання.