Podział encji na domenowe i JPA

Podział encji na domenowe i JPA

Wątek przeniesiony 2023-10-12 18:34 z Java przez Riddle.

Tak
83%
83% [5]
Nie
17%
17% [1]
NO
  • Rejestracja:ponad 2 lata
  • Ostatnio:około 3 godziny
  • Postów:135
0

Rozdzielacie encje na te domenowe i JPA? Z jednej strony powinno się tak robić, żeby domena była czysta i nie wiedziała nic o frameworkach, z drugiej tworzy to trochę dodatkowego kodu i pochłania dodatkową ilość czasu. Szkoda, że Hibernate nie umie sobie wygenerować sam tych encji na podstawie obiektów domenowych.

edytowany 1x, ostatnio: Riddle
jarekr000000
  • Rejestracja:ponad 8 lat
  • Ostatnio:42 minuty
  • Lokalizacja:U krasnoludów - pod górą
  • Postów:4706
3

Polecam nie używać JPA - problem się wówczas rozwiązuje.
Ale serio - dużo innych problemów też Cie ominie. Chyba, że chcesz zostać ekspertem od problemów z JPA - wtedy to co innego.
Proste alternatywy JOOQ i JDBI (nie JDBC).


jeden i pół terabajta powinno wystarczyć każdemu
W0
  • Rejestracja:ponad 12 lat
  • Ostatnio:około 2 godziny
  • Postów:3538
1

Tak jak napisano - daruj sobie JPA.
Natomiast podział na encją domenowe i bazodanowe ma sens wtedy i tylko wtedy, gdy twoja domena mocno różni się od tabel w SQLu. Jeśli model domenowy to 1:1 to, co w bazie danych to nie widzę powodu, żeby kod duplikować bo tak napisano w książce.

edytowany 1x, ostatnio: wartek01
Riddle
Administrator
  • Rejestracja:prawie 15 lat
  • Ostatnio:32 minuty
  • Lokalizacja:Laska, z Polski
  • Postów:10053
0

Znaczy, nie wiem czy w ogóle słowo "podział" ma jakikolwiek sens, bo to sugeruje że jest jakaś relacja/reprezentacja między nimi, a to przecież są zupełnie inne byty które nie powinny mieć ze sobą nic wspólnego. Więc moim zdaniem zawsze jest sens je oddzielać, nie chcesz mieć tight-coupling na warstwę persystencji w swojej aplikacji.

Brzmi to trochę tak, jakbyś dla encji JPA z automatu robił jakiś odpowiedni w domenie (albo odwrotnie), a to w ogóle nie ma sensu. Powinieneś mieć zakorzenione z tyłu głowy że domena to jedno, a persystencja to drugie, one nie powinny być do siebie podobne.

I tytułem dygresji, może dodam że JPA jako warstwa abstrakcji na bazę jest raczej średna, i ja bym chyba poszukał czegoś innego.

edytowany 6x, ostatnio: Riddle
Grzyboo
  • Rejestracja:ponad 9 lat
  • Ostatnio:4 miesiące
  • Postów:206
1

Tak, zawsze. Najlepiej nie używać JPA, ale jak jakiś spring tutorial architect się upiera to chociaż oddzielać te 2 encje, bo utrzymywanie kodu, w którym JPA przeplata się z encjami logiką biznesową to koszmar i wieczne błędy.

wartek01 napisał(a):

podział na encją domenowe i bazodanowe ma sens wtedy i tylko wtedy, gdy twoja domena mocno różni się od tabel w SQLu. Jeśli model domenowy to 1:1 to, co w bazie danych to nie widzę powodu, żeby kod duplikować bo tak napisano w książce.

Z tym argumentem mam zawsze taki problem, że nigdy nie wiesz kiedy model przestanie być 1:1 i w pewnym momencie zrefactorowanie takiego kodu żeby te modele wydzielić może być drogą przez mękę.
A sytuacja, że modele przestają być 1:1 jest dosyć częsta w przeciwieństwie to np. mitycznego zmieniania DBMSa, które jest nieraz argumentem "za" używaniem JPA

edytowany 2x, ostatnio: Grzyboo
jarekr000000
  • Rejestracja:ponad 8 lat
  • Ostatnio:42 minuty
  • Lokalizacja:U krasnoludów - pod górą
  • Postów:4706
3

Widziałem głupie błedy w aplikacjach gdzie były tylko encje JPA - wystawiane "na chama" przez rest.
I widziałem głupie błedy w aplikacjach gdzie ludzie poświęcili czas na wprowadzanie i mapowanie na DTO - czy jeszcze zabawnej na jakiś model domenowy.
W tym drugim przypadku zwykle pojawiają się jakieś gówniane automappery, ktore robią z przykrego przypadku - beznadziejny.
(np. nie da się łatwo wyszukać kto i gdzie ustawia pole, bo jest to robione mapperem przez fefleksje).

Btw @Riddle nie wiem co kierowało Tobą, że przeniosłeś to z działu Java. Nie dość, że JPA jest naprawdę specyficzne dla Javy to jeszcze wstyd trochę.


jeden i pół terabajta powinno wystarczyć każdemu
edytowany 1x, ostatnio: jarekr000000
jarekr000000
miało być mappere przez refleksje - ale fefleksja podoba mi się bardziej i od razu sugeruje lekkie upośledzenie, więc zostawiam.
RequiredNickname
imho większy nacisk został położony na kwestie odseparowania domeny od persystencj ianiżeli stricte wykorzystanie w tym celu jpa bo przecież to dosyć uniwersalne.
CH
Fefleksja +1
NO
  • Rejestracja:ponad 2 lata
  • Ostatnio:około 3 godziny
  • Postów:135
1

Znalazłem sposób na to. Całe mapowaniem przeniosłem do jednego pliku xml, dzięki temu encje domenowe mogą być czyste i nic nie wiedzieć o żadnym JPA. Został jedynie bezparametrowy konstruktor, ale może być prywatny

SL
  • Rejestracja:około 7 lat
  • Ostatnio:około 11 godzin
  • Postów:862
1
Nofenak napisał(a):

Znalazłem sposób na to. Całe mapowaniem przeniosłem do jednego pliku xml, dzięki temu encje domenowe mogą być czyste i nic nie wiedzieć o żadnym JPA. Został jedynie bezparametrowy konstruktor, ale może być prywatny

Brzmi jak wyleczenie bólu ręki amputacją. Podział nie jest po to, żeby nie było tych wrednych adnotacji, tylko:

  • domena może być bardziej zaawansowana np. używać zaawansowanych struktur danych. Model używany przez bazę jest często ograniczony, bo mapper baza <-> kod jest ograniczony
  • mieć elastyczność. Przykładowo w przypadku bazy musimy dbać o kompatybilność wsteczną. Model może być bardziej elastyczny i mogę sobie zmienić nazwę pola albo typ
  • domena nie koniecznie musi być używana przez bazę albo może być użyta w innym kontekście. Mając odzielonny kod możesz łatwo podmienić bazę np. z SQL na Redisa albo SQL na wywołanie API

Wrzucenie mapowania do pliku XML nic nie rozwiązuje a dodaje dużo nowych problemów jak utrzymanie XMLa, który jest jeszcze bardziej upierdliwy niż adnotacje. Jak chcesz automatyzacji to użyj mappera https://www.baeldung.com/java-performance-mapping-frameworks , którego można sie zawsze pozbyć jak się okaże, że gra nie jest warta świeczki

Riddle
Administrator
  • Rejestracja:prawie 15 lat
  • Ostatnio:32 minuty
  • Lokalizacja:Laska, z Polski
  • Postów:10053
0
Nofenak napisał(a):

Znalazłem sposób na to. Całe mapowaniem przeniosłem do jednego pliku xml, dzięki temu encje domenowe mogą być czyste i nic nie wiedzieć o żadnym JPA. Został jedynie bezparametrowy konstruktor, ale może być prywatny

To nadal nie jest dobre rozwiązanie, bo nazwy pól i typy pól są uzależnione od siebie.

Nie mówiąc o tym, że nie każda encja JPA powinna mieć swój odpowiednik w domenie i odwrotnie.

edytowany 1x, ostatnio: Riddle
NO
  • Rejestracja:ponad 2 lata
  • Ostatnio:około 3 godziny
  • Postów:135
0
slsy napisał(a):
Nofenak napisał(a):

Znalazłem sposób na to. Całe mapowaniem przeniosłem do jednego pliku xml, dzięki temu encje domenowe mogą być czyste i nic nie wiedzieć o żadnym JPA. Został jedynie bezparametrowy konstruktor, ale może być prywatny

Brzmi jak wyleczenie bólu ręki amputacją. Podział nie jest po to, żeby nie było tych wrednych adnotacji, tylko:

  • domena może być bardziej zaawansowana np. używać zaawansowanych struktur danych. Model używany przez bazę jest często ograniczony, bo mapper baza <-> kod jest ograniczony
  • mieć elastyczność. Przykładowo w przypadku bazy musimy dbać o kompatybilność wsteczną. Model może być bardziej elastyczny i mogę sobie zmienić nazwę pola albo typ
  • domena nie koniecznie musi być używana przez bazę albo może być użyta w innym kontekście. Mając odzielonny kod możesz łatwo podmienić bazę np. z SQL na Redisa albo SQL na wywołanie API

Wrzucenie mapowania do pliku XML nic nie rozwiązuje a dodaje dużo nowych problemów jak utrzymanie XMLa, który jest jeszcze bardziej upierdliwy niż adnotacje. Jak chcesz automatyzacji to użyj mappera https://www.baeldung.com/java-performance-mapping-frameworks , którego można sie zawsze pozbyć jak się okaże, że gra nie jest warta świeczki

Ale to i tak i tak tę zaawansowaną strukturę danych będzie trzeba jakoś zapisać w bazie, więc nie rozumiem tego argumentu. Jakiś konkretny przykład?
W XML też można zmapować pola o różnych nazwach, np userId -> id
Alternatywą jest utrzymywanie sporej ilości mapperów, pewnie jakiegoś frameworka do mapowania no i oczywiście osobnych modeli danych. Wolę jednego xmla

Riddle napisał(a):
Nofenak napisał(a):

Znalazłem sposób na to. Całe mapowaniem przeniosłem do jednego pliku xml, dzięki temu encje domenowe mogą być czyste i nic nie wiedzieć o żadnym JPA. Został jedynie bezparametrowy konstruktor, ale może być prywatny

To nadal nie jest dobre rozwiązanie, bo nazwy pól i typy pól są uzależnione od siebie.

Nie mówiąc o tym, że nie każda encja JPA powinna mieć swój odpowiednik w domenie i odwrotnie.

Nazwy pól nie są od siebie uzależnione, bo tak jak mówiłem można sobie mapować np. userId na id a z typami jest chyba podobnie
No wiadomo, nie wszystko trzeba zapisywać w bazie, nawet mam takich przykład u siebie w apce, mail - mam tylko encje domenową

W ogolę, to pomysł na tego xmla wziąłem z tej prezentacji. Gość zrobił coś podobnego w PHP w 16.50:

edytowany 2x, ostatnio: Nofenak
W0
  • Rejestracja:ponad 12 lat
  • Ostatnio:około 2 godziny
  • Postów:3538
3
Grzyboo napisał(a):

Z tym argumentem mam zawsze taki problem, że nigdy nie wiesz kiedy model przestanie być 1:1 i w pewnym momencie zrefactorowanie takiego kodu żeby te modele wydzielić może być drogą przez mękę.

Czasem model przestaje się zgadzać, czasem nie. Zbyt wiele aplikacji widziałem, gdzie encje bazodanowe, obiekty domenowe oraz obiekty wystawione dla widoku były tym samym, żeby się zgodzić.
Pewne rzeczy można przewidywać - jak masz jakąś większą aplikację to podział "na zaś" może mieć sens, ale jak masz izolowany mikroserwis to koszt jego refaktoru jest niewielki - a i tak przy zmianie musisz go dokonać.

Kliknij, aby dodać treść...

Pomoc 1.18.8

Typografia

Edytor obsługuje składnie Markdown, w której pojedynczy akcent *kursywa* oraz _kursywa_ to pochylenie. Z kolei podwójny akcent **pogrubienie** oraz __pogrubienie__ to pogrubienie. Dodanie znaczników ~~strike~~ to przekreślenie.

Możesz dodać formatowanie komendami , , oraz .

Ponieważ dekoracja podkreślenia jest przeznaczona na linki, markdown nie zawiera specjalnej składni dla podkreślenia. Dlatego by dodać podkreślenie, użyj <u>underline</u>.

Komendy formatujące reagują na skróty klawiszowe: Ctrl+B, Ctrl+I, Ctrl+U oraz Ctrl+S.

Linki

By dodać link w edytorze użyj komendy lub użyj składni [title](link). URL umieszczony w linku lub nawet URL umieszczony bezpośrednio w tekście będzie aktywny i klikalny.

Jeżeli chcesz, możesz samodzielnie dodać link: <a href="link">title</a>.

Wewnętrzne odnośniki

Możesz umieścić odnośnik do wewnętrznej podstrony, używając następującej składni: [[Delphi/Kompendium]] lub [[Delphi/Kompendium|kliknij, aby przejść do kompendium]]. Odnośniki mogą prowadzić do Forum 4programmers.net lub np. do Kompendium.

Wspomnienia użytkowników

By wspomnieć użytkownika forum, wpisz w formularzu znak @. Zobaczysz okienko samouzupełniające nazwy użytkowników. Samouzupełnienie dobierze odpowiedni format wspomnienia, zależnie od tego czy w nazwie użytkownika znajduje się spacja.

Znaczniki HTML

Dozwolone jest używanie niektórych znaczników HTML: <a>, <b>, <i>, <kbd>, <del>, <strong>, <dfn>, <pre>, <blockquote>, <hr/>, <sub>, <sup> oraz <img/>.

Skróty klawiszowe

Dodaj kombinację klawiszy komendą notacji klawiszy lub skrótem klawiszowym Alt+K.

Reprezentuj kombinacje klawiszowe używając taga <kbd>. Oddziel od siebie klawisze znakiem plus, np <kbd>Alt+Tab</kbd>.

Indeks górny oraz dolny

Przykład: wpisując H<sub>2</sub>O i m<sup>2</sup> otrzymasz: H2O i m2.

Składnia Tex

By precyzyjnie wyrazić działanie matematyczne, użyj składni Tex.

<tex>arcctg(x) = argtan(\frac{1}{x}) = arcsin(\frac{1}{\sqrt{1+x^2}})</tex>

Kod źródłowy

Krótkie fragmenty kodu

Wszelkie jednolinijkowe instrukcje języka programowania powinny być zawarte pomiędzy obróconymi apostrofami: `kod instrukcji` lub ``console.log(`string`);``.

Kod wielolinijkowy

Dodaj fragment kodu komendą . Fragmenty kodu zajmujące całą lub więcej linijek powinny być umieszczone w wielolinijkowym fragmencie kodu. Znaczniki ``` lub ~~~ umożliwiają kolorowanie różnych języków programowania. Możemy nadać nazwę języka programowania używając auto-uzupełnienia, kod został pokolorowany używając konkretnych ustawień kolorowania składni:

```javascript
document.write('Hello World');
```

Możesz zaznaczyć również już wklejony kod w edytorze, i użyć komendy  by zamienić go w kod. Użyj kombinacji Ctrl+`, by dodać fragment kodu bez oznaczników języka.

Tabelki

Dodaj przykładową tabelkę używając komendy . Przykładowa tabelka składa się z dwóch kolumn, nagłówka i jednego wiersza.

Wygeneruj tabelkę na podstawie szablonu. Oddziel komórki separatorem ; lub |, a następnie zaznacz szablonu.

nazwisko;dziedzina;odkrycie
Pitagoras;mathematics;Pythagorean Theorem
Albert Einstein;physics;General Relativity
Marie Curie, Pierre Curie;chemistry;Radium, Polonium

Użyj komendy by zamienić zaznaczony szablon na tabelkę Markdown.

Lista uporządkowana i nieuporządkowana

Możliwe jest tworzenie listy numerowanych oraz wypunktowanych. Wystarczy, że pierwszym znakiem linii będzie * lub - dla listy nieuporządkowanej oraz 1. dla listy uporządkowanej.

Użyj komendy by dodać listę uporządkowaną.

1. Lista numerowana
2. Lista numerowana

Użyj komendy by dodać listę nieuporządkowaną.

* Lista wypunktowana
* Lista wypunktowana
** Lista wypunktowana (drugi poziom)

Składnia Markdown

Edytor obsługuje składnię Markdown, która składa się ze znaków specjalnych. Dostępne komendy, jak formatowanie , dodanie tabelki lub fragmentu kodu są w pewnym sensie świadome otaczającej jej składni, i postarają się unikać uszkodzenia jej.

Dla przykładu, używając tylko dostępnych komend, nie możemy dodać formatowania pogrubienia do kodu wielolinijkowego, albo dodać listy do tabelki - mogłoby to doprowadzić do uszkodzenia składni.

W pewnych odosobnionych przypadkach brak nowej linii przed elementami markdown również mógłby uszkodzić składnie, dlatego edytor dodaje brakujące nowe linie. Dla przykładu, dodanie formatowania pochylenia zaraz po tabelce, mogłoby zostać błędne zinterpretowane, więc edytor doda oddzielającą nową linię pomiędzy tabelką, a pochyleniem.

Skróty klawiszowe

Skróty formatujące, kiedy w edytorze znajduje się pojedynczy kursor, wstawiają sformatowany tekst przykładowy. Jeśli w edytorze znajduje się zaznaczenie (słowo, linijka, paragraf), wtedy zaznaczenie zostaje sformatowane.

  • Ctrl+B - dodaj pogrubienie lub pogrub zaznaczenie
  • Ctrl+I - dodaj pochylenie lub pochyl zaznaczenie
  • Ctrl+U - dodaj podkreślenie lub podkreśl zaznaczenie
  • Ctrl+S - dodaj przekreślenie lub przekreśl zaznaczenie

Notacja Klawiszy

  • Alt+K - dodaj notację klawiszy

Fragment kodu bez oznacznika

  • Alt+C - dodaj pusty fragment kodu

Skróty operujące na kodzie i linijkach:

  • Alt+L - zaznaczenie całej linii
  • Alt+, Alt+ - przeniesienie linijki w której znajduje się kursor w górę/dół.
  • Tab/⌘+] - dodaj wcięcie (wcięcie w prawo)
  • Shit+Tab/⌘+[ - usunięcie wcięcia (wycięcie w lewo)

Dodawanie postów:

  • Ctrl+Enter - dodaj post
  • ⌘+Enter - dodaj post (MacOS)