Aggregate를 어떤 저장소에 구현할까?
ORM: 객체기반 도메인 모델 - 관계형 데이터 모델 간 매핑을 처리하는 기술
Java에서는 ORM 표준인 JPA를 주로 사용한다.
Repository는 Aggregate와 같이 Domain 영역에 속하고, Repository 구현체는 Infrastructure 영역에 속한다.
public interface OrderRepository {
Order findById(OrderNo no); // ID로 Aggregate 조회
void save(Order order); // Aggregate 저장
}
Interface는 Aggregate Root 기준으로 작성한다.
주문 Aggregate에서 Value에는 @Embeddable 을 사용하여 매핑한다.
@Entity
@Table(name = "purchase_order")
public class Order {
@Embedded
private MemberId memberId;
...
}
@Embeddable
public class MemberId implements Serializble {
private String id;
}
실제 DB 컬럼명이 memberId가 아닌 orderer_id라면, @AttributeOverrides 를 사용한다.
@Entity
@Table(name = "purchase_order")
public class Order {
@Embedded
@AttributeOverrides(
@AttributeOverride(name = "id", column = @Column(name = "orderer_id"))
)
private MemberId memberId;
...
}
Value 안에 여러 속성을 합쳐서 DB의 한 컬럼에 매핑시켜야 할 때, AttributeConverter를 사용한다.
public class Length {
private int value;
private String unit;
}
value: 10000, unit: mm
=> 10000mm 로 저장
package javax.persistence;
public interface AttributeConverter<X, Y>{
public Y convertToDatabaseColumn (X attribute);
public X convertToEntityAttribute (Y dbData);
}
X: Value, Y: Database type
ex)
@Converter(autoApply = true)
public class MoneyConverter implements AttributeConverter<Money, Integer> {
@Override
public Integer convertToDatabaseColumn(Money money) {
return money == null ? null : money.getValue();
}
@Override
public Money convertToEntityAttribute(Integer value) {
return value == null ? null : new Money(value);
}
}
@Converter(autoApply = true) 는 모델에 출현하는 모든 Money 타입의 프로퍼티에 대해 MoneyConverter를 자동으로 적용한다.