JPA / Hibernate Architecture
💡 체크: 객체는 '참조'를 통해 관계를 맺고, DB 테이블은 '외래 키(FK)'를 통해 관계를 맺는다.
1. 연관 관계의 4가지 유형
- @OneToOne (1:1): 회원이 하나의 프로필을 가지는 것과 같은 관계
- @ManyToOne (N:1): 여러 개의 게시글이 하나의 게시판에 속하는 관계입니다. 실무에서 가장 많이 쓰이는 구조
- @OneToMany (1:N): 하나의 부서에 여러 사원이 있는 관계입니다. 보통 N:1의 반대 방향
- @ManyToMany (N:M): 학생과 과목의 관계입니다. 실무에서는 사용을 지양하고, 중간 엔티티를 두어 1:N - N:1로 풀어내는 것이 정석입니다.
2. 단방향 vs 양방향, 그리고 '주인'
객체는 한 쪽만 참조하면 단방향, 양쪽이 서로 참조하면 양방향이 됩니다. 여기서 가장 중요한 개념이 바로 연관 관계 이다.
⚠️ 핵심 원칙: 외래 키(FK)를 가진 엔티티가 주인이다
주인만이 데이터베이스의 외래 키를 등록, 수정할 수 있고 , 주인이 아닌 쪽은
주인만이 데이터베이스의 외래 키를 등록, 수정할 수 있고 , 주인이 아닌 쪽은
mappedBy 속성을 통해 조회만 가능하다3. 코드로 보는 N:1 양방향 관계
// 주인 (Many 쪽): 외래 키를 직접 관리함
@Entity
public class Memo {
@Id @GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
@ManyToOne
@JoinColumn(name = "user_id") // 외래 키 이름 설정
private User user;
}
// 주인이 아닌 쪽 (One 쪽): mappedBy로 연결됨
@Entity
public class User {
@Id @GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
@OneToMany(mappedBy = "user") // Memo 엔티티의 user 필드에 의해 매핑됨
private List<Memo> memoList = new ArrayList<>();
}
4. 체크
- @JoinColumn의 위치: 주인이 되는 엔티티의 필드에
@JoinColumn을 선언해야 합니다.
정리
JPA 연관 관계의 핵심은 "DB의 FK를 누가 관리하느냐"를 결정하는 것.
Q1. 연관 관계의 주인(Owner)이란 무엇이며, 왜 정해야 하나요?
- 답변: 객체의 양방향 관계에서 어느 쪽이 데이터베이스의 외래 키(Foreign Key)를 관리할지 결정하는 것입니다. 주인이 아닌 쪽은 조회만 가능하며(mappedBy), 주인만이 외래 키의 등록 및 수정을 담당합니다. 이를 정하지 않으면 스프링은 양쪽 참조가 변할 때마다 어떤 정보를 기준으로 DB를 업데이트할지 판단할 수 없게 되어 정합성이 깨질 수 있습니다.
Q2. mappedBy의 역할은 무엇인가요?
- 답변: 양방향 관계에서 "나는 연관 관계의 주인이 아니며, 저 필드에 의해 매핑된 거울일 뿐이다"라고 선언하는 속성입니다. mappedBy가 적힌 필드는 데이터베이스 테이블에 어떠한 영향을 주지 않고, 오직 객체 그래프 탐색(조회) 용도로만 사용됩니다.
Q3. 실무에서 @ManyToMany를 지양하는 이유는 무엇인가요?
- 답변: @ManyToMany를 사용하면 JPA가 중간 테이블을 자동으로 생성해주지만, 실무에서는 그 중간 테이블에 단순히 ID값들만 들어가는 경우가 드뭅니다. 보통 생성일, 수량 같은 추가적인 정보가 필요한데, 자동 생성된 테이블에는 이를 추가할 수 없습니다. 따라서 중간 엔티티 클래스를 직접 만들어 1:N, N:1 관계로 풀어내는 것이 확장성과 유지보수 면에서 훨씬 유리합니다.
Q4. 양방향 연관 관계 사용 시 주의할 점은 무엇인가요?
- 답변: 가장 큰 주의점은 무한 루프입니다. JSON 직렬화(Lombok의 @ToString 등) 과정에서 서로를 계속 참조하다가 StackOverflowError가 발생할 수 있습니다. 또한, 순수 자바 객체 상태에서도 양쪽 모두에 값을 세팅해주지 않으면 한 쪽에서만 조회가 되는 등의 상태 불일치가 발생할 수 있으므로 연관 관계 편의 메서드 작성이 필수적입니다.
'Spring > spring 숙련' 카테고리의 다른 글
| RestTemplate (0) | 2026.04.09 |
|---|---|
| Vaildation (1) | 2026.04.09 |
| Session/Cookie/Filter/Listener (0) | 2026.04.09 |
| 쿠키(Cookie)와 세션(Session) (1) | 2026.04.09 |
| 인증(Authentication) vs 인가(Authorization) (0) | 2026.04.09 |
