아키텍처 스타일 개요
계층화 아키텍처 스타일
- 표현 계층: 사용자 인터페이스 또는 외부 API가 구현된 계층
- 비즈니스 로직 계층
- 영속 계층: DB와 상호 작용 로직 구현
1) 표현 계층이 하나 -> 애플리케이션을 호출하는 시스템이 정말 하나?
2) 영속화 계층이 하나 -> 상호 작용하는 DB가 정말 하나?
3) 비즈니스 로직 계층을 영속화 계층에 의존하는 형태로 정의 -> 이런 디펜던시로 DB없이 비즈니스 로직을 테스트하는 건 불가능
육각형 아키텍처
- 인바운드 어댑터: 비즈니스 로직을 호출해 외부에서 들어온 요청을 처리
- 아웃바운드 어댑터: 비즈니스 로직에 의해 호출되고 외부 애플리케이션을 호출
- db 작업이 구현된 DAO 클래스, 원격 서비스를 호출하는 프록시 클래스
비즈니스 로직이 어댑터에 의존하지 않고 어댑터가 비즈니스 로직에 의존,
마이크로서비스 아키텍처는 일종의 아키텍처 스타일이다..?
서비스란 무엇인가?
- 어떤 기능이 구현되어 단독 배포가 가능한 소프트웨어 컴포넌트
느슨한 결합
- API를 통해서만 동작하므로 서비스가 직접 DB와 통신하는 일은 불가능
- 클래스 필드 같은 서비스의 영속적 데이터는 반드시 프라이빗
공유 라이브러리의 역할
- 코드 중복 방지를 위해 여러 애플리케이션에서 재사용 가능한 기능을 라이브러리로 패키징하는 건 당연한 일
서비스 규모는 별로 중요하지 않다
- 마이크로여서 작게해야할 것 같은데 꼭 그건 아니다!
아키텍처 정의
시스템 작업 식별
아래 2단계 프로세스로 시스템 작업을 정의한다.
- 시스템 작업을 기술하기 위해 핵심 클래스로 구성된 고수준의 도메인 모델 생성
- 시스템 작업 식별 후 그 동작을 도메인 모델 관점에서 기술
고수준의 도메인 모델
given - when -then 으로 시나리오를 작성해보고 이중에서 명사인 것들을 추출해본다..
시스템 작업 정의
커맨드(CUD), 쿼리(R) 작업을 식별해본다
서비스 정의: 비즈니스 능력 패턴별 분해

서비스 정의: 하위 도메인 패턴별 분해
기존에는 소비자, 주문 등 비즈니스 엔티티를 각자 정의했다. 이렇게 모델링하면 하나의 모델에 대해 부서 합의가 어려울 수 있다.
DDD는 도메인을 구성하는 각 하위 도메인마다 도메인 모델을 따로 정의한다.

분해 지침
- 단일 책임 원칙
- 클래스는 오직 하나의 변경 사유를 가져야 한다.
- 공동 폐쇄 원칙
- 패키지의 클래스들은 동일한 유형의 변경에 대해 닫혀 있어야 한다.
- 어떤 두 클래스가 동일한 사유로 맞물려 변경되면 동일한 패키지에 있어야 한다는 것!!
서비스 분해의 장애물
- 네트워크 지연
- 한 차례 왕복으로 여러 객체를 한 번에 가져오는 배치 API 사용, 언어 수준의 메서드 호출로 대체
- 동기 통신으로 인한 가용성 저하
- 여러 서비스에 걸쳐 데이터 일관성 유지
- 여러 서비스에 있는 데이터를 업데이트를 할 때, 이 두 업데이트는 원자적으로 일어나야 한다. 이건 사가 패턴으로 관리해야 한다.
- 데이터의 일관된 뷰 확보
- 분해를 저해하는 만능 클래스
- DDD 를 적용해 각 서비스를 자체 도메인 모델을 갖고 있는 개별 하위 도메인으로 취급해보자


서비스 API 정의
서비스 API 작업은 아래 둘 중 하나다!
- 외부 클라이언트 또는 타 서비스가 호출하는 시스템 작업
- 서비스 간 협동을 지원하기 위해 타 서비스 호출 전용으로 만든 작업
서비스 API를 정의하려면 각각의 시스템 작업을 서비스로 매핑한 후, 그 시스템 작업을 구현하려면 어느 서비스가 서로 협동해야 할지 파악이 필요하다.
