인프런 커뮤니티 질문&답변

zzzzz님의 프로필 이미지

작성한 질문수

실전! 스프링 부트와 JPA 활용1 - 웹 애플리케이션 개발

엔티티 필드 순서에 대해 질문드립니다.

작성

·

155

·

수정됨

0

@Entity
@Table(name = "orders")
@Getter
@Setter
@NoArgsConstructor(access = AccessLevel.PROTECTED)
public class Order {

    @Id
    @GeneratedValue
    @Column(name = "order_id")
    private Long id;

    @ManyToOne(fetch = FetchType.LAZY)
//    @ManyToOne
    @JoinColumn(name = "member_id")
    private Member member;

    @JsonIgnore
    @OneToMany(mappedBy = "order", cascade = CascadeType.ALL)
    private List<OrderItem> orderItems = new ArrayList<>();

    @JsonIgnore
    @OneToOne(fetch = FetchType.LAZY, cascade = CascadeType.ALL)
//    @OneToOne
    @JoinColumn(name = "delivery_id")
    private Delivery delivery;

    private LocalDateTime orderDate; //주문시간

    @Enumerated(EnumType.STRING)
    private OrderStatus status; //주문상태 [ORDER, CANCEL]

 

 

  1. 이렇게 작성하면 보면 h2에서 필드에 작성한대로 id ||member || delivery 이렇게 나와야 하는데

저는 member || delivery ||id 이렇게 나 순서가 보장되지 않게 나옵니다.

인터넷에 찾아보니 엔티티 필드 순서가 데이터베이스의 컬럼 순서를 결정하지 않기 때문에 schema-generation.scripts.create-target을 주어야 한다고 나와있는데 해당 강의 코드를 보아도 저런 걸 설정하지 않았는데 강의에서는 어떻게 필드가 순서가 보장이 되었나요?

1번답변을 https://www.inflearn.com/questions/17359/hbm2ddl-%EB%A5%BC-%EC%9D%B4%EC%9A%A9%ED%95%B4-%ED%85%8C%EC%9D%B4%EB%B8%94-%EC%83%9D%EC%84%B1%EC%8B%9C-%EC%BB%AC%EB%9F%BC-%EC%88%9C%EC%84%9C-%EC%88%98%EC%A0%95-%EB%B0%A9%EB%B2%95

여기서 찾았는데요. 실무에서는 ddl을 직접입력하라는건데요. 그런데 궁금한점이 실무에서는 fechjoin이나 joincolum을 안쓰나요? ddl을 입력하는거면 joincolum(외래키)까지 같이입력하는거 아닌가요?

 2. @ManyToOne 컬럼에서 조인할 때 데이터 테이블명을 기준으로 조인하고 OneToMany는 mappedBy 할 때 클래스명을 기준으로 하는것처럼 보입니다. 혹시 이유 좀 알 수 있나요? OneToMany에서 자기 자신을 바라봐서 mapped by여도 참조는 둘다 똑같이 클래스로 들어가거나 테이블명으로 들어가야 하는거 아닌가요?

3.엔티티 설계시 주의점 24분에서 질문이있습니다. 아래처럼 연관관계 메소드는 중심이 되는지점에 입력하라고 하셨는데요. member 메소드에는 왜 getOrders() 에서 add()이고 orderItem은 왜 그냥 add(orderItem);만 붙나요? 저는 orders가 리스트라서 getOrders로 붙이는 줄 알았는데 orderItems도 리스트라서요.

 

그리고 orderItem에서 가르키는 this는 무엇인가요? 매소드 내에서 this가 없어요. this 우선순위가 메소드 내부에 this가 있을 때 this를 지칭하고 나머지는 클래스를 지칭하는건가요?

// setMember 메서드는 Order 객체에 Member 객체를 연결하고, 역방향으로도 Member의 주문 목록에 이 Order를 추가합니다.
public void setMember(Member member) {
    // 현재 Order 객체의 member 필드에 매개변수로 받은 Member 객체를 할당합니다.
    this.member = member;

    // Member 객체의 getOrders 메서드를 호출해 주문 목록을 가져온 뒤, 현재 Order 객체(this)를 그 목록에 추가합니다.
    // 이는 Member 객체 내부의 주문 목록에도 현재 Order 객체가 포함되도록 하는 역방향 연결을 설정합니다.
    member.getOrders().add(this);
}


public void addOrderItem(OrderItem orderItem) {
    orderItems.add(orderItem);
    orderItem.setOrder(this);
}

답변 1

0

안녕하세요. zzzzz님, 공식 서포터즈 코즈위버입니다.

  1. 네 맞습니다. 테이블 스키마를 작성할 때는 P.K, F.K도 직접 작성해야 하는데요, 이 때 컬럼 명이 엔터티에 작성한것과 일치하지 않으면 문제가 생깁니다. 엔터티의 @JoinColumn 작성한 필드명이 DDL에 동일한 이름으로 명시되어 있어야 합니다.

  2. @JoinColum 에서 name 은 테이블의 컬럼명을 명시하게 되어 있고, @OneToMany의 mappedBy 는 엔터티의 필드명을 작성하는것이 스펙입니다. 이 부분은 혼동하기 쉬운 부분이라고 동감합니다.

  3. 이 부분은 질문을 조금더 보충해서 설명해주시길 부탁드립니다 🙂 메서드 안에서 this 는 클래스의 '인스턴스' 자신을 지칭하는 키워드 입니다.

감사합니다.

zzzzz님의 프로필 이미지
zzzzz
질문자

  1. ddl이 예를들어 아래처럼 이면요. 여기서 @JoinColumn이 어떻게 작성되는거에요?

     

  2. CREATE TABLE superheroes ( id INTEGER PRIMARY KEY AUTOINCREMENT, 이름 TEXT NOT NULL, 직업 TEXT NOT NULL, 능력 TEXT, 국적 TEXT, 소속회사 TEXT, 나이 INTEGER );

    출처: https://edder773.tistory.com/186 [개발하는 차리의 공부 일기:티스토리]

zzzzz님의 프로필 이미지
zzzzz
질문자

3번 추가 질문입니다.

member.getOrders().add(this);<-setMember(Member member) {부분

orderItems. add(orderItem);<-void addOrderItem(OrderItem orderItem)

왜 같은 add면서 위에는 getOrders()가 붙고 아래는 안붙어요?

슈퍼히어로 테이블이 만약 시민 테이블의 시민번호를 외래키로 참조한다고 가정하면

테이블 생성 쿼리는 아래와 같습니다.

CREATE TABLE superheroes ( 
    hero_id BIGINT AUTOINCREMENT, 
    civil_id BIGINT,
    이름 TEXT NOT NULL, 
    직업 TEXT NOT NULL, 
    능력 TEXT, 
    국적 TEXT, 
    소속회사 TEXT, 
    나이 INTEGER. 
    PRIMARY KEY (hero_id),
    FOREIGN KEY (civil_id) REFERENCES civil(civil_id)
);

 

이 경우 SuperHeroes 엔터티의 설정은 다음과 같아야 합니다.

(정확한 코드는 아니고 개략적인 내용만 확인해주세요)

@Entity
public class SuperHeroes {
    @Id
    @Column(name = "hero_id")
    private Long id

    @ManyToOne(...)
    @JoinColumn(name = "civil_id")
    private Civil civil;
}

@Entity
public class Civil {
    @Id
    @Column(name = "civil_id")
    private Long id;

    @OneToMany(mappedBy="civil")
    List<SuperHeroes> heroList = new ArrayList<>();
}

 

감사합니다.

zzzzz님의 프로필 이미지

작성한 질문수

질문하기