2012-09-19 15 views
8

Tengo 2 entidades/tablas de hibernación y necesito combinar información de ambas para usar en una vista. Las tablas sonLa mejor manera de unir 2 tablas usando Hibernate

Table Client: 
    clientId, 
    firstName, 
    lastName, 
    phone, 
    cellPhone 

Table Appointment: 
    apptTime, 
    clientId (and some other fields I don't need now) 

Existe una relación uno a muchos entre el cliente y la Cita, basada en clientID. En SQL regular, simplemente diría algo como:

Select 
    client.clientId, 
    appt.apptTime, 
    client.firstName, 
    client.lastName 
from 
    Client client, 
    Appointment app 
where 
    client.clientId = appt.clientId 

y use el conjunto de registros que se devolvió.

No estoy seguro de cómo hacer esto en Hibernate. ¿Debo crear una entidad ClientAppt y luego hacer algo como la selección anterior (modificado algo para HQL)?

Nota, pensé en usar el método SecondaryTable, pero creo que eso requiere una relación de 1 a 1? Supongo que podría mapear uno a muchos, pero ¿hay alguna alternativa? Este es un cambio de una vez y mapear una relación de uno a muchos puede ser un poco caro para algo tan pequeño? ¿Cuál es el mejor enfoque? Gracias

Respuesta

2

Puede modelar esto de muchas maneras. Lo que haría es hacer que el Cliente sea una Entidad, y que las diversas citas sean una colección de elementos. No ha especificado el idioma, pero en Java que sería como:

@Entity 
@Table(name="person") 
public class ClientAppts { 
    ... 

    @OneToMany(mappedBy="client") 
    Set<Appointment> appointments; 
} 

@Entity 
@Table(name="person") 
public class Appointment { 
    .... 

    @ManyToOne 
    @JoinColumn(name="person_id") 
    private ClientAppts client; 

    .... 
}  

A continuación, puede ir a buscar clientes utilizando cualquier método que prefiera, con el ser más simple:

session.get(Client.class, clientId); 

Hibernate hacer la unión y devolver un objeto Cliente con un conjunto de citas. Puede ir más allá para hacer que el conjunto sea SortedSet, o agregarle un índice para hacerlo una lista.

+0

Gracias, sharakan. Creo que probaré este método y veré qué pasa. – Dave

+0

sharakan, probé tu método pero me aparece un error. La descripción está aquí - http: // stackoverflow.com/questions/12502850/class-not-mapped-exception-but-it-is-mapped – Dave

+0

OK, a partir de la definición de cita que tiene allí (especialmente el hecho de que tiene una identificación, de la que no tenía conocimiento) , Creo que de hecho quieres una Entidad. Actualizaré mi respuesta. Sin embargo, no puedo comentar sobre la falta de mapeo, no estoy familiarizado con la configuración de Glassfish. – sharakan

1

Debe usar Projections.alias para especificar la lista de columnas que le interesan. Consulte el manual de hibernación here por ejemplo.

0

¿Ha anotado su código con los metadatos de las relaciones? Si lo hiciera, debería poder consultar la lista de clientes y luego obtener sus citas accediendo al campo que los contiene.

4

La "mejor" manera (imho) es no pensar en la forma normal de SQL. No piense en seleccionar ciertos campos y hay tablas a las que se está uniendo. Debería tratar de crear entidades comerciales significativas y debería trabajar en esas entidades comerciales.

Por ejemplo, aquí es lo que haría:

(código no real, simplemente mostrar la idea)

@Entity 
public class Client { 
    @Id 
    @Column(name="clientId") 
    private Long id; 

    @Column 
    private String longName; 
} 

@Entity 
public class Appointment { 
    @Id 
    private Long id; 

    @ManyToOne 
    @Column(name="clientId") 
    private Client client; 
} 

Con la asignación anterior, lo que hay que hacer es nada más que una HQL from Appointment a where a.client.id = :whatEverIdYouWant, o, para guardar la consulta adicional a DB, from Appointment a join fetch a.client where a.client.id = :whatEverIdYouWant

también puede agregar el mapeo de @ Sharakan si su diseño no le importa cliente dependiendo de nombramiento

0
public class Appoinment { 

@Override 
public List<Appointment > methodName(String search) { 
    String hql =" from Appointment a join fetch a.client where a.client.id = 
        :search"; 

    Query<Appointment > query=this.getSession().createQuery(hql,Appointment 
      .class); 
    Long id=-1L; 
    try { 
     id=Long.parseLong(search); 
    }catch (NumberFormatException ex) { 
     ex.printStackTrace(); 
    } 
    query.setParameter("id", id); 
    query.setParameter("search", "%" +search+ "%"); 
    return query.getResultList(); 
} 

} 
Cuestiones relacionadas