외래 키(FK) 역할을 객체 참조를 통해 선언하는 역할
현재 객체는 Member 가 Team을 가졌으나,
Team 은 Member를 가지지 못한다
이것이 객체 참조와 외래키 (FK ) 의 가장 큰 차이점
테이블은 FK만 있으면 양쪽에 연관관계를 알 수 있다.
// TEAM 테이블 @OneToMany(mappedBy = "team") // Member테이블의 변수명과 동일해야한다 private List<Member> member = new ArrayList<Member>(); // Member 테이블 @ManyToOne // Team 클래스에서 "하나" 가져오기 @JoinColumn(name = "TEAM_ID") // 연관 컬럼 이어주기 , TEAM 명칭과 반드시 동일해야한다 private Team team;
관계 2개
Member 객체 에서 -> Team 객체로 연관관계 1개 ( 단 방향 )
Team 객체에서 -> Member객체로 가는 연관관계 1개 ( 단 방향 )
= 따라서 관계는 2개
양방향 매핑이긴 하나
사실은 단방향 매핑이 2개가 있는 것.
Member 에서 Team 으로 가는 Team 참조 값과, ( Member to Team )
Team 에서 Member로 가는 Member 참조 값이 있다. ( Team to Member )
그런데 만약
Member 에서 Team 값이 수정 되었을 때, Member 테이블의 TEAM_ID 가 수정되어야 하는지,
Team 에서 Member 값을 수정해야하는지 딜레마 가 있다.
양방향 테이블에서 수정이 발생할 때,
DB입장에서는 Member 테이블에 있는 TEAM_ID 만 Update 시키면 된다.
단, 이때 양방향 매핑 규칙(연관관계의 주인) 을 따라야 한다.
객체의 두 관계 중 하나를 연관관계의 주인으로 지정
오직 연관관계의 주인만이 외래 키를 관리 및 수정이 가능하다.
( 주인이 아니라면 읽기 전용 )
주인은 @MappedBy 속성을 사용하지 않는다.
따라서 Member 테이블에서 수정하면
TEAM 테이블 은 수정사항이 반영이 되는 구조.
연관관계 편의 메소드를 생성하라
member.setTeam(team); team.getMember().add(member);
하위 테이블에도 TEAM 단방향 추가 +
상위 테이블에도 MEMBER 단방향 추가 +
@ManyToOne // Team 클래스에서 "하나" 가져오기 @JoinColumn(name = "TEAM_ID") // 연관 컬럼 이어주기 , TEAM 명칭과 반드시 동일해야한다 @Setter(value = AccessLevel.NONE) // lombok 옵션 setter 설정을 막는다 private Team team; // 단방향 2개 설정 메소드 public void changeTeam(Team team) { this.team = team; team.getMember().add(this); // = team.getMember().add(member); } }
public void addMember(Member member) { member.setTeam(this); this.member.add(member); }
단 방향 매핑 만으로도 연관관계 매핑을 완료가 된다
양 방향 매핑은 반대 방향으로 조회기능이 추가된 것 뿐이다.
양방향 사용이유 = JPQL 에서 역방향으로 탐색(조회)할 일이 많음
단 방향매핑을 필수로 하되, 양 방향매핑은 필수적이지 않다
( 테이블에 영향을 주지않기에 필요할 경우에만 양 방향매핑 기능을 추가한다 )