1

I was trying to use FetchMode.JOIN in Hibernate to understand but facing certain issues . I have 3 classes Department , Employee and EmployeeMain Class. Department has oneToMany relation with Employee .

Below is the code Department Class :-

@Entity @Table(name="DEPARTMENT") public class Department { @Id @GeneratedValue @Column(name="DEPARTMENT_ID") private Long departmentId; @Column(name="DEPT_NAME") private String departmentName; @OneToMany(mappedBy="department") @Fetch(FetchMode.JOIN) private List<Employee> employees = new ArrayList<>(); public Long getDepartmentId() { return departmentId; } public void setDepartmentId(Long departmentId) { this.departmentId = departmentId; } public String getDepartmentName() { return departmentName; } public void setDepartmentName(String departmentName) { this.departmentName = departmentName; } public List<Employee> getEmployees() { return employees; } public void setEmployees(List<Employee> employees) { this.employees = employees; } } 

Employee class :-

@Entity @Table(name="EMPLOYEE") public class Employee { @Id @GeneratedValue @Column(name="employee_id") private Long employeeId; @Column(name="firstname") private String firstname; @Column(name="lastname") private String lastname; @Column(name="birth_date") private Date birthDate; @Column(name="cell_phone") private String cellphone; @ManyToOne @JoinColumn(name="department_id") private Department department; public Employee() { } public Department getDepartment() { return department; } public void setDepartment(Department department) { this.department = department; } public Employee(String firstname, String lastname, String phone) { this.firstname = firstname; this.lastname = lastname; this.birthDate = new Date(System.currentTimeMillis()); this.cellphone = phone; } public Long getEmployeeId() { return employeeId; } public void setEmployeeId(Long employeeId) { this.employeeId = employeeId; } public String getFirstname() { return firstname; } public void setFirstname(String firstname) { this.firstname = firstname; } public String getLastname() { return lastname; } public void setLastname(String lastname) { this.lastname = lastname; } public Date getBirthDate() { return birthDate; } public void setBirthDate(Date birthDate) { this.birthDate = birthDate; } public String getCellphone() { return cellphone; } public void setCellphone(String cellphone) { this.cellphone = cellphone; } 

}

Main Class :-

public class EmployeeMain { public static void main(String[] args) { SessionFactory sessionFactory = new Configuration().configure("hibernate.xml").buildSessionFactory(); Session session = sessionFactory.openSession(); session.beginTransaction(); Department department1 = new Department(); department1.setDepartmentName("Sales"); session.save(department1); Department department2 = new Department(); department2.setDepartmentName("Operations"); session.save(department2); Employee emp1 = new Employee("Nina", "Mayers", "111"); Employee emp2 = new Employee("Tony", "Almeida", "222"); Employee emp3 = new Employee("Rina", "Coyeet", "333"); Employee emp4 = new Employee("Mary", "Land", "444"); emp1.setDepartment(department1); emp2.setDepartment(department1); emp3.setDepartment(department2); emp4.setDepartment(department2); department1.setEmployees(new ArrayList<Employee>()); department1.getEmployees().add(emp1); department1.getEmployees().add(emp2); department2.getEmployees().add(emp3); department2.getEmployees().add(emp4); session.save(emp1); session.save(emp2); session.save(emp3); session.save(emp4); session.getTransaction().commit(); session.close(); session = sessionFactory.openSession(); session.beginTransaction(); List<Department> departmentList = session.createQuery("from Department").list(); for(Department department : departmentList){ department.getEmployees(); } } } 

I have inserted 2 departments and 2 Employees under each department . Even though in the Department class I have mentioned @Fetch(FetchMode.JOIN) for employees object still the query for Employees is run twice once for each department . That is basically if I mentioned correctly is the N+1 select problem . But according to me if the FetchMode is Join then a single query would have been fired joining Employee and department and should have fetched the data . But the following queries were fired . Query 1

Hibernate: select department0_.DEPARTMENT_ID as DEPARTME1_0_, department0_.DEPT_NAME as DEPT_NAM2_0_ from DEPARTMENT department0_ 

Query 2

Hibernate: select employees0_.department_id as departme6_0_0_, employees0_.employee_id as employee1_1_0_, employees0_.employee_id as employee1_1_1_, employees0_.birth_date as birth_da2_1_1_, employees0_.cell_phone as cell_pho3_1_1_, employees0_.department_id as departme6_1_1_, employees0_.firstname as firstnam4_1_1_, employees0_.lastname as lastname5_1_1_ from EMPLOYEE employees0_ where employees0_.department_id=? 

Query 3

Hibernate: select employees0_.department_id as departme6_0_0_, employees0_.employee_id as employee1_1_0_, employees0_.employee_id as employee1_1_1_, employees0_.birth_date as birth_da2_1_1_, employees0_.cell_phone as cell_pho3_1_1_, employees0_.department_id as departme6_1_1_, employees0_.firstname as firstnam4_1_1_, employees0_.lastname as lastname5_1_1_ from EMPLOYEE employees0_ where employees0_.department_id=? 

1 Answer 1

5

HQL queries do not fetch associations based on annotations. To achieve this goal you have do specify the fetch strategy in the HQL query:

from Department d inner join fetch d.employees 
Sign up to request clarification or add additional context in comments.

Comments

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.