Logika biznesowa w MVC [zamknięte]

184

Mam 2 pytania:

Pytanie 1 Gdzie dokładnie leży „logika biznesowa” we wzorze MVC? Jestem zdezorientowany między modelem a kontrolerem.

Q2 Czy „logika biznesowa” jest taka sama jak „reguły biznesowe”? Jeśli nie, jaka jest różnica?

Byłoby wspaniale, gdybyś mógł wyjaśnić za pomocą małego przykładu.

hmthur
źródło

Odpowiedzi:

173

W modelu obowiązują reguły biznesowe.

Załóżmy, że wyświetlałeś e-maile z listą adresową. Użytkownik klika przycisk „usuń” obok jednego z e-maili, kontroler powiadamia model o usunięciu wpisu N, a następnie powiadamia widok, który zmienił model.

Być może e-mail administratora nigdy nie powinien zostać usunięty z listy. To reguła biznesowa, że ​​wiedza należy do modelu. Widok może ostatecznie w jakiś sposób reprezentować tę regułę - być może model ujawnia właściwość „IsDeletable”, która jest funkcją reguły biznesowej, tak że przycisk usuwania w widoku jest wyłączony dla niektórych wpisów - ale sama reguła nie jest zawarta w widoku.

Model jest ostatecznie strażnikiem danych. Powinieneś być w stanie przetestować logikę biznesową bez dotykania interfejsu użytkownika.

Błoto
źródło
5
Dzięki za przykład. Czy w przypadku wpisu e-mail administratora (kontrolującego, czy można go usunąć, czy nie), nie możemy kontrolować tego przy użyciu naszego kontrolera?
hmthur,
2
@mud co jeśli podzielimy nasz model na dwie kolejne warstwy, tj. warstwę usługową i repozytorium ... warstwa usługowa jest odpowiedzialna za logikę biznesową, a repozytorium jest odpowiedzialne za warstwę danych ...?
Dragon,
3
@PeterMatisko „Modele powinny przenosić tylko dane”. Nie rozumiesz, co oznacza M w „MVC”. V to czysta prezentacja. C jest klejem między prezentacją a modelem. (W rzeczywistości „VC” często uważa się razem za warstwę prezentacji, a popularne odmiany MVC, takie jak MVVM - Model View Viewmodel - czynią to jeszcze wyraźniejszym.) M to wszystko inne : wszystkie dane i logika Twojej aplikacji. W tej warstwie można segregować dane i logikę biznesową, a część danych tej warstwy można nazwać „modelem”, ale nie do tego odnosi się „M” w „MVC”.
Błoto
1
@PeterMatisko "w laravel, ludzie następnie wrzucają wszystko do kontrolerów lub modeli. Zła zła architektura." Zły jak ? Być specyficznym. „V” oznacza „widok”. Wszystko, co nie jest widokiem, musi koniecznie występować w „M” lub „C”. „MVC to po prostu za mało, nie mówi wprost o logice biznesowej i jej miejscu”. Jasne, że tak. „M” to model aplikacji, czyli dane, otaczająca je logika biznesowa i wszystko inne, co nie jest prezentacją. „V” i „C” to warstwa prezentacji, dane wejściowe i wyjściowe użytkownika.
Błoto
2
@Mud Problem polega na tym, że laravel nazywa „Model” tylko nośnikiem danych. Kiedy tutoriale mówią, że Laravel używa MVC, a potem widzisz, że „Model” ma bardzo konkretny cel, to nie masz pojęcia, gdzie umieścić logikę biznesową. A jedynym rozsądnym miejscem jest kontroler, co nie jest dobre. Nie zmyślam tego, po prostu skomentowałem typowe projekty laravel (i samouczki), które często widzę.
Peter Matisko
191

Pięść wszystkich:
wierzę, że łączysz wzór MVC i zasady projektowania oparte na n-poziomach.

Zastosowanie podejścia MVC nie oznacza, że ​​nie powinieneś nakładać warstwy na aplikację.
Może to pomóc, jeśli zobaczysz MVC bardziej jak rozszerzenie warstwy prezentacji.

Jeśli umieścisz kod nie-prezentacji we wzorcu MVC, może bardzo szybko skończyć się skomplikowanym projektem.
Dlatego proponuję umieścić logikę biznesową w osobnej warstwie biznesowej.

Wystarczy spojrzeć na to: Artykuł w Wikipedii na temat architektury wielowarstwowej

Mówi:

Obecnie MVC i podobny model-view-prezenter (MVP) są wzorcami projektowymi separacji problemów, które dotyczą wyłącznie warstwy prezentacji większego systemu.

W każdym razie ... gdy mówimy o aplikacji internetowej dla przedsiębiorstw, połączenia z interfejsu użytkownika do warstwy logiki biznesowej powinny być umieszczone wewnątrz kontrolera (prezentacji).

Jest tak, ponieważ kontroler faktycznie obsługuje połączenia z określonym zasobem, wysyła zapytania do danych, wykonując połączenia z logiką biznesową i łączy dane (model) z odpowiednim widokiem.

Błoto powiedziało ci, że zasady biznesowe są zgodne z modelem.
To także prawda, ale pomieszał model (prezentacji) („M” w MVC) i model warstwy danych w projektowaniu opartym na warstwach.
Dlatego prawidłowe jest umieszczenie reguł biznesowych związanych z bazą danych w modelu (warstwa danych) aplikacji.
Nie należy jednak umieszczać ich w modelu warstwy prezentacji o strukturze MVC, ponieważ dotyczy to tylko określonego interfejsu użytkownika.

Ta technika jest niezależna od tego, czy używasz projektu opartego na domenie, czy podejścia opartego na skrypcie transakcji.

Pozwól mi to sobie wyobrazić:


Warstwa prezentacji: Model - Widok - Kontroler


Warstwa biznesowa: logika domeny - logika aplikacji


Warstwa danych: repozytoria danych - warstwa dostępu do danych


Powyższy model oznacza, że ​​masz aplikację korzystającą z MVC, DDD i niezależną od bazy danych warstwę danych.
Jest to powszechne podejście do projektowania większych aplikacji internetowych dla przedsiębiorstw.

Ale można go również zmniejszyć, aby użyć prostej warstwy biznesowej innej niż DDD (warstwa biznesowa bez logiki domeny) i prostej warstwy danych, która zapisuje bezpośrednio do określonej bazy danych.
Możesz nawet upuścić całą warstwę danych i uzyskać dostęp do bazy danych bezpośrednio z warstwy biznesowej, chociaż nie polecam tego.

To jest sztuczka ... Mam nadzieję, że to pomaga ...

[Uwaga:] Należy również pamiętać, że obecnie w aplikacji jest więcej niż jeden „model”. Zwykle każda warstwa aplikacji ma własny model. Model warstwy prezentacji jest specyficzny dla widoku, ale często niezależny od zastosowanych kontrolek. Warstwa biznesowa może również mieć model zwany „modelem domeny”. Zazwyczaj dzieje się tak, gdy decydujesz się na podejście oparte na domenie. Ten „model domeny” zawiera zarówno dane, jak i logikę biznesową (główną logikę programu) i zwykle jest niezależny od warstwy prezentacji. Warstwa prezentacji zwykle wywołuje warstwę biznesową w określonym „zdarzeniu” (naciśnięcie przycisku itp.) W celu odczytania danych lub zapisania danych w warstwie danych. Warstwa danych może również mieć własny model, który zazwyczaj jest związany z bazą danych.

Pytanie brzmi: jak to pasuje do koncepcji MVC?

Odpowiedź -> Nie!
Cóż - to trochę tak, ale nie do końca.
Wynika to z faktu, że MVC to podejście opracowane pod koniec lat siedemdziesiątych dla języka programowania Smalltalk-80. W tym czasie GUI i komputery osobiste były dość rzadkie, a sieć nawet nie została wynaleziona! Większość współczesnych języków programowania i IDE opracowano w latach 90. W tym czasie komputery i interfejsy użytkownika były zupełnie inne niż w latach siedemdziesiątych.
Należy o tym pamiętać, rozmawiając o MVC.
Martin Fowler napisał bardzo dobry artykuł o MVC, MVP i dzisiejszych GUI.

Szczery
źródło
10
+1 za prawidłowe wyświetlenie różnicy między aplikacjami mvc i n-tier. Większość aplikacji dla przedsiębiorstw, które opracowuję, ma warstwę n i używa mvc tylko jako warstwy prezentacji.
Retired_User
Powiedzmy, że 1) Zobacz modele w MVC (warstwa prezentacji) 2) Niektóre technologie C # (warstwa biznesowa) dla autoryzowanych transakcji, podstawowa logika reguł biznesowych. 3) Repozytorium i jednostka pracy w (Warstwa dostępu do danych) Proszę wskazać niektóre technologie (lub wzorce najlepszych praktyk), które można wykorzystać do zbudowania warstwy biznesowej, które powinny umożliwiać swobodny dostęp i udostępnianie modelu, repozytorium dostępu do kontrolera w warstwie prezentacji (górna część Warstwa). Zasadniczo uważam, że dodaj, usuń, zaktualizuj i jego połączenie jako logikę biznesową i powinny być przechowywane w ramach transakcji. Uprzejmie rozprowadź o tym dodatkowe światło.
Mark Macneil Bikeio
Cześć Rahul, jeśli dobrze cię rozumiem, masz rację. Operacje CRUD są w zasadzie atomowymi częściami transakcji biznesowych. Osobiście wolę używać potężnego mapera OR, takiego jak Hibernacja, jako repozytorium zamiast budowania własnego. Jest tak, ponieważ hibernacja już wewnętrznie implementuje wzorzec jednostki pracy. Poza tym zwykle umieszczam transakcje biznesowe w osobnych usługach biznesowych.
Frank
Dla modelu widoku mogę podać następujący przykład: Po prostu obraz zawiera GUI z podwójnym widokiem listy. Ten podwójny widok listy używa modelu podwójnego widoku listy jako modelu danych. Ten model danych jest tylko kompozycją dwóch prostych list. Tak więc model podwójnej listy widoków zależy od implementacji warstwy prezentacji, ponieważ nie jest częścią modelu domeny, w przeciwieństwie do dwóch prostych list, które są używane do tworzenia modelu widoku. W zależności od graficznego interfejsu użytkownika, który chcesz utworzyć, istnieje kilka przypadków, w których możesz chcieć powiązać konkretny model widoku z widokiem zamiast modelu domeny.
Frank
Część reguł biznesowych / logiki jest nieco trudna do wyjaśnienia. Aby rozpocząć przetwarzanie danych, wywołujesz metodę z jednej ze swoich usług. Oznacza to, że zasadniczo zaczynasz transakcję. Jeśli ta metoda zawiera logikę biznesową, nazywa się to „skryptem transakcji”. Jest to zwykle zła rzecz, ponieważ nie można jej ponownie wykorzystać. Byłoby lepiej, gdyby ta metoda wywoływała logikę biznesową modelu domeny. Oznacza to, że model domeny musi być tak zaprojektowany, aby mógł zawierać logikę biznesową. To podejście oparte na domenie nie będzie działać z niepełnym lub niewłaściwym modelem domeny.
Frank
73

Pojęcie logiki biznesowej nie jest moim zdaniem dokładną definicją. Evans mówi w swojej książce Domain Driven Design o dwóch rodzajach logiki biznesowej:

  • Logika domeny.
  • Logika aplikacji.

Ten podział jest moim zdaniem znacznie wyraźniejszy. A gdy zdamy sobie sprawę, że istnieją różne rodzaje reguł biznesowych, przychodzi także świadomość, że nie wszystkie muszą iść w to samo miejsce.

Logika domeny to logika odpowiadająca rzeczywistej domenie. Więc jeśli tworzysz aplikację księgową, wówczas reguły domeny byłyby regułami dotyczącymi kont, księgowań, podatków itp. W zwinnym narzędziu do planowania oprogramowania, reguły takie jak obliczanie dat wydania na podstawie prędkości i punktów historii w zaległościach, itp.

W przypadku obu tych typów aplikacji import / eksport CSV może być odpowiedni, ale zasady importu / eksportu CSV nie mają nic wspólnego z rzeczywistą domeną. Ten rodzaj logiki jest logiką aplikacji.

Logika domen z pewnością wchodzi w warstwę modelową. Model odpowiadałby również warstwie domenowej w DDD.

Logika aplikacji nie musi jednak koniecznie znajdować się w warstwie modelu. Można to umieścić bezpośrednio w kontrolerach lub utworzyć osobną warstwę aplikacji obsługującą te reguły. To, co jest najbardziej logiczne w tym przypadku, zależy od rzeczywistej aplikacji.

Pete
źródło
1
To jest najprawdziwsza prawda! Istnieją tutaj dwa modele: View View i Your Domain Model. Myślę, że to prawie niefortunne, że układ projektów MVC powoduje, że początkujący programiści uważają, że powinni po prostu wcisnąć swój kod w model widoku.
Jonathan
1
Twoja odpowiedź jest bardziej akceptowalna i zrozumiała. Dzięki.
revo
27

A1 : Logika biznesowa bierze Modeludział MVC. Rola Modelpolega na przechowywaniu danych i logiki biznesowej. Controllerz drugiej strony odpowiada za otrzymywanie informacji od użytkowników i decydowanie o tym, co robić.

A2 : A Business Rulejest częścią Business Logic. Mają has azwiązek. Business Logicma Business Rules.

Spójrz na Wikipedia entry for MVC. Idź do Przeglądu, gdzie wspomina przepływ MVCwzoru.

Zobacz także Wikipedia entry for Business Logic. Wspomniano, że Business Logicskłada się z Business Rulesi Workflow.

decyklon
źródło
16

Jak wskazało kilka odpowiedzi, uważam, że istnieje pewne nieporozumienie dotyczące architektury wielopoziomowej w porównaniu z architekturą MVC.

Architektura wielowarstwowa obejmuje rozbicie aplikacji na warstwy / warstwy (np. Prezentacja, logika biznesowa, dostęp do danych)

MVC to styl architektoniczny dla warstwy prezentacji aplikacji. W przypadku nietrywialnych aplikacji logiki biznesowej / reguł biznesowych / dostępu do danych nie należy umieszczać bezpośrednio w modelach, widokach lub kontrolerach. W tym celu umieszczenie logiki biznesowej w warstwie prezentacji, a tym samym ograniczenie ponownego użycia i łatwości konserwacji kodu.

Model jest bardzo rozsądnym wyborem do umieszczenia logiki biznesowej, ale lepszym / łatwiejszym w utrzymaniu podejściem jest oddzielenie warstwy prezentacji od warstwy logiki biznesowej i utworzenie warstwy logiki biznesowej i po prostu wywołanie warstwy logiki biznesowej z modeli w razie potrzeby. Warstwa logiki biznesowej z kolei wywoła się w warstwę dostępu do danych.

Chciałbym zauważyć, że często zdarza się, aby znaleźć kod, który łączy logikę biznesową i dostęp do danych w jednym z komponentów MVC, zwłaszcza jeśli aplikacja nie została zaprojektowana przy użyciu wielu warstw. Jednak w większości aplikacji korporacyjnych zwykle można znaleźć wielowarstwowe architektury z architekturą MVC w warstwie prezentacji.

Treefiddy
źródło
2
Najlepsza odpowiedź w tej sprawie. Należy głosować wyżej. Najgorsza odpowiedź jest oznaczona jako zaakceptowana.
Peter Matisko
Najlepsza odpowiedź .. bez wątpienia
salman
Czy to zależy od wielkości danych i aplikacji? W przypadku małej aplikacji zgaduję, że cała logika mogłaby przejść do modeli bez żadnego zamieszania. Jeśli tak, to jaki jest próg wielkości, aby zacząć rozdzielać się na osobną warstwę?
mLstudent33
15

To jest odpowiedź na pytanie, ale dam „jeden cent”:

Reguły biznesowe należą do modelu. „Model” zawsze składa się z (logicznie lub fizycznie oddzielonych):

  • model prezentacji - zestaw klas, który dobrze nadaje się do użycia w widoku (dostosowany do konkretnego interfejsu użytkownika / prezentacji),
  • model domeny - niezależna od interfejsu część modelu, oraz
  • repozytorium - część „modelu” uwzględniająca pamięć.

Reguły biznesowe działają w modelu domeny, są prezentowane w formie odpowiedniej do prezentacji w modelu „prezentacji”, a czasami są powielane (lub egzekwowane) w „warstwie danych”.

G. Stoynev
źródło
5

Nie ma sensu umieszczanie warstwy biznesowej w modelu dla projektu MVC.

Powiedz, że twój szef decyduje się na zmianę warstwy prezentacji na coś innego. Warstwa biznesowa powinna stanowić oddzielny zestaw. Model zawiera dane pochodzące z warstwy biznesowej, która przechodzi do widoku do wyświetlenia. Następnie na przykład, model wiąże się z klasą Person, która znajduje się w warstwie biznesowej i wywołuje PersonBusiness.SavePerson (p); gdzie p jest klasą Person. Oto, co robię (brakuje klasy BusinessError, ale też przejdzie do BusinessLayer):wprowadź opis zdjęcia tutaj

Alex
źródło
Czy wyjaśniłbyś to oświadczenie? „ Model zawiera dane pochodzące z warstwy biznesowej, która przechodzi do widoku do wyświetlenia.”
Anthony Rutledge
2

P1:

Logikę biznesową można rozpatrywać w dwóch kategoriach:

  1. Logika domeny, taka jak kontrola adresu e-mail (unikalność, ograniczenia itp.), Uzyskiwanie ceny produktu na fakturę lub obliczanie łącznej ceny shoppingCart na podstawie obiektów produktu.

  2. Bardziej rozbudowane i skomplikowane przepływy pracy zwane procesami biznesowymi, takie jak kontrolowanie procesu rejestracji dla ucznia (który zwykle obejmuje kilka kroków i wymaga różnych kontroli i ma bardziej skomplikowane ograniczenia).

Pierwsza kategoria idzie do modelu , a drugi jeden należący do kontrolera . Wynika to z faktu, że przypadki w drugiej kategorii to szerokie logiki aplikacji, a umieszczenie ich w modelu może mieszać abstrakcję modelu (na przykład nie jest jasne, czy musimy umieścić te decyzje w tej czy innej klasie modeli, ponieważ są one powiązane do obu!).

Zobacz tę odpowiedź, aby uzyskać szczegółowe rozróżnienie między modelem a kontrolerem, ten link dla bardzo dokładnych definicji, a także ten link dla ładnego przykładu Androida.

Chodzi o to, że nuty wspomniane powyżej przez „Mud” i „Frank” mogą być zarówno prawdziwe, jak i „Pete'a” (logikę biznesową można umieścić w modelu lub kontrolerze, zgodnie z rodzajem logiki biznesowej).

Na koniec zauważ, że MVC różni się w zależności od kontekstu. Na przykład w aplikacjach na Androida sugerowane są niektóre alternatywne definicje, które różnią się od definicji internetowych (zobacz na przykład ten post ).


Q2:

Logika biznesowa jest bardziej ogólna i (jak wspomniano powyżej „decyklon”) mamy między nimi następującą relację:

reguły biznesowe log logika biznesowa

Alisa
źródło
0

Dlaczego nie wprowadzisz warstwy usług. wtedy twój kontroler będzie szczupły i bardziej czytelny, wtedy wszystkie funkcje kontrolera będą czystymi działaniami. możesz rozkładać logikę biznesową tak bardzo, jak potrzebujesz w warstwie usług. możliwość ponownego użycia kodu jest wysoka. bez wpływu na modele i repozytoria.

Indygowiec
źródło
-5

Model = kod operacji bazy danych CRUD.

Kontroler = odpowiada na działania użytkownika i przekazuje żądania użytkownika dotyczące pobrania danych lub usunięcia / aktualizacji do modelu, zgodnie z regułami biznesowymi specyficznymi dla organizacji. Te reguły biznesowe można zaimplementować w klasach pomocniczych lub, jeśli nie są one zbyt skomplikowane, bezpośrednio w akcjach kontrolera. Kontroler w końcu prosi widok, aby sam się zaktualizował, aby przekazać użytkownikowi informację zwrotną w postaci nowego wyświetlacza lub komunikatu typu „zaktualizowano, dziękuję” itp.,

Widok = interfejs użytkownika generowany na podstawie zapytania w modelu.

Nie ma twardych i szybkich reguł dotyczących tego, gdzie powinny iść reguły biznesowe. W niektórych projektach wchodzą w model, podczas gdy w innych są dołączone do kontrolera. Ale myślę, że lepiej trzymać je ze sterownikiem. Pozwól modelowi martwić się tylko o połączenie z bazą danych.

Hoven
źródło
Jeśli umieścisz reguły biznesowe w kontrolerze i wykonasz wiele działań - czy zamierzasz powielić regułę biznesową wiele, wiele razy? Nie. Rozdzielisz to metodą pomocniczą lub jakąś klasą. Umieść tę „rzecz” w modelu, do którego należy.
G. Stoynev
3
MVC nie jest wzorcem aplikacji dla operacji na bazie danych CRUD (chociaż można go w ten sposób wykorzystać), dlatego Model nie może być „kodem dla operacji na bazie danych CRUD”. Model definiuje podmioty aplikacji, w tym dane i reguły biznesowe. Kontroler koordynuje interakcję między widokiem a modelem. Widok to interfejs użytkownika pokazujący model i dostępne operacje w modelach ujawnionych przez kontroler.
Jon Davis,