peacekim
할 수 있는 것과 할 수 없는 것.
peacekim
전체 방문자
오늘
어제
  • 분류 전체보기 (68)
    • 👨‍🏫ps (44)
      • ❄️프로그래머스 (20)
      • 🔟0️⃣백준 (21)
      • leetcode (3)
    • ✍🏻study (20)
      • 👐java (6)
      • 🍃spring (1)
      • 🥇algorithm (0)
      • 🚘oodp (4)
      • 📒 jpa (3)
      • 👣DB (2)
      • 🌂네트워크 (0)
      • 🎸기타 (3)
      • 👊 kotlin (1)
      • 🫥 jvm (0)
    • 📽project (4)
      • 🎀ReBoN (4)

블로그 메뉴

  • 홈
  • 태그
  • 방명록

인기 글

최근 글

티스토리

hELLO · Designed By 정상우.
peacekim

할 수 있는 것과 할 수 없는 것.

✍🏻study/📒 jpa

연관 관계 편의 메소드❓

2022. 3. 24. 16:00
반응형

연관 관계 편의 메서드라는 말을 공부할 때, 들었고, 김영한님이 이거 실수 하는 사람들 많다고 말씀하셔서, 나는 안 그러겠지라고 했는데, 그랬다,,,이제 실수를 하지 않기 위해서 정리를 하자,,,!!!

 

연관 관계 편의 메서드를 알아보기 전 연관 관계부터 알아보자!!

 

연관 관계란❓

내가 사용하는 JPA는 관계형 DB(MySQL, Oracle, etc)에 대해서 지원을 한다.

관계형 데이터베이스는 키(key)와 값(value)들의 간단한 관계를 테이블화 시킨 매우 간단한 전산정보 데이터베이스이다.
ORM은 Object Relation Mapping 즉, 객체와 관계형 데이터 베이스간의 매핑이라고 말할 수 있다.    

 

위에 관계형 데이터베이스 설명처럼 각 테이블에 관계가 있다. 테이블에서는 왜리키를 통해서 관계를 맺는다.
하지만, 객체는 참조를 사용해서 객체간의 관계를 만든다. 

객체의 관계를 만드는 방식이 둘 간의 차이가 존재하기 때문에, 객체와 관계형 데이터 베이스를 매핑할 때 어렵게 만든다!!

 

연관 관계란 객체와 객체간의 관계, 테이블과 테이블간의 관계가 있는 것을 연관관계라고 할 수 있다.

 

내가 겪은 문제😅

Review라는 엔티티와 review image라는 엔티티, 두 개가 존재했다. 두 엔티티의 관계는 일대다 관계였다. 즉 한개의 리뷰가  여러 개의 review image를 가질 수 있는 관계였다. 

그래서 나는 리뷰 등록을 할 때, 리뷰 이미지에 해당 리뷰를 등록해주는 연관관계 편의 메소드를 사용해서 두 객체의 연관 관계를 맺어주려고 했다. 그래서 처음에는

@Entity
public class Review extends BaseEntity {

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

    @ManyToOne(fetch = FetchType.LAZY)
    private Member member;

    @ManyToOne(fetch = FetchType.LAZY)
    private Shop shop;

    @Embedded
    private ReviewContent reviewContent;

    @Embedded
    @OneToMany(mappedBy = "review", cascade = CascadeType.PERSIST)
    private List<reviewImage> reviewImages = new ArrayList<>();

    @Embedded
    private ReviewScore reviewScore;

    @OneToMany(mappedBy = "review")
    private List<Empathy> empathies = new ArrayList<>();

    public void addReviewImages(ReviewImage reviewImage) {
        this.reviewImages.add(reviewImage);
    }

}

 

처음에는 review에서만 reviewImage를 넣어주고, reviewImage에는 review를 넣어주지 않았다. 그래서 데이터 베이스에 값이 들어갈 때 reviewImage는 review_id가 null로 들어가는 문제가 생겼다. 

연관관계 메소드라는 것이 떠올라, 연관관계 메소드를 만들어 주어서 이 문제를 해결 하였다!!

 

@Entity
@NoArgsConstructor(access = AccessLevel.PROTECTED)
public class ReviewImage {

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

    private String url;

    @ManyToOne(fetch = FetchType.LAZY)
    private Review review;

    public ReviewImage(String url) {
        this.url = url;
    }

    public void belongTo(Review review) {
        this.review = review;
    }
}

 

ReviewImage에서는 belongTo라는 메소드를 추가해줬고!!

review에서 reviewImage를 추가할 때, 해당 메소드를 불러주어, reviewImage에도 review를 매핑해줬다!!

 

 public void addReviewImages(ReviewImage reviewImage) {
        this.reviewImages.add(reviewImage);
        reviewImage.belongTo(this);
 }

 

객체와 테이블은 차이가 있다. 객체는 연관 관계가 있는 두 군데에 모두 참조할 수 있는 객체가 존재해야만, 서로를 참조할 수 있고, 테이블은 외래키 하나만으로 두 객체가 서로 참조할 수 있다.

그래서, 테이블 관점으로 보면, 한곳에만 외래키가 있기때문에, 객체에서도 한곳에서 참조값을 넣어주면, 당연히 들어가겠지라고 생각을 할 수 있다. 하지만, 객체에서는 두군데에 다 참조값을 넣어줘야만, 참조가 가능하기 때문에, 그 점을 잊지말고 두 군데에 넣어주도록 하자,,!!
그리고 두 군데에 넣어 줄 때는 한곳에서만 연관관계 편의메소드를 만들어, 논리적으로 넣는 곳에서 값을 넣을 때 모든 것을 처리할 수 있도록 하자!!

Reference

  • https://www.inflearn.com/course/ORM-JPA-Basic/dashboard
  • 자바 ORM 표준 JPA 프로그래밍 - 김영한님
  • https://ko.wikipedia.org/wiki/%EA%B4%80%EA%B3%84%ED%98%95_%EB%8D%B0%EC%9D%B4%ED%84%B0%EB%B2%A0%EC%9D%B4%EC%8A%A4​
반응형

'✍🏻study > 📒 jpa' 카테고리의 다른 글

영속성 관리  (0) 2022.04.15
JPA N+1 문제  (0) 2022.03.29
    '✍🏻study/📒 jpa' 카테고리의 다른 글
    • 영속성 관리
    • JPA N+1 문제
    peacekim
    peacekim
    할 수 있는 것과 할 수 없는 것. github: https://github.com/PyeongGangKim

    티스토리툴바