7.1 여러 애그리거트가 필요한 기능.
도메인 영역을 구분하다보면 하나의 에거리거트로 기능을 구현할 수 없을 때가 있다.
예) 결제 금액 계산 로직의 경우 ( 상품, 주문, 할인 쿠폰, 회원 ) 같은 내용이 필요하다.
한 애그리거트에 넣기 애매한 도메인 기능을 억지로 특정 애거리거트에 구현하면 안된다.
억지로 구현하면 자신의 책임 범위를 넘어서는 기능을 구현하기 때문에 코드가 길어지고, 외부에 대한 의존이 높아지게 되며 코드를 복잡하게 만들어 수정을 어렵게 만드는 요인이 된다.
=> 애그리거트의 범위를 넘어서는 도메인 개념이 애그리거트에 숨어들어 명시적으로 드러나지 않게 됨.
7.2 도메인 서비스
도메인 서비스는 도메인 영역에 위치한 도메인 로직을 표현할 때 사용.
( 계산 로직, 외부시스템 연동이 필요한 도메인 로직 )
*** 응용서비스 != 도메인서비스
도메인 서비스를 사용하는 주체는 애그리거트가 될 수도 있고, 응용 서비스가 될 수 도 있다.
**도메인 서비스 객체를 애그리거트에 주입하지 않기!!
애그리거트의 메서드를 실행할 때 도메인 서비스 객체를 파라미터로 전달하기 보다 애그리거트에서 의존 주입을 사용하고 싶을 수 있다. 하지만 이것은 좋은 방법이 아니다.
도메인 객체는 하나의 개념적인 모델인데 db 보관 되상도 아니고 관련이 없는 서비스 객체를 의존성 주입을 할 필요가 없다.
애그리거트 매서드를 시행할때 도메인 서비스를 인자로 전달하지 않고, 반대로 도메인 서비스의 기능을 실행할 때 애그리거트를 전달하는 경우도 있는데 계좌 이체가 예시라고 볼 수 있다.
public class TransferService {
public void transfer(Account fromAcc, Account toAcc, Money amounts) {
fromAcc.withdraw(amount);
toAcc.credit(amount);
}
...
두 Account 애그리거트를 구한 뒤에 해당 도메인 영역의 도메인서비스를 이용해서 계좌 이체 도메인 기능을 실행한 것이다.
도메인 서비스는 도메인 로직을 수행하지 응용 로직을 수행하진 않는다.
트랜잭션 처리와 같은 로직은 응용로직이므로 도메인 서비스가 아닌 응용 서비스에서 처리해야한다.
**특정 기능이 응용서비스인지 도메인 서비스인지 구별하는 방법.
애그리거트의 상태를 변경하거나 상태 값을 계사하는지 검사.
도메인 로직이면서 한 애그리거트에 넣기에 적합하지 않을때, 도메인 서비르로 구현.
외부 시스템이나 타 도메인과의 연동 기능도 도메인 서비스가 될 수 있다.
도메인 서비스의 패키지 위치
도메인 서비스는 도메인 로직을 표현하므로 도메인 서비스의 위치는 다른 도메인 구성요소와 동일한 패키지에 위치한다.
domain 패키지 밑에 domain.model, domain.service, domain.repository와 같이 하위 패키지를 구분하여 위치시켜도 좋다.
도메인 서비스 자체를 인터페이스로 구현하고, 이를 구현한 클래스를 둘 수도 있다.
예) 할인 금액 계산로직을 룰엔진을 이용해서 구현한다면,
-> 도메인 서비스의 구현이 특정 기술에 종속되면 인터페이스와 구현 클래스로 분리한다.
'책 리뷰 > 도메인 주도 개발하기' 카테고리의 다른 글
8장 애그리거트 트랜잭션 관리 (0) | 2022.07.23 |
---|---|
9장 도메인 모델과 바운디드 컨텍스트 (0) | 2022.07.16 |
6장 응용 서비스와 표현 영역 (0) | 2022.07.10 |
도메인 주도 개발하기 - 2장. 아키텍처 개요 (0) | 2022.06.25 |
도메인 주도 개발하기 - 1장. 도메인 모델 시작하기 (0) | 2022.06.19 |