/ / Hibernate ManyToMany führt zu einem kartesischen Produkt - Java, Hibernate, JPA

Hibernate ManyToMany führt zu kartesischen Produkten - Java, Winterschlaf, jpa

Ich bin ein Neuling im Winterschlaf / JPA und entschuldige mich für diese Noob-Frage. Ich verfolge Beziehungen zu Entitäten

  • Manager hat viele zu viele Beziehungen zu Worker
  • Der Arbeiter hat viel zu viel Beziehung zu der Aufgabe

Es folgt die ERD

Bildbeschreibung hier eingeben

Es folgen meine Java-Kurse

@Entity
@table(name="manager")
public class Manager {

private long id;

private String name;

@ManyToMany(fetch = FetchType.EAGER)
@JoinTable(name = "manager_worker", joinColumns = { @JoinColumn(name = "manager_id") },
inverseJoinColumns = { @JoinColumn(name = "worker_id") })
private ArrayList<Worker> workers = new ArrayList<Worker>();

// ......getter setter
}

@Entity
@Table(name = "worker")
public class Worker {

@Id
private long id;

private String name;
@ManyToMany(fetch = FetchType.EAGER)
@JoinTable(name = "worker_task", joinColumns = { @JoinColumn(name = "worker_id") },
inverseJoinColumns = { @JoinColumn(name = "task_id") })
private ArrayList<Task> tasks = new ArrayList<Task>();
...........................
}

@Entity
@Table(name = "task")
public class Task {

@Id
private long id;

private String title;
.................
}

Ich habe folgende Daten:

  • Manager M1 hat Arbeiter W1 und W2
  • W1 hat die Aufgaben TW1, TW2, TW3
  • W2 hat die Aufgaben TW2 und TW2

Wenn ich das Manager-Objekt für die ID M1 erhalte, wird das Ergebnis angezeigthat kartesisches Produkt von Worker und Task, d. h. W1-Daten werden dreimal wiederholt und W2-Daten werden zweimal wiederholt, d. h. Manager.worker-Array-Liste hat 5 Worker-Objekte anstelle von 2.

Zum Laden der Daten verwende ich die Methode Session.get ()

public E find(final K key) {
return (E) currentSession().get(daoType, key);
}

Kann mir jemand bitte sagen, wie ich das beheben kann, und mich auf bewährte Methoden hinweisen, die ich in diesem Fall verwenden sollte.

Vielen Dank

Antworten:

3 für die Antwort № 1

Das passiert weil beides @ManyToMany Beziehungen sind gespannt.

Dies führt zu einer äußeren Verknüpfung aller drei Tabellen. Das Ergebnis dieser Abfrage sind fünf Zeilen, in denen W1 dreimal und W2 zweimal angezeigt wird. Soweit ist alles in Ordnung.

Aus irgendeinem Grund stellt Hibernate jedoch nur alle Mitarbeiter in die Sammlungen, auch wenn es sich um Duplikate handelt. Es ist sogar beschrieben in FAQ.

Es gibt mehrere Möglichkeiten, um dieses Problem zu beheben:

  • Ändern Sie eine der Beziehungen in Lazy Loading
  • Verwenden Sie ein Set anstelle einer Liste (sollten Sie nicht verwenden) ArrayList als Typ für Variablen (besonders im Ruhezustand)
  • benutzen @Fetch(FetchMode.SELECT) zum tasks

2 für die Antwort № 2

Wo ist dein targetEntity in dem @ManyToMany Beziehung?

du solltest etwas haben wie:

@ManyToMany(targetEntity = Task.class)
@JoinTable(name = "worker_task", joinColumns = { @JoinColumn(name = "worker_id") },
inverseJoinColumns = { @JoinColumn(name = "task_id") })
private ArrayList<Task> tasks = new ArrayList<Task>();

Ich schlage vor, Sie zu ändern @OneToMany und @ManyToOne Beziehung sowieso. Dieses Konzept ist besser mit dem Datenbankdesign kompatibel und verständlicher, wenn eine Person die ERD betrachtet. So Manager hat eine Eins-zu-Viele-Beziehung zu Manager_Worker, daher hat manager_worker eine Viele-zu-Eins-Beziehung zu Manager. Behalten Sie dasselbe für den Rest der Entitäten bei.