Hibernate Mapping - Nur eine Spalte per Join aus anderer Tabelle holen

peez

Bekanntes Mitglied
Ich habe ein Hibernate-Mapping und nur eine Spalte daraus soll per Join aus einer anderen Tabelle (nur lesend, muss nicht schreiben können) geholt werden. Der Unterschied zu 90% der Beispiele aus dem Netz ist, dass der FK nicht in der zweiten Tabelle sitzt, sondern in der ersten. Hier mein Beispiel.

Ich habe diese beiden Tabellen:
Code:
PERSON
-----------------------------
  personId
  personName
  FKadresseId

ADRESSE
-----------------------------
  adresseId
  ort
  strasse

Im Mapping soll zum Namen der Person lediglich der Ort auftauchen.

Das habe ich jetzt so gemacht (funktioniert leider nicht):
[XML]
<!-- .... -->
<property name="name" column="personName" type="java.lang.String" />

<join table="ADRESSE">
<key column="FKadresseId" />
<property name="ort" column="ort" type="java.lang.String" insert="false" update="false" />
</join>
[/XML]

Leider baut Hibernate den Join falsch rum auf. Es kommt sowas in der Art raus:

SQL:
SELECT personName, ort
FROM PERSON
INNER JOIN ADRESSE ON PERSON.personId = ADRESSE.FKadresseId

Das heißt er geht davon aus, dass der ForeignKey in der ADRESSE-Tabelle ist, statt in meiner Haupt-Tabelle (PERSON).
Hat jemand eine Idee wie ich das anders rum machen könnte? Zur Not auch mit Subselect / formula o.ä...
 

F.S.WhiTeY

Bekanntes Mitglied
Moin,

es ist zwar nicht der weg den du einschlagen willst aber warum benutzt du nicht einfach die JPQL ?

Java:
 EntityManagerFactory emf = Persistence.createEntityManagerFactory("PersistenceUnit");

Query q = emf.createEntityManager().createQuery("Hier deine SQL-Abfrage mit der JPQL");
 
q.setParameter("a", "Parameter falls gebraucht");

Ich mag mich persönlich bei solchen sachen nicht auf Hibernate verlassen und baue meine Abfragen immer selbst auf. Zum wiederverwenden kann man daraus ja ein NamedQuery machen.


LG
 

peez

Bekanntes Mitglied
Naja - die Umgebung ist eben 100% auf Businessobjekten aufgebaut.
Sache ist, bisher war der "ort" als String in der Personentabelle gespeichert und zusätzlich per Fremdschlüssel die Adresse-Tabelle referenziert.

Jetzt ist aufgefallen (oh Wunder :lol:), dass wenn jemand was in der Adresse-Tabelle ändert, der Ort beim Anzeigen nicht aktualisiert wird.
Und er Ort wird halt an zig Stellen über das Businessobjekt mit .getOrt() angesprochen.
Da jetzt überall noch ein JPQL dazwischenzuschalten halte ich für unnötigen Aufwand (und unnötige verkomplizierung im Code), wenn Hibernate das schon so ins Bo reinjoinen kann...

Ganz abgesehen von der Performance - ein einzelner Join gegen zig zusätzliche Selects...
 

F.S.WhiTeY

Bekanntes Mitglied
Zjaa wenn euch das schon aufgefallen ist, dann wäre es ja mal angebracht sich die Entitys näher anzuschauen ;)

Wenn du sie posten magst? Ich denke mal ihr habt da an der ein oder anderen Stelle die falschen Beziehungen / Annotationen.

btw: Ein NamedQuery macht da auch nichts anderes, wie du schon geschrieben hast baut Hibernate einen Join auf. Das kann man auch mit NamedQuerys und auch so ablegen, das man nicht überall ein Query im code braucht. ( z.B. einen zusätzlichen getter im Entity ;) ).
 

peez

Bekanntes Mitglied
Nein ich will da eigentlich keine NamedQuery oder sonst was zusätzliches verwenden..

Genau dafür gibts doch Entities / Businessobjekte.
1. Damit man sich um die zugrundeliegenden Selects - egal ob SQL oder HQL / JPQL - keine größeren Gedanken machen muss wenns mal initial eingerichtet ist.
2. Dass sich bei Bedarf die zugrundeliegende Datenstruktur ändern kann ohne an allen Stellen Anpassungen vorzunehmen.
 

F.S.WhiTeY

Bekanntes Mitglied
Java:
import java.io.Serializable;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;

/**
 *
 * @author david
 */
@Entity(name="person")
public class Person implements Serializable, Comparable<Person> {

    private static final long serialVersionUID = 1L;
    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    private Long id;

    private String name;
    //das hier ist wichtig
    @OneToOne(mappedBy="person")
    private Adresse adresse;
    
   //restliche getter und setter blah sülz

  public String getOrt(){
   return this.adresse.getOrt();
   }



    @Override
    public int hashCode() {
        int hash = 0;
        hash += (id != null ? id.hashCode() : 0);
        return hash;
    }

    @Override
    public boolean equals(Object object) {
        
        if (!(object instanceof Person)) {
            return false;
        }
        Person other = (Perso) object;
        if ((this.id == null && other.id != null) || (this.id != null && !this.id.equals(other.id))) {
            return false;
        }
        return true;
    }

    @Override
    public String toString() {
        return "de.paket.Person[ id=" + id + " ]";
    }
    
    @Override
    public int compareTo(Person person){
        //oder was auch immer
        return this.name.compareTo(person.name);
    }
    
}
 
Ähnliche Java Themen
  Titel Forum Antworten Datum
A JPA Postgresql/JPA/EclipseLink - Mapping Fehler? Data Tier 7
OnDemand OneToMany Composite Key Mapping Data Tier 18
G Hibernate Collection Mapping - Fehler beim Updaten der DB Data Tier 0
R mapping-file für hibernate zum Überschreiben der Annotationen Data Tier 7
M Problem mit @Temporal Mapping und SQL Server Data Tier 3
H Hibernate - Mapping für Enumeration Data Tier 1
S (Hibernate) Mapping einer Datenbanktabelle mit mehreren Fremdschlüssel Data Tier 7
Kessi Hibernate Mapping-File vs. Annotations Data Tier 4
M Hibernate Mapping mal anders Data Tier 2
N Hibernate boolean mapping Data Tier 7
M JPA: Mapping von bestehender DB Data Tier 2
byte Hibernate: duplicate property mapping Data Tier 3
N Mapping einer 1:n in Hibernate Data Tier 11
F OR-Mapping Data Tier 4
I Hibernate / JPA: Eine Datenbank und pro User ein Schema Data Tier 9
G wie persistiere ich eine abstrakte Superklasse? Data Tier 3
Z Hibernate: Many-To-Many nur eine bestimmte Spalte Data Tier 3
M Problem beim Laden von Objekten, die von anderen Applikationen in eine DB eingefügt wurden Data Tier 5
C EclipseLink in eine JavaEE Tomcat Anwendung einbinden Data Tier 7
H Zusammengesetzte mehrere Klasse als eine Tabelle Data Tier 6
Landei JPA - wie muss ich eine Untertabelle anbinden? Data Tier 4
M JPA ManyToMany mit zusätzlicher Spalte Data Tier 0
Java.getSkill() Hibernate und Spalte vom Typ xml Data Tier 6
S Hibernate: Tabelle ohne ID-Spalte Data Tier 2

Ähnliche Java Themen


Oben