8-경계 간 매핑하기

각 계층의 모델을 매핑 두 계층 간에 매핑을 하지 않으면 양 계층에서 같은 모델을 사용해야 하는데 이렇게 하면 두 계층이 강하게 결합된다. 각 계층의 모델을 매핑하지 않음 두 계층 간에 매핑을 하게 되면 보일러플레이트 코드를 너무 많이 만들게 된다. 많은 유스케이스들이 오직 CRUD만 수행하고 계층에 걸쳐 같은 모델을 사용하기 때문에 계층 사이의 매핑은 과하다. ‘매핑하지 않기’ 전략 웹 계층, 애플리케이션 계층, 영속성 계층 모두 같은 Account 모델을 사용한다. 장점: 매핑할 필요가 전혀 없어서 단순하다....

2025-02-17 · 3 min · 567 words

12-아키텍처 스타일 정하기

도메인이 왕이다 육각형 스타일과 같은 도메인 중심의 아키텍처 스타일은 DDD의 조력자라고 말할 수 있다. 경험이 여왕이다 우리가 과거에 했던 일에 편안함을 느낀다면 무언가를 바꿀 필요가 없다. 육각형 아키텍처에 대한 확신이 없다면 지금 만들고 있는 애플리케이션의 작은 모듈에 먼저 시도해 보자. 그때그때 다르다 정답은 없다.

2025-01-14 · 1 min · 44 words

10-아키텍처 경계 강제하기

경계와 의존성 가장 안쪽 계층에는 도메인 엔티티가 있다. 애플리케이션 계층은 애프리케이션 서비스 안에 유스케이스를 구현하기 위해 도메인 엔티티에 접근한다. 어댑터는 인커밍 포트를 통해 서비스에 접근하고, 반대로 서비스는 아웃고잉 포트를 통해 어댑터에 접근한다. 설정 계층은 어댑터와 서비스 객체를 생성할 팩터리를 포함하고 있고, 의존성 주입 메커니즘을 제공한다. 접근 제한자 package-private 제한자: 패키지 내에 있는 클래스들은 서로 접근 가능하지만, 패키지 바깥에서는 접근할 수 없다. 모듈의 진입점으로 활용될 클래스들만 골라서 public으로 만들면, 의존성이 잘못된 방향을 가리켜서 의존성 규칙을 위반할 위험이 줄어든다....

2025-01-14 · 2 min · 359 words

11-의식적으로 지름길 사용하기

왜 지름길은 깨진 창문 같을까? 품질이 떨어진 코드에서 작업할 때 더 낮은 품질의 코드를 추가하기가 쉽다. 코딩 규칙을 많이 어긴 코드에서 작업할 때 또 다른 규칙을 어기기도 쉽다. 지름길을 많이 사용한 코드에서 작업할 때 또 다른 지름길을 추가하기도 쉽다. 유스케이스 간 모델 공유하기 유스케이스마다 다른 입출력 모델을 가져야 한다. 유스케이스가 입출력 모델을 공유하는 것은 단일 책임 원칙에서 이야기하는 ‘변경할 이유’를 공유하는 것이다. 유스케이스 간 입출력 모델을 공유한느 것은 유스케이스들이 기능적으로 묶여 있을 때 유요하다....

2025-01-07 · 2 min · 369 words

9-애플리케이션 조립하기

왜 조립까지 신경 써야 할까? 아키텍처에 대해 중립적이고 인스턴스 생성을 위해 모든 클래스에대한 의존성을 가지는 설정 컴포넌트(configuration component)가 있어야 한다. 이유: 코드 의존성이 올바른 방향을 가리키게 하기 위해 부수효과: 클래스가 필요로 하는 모든 객체를 생성자로 전달 수 있다면 실제 객체 대신 목으로 전달할 수 있고, 이렇게 되면 격리된 단위 테스트를 생성하기 쉬워진다. 설정 컴포넌트의 역할: 우리가 제공한 조각들로 애플리케이션을 조립 설정 파일이나 커맨드라인 파라미터 등과 같은 설정 파라미터의 소스에도 접근할 수 있어야 한다....

2025-01-02 · 2 min · 373 words

7-아키텍처 요소 테스트하기

테스트 피라미드 단위 테스트: 피라미드의 토대 일반적으로 하나의 클래스를 인스턴스화하고 해당 클래스의 인터페이스를 통해 기능들을 테스트한다. 만약 테스트 중인 클래스가 다른 클래스에 의존한다면 의존되는 클래스들은 인스턴스화하지 않고 테스트하는 동안 필요한 작업들을 흉내 내는 목으로 대체한다. 통합 테스트: 여러 유닛을 인스턴스화하고 시작점이 되는 클래스의 인터페이스로 데이터를 보낸 후 유닛들의 네트워크가 기대한대로 잘 동작하는지 검증한다. 이 책에서 정의한 통합 테스트에서는 두 계층 간의 경계를 걸쳐서 테스트할 수 있기 때문에 객체 네트워크가 와넞ㄴ하지 않거나 어떤 시점에는 목을 대상으로 수행해야 한다....

2024-12-18 · 3 min · 452 words

6-영속성 어댑터 구현하기

의존성 역전 영속성 어댑터의 책임 영속성 어댑터가 하는 일 입력을 받는다. 입력을 데이터베이스 포맷으로 매핑한다. 입력을 데이터베이스로 보낸다. 데이터베이스 출력을 애플리케이션 포맷으로 매핑한다. 출력을 반환한다. JPA를 사용하는 경우에는 입력 모델을 JPA 엔티티 객체로 매핑할 것이다. 맥락에 따라서 입력 모델을 JPA 엔티티로 매핑하는 것이 들이는 노력에 비해 얻는 것이 많지 않은 일이될 수 있으므로 매핑하지 않는 전략도 존재한다. 영속성 어댑터의 입력 모델은 애플리케이션 코어에 있기 때문에 영속성 어댑터 내부를 변경하는 것이 코어에 영향을 미치지 않는다....

2024-12-05 · 2 min · 371 words

5-웹 어댑터 구현하기

의존성 역전 인커밍 어댑터는 애플리케이션 서비스에 의해 구현된 인터페이스인 전용 포트를 통해 애플케이션 계층과 통신한다. 어댑터와 유스케이스 사이에 간접 계층을 넣어야 되는 이유 포트: 애플리케이션 코어와 외부 세계와 통신할 수 있는 곳에 대한 명세이다. 포트를 적절한 곳에 위치시키면 외부와 어떤 통신이 일어나고 있는지 정확히 알 수 있다. 웹 소켓의 경우 웹 어댑터에서 아웃고잉 포트를 구현하고 애플리케이션 코어에서 호출해야 한다. 웹 어댑터의 책임 웹 어댑터가 일반적으로 하는 일 HTTP 요청을 자바 객체로 매핑 권한 검색 입력 유효성 검증 입력을 유스케이스의 입력 모델로 매핑 유스케이스 호출 유스케이스의 출력을 HTTP로 매핑 HTTP 응답을 반환 유스 케이스 입력 모델의 검증과 차이점 웹 어댑터 입력 모델과 유스 케이스 입력 모델에는 차이가 있을 수 있으므로 또 다른 검증을 수행해야 한다....

2024-12-05 · 2 min · 253 words

4-유스케이스 구현하기

육각형 아키텍처는 도메인 중심의 아키텍처에 적합하다. 유스케이스 둘러보기 일반적으로 유스케이스는 다음과 같은 단계를 따른다. 입력을 받는다. 입력 유효성 검증은 다른 곳에서 처리한다. (유스케이스 코드가 도메인 로직에만 신경 써야하고 입력 유효성 검증으로 오염되면 안된기 떄문) 비즈니스 규칙을 검증한다. 도메인 엔티티와 유스케이스가 책임을 공유한다. 모델 상태를 조작한다. 영속성 어댑터를 통해 구현된 포트로 변경된 상태를 전달해서 저장될 수 있게 한다. 출력을 반환한다. 입력 유효성 검증 입력 유효성 검증은 입력 모델의 생성자 내에서 이루어진다....

2024-11-13 · 2 min · 391 words

3-코드 구성하기

계층으로 구성하기 buckapl |--- domain | |----- Account | |----- Activity | |----- AccountRepository | |----- AccountService |--- persistence | |----- AccountRepositoryImpl |--- web | |----- AccountController domain 패키지에 AccountRepository 인터페이스를 추가하고, persistence 패키지에 AccountRepositoryImpl 구현체를 둠으로써 의존성을 역전시켰다. 위 패키지 구조가 최적이 아닌 이유 애플리케이션의 기능 조각이나 특성을 구분 짓는 패키지 경계가 없다. 애플리케이션이 어떤 유스케이스들을 제공하는지 파악할 수 없다. 패키지 구조를 통해서는 우리가 목표로하는 육각형 아키텍처를 파악하기 어렵다. 기능으로 구성하기 buckpal |-- account |-- Account |-- AccountController |-- AccountRepository |-- AccountRepositoryImpl |-- SendMoneyService 패키지 경계를 package-private 접근 수준과 결합하면 각 기능 사이의 불필요한 의존성을 방지할 수 있다....

2024-11-11 · 2 min · 384 words

2-의존성 역전하기

단일 책임 원칙 오해의 소지가 있는 해석: 하나의 컴포넌트는 오로지 한 가지 일만 해야 하고, 그것을 올바르게 수행해야 한다. 올바른 해석: 컴포넌트를 변경하는 이유는 오직 하나뿐이어야 한다. 변경할 이유라는 것은 컴포넌트 간의 의존성을 통해 쉽게 전파된다. 어떤 컴포넌트의 의존성 각각은 이 컴포넌트를 변경하는 이유 하나씩에 해당한다. 단일 책임 원칙을 위반하면 시간이 갈수록 변경하기 어려워지고 그로 인해 변경 비용도 증가한다. 부수효과에 관한 이야기 잘못 구조화된 소프트웨어를 변경하는 데는 부수 효과로 인해 더 많은 비용을 지불하도록 만드는 경우가 많다....

2024-11-06 · 2 min · 413 words

1-계층형 아키텍처의 문제는 무엇일까?

계층형 아키텍처는 코드에 나쁜 습관들이 스며들기 쉽게 만들고 시간이 지날수록 소프트웨어를 점점 더 변경하기 어렵게 만드는 수많은 허점들을 노출한다. 계층형 아키텍처는 데이터베이스 주도 설계를 유도한다 웹 계층은 도메인 계층에 의존하고, 도메인 계층은 영속성 계층에 의존하기 때문에 자연스레 데이터베이스에 의존하게 된다. 애플리케이션을 개발할 때 상태가 아니라 행동을 중심으로 모델링 해야한다. 행동이 상태를 바꾸는 주체이기 때문에 행동이 비즈니스를 이끌어간다. 하지만 전통적인 계층형 아키텍처에서는 데이터베이스의 구조를 먼저 생각하고, 이를 토대로 도메인 로직을 구현하게 된다....

2024-10-23 · 3 min · 440 words