Увійти Реєстрація
Блог Серії
Кар'єра
Вакансії Компанії
Навчання
Документація Співбесіди Тестування Відео
Екосистема
Пакети Ресурси Проєкти Інструменти Події
Інше
Про нас Реклама

Фасади чи впровадження залежностей: що обрати і як це впливає на тестування?

Фасад - статичний «інтерфейс» до об'єкта з контейнера: Cache::get(), Mail::to(), Http::get(). За кулісами Cache звертається до контейнера й викликає метод справжнього об'єкта.

// фасад
final class ExchangeRates
{
    public function rate(string $currency): float
    {
        return Cache::remember("rate:$currency", 3600, fn () => Http::get(...)->json('rate'));
    }
}

// впровадження залежностей
final class ExchangeRates
{
    public function __construct(
        private CacheRepository $cache,
        private HttpFactory $http,
    ) {}
}

Тестування - обидва способи працюють. Попри статичний синтаксис, фасади Laravel підмінюються:

Cache::shouldReceive('remember')->once()->andReturn(41.5);
Http::fake(['bank.example/*' => Http::response(['rate' => 41.5])]);
Mail::fake();
Queue::fake();

Це головна відмінність від справжніх статичних класів: фасад - не глобальний стан, а точка доступу до контейнера.

Аргументи на користь впровадження залежностей:

  • явні залежності: з конструктора видно, з чим працює клас. Клас з десятком фасадів у методах може приховувати десяток залежностей;
  • «запах» розростання: конструктор з вісьмома параметрами одразу показує, що клас робить забагато; фасади ховають цю проблему;
  • незалежність від фреймворку: клас з інтерфейсами в конструкторі можна використати поза Laravel (бібліотека, пакет);
  • статичний аналіз і IDE краще розуміють впроваджені залежності.

Аргументи на користь фасадів:

  • лаконічність - особливо в контролерах, маршрутах, Blade, коді, що не перевикористовується;
  • готові фейки (Mail::fake(), Storage::fake(), Bus::fake()) з виразними перевірками;
  • ідіоматичність: документація й більшість Laravel-коду використовують фасади.

Практичний підхід, поширений у командах:

  • фасади - у «краях» застосунку: контролери, маршрути, команди, конфігурація, тести;
  • впровадження через конструктор - у класах бізнес-логіки (actions, сервіси, домен), де важлива явність залежностей;
  • не змішувати обидва підходи в одному класі без причини.

Real-time фасади (use Facades\App\Services\Rates;) дають статичний доступ до будь-якого класу - зручно, але ще більше ховають залежності.

Докладніше в документації: Laravel: фасади чи впровадження залежностей

Перевір себе

20 випадкових питань за спробу, після завершення - розбір кожної помилки

Схожі питання