marți, 28 octombrie 2008

Hibernate si chei composite

Hibernate este un ORM extrem de utilizat in zilele noastre. In ultimele versiuni a aparut si Hibernate Annotations. In aceasta maniera se reuseste o uniformizare a framework-ului si o apropiere de JPA. Se foloseste Hibernate in Java pentru a mapa entitati(obiecte) la tabele din baza de date. In continuare prezint o modalitatea de a manipula o relatie many-to-many.


Problema intalnita este enuntata in cele ce urmeaza: am o relatie many-to-many intre un pachet de gazduire si tehnologie. Entitatea TehnologiiPachet, rezultata este implementata prin hibernate. Este evident faptul ca pentru aceasta entitate, cheia primara va fi: (pachet, tehnologie) => intr-un pachet nu pot sa am aceeasi tehnologie de mai multe ori. In continuare postez codul pentru aceste entitati precum si pentru cheia primara:

@Entity
@Table(name="tblpachete")
public class PachetGazduire
{
@Id
private int id;

/* aici vin implementate alte proprietati si metodele getter/setter */
@OneToMany(fetch=FetchType.EAGER, mappedBy="id.pachet")
private ArrayList tehnologii;
}


@Entity
@Table(name="tbltehnologii")
public class Tehnologie
{
@Id
private int id;

/* aici vin implementate alte proprietati si metodele getter/setter */
}



/* aici implementez cheia primara compozita */
@Embeddable
public class TehnologiiPachetPK
{
@ManyToOne
@JoinColumn(name="fk_pachet", referencedColumnName="id")
private PachetGazduire pachet;


@ManyToOne
@JoinColumn(name="fk_tehnologie", referencedColumnName="id")
private Tehnologie tehnologie;

/* aici vin implementate alte proprietati si metodele getter/setter */
}



/* aici vine entitatea de legatura */
@Entity
@Table(name="tbltehnologiipachet")
public class TehnologiiPachet
{
@Id
private TehnologiiPachetPK id;

int laCerere;
int nrConturi;
int pretLaCerere;

/* aici vin implementate alte proprietati si metodele getter/setter */
}


Acesta este codul care poate fi testat. In principiu, tabelele care se ascund in spatele acestor entitati pot fi generate relativ usor. O explicatie ce cred ca este binevenita: fetch=FetchType.EAGER. In mod implicit, hibernate face instantiere lazy. Asta inseamna ca vectorul de TehnologiiPachet ar fi incarcat doar daca incerc sa apelez un element din el. Acest caz presupune ca sesiune de hibernate ramane deschisa. Intr-o aplicatie de desktop acest lucru functioneaza, dar pentru o aplicatie de web nu mai este viabil. Din acest motiv folosesc o incarcare EAGER. Asta imi permite ca la orice moment ulterior incarcarii din baza de date accessare unei tehnologii din vector.

Cam atat pentru acum. Voi reveni cu noi solutii pentru probleme mai speciale.

Cosnita Radu!

Niciun comentariu:

Trimiteți un comentariu