Wyobraźmy sobie, że mam Grupy i Użytkowników, a gdy użytkownik chce dołączyć do grupy, dzwonię do metody groupsService.AddUserToGroup (grupa, użytkownik). W DDD powinienem zrobić group.JoinUser (użytkownik), który wygląda całkiem nieźle.
Ale DDD zachęca również do korzystania z usług (bezstanowych) do wykonywania zadań, jeśli dane zadanie jest zbyt złożone lub nie pasuje do modelu jednostki. Można mieć usługi w warstwie domeny. Ale usługi w warstwie domeny powinny obejmować wyłącznie logikę biznesową. Z drugiej strony zadania zewnętrzne i logika aplikacji (np. Wysyłanie wiadomości e-mail) powinny korzystać z usługi domeny w warstwie aplikacji, w której na przykład można mieć oddzielną usługę (aplikację) do jej pakowania.
Problem pojawia się, jeśli istnieją pewne reguły sprawdzania poprawności dotyczące dodawania użytkownika ...
Reguły sprawdzania poprawności należą do modelu domeny! Powinny być zamknięte w obiektach domeny (byty itp.).
... lub niektóre zadania zewnętrzne należy uruchomić, gdy użytkownik zostanie dodany do grupy. Wykonywanie tych zadań spowoduje, że jednostka będzie miała zewnętrzne zależności.
Chociaż nie wiem, o jakim zewnętrznym zadaniu mówisz, zakładam, że jest to coś w rodzaju wysłania wiadomości e-mail itp. Ale to nie jest tak naprawdę część twojego modelu domeny. Powinien żyć w warstwie aplikacji i być tam obsługiwany. W warstwie aplikacji możesz mieć usługę, która działa na usługach domenowych i jednostkach do wykonywania tych zadań.
Ale fakt, że Jednostka zależy od niektórych zewnętrznych usług / klas, nie wydaje mi się tak dobry i „naturalny”.
To jest nienaturalne i nie powinno się dziać. Podmiot nie powinien wiedzieć o rzeczach, za które nie jest odpowiedzialny. Usługi powinny być wykorzystywane do koordynowania interakcji między jednostkami.
Jaki jest właściwy sposób radzenia sobie z tym w DDD?
W twoim przypadku związek powinien być prawdopodobnie dwukierunkowy. To, czy użytkownik dołączy do grupy, czy grupa zabiera użytkownika, zależy od Twojej domeny. Czy użytkownik dołącza do grupy? Czy użytkownik został dodany do grupy? Jak to działa w Twojej domenie?
W każdym razie masz relację dwukierunkową, dzięki czemu możesz określić liczbę grup, do których użytkownik należy już w ramach agregacji użytkowników. To, czy przekażesz użytkownika do grupy, czy grupę do użytkownika, jest technicznie trywialne po ustaleniu klasy odpowiedzialnej.
Jednostka powinna następnie przeprowadzić walidację. Cała sprawa jest wywoływana z usługi warstwy aplikacji, która może również robić rzeczy techniczne, takie jak wysyłanie wiadomości e-mail itp.
Jeśli jednak logika sprawdzania poprawności jest naprawdę złożona, usługa domeny może być lepszym rozwiązaniem. W takim przypadku należy zawrzeć w nim reguły biznesowe, a następnie wywołać je z poziomu warstwy aplikacji.
Podejdę do problemu sprawdzania poprawności w następujący sposób: Utwórz usługę domenową o nazwie
MembershipService
:Należy wstrzyknąć podmiotowi z Grupy
IMemberShipService
. Można to zrobić na poziomie klasy lub metody. Załóżmy, że robimy to na poziomie metody.Usługa aplikacji:
GroupService
można wstrzykiwać zaIMemberShipService
pomocą wstrzykiwania konstruktora, który następnie można przekazać doJoinUser
metodyGroup
klasy.źródło