Infrastructure Layer

외부 시스템과의 통신을 담당하며, 애플리케이션의 비즈니스 로직과 외부 시스템 간의 추상화 계층 역할을 합니다.

주요 역할

  • 데이터베이스, 파일 시스템, 네트워크 서비스 등의 외부 리소스와의 상호작용
  • 구현 기술에 대한 세부사항 처리: 레포지토리 구현, 인프라 서비스 포함

인프라스트럭처 서비스 예시

  1. 외부 API 통합
    • RESTful API 및 GraphQL API 통합
    • 소셜 미디어 API (예: Facebook, Twitter)
    • 지불 게이트웨이 (예: Stripe, PayPal)
    • HTTP 클라이언트 사용: Axios, Fetch 등
  2. 메시징 서비스
    • 이메일 발송 : AWS SES, SendGrid
    • SMS 발송 : Twilio, Nexmo
    • 메시지 큐 : RabbitMQ, Kafka, AWS SQS
  3. 데이터베이스 접근
    • ORM 설정: TypeORM, Sequelize, Prisma
    • 데이터베이스 연결 관리 및 트랜잭션 처리

이점

코드 작성

책임 분리 (Separation of Concerns)

  • 비즈니스 로직과 기술적 구현을 분리하여, 각 레이어의 역할이 명확
  • 예) 도메인 레이어는 데이터 처리 규칙만 다루고, 인프라스트럭처 레이어는 데이터베이스 접근만 담당

유지보수 용이성

  • 외부 시스템(데이터베이스, API 등)이 변경되더라도, 인프라스트럭처 레이어에서만 수정하면 된다.
  • 구현 세부 사항이 도메인 로직에 노출되지 않아, 코드 수정 범위를 최소화 가능

재사용성

  • 공통적으로 사용하는 서비스(예: 이메일 발송, API 호출 등)를 모듈화하여 재사용 가능
  • 여러 도메인에서 동일한 인프라스트럭처 서비스를 활용

확장성

  • 새로운 데이터베이스나 외부 API를 추가하거나 변경할 때도 기존 구조를 크게 변경하지 않고 확장가능

협업

역할 집중

  • 외부 시스템과의 통신을 인프라스트럭처 레이어가 담당하여, 도메인 팀은 비즈니스 로직에만 집중 가능

변경 시 영향 최소화

  • 외부 API나 데이터베이스 변경 시, 인프라스트럭처 레이어에서만 작업하면 되므로 다른 팀원 작업에 영향이 적음.

표준화된 인터페이스

  • 인터페이스(예: 레포지토리 패턴)를 통해 도메인 로직과 인프라스트럭처 간의 통신 방식을 표준화하여 충돌 방지
  • 일관된 방식으로 외부 시스템과 상호작용하게 되어 협업 효율이 향상

테스트 코드

테스트 용이성

  • Mock 객체 또는 Stub을 사용하여 외부 시스템 의존성을 제거
  • 외부 시스템과 독립적으로 도메인 로직이나 비즈니스 규칙에 대한 단위 테스트 수행 가능

테스트 환경

  • 운영 환경과 유사한 조건에서 전체적인 통합 동작 검증 가능
  • 외부 시스템과의 통합 동작을 실제 환경이나 시뮬레이션된 환경에서 검증
  • 실제 데이터베이스 연결이나 API 호출이 제대로 동작하는지 확인가능

문제진단 용이

  • 외부 시스템 관련 문제는 외부 연동과 관련된 코드를 우선적으로 살펴보고 빠르게 진단하고 해결가능

 

 

  •  

목차

1번 구조 : 기본적인 NestJS 구조

참조

구조 특징

modules 폴더를 중심으로 모듈 단위로 코드를 관리합니다.
각 모듈은 컨트롤러, 서비스, 엔티티, 인터페이스 등의 파일을 함께 포함합니다.

사용 이유와 원리

  • 모듈화: 기능별로 디렉토리를 분리하여 각 기능이 독립적으로 동작할 수 있도록 설계합니다.
    • 예: user 모듈은 사용자 관련 로직만을 포함.
  • NestJS의 표준 권장사항 준수: NestJS의 모듈 기반 아키텍처 철학에 따라 관리와 확장이 용이.
  • 개발과 유지보수의 편의성: 각 모듈이 독립적이므로 특정 기능 변경 시 다른 모듈에 미치는 영향이 적음.

폴더 구성

src/
  ├── modules/
  │     ├── user/
  │     │     ├── user.controller.ts
  │     │     ├── user.service.ts
  │     │     ├── user.entity.ts
  │     │     └── user.dto.ts
  │     ├── auth/
  │     │     ├── auth.controller.ts
  │     │     ├── auth.service.ts
  │     │     └── auth.module.ts
  ├── app.module.ts
  ├── main.ts

 

2번 구조 : 클린 아키텍처(Clean Architecture) 적용

참조

구조 특징

애플리케이션의 비즈니스 로직을 중심으로 설계합니다.
의존성 방향을 안쪽으로 향하게 설계하여 핵심 도메인이 외부 프레임워크에 의존하지 않도록 구성합니다.

  • 의존성 방향을 안쪽으로 향하게?
    • 시스템의 고수준 모듈저수준 모듈 에 의존하지 않도록 하고, 대신 추상화를 통해 두 모듈이 서로 독립적으로 동작할 수 있게 설계하자는 내용
      • 고수준 모듈: 비즈니스 로직을 처리하는 서비스 클래스
      • 저수준 모듈: 데이터베이스, 외부 API 등 실제 구현을 담당하는 클래스
      • 고수준 모듈은 저수준 모듈의 구현을 알 필요 없이, 인터페이스나 추상화된 계약에 의존하여 기능을 수행

사용 이유와 원리

  • 독립성 유지:
    • 비즈니스 로직(application)과 기술 세부사항(infrastructure)을 분리.
    • 도메인 계층(domain)은 외부 의존성과 무관하게 설계.
  • 테스트 용이성:
    • 비즈니스 로직이 외부 의존성 없이 독립적으로 작성되어 테스트가 쉬움.
  • 확장성과 유지보수성:
    • 프레임워크나 ORM 변경이 요구되더라도 핵심 로직에 미치는 영향 최소화.
  • 클린 아키텍처 원칙 준수:
    • Use Case와 Entity를 중심으로 설계하여 애플리케이션 안정성 증대.

폴더 구성

src/
  ├── application/
  │     ├── use-cases/
  │     │     ├── create-user.use-case.ts
  │     │     └── find-user.use-case.ts
  ├── domain/
  │     ├── entities/
  │     │     ├── user.entity.ts
  │     └── repositories/
  │           └── user.repository.ts
  ├── infrastructure/
  │     ├── controllers/
  │     │     └── user.controller.ts
  │     ├── services/
  │     │     └── user.service.ts
  │     ├── orm/
  │           └── user.orm-entity.ts
  ├── app.module.ts
  ├── main.ts

3번 구조 : 프로젝트 전체를 계층 중심으로 분리

참조

구조 특징

이 구조는 대규모 프로젝트를 위한 설계로, 모듈을 기능 중심 (1번 구조)이 아닌 프로젝트 전체를 계층 중심으로 분리합니다.
코드를 기능(Feature)이 아닌 역할과 책임(Layer)을 기준으로 분리.
주요 계층은 API, Service, Repository, Entity로 나누고, 공통 유틸리티는 별도로 관리합니다.

사용 이유와 원리

  • 대규모 프로젝트 적합성:
    • 계층별로 분리하여 복잡한 프로젝트의 역할을 명확히 관리.
  • 유지보수 용이성:
    • 계층 독립성으로 변경 시 다른 계층에 미치는 영향을 최소화.
  • 재사용성:
    • 공통 코드를 별도로 관리하여 코드 중복 제거.
  • 규모 확장성:
    • 계층 구조 확장을 통해 아키텍처 안정성 확보.

폴더 구성

src/
  ├── api/
  │     ├── user/
  │     │     ├── user.controller.ts
  │     │     └── user.dto.ts
  ├── services/
  │     ├── user/
  │     │     └── user.service.ts
  ├── repositories/
  │     ├── user/
  │     │     └── user.repository.ts
  ├── entities/
  │     ├── user.entity.ts
  ├── common/
  │     ├── utils/
  │     │     ├── logger.util.ts
  │     │     └── validation.util.ts
  │     └── interceptors/
  ├── app.module.ts
  ├── main.ts

1번, 2번, 3번 구조 비교 요약

구조 유형 구조 설계 방식 주요 특징 장점 적합한 프로젝트
1번  모듈 중심 설계 - 기능별 모듈(user, auth 등) 단위로 구성
- 모듈 내에 컨트롤러, 서비스, 엔티티 등이 함께 포함됨
- NestJS의 표준 구조
- 간결하고 직관적
- 모듈 단위로 관리가 쉬움
소규모~중규모 프로젝트
2번  클린 아키텍처 - 비즈니스 로직 중심 설계
- 의존성 방향이 안쪽으로 향함
- Application, Domain, Infrastructure로 분리
- 비즈니스 로직과 기술 세부사항 분리
- 유지보수와 테스트 용이
- 핵심 도메인이 외부 의존성 없음
중규모~대규모 프로젝트
3번  계층 중심 설계
(Layer-Oriented Design)
- 역할(계층) 중심으로 코드 분리
- 주요 계층: API, Service, Repository, Entity
- 공통 유틸리티 별도 관리
- 코드 책임 분리 명확
- 대규모 프로젝트에 적합
- 확장성과 재사용성 극대화
대규모 프로젝트 및 팀 협업

추가 설명

  • 1번 구조는 NestJS의 기본 구조로 빠른 프로토타이핑과 간단한 프로젝트에 적합.
  • 2번 구조는 클린 아키텍처를 적용하여 비즈니스 로직 중심으로 설계하며, 기술 스택의 변경에 유연.
  • 3번 구조는 계층 중심으로 프로젝트를 조직화해 대규모 팀 프로젝트에서 효율적입니다.

계층화 구조 ( Layered Architcture)

presentation, application, domain, infrastructure 계층을 사용하여 폴더를 기능별로 분리하는 것

이점

- 각 계층의 책임을 명확하게 분리 → 각 시스템이 어떻게 동작하는지 이해하기 쉽다.

- 각 계층간의 의존도가 적다 → 변경 사항이 다른 계층에 미치는 영향을 최소화할 수 있다.

 

각 계층의 역할

Presentation Layer

- 사용자(웹 브라우저)로 부터 요청(Request)을 받아  application layer 에 전달하고 application layer에서 처리된 결과를 받아 사용자에게 응답(Response)

- 외부로부터의 요청을 받고, 적절한 응답을 구성

- 사용자 인터페이스와 상호작용하는 부분으로, 컨트롤러를 포함

 

Application Layer

- 도메인 레이어를 사용하여 사용자의 요청을 처리하고 응답을 구성

- 애플리케이션 로직(흐름 제어, 트랜잭션 관리 등)을 담당

- DTO(Data Transfer Objects), 인터페이스 정의, 서비스 구현 등을 포함

 

Domain Layer

- 애플리케이션의 비즈니스 로직과 도메인 모델을 포함

- 엔티티(Entity)와 값 객체(Value Object)를 사용해 핵심 비즈니스 데이터를 모델링하고 도메인 서비스, 도메인 이벤트 등을 포함

- 비즈니스 규칙과 불변성을 유지

- 다른 계층(application, infrastructure)과 독립적으로 설계

Infrastructure Layer

- 데이터베이스, 파일 시스템, 네트워크 서비스 등의 외부 시스템과의 통신을 담당

- 구현기술에 대해 다루는 영역 : 레포지토리 구현, 인프라 스트럭쳐 서비스를 포함 

  * 인프라 스트럭처 서비스 :

      외부 API 통합 : 소셜 미디어 API, 지불 게이트웨이, 지리적 위치 서비스 등 외부 시스템과의 연동

      메세징 서비스 : 이메일 발송, SMS 발송 등

      데이터베이스 엑세스 : ORM 설정, 데이터 베이스 연결

 

 

 

 

참고자료

https://hesh1232.tistory.com/153

+ Recent posts