konie

Dependency Injection na prostym przykładzie w PHP

Cześć! Dzisiaj na tapecie wzór projektowy wstrzykiwanie zależności. Co znajdziesz w tym wpisie:

Czym jest wstrzykiwanie zależności?

Jest to przekazywanie potrzebnej zależności poprzez argument zamiast tworzenia jej. Zanim poznałem DI, miałem zwyczaj pisać kod który w locie tworzył sobie potrzebne zależności. Przykład z życia wzięty:

Jak byś przetestował tą klasę? Ja widzę tylko jedną opcję:

  1. Tworzysz nową instancję,
  2. Za jej pomocą wgrywasz plik na S3,
  3. Weryfikujesz czy plik został wgrany na S3.

Skomplikowane prawda? Wynika to z faktu że klasa jest silnie (wręcz nierozerwalnie) powiązana z klasą klienta S3. Nie możemy przekazać imitacji klienta. To powoduje następujące konsekwencje:

  • nie da się napisać testu jednostkowego – test jest integracyjny,
  • testowanie wymaga połączenia sieciowego oraz poprawnej konfiguracji S3,
  • takie test będzie trwał dużo dłużej niż prosty test jednostkowy.

Jak rozwiązać ten problem? Użyj wstrzykiwania zależności!

Jak je zaimplementować?

Tej klasie do działania potrzebna jest instancja klienta S3. Przekażę ją przez argument konstruktora:

Alternatywną opcją jest użycie settera. Dzięki temu podejściu możemy w łatwy sposób przekazać właściwą instancję klienta S3. Prawdziwą w środowisku produkcyjny a w środowisku testowym imitację.

Implementacja testu w PHPSpec:

Cały test jest bardzo prosty do napisania, trwa 93ms 🙂

Jakie ma plusy i minusy?

Zacznę od plusów:

  • ułatwia a czasem wręcz umożliwia pisanie testów jednostkowych,
  • rozluźnia powiązanie między klasami, w przypadku użycia interfejsów czy klas abstrakcyjnych powiązanie jest jeszcze słabsze,
  • wyprowadzania logikę tworzącą obiekty w inne miejsca

Minusy:

  • gdzieś te obiekty trzeba stworzyć, w prostych projektach tworzę klasy fabryki, w większych zdecydowanie polecam użycie kontenera wstrzykiwania zależności,
  • kod może się wydawać trudniejszy do zrozumienia.

Linki

Jedna myśl do “Dependency Injection na prostym przykładzie w PHP”

Dodaj komentarz

Twój adres email nie zostanie opublikowany. Pola, których wypełnienie jest wymagane, są oznaczone symbolem *