전술적 DDD를 사용하여 마이크로 서비스 설계
DDD(도메인 기반 디자인)는 전체 시스템에 단일 통합 모델을 갖는 개념에 반대합니다. 대신, 각각 고유한 모델을 사용하여 시스템을 제한된 컨텍스트로 분할하는 것이 좋습니다. DDD의 전략적 단계에서는 비즈니스 도메인을 매핑하고 도메인 모델에 대한 제한된 컨텍스트를 정의합니다.
전술적 DDD는 더 상세하게 도메인 모델을 정의하는 경우입니다. 전술적 패턴은 제한된 단일 컨텍스트 내에서 적용됩니다. 경계가 지정된 각 컨텍스트가 마이크로 서비스 후보인 마이크로 서비스 아키텍처에서 엔터티 및 집계 패턴은 유의해야 합니다. 이러한 패턴을 적용하면 애플리케이션의 서비스에 대한 자연 경계를 식별하는 데 도움이 됩니다. 자세한 내용은 마이크로 서비스 경계 식별을 참조하세요. 일반적으로 마이크로 서비스는 집계보다 작지 않아야 하며 제한된 컨텍스트보다 크지 않아야 합니다.
이 문서에서는 전술 패턴을 검토한 다음 드론 배달 애플리케이션의 배송 경계 컨텍스트에 적용합니다.
전술적 패턴 개요
이 섹션에서는 전술 DDD 패턴에 대한 간략한 요약을 제공합니다. DDD에 익숙한 경우 건너뛰도록 선택할 수 있습니다. 이러한 패턴은 에릭 에반스의 책 5장과 6장, 본 버논의 Domain-Driven 디자인 구현 에 자세히 설명되어 있습니다.
엔터티. 엔터티는 시간이 지나도 지속되는 고유의 ID가 있는 개체입니다. 예를 들어 뱅킹 애플리케이션에서 는 고객과 계좌가 엔터티입니다.
엔터티에는 엔터티를 조회하거나 검색하는 데 사용할 수 있는 고유의 식별자가 있습니다. 식별자가 항상 사용자에게 직접 노출되는 것은 아닙니다. 데이터베이스의 GUID 또는 기본 키가 될 수 있습니다.
ID는 여러 바인딩된 컨텍스트에 걸쳐 있을 수 있으며 애플리케이션의 수명을 초과하여 지속될 수 있습니다. 예를 들어 은행 계좌 번호 또는 정부 발행 ID는 특정 애플리케이션에 연결되지 않습니다.
엔터티의 특성은 시간이 지남에 따라 변경 될 수 있습니다. 예를 들어 사람의 이름이나 주소는 변경될 수 있지만 동일한 개인으로 유지됩니다.
값 개체. 값 개체에는 ID가 없습니다. 특성의 값에 의해서만 정의합니다. 값 개체는 변경할 수 없습니다. 값 개체를 업데이트하기 위해 이전 인스턴스를 대체할 새 인스턴스가 만들어집니다. 값 개체에는 도메인 논리를 캡슐화하는 메서드가 포함될 수 있지만 이러한 메서드는 부작용을 일으키거나 개체의 상태를 수정해서는 안 됩니다. 값 개체의 일반적인 예로는 색, 날짜 및 시간 및 통화 값이 있습니다.
집계. 집계는 하나 이상의 엔터티에 대한 일관성 경계를 정의합니다. 한 집계에서 정확히 한 엔터티가 루트입니다. 조회는 루트 엔터티의 식별자를 사용하여 수행됩니다. 집계의 다른 엔터티는 루트의 자식 요소로, 루트의 다음 포인터에서 참조합니다.
집계의 목적은 트랜잭션 고정 항목을 모델링하는 것입니다. 현실은 매우 복잡한 관계로 얽혀있습니다. 고객이 주문을 접수하고, 주문에는 제품이 포함되어 있으며, 제품을 제공하는 공급자가 있는 등 이와 같은 관계가 계속 이어집니다. 애플리케이션이 몇 가지 관련 개체를 수정하는 경우 일관성을 어떻게 유지하나요? 고정 항목을 어떻게 추적하고 적용할까요?
전통적 애플리케이션에서는 데이터베이스 트랜잭션을 사용하여 일관성을 적용하는 경우가 종종 있었습니다. 그러나 분산형 애플리케이션의 경우 현실성이 떨어지는 경우가 많았습니다. 단일 비즈니스 트랜잭션이 여러 데이터 저장소에 걸쳐 있거나, 오래 실행되거나, 타사 서비스와 관련될 수 있습니다. 궁극적으로 이것은 데이터 계층이 아니라 도메인에 필요한 불변 항목을 시행하는 애플리케이션에 달려 있습니다. 이것이 집계가 모델링에서 갖는 의미입니다.
참고
집계는 자식 엔터티 없이 단일 엔터티로 구성될 수 있습니다. 집계를 만드는 것은 트랜잭션 경계입니다.
도메인 및 애플리케이션 서비스. DDD 용어에서 서비스란 상태를 유지하지 않고 일부 논리를 구현하는 개체입니다. Evans는 도메인 논리를 캡슐화하는 도메인 서비스와, 사용자 인증이나 SMS 메시 전송 같은 기술적 기능을 제공하는 애플리케이션 서비스를 구분하고 있습니다. 도메인 서비스는 종종 여러 엔터티를 포괄하는 동작을 모델링하는 데 사용됩니다.
참고
서비스라는 용어는 소프트웨어 개발에서 범위가 넓습니다. 여기서 사용되는 정의는 마이크로 서비스와 직접 관련이 없습니다.
도메인 이벤트. 도메인 이벤트는 문제가 발생할 때 시스템의 다른 부분에 알릴 수 있습니다. 이름에서 설명한 대로 도메인 이벤트는 도메인 내에서 의미 있는 항목을 나타내야 합니다. 예를 들어 "테이블에 레코드가 삽입되었습니다."는 도메인 이벤트가 아닙니다. "배달이 취소되었습니다"는 도메인 이벤트입니다. 도메인 이벤트는 마이크로 서비스 아키텍처에서 특히 중요합니다. 마이크로 서비스는 분산되고 데이터 저장소를 공유하지 않으므로 도메인 이벤트는 서비스 간의 조정을 가능하게 합니다. 비동기 메시징에 대한 자세한 내용은 서비스 간 통신을 참조하세요.
팩터리, 리포지토리 및 모듈을 포함하여 여기에서 다루지 않는 몇 가지 다른 DDD 패턴이 있습니다. 이러한 패턴은 마이크로 서비스를 구현할 때 유용할 수 있지만 마이크로 서비스 간의 경계를 디자인할 때는 관련성이 떨어집니다.
드론 배달: 패턴 적용
경계가 있는 컨텍스트 Shipping이 처리해야 하는 시나리오부터 시작합니다.
- 고객이 드론 배달 서비스에 등록한 기업으로부터 물품 수거를 위해 드론을 요청할 수 있습니다.
- 보내는 사람은 패키지에 표시할 태그(바코드 또는 RFID)를 생성합니다.
- 드론이 원본 위치에서 패키지를 수거하여 대상 위치로 배달합니다.
- 고객이 배달을 예약할 때 시스템은 경로 정보, 기상 상황, 이력 데이터를 기준으로 ETA를 제공합니다.
- 드론이 이동 중일 때 사용자는 현재 위치와 최신 ETA를 추적합니다.
- 드론이 패키지를 수거하기 전에는 고객이 배달을 취소할 수 있습니다.
- 배달이 완료되면 고객에게 알림이 전달됩니다.
- 보내는 사람은 서명이나 지문의 형태로 고객의 배달 확인을 요청할 수 있습니다.
- 사용자는 완료된 배달의 기록을 조회할 수 있습니다.
이러한 시나리오에서 개발 팀은 다음 엔터티를 식별했습니다.
- 배달
- 패키지
- 드론
- 계정
- 확인
- 알림
- 태그
처음 4개, 즉 Delivery, Package, Drone 및 Account은 모두 트랜잭션 일관성 경계를 나타내는 집계입니다. Confirmations 및 Notifications는 Deliveries의 자식 엔터티, Tags는 Packages의 자식 엔터티입니다.
이 설계의 값 개체에는 Location, ETA, PackageWeight 및 PackageSize가 포함됩니다.
이를 설명하기 위한 Delivery 집계의 UML 다이어그램입니다. Account, Package 및 Drone 등, 다른 집계에 대한 참조가 포함되었습니다.
다음 두 가지 도메인 이벤트가 있습니다.
드론이 이동 중인 동안 Drone 개체는 드론의 위치와 상태(이동 중, 착륙함)를 설명하는 DroneStatus 이벤트를 보냅니다.
Delivery 엔터티는 배달 단계가 변경될 때마다 DeliveryTracking 이벤트를 보냅니다. DeliveryTracking 이벤트에는 DeliveryCreated, DeliveryRescheduled, DeliveryHeadedToDropoff 및 DeliveryCompleted가 포함됩니다.
이러한 이벤트는 도메인 모델 안에서 유의미한 사항을 설명합니다. 도메인과 관련한 무언가를 설명하며 특정 프로그래밍 언어 구조와 연관이 없습니다.
개발 팀은 지금까지 설명한 엔터티 중 어디에도 정확히 부합하지는 않는 기능 영역을 하나 더 확인했습니다. 시스템의 일부는 배달 예약 또는 업데이트에 관련된 모든 단계를 조정해야 합니다. 따라서 개발 팀은 두 개의 도메인 서비스를 디자인에 추가했습니다. 즉, 단계를 조정하는 Scheduler 와 각 단계의 상태를 모니터링하는 감독자를 추가하여 단계가 실패했는지 또는 시간이 초과되었는지를 감지했습니다. 이 방법은 Scheduler 에이전트 감독자 패턴의 변형입니다.
다음 단계
다음 단계는 각 마이크로 서비스에 대한 경계를 정의하는 것입니다.