Java design pattern: DAO vs repositories

Tr3x

Lieutenant
Registriert
Feb. 2007
Beiträge
638
Hi,

ich kämpfe gerade mit dem Verständnis zwischen einem design patter: DAO (data access object) vs repositories in Java.

Vorab: Ich tüfftle gerade an einem Backend das per REST API diverse Objete erstellt und diese auch in die Datenbank speichert bzw. abruft und bediene mich an einem DAO pattern. Genauer gesagt je nach Objekte gibt es eigene konkrete DAO implementierung (AccountService -> Accounts DAO).

Jetzt bin ich auf das repository pattern gestoßen und ich hab einfach das Problem zu verstehen was der Unterschied ist bzw. wann man welches Pattern eher nutzt. Soweit ich verstehe verwendet man die repositories mehr wenn man mit mehreren Objekten (Listen, Sets) gleichzeitig arbeitet und wenn einzelne geändert werden, man diese auf einen Schlag wieder speichert. DAOs eher für einzelne Objekte. Seht ihr das auch so? Bzw. gibt es eine ganz simple einfache erklärung zu den beiden Pattern.

Ich habe zwei Quellen die ich bisher ganz ok fand (https://uthrive-in-unity.com/798-dao-vs-repository-patterns und https://ducmanhphan.github.io/2019-04-28-Repository-pattern/) Aber irgendwie fehlt mir hier der Aha Effekt.

Freue mich wenn mir hier jemand mit einer DAU Erklärung helfen kann.
 
Ich habe jetzt nur den ersten Artikel durchgelesen, aber wo genau ist da das Verständnisproblem?

Das Repository Zeugs klingt zwar mehr als wäre es dem Kopf eines PR-Menschen entsprungen, aber DAO orientiert sich noch an der Struktur mit der die Daten tatsächlich abgespeichert werden und macht dies auch sichbar.
Also beispielsweise bei relationalen Datenbanken entspricht ein Objekt einem Tabellen-Eintrag. Verknüpfungen über mehrere Tabellen werden von Hand gemacht.

Die Repositories abstrahieren das dann weiter und können zb auch schon diese Verknüpfungen automatisch machen und verstecken so, wie die Daten genau gespeichert sind.

Ich fand das mit der JPA nur seltsam, da JPA ja auch die Modellierung als Repository beinhaltet, das dann aber im Code nicht genutzt wurde...

Sich nur auf DAO zu beschränken, macht Sinn, wenn man auf die Performance achten und vermeiden will, dass die abstraktere Darstellung auf Weisen genutzt wird, die ineffizient sind, oder wenn man nicht eine fertige Library nutzt, die sich schon gut genug um beides kümmert.

Während das Verwenden einer abstrakteren API eine Änderung der Speicherung (zB weg von relationalen Datenbanken) einfacher macht, da die Business-Logik davon entkoppelt ist.
 
Hi,

mein Problem ist wofür man das repository pattern überhaupt braucht wenn es eigentlich nur Nachteile hat, bis auf die Ausnahme das man in der business logik es bequemer hat.
 
Wieso nur Nachteile? Das ist einfach der klassische Tradeoff zwischen Abstraktion und "Hardwarenähe".

Mehr Abstraktion ist bequemer, einfacher zu nutzen und flexibler, versteckt aber auch die Komplexität von bestimmten Operationen und ist zusätzliche Komplexität im System die man erstmal korrekt am Laufen haben muss.

Die Vorteile werden dir auch klar ersichtlich wenn du deine Accounts mit weiteren Daten verknüpfst.
Dann muss man mit reinem DAO explizit nach zB Messages von Account.id fragen, während das als Repository gekapselt einfach Account.messages ist. Wenn die verküpfungen aufwendiger werden und mehr als 2 Tabellen verknüpfen, wird das auch deutlich mehr Schreibarbeit.
 
Tr3x schrieb:
Jetzt bin ich auf das repository pattern gestoßen und ich hab einfach das Problem zu verstehen was der Unterschied ist bzw. wann man welches Pattern eher nutzt.
ImHo, wenn du nicht siehst, wieso du ein Pattern verwenden solltest, dann solltest du es auch einfach nicht verwenden. Unverständnis kommt meiner Erfahrung nach oft davon, dass der Lösungsansatz kein Problem löst, das man selber hat.

DAOs sind ja ein sein dünner Layer bzw. bieten wenig Abstraction und bietet z.B. keinen OOP Weg bei Anfragen wie "Gib mir die Kunden, die letzten Monat Elektroartikel im Wert von mindestens 100 Euro gekauft haben". Vielleicht sind die Kundendaten in der lokalen Datenbank, aber die Produktdaten liegen bei einem externen Dienstleister. Vielleicht brauchst du später noch ein weiteres Kriterium "... und die in Hamburg oder Berlin wohnen" und willst aber vermeiden, dass dein Query der deine 10 Millionen Kundendaten abfragt nochmal von vorne startet, sondern auf der Ergebnismenge des vorherigen Queries arbeitet. Dann ist es eventuell schlecht, wenn die Ergebnismenge eine Liste von Domänenobjekten ist.
 
BeBur schrieb:
ImHo, wenn du nicht siehst, wieso du ein Pattern verwenden solltest, dann solltest du es auch einfach nicht verwenden. Unverständnis kommt meiner Erfahrung nach oft davon, dass der Lösungsansatz kein Problem löst, das man selber hat.

DAOs sind ja ein sein dünner Layer bzw. bieten wenig Abstraction und bietet z.B. keinen OOP Weg bei Anfragen wie "Gib mir die Kunden, die letzten Monat Elektroartikel im Wert von mindestens 100 Euro gekauft haben". Vielleicht sind die Kundendaten in der lokalen Datenbank, aber die Produktdaten liegen bei einem externen Dienstleister. Vielleicht brauchst du später noch ein weiteres Kriterium "... und die in Hamburg oder Berlin wohnen" und willst aber vermeiden, dass dein Query der deine 10 Millionen Kundendaten abfragt nochmal von vorne startet, sondern auf der Ergebnismenge des vorherigen Queries arbeitet. Dann ist es eventuell schlecht, wenn die Ergebnismenge eine Liste von Domänenobjekten ist.

Naja das Pattern für DAOs war mir schon soweit bekannt und verstehe ich, nur mir dem repository wird quasi mein Weltanschauen zerstört :)

Mit dem Beispiel würde ich mir über die DAOs einmal die Daten holen und für weitere Abfragen etc in der business Logik also im repository machen. Spar ich mir den erneuten Abruf der DB und macht Sinn. Heißt ich schalte zwischen meinem Service API und dem DAO einfach das repository das wider rum meinen DAO hat.
Je nachdem wie viele Objekte bzw. es tiefe geht, würde ich neben einem Account DAO vll. auch eine Adressen DAO im repository haben. Macht das Sinn bzw. ist das gängige Praxis?
 
Zurück
Oben