DraegerMTN
DraegerMTN

Reputation: 1131

How to correctly set up @OneToOne relationship with JPA Hibernate?

I'm quite new to this and I am attempting to set up a simple one-to-one relationship between a Student object and their Grades object. I'm using spring boot with the hsqldb in-memory database. I'll show my code first then explain my issues.

Student.java

@Entity
public class Student {

  @Id
  @GeneratedValue(strategy = GenerationType.AUTO)
  private Long id;

  private String firstName;
  private String lastName;

  @OneToOne(cascade = CascadeType.ALL)
  private Grades grades;

  //Getters and setters
}

Grades.java

@Entity
  public class Grades {

  @Id
  @GeneratedValue(strategy = GenerationType.AUTO)
  private Long id;

  private int midterm;
  private int finalExam;

  @OneToOne(cascade = CascadeType.ALL)
  private Student student;

  //Getters and setters
}

StudentRepository.java

public interface StudentRepository extends JpaRepository<Student, Long> {
}
  1. Is my setup for Student and Grades correct? I just one a simple one-to-one relationship where I store the Grades ID in a Student object as a foreign key.

  2. Whenever I create a Grades object using new Grades() and pass that into a Student object in the constructor, it allows me to assign the same Grades object to multiple students. How is that possible when they're annotated with one-to-one?

  3. I turned on hibernate sql logging to see what is happening when using the database. It seems to store grades_id in a Student object just fine, but it shows student_id in the Grades object as being null. Why is this null?

Thanks for any help.

Upvotes: 0

Views: 1095

Answers (1)

vhula
vhula

Reputation: 497

Is my setup for Student and Grades correct?

It's questionable. Both sides of the relationship are mapped as owners of the relationship. One of them should be mapped as the owner, and other should use mappedBy attribute of the @OneToOne annotation. @OneToOne

Whenever I create a Grades object using new Grades() and pass that into a Student object in the constructor, it allows me to assign the same Grades object to multiple students. How is that possible when they're annotated with one-to-one?

You should create composite primary key or use uniqueness constraint to forbid using the same Grades record by multiple Students.

I turned on hibernate sql logging to see what is happening when using the database. It seems to store grades_id in a Student object just fine, but it shows student_id in the Grades object as being null. Why is this null?

Looks like Hibernate generated both tables with a foreign key column. Only one should have been generated.

You have to specify one side as an owner of the relationship. The other side should use mappedBy attribute of the @OneToOne annotation to tell Hibernate where is the mapping of the relationship.

...
@OneToOne(mappedBy="grades")
private Student student;
...

Upvotes: 1

Related Questions