fbpx
devstyle.pl - Blog dla każdego programisty
devstyle.pl - Blog dla każdego programisty
3 minut

DI: Kilka refleksji po wprowadzonych zmianach


03.09.2015

Po dość znacznej przerwie powracamy jeszcze na chwilę do tematu Dependency Injection. Pamiętacie cykl i moment, do którego dotarliśmy? Zastosowaliśmy SRP by uprościć kod. Wprowadziliśmy jawne zależności między komponentami i ubraliśmy je w interfejsy. Spróbowaliśmy napisać własny kontener Dependency Injection, a potem zobaczyliśmy dlaczego lepiej użyć jednak czegoś gotowego. I stanęło na Autofac, kiedy to obiecałem “kilka finalnych refleksji”. Oto one.

Czy jest lepiej?

Tak, zdecydowanie można stwierdzić, że JEST lepiej. Po porównaniu kodu początkowego z kodem finalnym (tag demo5-start) aż dziw bierze, że tak proste zabiegi mogą mieć tak pozytywny efekt.

Zwiększyliśmy czytelność: zamiast jednej wielkiej klasy mamy teraz kilka mniejszych, mieszczących się na jednym ekranie. Takie komponenty łatwo jest przeczytać i zrozumieć. Szczerze mówiąc zwykle staram się pisać klasy w ten właśnie sposób: by całość mieściła się na jednym ekranie. Czy mam wtedy dużo klas? Tak! Czy to coś złego? Tu można dywagować, ale: u mnie się sprawdza.

Dzięki poprzedniemu zabiegowi: wprowadziliśmy testy. Znaleźliśmy nawet buga bez uruchamiania systemu i… poprawiliśmy go! O tym jak bardzo istotne są testy automatyczne dzisiaj rozpisywać się nie będę, ale: wiadomo jak jest :). Pokrycie testami pierwotnego kodu było średnio możliwe.

Wszystkie zastosowane zabiegi miały wpłynęły pozytywnie na najważniejszą cechę oprogramowania: stało się ono bardziej utrzymywalne! Do tego dążymy, o to dbamy, tym się jaramy i to nas kręci ;).

Ale…

Czy jest idealnie?

Nigdy nie jest idealnie :). Niestety, w aktualnej postaci nie jest nawet “wystarczająco dobrze“.

Spójrzmy na kawałek naszego UsersController:

public UsersController (
    IEmailValidator emailValidator,
    IActivationLinkGenerator activationLinkGenerator,
    IEmailService emailService
)
    {
        _emailValidator = emailValidator;
        _activationLinkGenerator = activationLinkGenerator;
        _emailService = emailService;
    }

https://github.com/maniserowicz/di-talk/blob/demo5-start/src/app/UsersController.cs

Co oczom naszym się ukazuje? Ano konstruktor. Z iloma zależnościami? Z trzema. Czy to dużo? Jak zwykle: “to zależy”. Trzy zależności zwykle “ujdą”, ale tutaj mamy do czynienia z zabawną sytuacją: kontroler potrzebuje do działania prawie wszystkich innych komponentów w systemie! Code-smell jak nic.

Wiecie dlaczego zostawiłem kod w takiej postaci i nie ciągnąłem refactoringu? Bo na dłuższą metę to nie ma sensu. Jeśli będziemy podążać tą drogą to i tak na końcu wylądujemy z brzydkim kontrolerem. “Kontrolerem-orchestratorem”. Jego jedyną odpowiedzialnością będzie przyjęcie X zależności i wywoływanie metod w odpowiedniej kolejności. “Przecież dokładnie do tego służy kontroler!” – mógłby ktoś zakrzyknąć. I z jednej strony: będzie miał rację. A z drugiej: kontrolery w MVC są bytem sztucznym i zbędnym (ale o tym innym razem).

W celu podniesienia jakości tego kodu jeszcze bardziej trzeba zmienić trochę podejście. “Wyewoluować” od standardowego MVC… trochę dalej. Wprowadzić do systemu pojęcie “komend”. I “zdarzeń”. Już wiadomo o czym mówię, o co chodzi, prawda? Naturalną konsekwencją mojej prezentacji o Dependency Injection było przygotowanie kolejnej, tym razem o CQRS. I tego tematu możecie wkrótce spodziewać się na blogu.

0 0 votes
Article Rating
11 Comments
Oldest
Newest Most Voted
Inline Feedbacks
View all comments
trackback
8 years ago

DI: Kilka refleksji po wprowadzonych zmianach

Dziękujemy za dodanie artykułu – Trackback z dotnetomaniak.pl

Maciej Nowicki
Maciej Nowicki
8 years ago

Cześć Maciej!

Po pierwsze miło zobaczyć nowy, techniczny wpis na blogu po wakacyjnym odwyku :)! Gratuluje również nowego Layoutu (widziałem już pare dni temu, ale nie było gdzie zostawić komentarza) – krok w bardzo dobrą stronę, bo stary mimo, że dawał poczucie profesjonalizmu (coś a’la ‘nie mam czasu na fajerwerki, zajmuję się poważnymi rzeczami’ ;) ) to byl już trochę zbyt przestarzały.

Co prawda zajmuję się głównie desktopowym .NETem, ale bardzo zaciekawiło mnie Twoje spostrzeżenie odnośnie wirtualności kontrolerów, idealnie wpasowałeś się w moje ostatnie rozważania na temat zastosowania kontrolerów wraz ze wzorcem MVVM. Jakiś czas temu, w ramach prób przekonania się do aplikacji webowych testowałem zastosowanie VM w MVC (dla zainteresowanych: http://www.edandersen.com/2013/05/30/asp-net-mvc-basics-part-2-viewmodel-to-model-mapping-and-editing/) i pozytywne wrażenia z tego eksperymentu zachęciły mnie to do eksperymentownia z architekturą aplikacji. Zasiałeś ziarno niepewnosci i muszę się dobrze zastanowić, czy zmierzam w dobrym kierunku.

Pozdrawiam,
Maciek

@rek
8 years ago

Aż sie prosi o fasadę do prawdziwej aplikacji. Kontroler powinien zawierać cały shit związany z HTTP czyli odp rediredty, status codey itp, to ze ma wziąć/wziasc z tej czy innej klasy to już logika aplikacji.

Ja bym widział w tej fasadzie use caseowe metody w stylu generate link , send e-mail. Fasada powinna jednoznacznie mowić co róbi aplikacja. Kontroler zaś tylko tłumaczy generyczna aplikacje na świat HTTP

@rek
8 years ago

Tak, śledziłem. Widziałem również prezentację. No właśnie o to mi chodzi, jeszcze mniej a nie bardziej. :)

https://gist.github.com/abenedykt/2f4dd0c64d8a13d4f6c5

Możemy o tym pogadać w realu (za tydzień będzie okazja :))

ja
ja
8 years ago

A kiedyw końcu obiecany tekst o CQRS? :)

Patryk
8 years ago

Mocno się zdziwiłem jak wpadłem w nowy layout. Myślałem, że znajduje się na jakimś blogu kulinarnym :).
Wracając do root tematu, jak pozbyć się nadmiarowości w konstruktorze ? Jestem amatorem i często mój kontroler puchnie z uwagi na rozszerzająca się funkcjonalność, co skutkuje pojawianiem się coraz większej ilości serwisów w konstruktorze.

Kurs Gita

Zaawansowany frontend

Szkolenie z Testów

Szkolenie z baz danych

Książka

Zobacz również