Monday 24 September 2012

JPA Hibernate one-to-many bidirectional mapping on List

This article illustrates how to use JPA and Hibernate annotation to do one-to-many bidirectional mapping for ordered entities.

The One side is the Teacher entity

@Entity
public class Teacher {
 
    @Id
    @GeneratedValue(strategy=GenerationType.AUTO)
    private int id;
 
    @Column
    private String name;
 
    @OneToMany(cascade={CascadeType.ALL}, fetch=FetchType.EAGER)
    @JoinColumn(name="STU_ID")
    @IndexColumn(name="IDX")
    private List<Student> students = new ArrayList<Student>();
  
    public Teacher(String name) {
        super();
        this.name = name;
    }
 
    public Teacher() {
        super();
    }

    public void addStudent(Student s){
        students.add(s);
        s.setTeacher(this);
    }

    //Setters and getters
}

Note the Teacher class has a List of Students, not a Set of Students. The @IndexColumn annotation is used to specify which column in Student table to store the index.

The Many side is the Student entity

@Entity
public class Student {
    @Id
    @GeneratedValue(strategy=GenerationType.AUTO)
    private int id;
 
    @Column
    private String name;
 
    @ManyToOne
    @JoinColumn(name="STU_ID", 
            insertable=false, updatable=false)
    private Teacher teacher;

    public Student(String name) {
        Super();
        this.name = name;
    }
 
    public Student() {
        super();
    }

    //Setters and getters 
}

The name attribute of @JoinColumn for Teacher and Student should match one another (in this case, it is "STU_ID").

Write a JUnit test case


public void testTeacherDao(){
    TeacherDao dao = (TeacherDao)applicationContext.getBean("teacherDao");
    Teacher teacher = new Teacher("t1");
    teacher.addStudent(new Student("s1"));
    teacher.addStudent(new Student("s2"));
    dao.save(teacher);
}            


Output:

Teacher table





Student table






This example works in Hibernate 4.1.7.