One-to-One Relationship Spring Data JPA

One-to-One Relationship Spring Data JPA

ยท

2 min read

In this article, we will quickly learn to implement one-to-one relationships between entities in Spring Boot JPA.

There are mainly three types of relationship between the entities:

  1. One-to-One
  2. One-to-Many/Many-to-One
  3. Many-to-Many

One-to-One Relationship

A one-to-one relationship is a relationship where a record in one table is associated with exactly one record in another table Let's take an example of Person entity which has one-to-one mapping with passport entity.

The person and passport classes are using Lombok to reduce boilerplate code, I suggest you to go through Lombok article .

PersonEntity.java

@Entity
@Table(name = "person")
@Getter @Setter @Builder
@NoArgsConstructor
@AllArgsConstructor
public class PersonEntity {

    @Id
    @Column(name = "person_id")
    @GeneratedValue(strategy = GenerationType.AUTO)
    private Integer personId;

    @Column(name = "person_name")
    private String personName;

    @OneToOne(cascade = CascadeType.ALL)
    @JoinColumn(name = "passport_number", unique = true)
    private PassportEntity passport;

}

PassportEntity.java

@Entity
@Table(name = "passport")
@Getter  @Setter  @Builder
@NoArgsConstructor
@AllArgsConstructor
public class PassportEntity {

    @Id
    @Column(name = "passport_id")
    @GeneratedValue(strategy = GenerationType.AUTO)
    private Integer passportId;

    @Column(name = "passport_number")
    private String passportNumber;

    @Column(name = "country")
    private String country;

    @Column(name = "passport_type")
    private String passportType;

    @OneToOne(mappedBy = "passport")
    private PersonEntity person;
}

The relationship in database ER Diagram is represented as follow.

image.png

In the above example, the meaning of CascadetType.ALL is that the persistence will propagate (cascade) all EntityManager operations (PERSIST, REMOVE, REFRESH, MERGE, DETACH) to the relating entities.

@JoinColumn(name = "passport_number", unique = true) specifies the column to join the entity association.

name attribute specifies the name of the foreign key column.

unique attribute specifies that the foreign key column is a unique attribute.

mappedBy attribute specifies the field that owns the relationship.

Testing

Let's see a test case to test the bidirectional one-to-one relationship between Person and Passport.

@SpringBootTest
@TestInstance(TestInstance.Lifecycle.PER_CLASS)
public class EntityMappingApplicationTests {


    @Autowired
    private PersonRepository personRepo;

    @Autowired
    private PassportRepository passportRepository;    

    private PersonEntity person = null;
    private PassportEntity passport = null;

    private Integer personId;

    @BeforeAll
    public void setup() {
        passport = PassportEntity.builder()
                .passportNumber("A1234567")
                .country("India")
                .passportType("Diplomatic")
                .build();

        person =  PersonEntity.builder()
                .personName("John Doe")
                .passport(passport)
                .cards(cards)
                .build();

        person = personRepo.save(person);
        personId = person.getPersonId();
    }

    @Test
    public void testOneToOne() {

        PersonEntity person  = personRepo.findById(personId).orElse(null);

        assertNotNull(person.getPassport());
        assertEquals("A1234567", person.getPassport().getPassportNumber());

        PassportEntity passport = passportRepository.findByPassportNumber("A1234567");

        assertNotNull(passport.getPerson());
        assertEquals("John Doe", passport.getPerson().getPersonName());

    }
}

On running this test case, we will find all these test cases runs successfully and verifies that our implementation is correct.

Summary

In this article, we learnt about implementation of one-to-one mapping relationship in Spring Data JPA. The other mapping relationship in Spring Data JPA will be discussed in further post.

You can find the source code of this post @ Github

ย