@ManyToOne

Disponível

2.1 Vinculando no nível da tabela

Vimos como o Hibernate armazena coleções em tabelas auxiliares. Agora vamos descobrir como organizar relacionamentos entre tabelas completas que armazenam classes Entity reais.

Existem quatro tipos de relacionamentos entre as classes Entity no Hibernate:

  • um para um
  • um para muitos
  • muitos -para- um
  • muitos -para- muitos

E vamos começar a análise com a opção mais simples - muitos para um .

Você já encontrou tal relacionamento entre tabelas no SQL. Aqui está o que geralmente parece:

eu ia nome ocupação salário idade data de afiliação
1 Ivanov Ivan Programador 100000 25 30/06/2012
2 Petrov Petr Programador 80000 23 12/08/2013
3 Ivanov Sergei Testador 40000 trinta 2014-01-01
4 Rabinovich Moisha Diretor 200000 35 2015-05-12
5 Kirienko Anastácia Gerente 40000 25 2015-10-10
6 Vaska Gato 1000 3 2018-11-11

tabela de funcionários:

Esta tabela tem as seguintes colunas:

  • id INT
  • nome VARCHAR
  • ocupação VARCHAR
  • salário INT
  • idade INT
  • data_de_entrada DATE

E é assim que fica a tabela de tarefas , que contém as tarefas para os funcionários:

eu ia ID do Empregado nome prazo final
1 1 Corrigir um bug no front-end 01/06/2022
2 2 Corrigir um bug no back-end 15/06/2022
3 5 comprar café 01/07/2022
4 5 comprar café 01/08/2022
5 5 comprar café 01/09/2022
6 (NULO) Limpe o escritório (NULO)
7 4 Aproveite a vida (NULO)
8 6 Aproveite a vida (NULO)

Esta tabela tem apenas 4 colunas:

  • id – número de tarefa exclusivo (e linhas na tabela);
  • employee_id – ID do funcionário da tabela de funcionários à qual a tarefa está atribuída;
  • nome – nome e descrição da tarefa;
  • deadline - o tempo em que a tarefa deve ser concluída.

Vemos que muitas linhas na tabela de tarefas podem se referir a uma única entrada na tabela de funcionários. Tal relacionamento em nível de tabela é chamado de muitos para um.

2.2 Relação com o nível de classe Java

Além da comunicação no nível da tabela, você também pode organizar a comunicação no nível das classes Entity no Hibernate. Isso é feito com uma anotação @ManyToOne.

Mas primeiro, vamos apenas criar duas classes: Employee e EmployeeTask :

@Entity
@Table(name="employee")
class Employee {
   @Column(name="id")
   public Integer id;

   @Column(name="name")
   public String name;

   @Column(name="occupation")
   public String occupation;

   @Column(name="salary")
   public Integer salary;

   @Column(name="join_date")
   public Date join;
}

E uma segunda classe para armazenar os trabalhos dos funcionários:

@Entity
@Table(name="task")
class EmployeeTask {
   @Column(name="id")
   public Integer id;

   @Column(name="name")
   public String description;

  @Column(name="employee_id")
   public Integer employeeId;

   @Column(name="deadline")
   public Date deadline;
}

Tudo está bem com essas classes, mas não há nenhum relacionamento entre elas que reflita o fato de que o campo employeeId da classe EmployeeTask refere-se ao campo id da classe Employee. É hora de consertar

2.3 Anotação @ManyToOne.

Primeiro, em Java estamos acostumados a operar em objetos (e referências a objetos) em vez de seu id. Em primeiro lugar, em vez do campo employeeId na classe EmployeeTask, vamos apenas apontar para um objeto do tipo Employee. Veja como ficará nossa nova classe:

@Entity
@Table(name="task")
class EmployeeTask {
   @Column(name="id")
   public Integer id;

   @Column(name="name")
   public String description;

   @ManyToOne
   @JoinColumn(name = "employee_id")
   public Employee employee;

   @Column(name="deadline")
   public Date deadline;
}

Com a ajuda da anotação @ManyToOne , indicamos que muitos objetos EmployeeTask podem se referir a um objeto do tipo Employee. Além disso, através da anotação @JoinColumn , indicamos em qual coluna da nossa tabela está armazenado o id do objeto Employee.

2.4 Exemplos de solicitação

E agora vamos mostrar alguns exemplos de como o Hibernate pode trabalhar com essas classes relacionadas.

Cenário um

Vamos escrever uma consulta para descobrir todas as tarefas atribuídas a um usuário específico. Veja como essa consulta ficaria em HQL:

from EmployeeTask where employee.name = "Ivan Ivanovich"

Você pode simplesmente se referir a campos de classes dependentes por meio de um ponto. É muito confortável. Mas ainda vamos escrever esta consulta na forma de código Java:

String hql = "from EmployeeTask where employee.name = :username";
Query<EmployeeTask> query = session.createQuery( hql, EmployeeTask.class);
query.setParameter("username", "Ivan Ivanovich");
List<EmployeeTask> resultLIst = query.list();

cenário dois

Vamos escrever uma consulta que retorne uma lista de funcionários com tarefas atrasadas. Uma tarefa está atrasada se seu prazo final estiver no passado. Veja como essa consulta ficaria em SQL:

SELECT DISTINCT employee.*
FROM task JOIN employee ON task.employee_id = employee.id
WHERE task.deadline < CURDATE();

DISTINCTé usado porque pode haver muitas tarefas atribuídas a um usuário.

E agora vamos escrever a mesma consulta em HQL:

select distinct employee from EmployeeTask where deadline < CURDATE();

Funcionário nesta consulta é um campo da classe EmployeeTask

Situação três

Atribua todas as tarefas não atribuídas ao diretor. A consulta SQL ficará assim:


UPDATE task SET employee_id = 4 WHERE employee_id IS NULL

E agora vamos escrever a mesma consulta em HQL:

update EmployeeTask set employee = :user where employee is null

A última consulta é a mais difícil. Precisamos passar o ID do diretor, mas a classe EmployeeTask não contém um campo onde podemos escrever um id, ao contrário, contém um campo Employee onde precisamos atribuir uma referência a um objeto do tipo Employee.

Employee director = session.get(Employee.class, 4);

String hql = "update EmployeeTask set employee = :user where employee is null";
Query<EmployeeTask> query = session.createQuery(hql, EmployeeTask.class);
query.setParameter("user", director);
query.executeUpdate();
Comentários
  • Populares
  • Novas
  • Antigas
Você precisa acessar para deixar um comentário
Esta página ainda não tem nenhum comentário