I am confused regarding the difference of OneToOne vs ManyToOne (not OneToMany).
Lets assume we have a Person class and a Department Class. When we say Many Persons can belong to one Department, we assume a ManyToOne relation and add a DeptID column in the Person class. This is what makes sense to me and works as said.
However, if we say that Person and Department has a OneToOne relation, this means one person has only one department and one department as only one person. However, this is where the problem comes. JPA allows two Person objects to share the same department nonetheless.
Person Class:
@Entity
@Table
public class Person {
@Id
@GeneratedValue(strategy= GenerationType.IDENTITY)
int id;
@Column
int age;
@Column(length = 20)
String name;
@Column(length = 20, nullable = true)
String cnic;
@Column(nullable = true)
boolean married;
@OneToOne
Department dep;
}
Department Class:
@Entity
public class Department {
@Id
int Id;
@Column
String name;
}
Making two Persons with same Department:
public void testOTO() {
System.out.println("Testing OTO");
Department dep = new Department(202, "CS");
depdb.saveAndFlush(dep);
Person p1 = new Person();
Person p2 = new Person();
p1.setDep(dep);
p2.setDep(dep);
db.saveAndFlush(p1);
db.saveAndFlush(p2);
}
I wanted to ask, is the difference between OneToOne and ManyToOne just semantic or am I missing something?
CodePudding user response:
JPA itself does not control if your one-to-one relationship is indeed one-to-one. But your database schema can. Just add a unique constraint to the foreign key column.
The reason JPA does not check this is, because it would be really expensive to do so on the application side. JPA would need to obtain a lock on the foreign key column for the whole table and then check that the value about to be inserted isn't there.
Database constraints on the other hand are mode for this. And while they still require locking, they only lock the index and they do it automatically.
I'm not sure if the popular JPA implementations generate the unique constraint when they generate the schema. If they don't, this might be because it would collide with certain scenarios where there exists two identical values for a short time. If you encounter such problems after creating a unique constraint you might want to check if your database supports deferred constraints.