- https://dsmweb.org/design-structure-matrix-dsm/
- https://dsmweb.org/introduction-to-dsm/
- https://v0o0v.tistory.com/4
- https://architecture101.blog/2009/11/02/dependency-structure-matrix/
- https://www.youtube.com/watch?v=moi49_V_4g0&list=WL&index=1&t=259s
- https://happycloud-lee.tistory.com/94
- https://dev-coco.tistory.com/166
-
Dependency-Structure-Matrix & DDD & Layered-ArchitectureDEV 2024. 1. 8. 20:58
project 내부 Dependency를 파악해 높은 응집력, 낮은 결합도를 가진 코드를 유지하는 방법과 도구를 DDD 관점에서 알아보자.
- 일반적으로 코드를 이해하는 데 개발 시간의 60%를 사용
- https://ieeexplore.ieee.org/document/7997917 - 코드 규모가 커지면 복잡도도 올라가기 때문에 코드 시각화, 코드 출력, 스크래치 리팩터링 등의 도움을 받을 수 있다.
코드 시각화
Dependency structure matrix(DSM)
- 프로젝트 내 dependency 파악하는 방법 중 하나
- 열을 기준으로 dependency 파악
- 다이어그램에서 dependency는 화살표가 들어오는 것으로 파악
- task1은 task3에 dependency(의존성)을 가진다.
- task3이 task1을 사용한다. - task2는 task1에 dependency(의존성)을 가진다.
- task4는 task2, task5에 dependency(의존성)을 가진다.
- 테스트 코드를 작성 시 테스트코드가 해당 모듈을 사용하는 모듈(해당모듈이 의존을 가지고 있는 모듈)이라고 생각하고 작성하면 편하다.
- task4에 대한 테스트코드를 작성한다면 화살표를 거꾸로 찾아가 task2, task5에서 실행할 만한 case를 테스트하면 된다.
Circular Dependency(순환참조)
- 메트릭스를 통해 순환참조를 쉽게 찾아낼 수 있다.
- A는 C에 의존, C도 A에 의존 = 순환참조
- 파란 선을 기준으로 포개었을 때 겹치는 부분이 있다면 Circular Dependency
순환참조의 문제점
- 변경에 의해 영향받는 범위를 파악하기 어렵다.
- 순환참조가 발생되면 컴포넌트 간의 명확한 경계가 사라지고 연쇄적으로 변경에 의한 영향 발생 가능성 - 메모리 누수, 가비지컬랙션 오버헤드, 예측 불가능한 동작, 코드 복잡도
DSM in Intellij
- 메뉴에 없다면 Plugins: Dependencies Structure Matrix 설정을 on으로 변경
- Ultimate license만 지원 🫤
- 메트릭스는 많이 사용되는 구성요소를 아래로 정렬
= 메트릭스 상단 구성요소가 아래 구성요소에 종속된다는 의미 - 종속성 = 파란색
- 순환참조 = 빨간색
- 초록색 → 사용 → 선택모듈 → 사용 → 노랑색
- 선택한 모듈을 수정했을 때 영향을 받는 모듈의 범위를 확인 가능
Domain-Driven Design(DDD)
- DDD에 대해 처음부터 설명할 수 없지만, DDD의 핵심목표는
- High cohesion, Loosly coupling(높은 응집력, 낮은 결합도) - 도메인은 서로 철저히 분리, 변경과 확장에 용이한 설계
Layered Architecture
- DDD의 구체적 설계 (Tactical Design) 목적별 계층으로 나누어 설계
- Presentation Layer: UI Layer
- Service Layer: Domain Layer와 Data Layer의 classclass들 간의 제어(Control) 또는 연결(Interface)
- 비지니스 로직은 구현 x - Domain Layer: Domain Object별로 Business Logic처리
- Data Layer: Database와의 CRUD처리
- spring boot 어노테이션
- Presentation Layer => @Controller, @RestController
- Service Layer, Domain Layer => @Service
- Data Layer => @Repository - Layered Architecture를 올바르게 구현하기 위한 두 가지 중요한 규칙
- 위의 계층에서 아래 계층에는 접근이 가능하지만 아래에서 위로는 불가능한 것을 기본으로 한다.
- 한 계층의 관심사와 관련된 어떤 것도 다른 계층에 배치되어서는 안 된다.
Layered Architecture in DSM
- 비교적 layer 구조가 잘 지켜진 시스템
- 위 계층이 아래 계층으로만 접근, 아래애서 위로 접근하지 않는다.
- 보다 엄격하게 한다면 하나의 레이어는 바로 아래 레이어에서만 접근
- model은 application만의 의존을 갖는다.
- util에서 수정이 일어날 경우 영향을 받는 범위는 framework에 국한된다.
- 좋은 구조이지만 실제로 하기는 쉽지 않다.
- util의 기능을 applicaton에서 사용하려 할 경우, framework, domain, model을 거쳐서 해당 기능을 제공해야 하기 때문에 오히려 비효율적일 수도
- 하위 레이어에서 상위 레이어를 호출
- util에서 application, model을 사용/참조
= 순환 참조 발생 가능성 - 해결방법
- 직접적인 순환 참조인 경우 새로운 패키지 생성
- 간접적인 참조의 경우 Interface로 연결
순환 끊기
- Entities에 새로 추가된 클래스 하나가 Authorizer를 사용하게 되어 순환참조가 일어난다면
- Database 컴포넌트에서 수정이 일어났을 때 Entities, Authorizer, Interactors와 호환 확인
- 순환참조가 일어나면서 Entities, Authorizer, Interactors가 거대한 컴포넌트가 되는 이슈
1. 의존성 역전 원칙 (DIP) 적용
2. 새로운 패키지 생성
- Entities와 Authorizer가 모두 의존하는 새로운 패키지를 만들고 두 컴포넌트가 모두 의존하는 클래스들을 이동
결론은
- High cohesion, Loosly coupling(높은 응집력, 낮은 결합도)
- 변경과 확장에 용이한 설계를 위한 모든 일들..
Ref.
728x90'DEV' 카테고리의 다른 글
추상 클래스, 인터페이스, 상속, 합성, 프록시/데코레이터 패턴 그리고 Spring AOP (0) 2024.01.20 심리적 안전과 지식공유, 강백호와 중경삼림 (0) 2024.01.12 빈약한 도메인 모델, 풍부한 도메인 모델, DDD 그리고 캡슐화 (0) 2023.12.31 LLM기반 chatBot 설계, 구조 변화 (1) 2023.12.29 무상태(stateless) 웹 계층에서 비정규화(de-normalization)까지 (1) 2023.12.23 - 일반적으로 코드를 이해하는 데 개발 시간의 60%를 사용