Zwiększ przejrzystość swojego monolitu dzięki ograniczonym kontekstom
sprawdź wideo z tego wykładu z ElixirConf 2017 poniżej
Aplikacje monolityczne są świetne, gdy zaczynasz budować swoją firmę, ale w miarę upływu czasu stają się trudne do utrzymania. Te kody, w miarę wzrostu, łatwo stają się dużymi kulami błota.
podczas budowania dużych aplikacji w frameworkach, takich jak Rails, zasady projektowania konwencyjnego nadkonfiguracji, które sprawiły, że Rails cieszyły się z używania, zaczynają przeszkadzać, gdy aplikacja rośnie w zasięgu. Możesz odczuwać te same bóle, jak również, jeśli:
- Refaktoryzacja jest trudna i żmudna, Ponieważ Metody i klasy zależą od zbyt wielu innych klas
- masz ciągle rosnącą listę obiektów biznesowych, które są trudne do utrzymania w głowie. W rzeczywistości wydaje się, że nikt nie jest w stanie zrozumieć systemu jako spójnej całości
- zmiana kodu w jednym obszarze kodu prowadzi do nieoczekiwanych i niezamierzonych skutków ubocznych w innych obszarach kodu, ponieważ łatwo jest wywołać globalne usługi i Obiekty
w naszym ostatnim wspólnym czacie omówiliśmy opracowanie wszechobecnego języka wraz z ekspertami biznesowymi i zespołem programistów, aby pomóc zespołowi w ściślejszej współpracy. Dzisiaj zamierzamy na tym skorzystać, wprowadzając nowe narzędzia do projektowania opartego na domenach (DDD). Następnie Przedstawimy nową strukturę folderów dla Twoich aplikacji Rails, przygotowując je na przyszłość, w której Twoja aplikacja będzie mniej powiązana i bardziej spójna. Zaczynajmy!
- porozmawiajmy o domenach
- ograniczone konteksty w przestrzeni rozwiązań
- wielki pomysł: Uporządkuj kod Rails w Moduły według subdomeny biznesowej
- Odwróć struktury folderów w płaskie grupowanie zorientowane na domenę
- Modulizuj klasy
- odwoływanie się do powiązanych modeli według pełnej nazwy klasy
- Informuj Kontrolery na bieżąco o tym, gdzie znaleźć ich nowo modulizowane widoki
- co dobrze działa z takim podejściem?
- czego się nauczyliśmy?
porozmawiajmy o domenach
kluczową zasadą w DDD jest to, że oprogramowanie, które tworzysz, musi ściśle odzwierciedlać domenę (biznesową) organizacji, która ją buduje. W związku z tym musimy odrobić trochę pracy domowej, aby zrozumieć domenę biznesową Twojego oprogramowania.
domena jest tym, co robi Firma, i kontekstem tego, jak to robi.
wróćmy do naszego przykładu Delorean z poprzedniego postu. W nim firma jest sprzedawana jako Uber dla wycieczek w czasie. Stąd jego” domeną “(“tym co czyni”) jest podróżowanie w czasie. W domenie znajduje się również “jak” tego, jak to robi – współpracując z kierowcami, którzy posiadają Pojazdy Delorean podróżujące w czasie z pasażerami, którzy chcą odbyć podróże w czasie.
aby uzyskać więcej niuansów w domenie biznesowej, DDD wprowadza inną koncepcję, zwaną subdomeną:
subdomena reprezentuje mniejsze grupy lub jednostki firmy, które współpracują na co dzień, aby osiągnąć cele biznesowe.
Delorean jest podzielony na kilka zespołów w firmie. Przyjrzyjmy się dwóm z nich i zobaczmy, za co są odpowiedzialni:
zespół platformy Trip | zespół operacji finansowych | |
---|---|---|
misja | Projektowanie i obsługa systemów, które wyznaczają trasy podróży i łączą kierowców z pasażerami | Zarządzanie systemami, które angażują instytucje finansowe i podmioty przetwarzające Karty kredytowe |
obowiązki |
|
|
każda z tych dwóch grup animuje odpowiedzialność biznesową lub subdomenę. Nazwijmy je odpowiednio: Ridesharing Experience i Ecommerce.
teraz mamy ogólną ilustrację biznesu i dwóch jego jednostek, które pomagają mu funkcjonować na co dzień. Domena i subdomena to sposoby modelowania przestrzeni problemowej Twojej firmy-i tego, jak działa, aby spełnić te role. Są szanse, że wykres organizacji firmy będzie ściśle odzwierciedlał subdomeny Twojej firmy. W realnym świecie, granice mogą być mniej jasne-zespoły mogą być odpowiedzialne za wiele, nakładających się subdomen.
wypełnimy ten diagram jeszcze kilkoma subdomenami w biznesie Delorean:
- subdomena Obsługi Klienta: rozwiązywanie zgłoszeń do obsługi klienta za pośrednictwem poczty e-mail
- subdomena marketingowa: zarządzanie marketingowymi kampaniami e-mailowymi i kodami kuponów marketingowych
- subdomena tożsamości: jak system śledzi każdego użytkownika i jego dane identyfikacyjne
ograniczone konteksty w przestrzeni rozwiązań
ten diagram przed nami odzwierciedla teraz cele biznesowe firmy, podzielone na jednostki logiczne, które (miejmy nadzieję) realizują swoje cele w świecie rzeczywistym. Teraz będziemy nakładać systemy programowe, które osiągają te cele na tym diagramie. Te systemy oprogramowania są opisane jako ograniczone konteksty:
Ograniczony kontekst to system, który realizuje cele biznesu w realnym świecie.
każdy z naszych systemów oprogramowania (takich jak usługa internetowa lub aplikacja internetowa), które działają jako konkretne instancje w świecie rzeczywistym, jest uważany za Ograniczony kontekst.
technicznie rzecz biorąc, Ograniczony kontekst w DDD-speak jest konkretną granicą w Twojej domenie, którą może zastosować tylko Twój słowniczek z twojego wszechobecnego języka – chodzi o to, że różne subdomeny mogą mieć konkurencyjne lub sprzeczne definicje terminów. Ten post nie będzie rozwijał niuansów językowych ograniczonego kontekstu. Więcej informacji można znaleźć w wyjaśnieniach Martina Fowlera dotyczących kontekstów ograniczonych.
teraz tak się składa, że w Delorean wszystkie te subdomeny są zaimplementowane w jednym systemie-jedna wielka kula szyn błotnych Monolith. Narysujemy niebieskie pole wokół subdomen, których funkcje są realizowane przez system oprogramowania. W tym przypadku zaczniemy od wspomnianego już Rails monolith:
ponieważ jest to monolit, w zasadzie robi wszystko-a więc tutaj, pożera wszystkie inne subdomeny na diagramie.
nie zapominajmy – mamy kilka innych systemów oprogramowania, których nie modelowaliśmy tutaj. A co ze wszystkimi przyjemnymi integracjami stron trzecich, z których korzysta firma? Są to również systemy programowe. Narysujemy je jako niebieskie pudełka.
przy okazji-narysowaliśmy tu mapę kontekstową-diagram łączący cele biznesowe z konkretnymi implementacjami systemów oprogramowania. Jest to przydatne do oceny położenia terenu systemów oprogramowania i wizualizacji zależności między zespołami.
teraz jest to rozsądne i czyste, ale żyjemy w prawdziwym świecie, a prawdziwe oprogramowanie rzadko wychodzi spójnie i spójnie. Jeśli zbudowałeś aplikację Rails zgodnie z jej gotowymi konwencjami, wewnętrznie nie ma w niej grup niezbędnych do wizualizacji aplikacji w jej składowych komponentach. W rzeczywistości kod Delorean wygląda mniej więcej tak:
chodzi o to, że Rails nie wymusza żadnych ograniczeń organizacyjnych na naszych systemach oprogramowania-co oznacza, że logiczne jednostki biznesowe (nasze subdomeny) sugerujące oddzielone interfejsy – nie są zmaterializowane w kodzie, co prowadzi do zamieszania i rosnącej złożoności z biegiem lat.
wielki pomysł: Uporządkuj kod Rails w Moduły według subdomeny biznesowej
mimo że Twoje klasy Ruby w Twojej aplikacji prawdopodobnie żyją w globalnej przestrzeni nazw, można je łatwo połączyć w Moduły. Naszym celem jest stworzenie logicznych grup kodu domeny, które można wyizolować w samodzielne komponenty.
jednym z celów projektów opartych na domenach jest mapowanie jeden do jednego z subdomen do ograniczonego kontekstu.
OK, co to znaczy? Przejdźmy do kilku zaleceń wraz z przykładami.
Odwróć struktury folderów w płaskie grupowanie zorientowane na domenę
możesz pamiętać, że przestrzeganie Konwencji Rails prowadzi nas do hierarchii folderów, które grupują klasy według ról:
przenieśmy wszystko do nowej struktury katalogów: grupujmy funkcjonalność według domeny. Zaczniemy od pierwszej odmiany, którą nazwałbym grupowaniem zorientowanym na domenę płaską.
Modulizuj klasy
następnie będziesz chciał modulizować klasy z tego, co były wcześniej. Ponieważ Klasa Sterownika mieści się w domenie współdzielenia przejazdów, dodamy ją do modułu współdzielenia przejazdów:
będziesz chciał to zrobić dla każdej klasy, którą przeniesiesz do płaskiej struktury katalogów app/domains
.
odwoływanie się do powiązanych modeli według pełnej nazwy klasy
dodatkowo musisz zmienić powiązania modelu ActiveRecord, aby odnosić się do klasy według pełnej, modulizowanej ścieżki:
Informuj Kontrolery na bieżąco o tym, gdzie znaleźć ich nowo modulizowane widoki
musisz również wstawić ten mały bit, aby trasy z kontrolera wiedziały, gdzie szukać widoków:
oto fajna sprawa: nie musisz przenosić całego kodu na raz. Możesz wybrać jedną małą domenę w aplikacji, najbardziej dojrzały obszar kodu lub obszar, który najlepiej rozumiesz, i zacząć przenosić swoje obawy do jednego folderu domeny, pozostawiając istniejący kod w spoczynku, dopóki nie będzie gotowy do przeniesienia.
teraz zrobiliśmy kilka małych kroków w celu osiągnięcia przejrzystości architektonicznej w naszej aplikacji. Jeśli spojrzymy teraz, nasze modułowe struktury folderów pomogły nam pogrupować nasz kod w ten sposób:
pod maską nasza aplikacja może wyglądać bardziej tak:
co dobrze działa z takim podejściem?
- w każdym katalogu plików jest mniej szumu – grupując pliki według specyfiki domeny, znajdujemy naturalny punkt organizacyjny
- encje, które pozostają w każdym folderze domeny, są wysoce spójne-najprawdopodobniej naturalnie komunikują się ze sobą i pojawiają się naturalnie ze sobą
- encje, które nie należą do siebie, są teraz oddzielone (luźniej połączone)
- jeśli masz zespoły inżynierskie, które pracują zgodnie z obowiązkami subdomeny, ci inżynierowie mogą teraz pracować w bardziej uproszczony, odizolowany sposób. Luźniejsze sprzężenie pozwala tym zespołom wprowadzać zmiany z pewnością, że nie wprowadzą regresji ani nie połączą konfliktów z powrotem do bazy kodu
- etap jest teraz ustawiony na dłuższą metę, aby rozpocząć przenoszenie każdego z tych folderów domeny do niezależnej usługi oprogramowania (więcej na ten temat w przyszłym poście na blogu)
jeśli chcesz uzyskać dalsze wskazówki dotyczące tej struktury folderów, opracowałem przykładową aplikację, która wyświetla tę zorientowaną na domenę strukturę folderów: http://github.com/andrewhao/delorean. Spójrz i daj mi znać, co myślisz.
czego się nauczyliśmy?
w naszych wspólnych czasach dowiedzieliśmy się o koncepcjach projektowania opartych na domenach wokół domen i subdomen. Nauczyliśmy się wizualizować nasze systemy jako ograniczone konteksty na mapie kontekstu, która pokazała nam obszary systemu, które należą do siebie jako spójne części.
kończąc na praktycznej notatce, zilustrowaliśmy, jak pliki i foldery Rails mogą być “odwrócone” i przekształcone jako grupy domenowe.
w moim następnym poście, będziemy kontynuować naszą dyskusję w nadchodzącym poście na blogu na temat dalszego oddzielenia naszego kodu Rails zorientowanego na domenę ze zdarzeniami domenowymi i ostatecznie udamy się do krainy mikroserwisów.