[디맷]Nest.js를 사용하는 이유와 구조

김인태·2023년 3월 9일
0
post-thumbnail

🥨 Nest를 선정하게 된 이유

일단 우리팀은 부트캠프에서 프론트엔드 교육만 받았던 사람이라 백엔드에 필요한 지식들이 많이 부족한 편이에요. Java나 ,python등의 언어를 선택할 수도 있었지만 React를 기반으로 학습을 했었기 때문에 제일 익숙한 Typescript 기반의 언어를 선택하게 되었고, Node.js를 선택할 수도 있었지만 왜 Nest를 사용하는지 다시 한 번 봐볼까요?

😅 이런 이유라기 보다는 좀 더 좋은 이유가 있습니다.

  • Nest는 시간을 단축시켜줍니다.
    기존의 express 기반의 어플리케이션을 만들 때는 eslint, 아키텍쳐등의 설정 등을 이것 저것 만들어야 할 것들이 많아 설정할 것이 많아 세팅하고 구조에 대해 회의 하는데 오랜 시간을 투자해야 합니다.

nest cli를 사용해 초기세팅을 했을 때 생기는 파일들입니다.
prettier와 eslint, jest등이 세팅 되어 있는 모습입니다!
아무래도 express 환경에서는 새로 설치해야 될 것들이 많으니 세팅하는데 오래걸리겠죠? 하지만 Nest는 이렇습니다!

  • cli가 잘 되어있다.

전역적으로 설치해서 어디든지 nest project, controller 등을 아주 쉽게 만들 수 있습니다! 어떻게 하는지는 초기세팅에서 다시.. 설명하겠습니다 !

Nest.js 의 구조

1. Controller

컨트롤러는 들어오는 요청을 처리하고
클라이언트에 응답을 반환하는 역할을 합니다 .
컨트롤러의 목적은 애플리케이션에 대한 특정 요청을 수신하는 것입니다. 라우팅 메커니즘 은 어떤 컨트롤러가 어떤 요청을 받는지 제어합니다. 종종 각 컨트롤러에는 둘 이상의 경로가 있으며 다른 경로는 다른 작업을 수행할 수 있습니다.기본 컨트롤러를 만들기 위해 클래스와 데코레이터를 사용합니다 . 데코레이터는 클래스를 필수 메타데이터와 연결하고 Nest가 라우팅 맵을 생성할 수 있도록 합니다(요청을 해당 컨트롤러에 연결).

요약하자면 컨트롤러는 요청하는 URL에 대한 제어를 합니다
예시를 보겠습니다!

cats.controller.ts

import { Controller, Get } from '@nestjs/common';

@Controller('cats')
export class CatsController {
  @Get()
  findAll(): string {
    return 'This action returns all cats';
  }
}

데코레이터로 컨트롤러를 선언해주고, 지금 사용하는 port가 localhost:3000 이라면,
http://localhost:3000/cats 에 get요 청을 했을 때 findAll 이라는 함수가 실행되어
해당 리턴 값을 반환합니다.
여기서 @ <- 이 골뱅이를 데코레이터라고 합니다.
잠깐 ! 데코레이터란 ?

데코레이터는 비즈니스와 상관 없는 로직들을 숨기면서 기능을 변경하거나 확장할 수 있게 합니다. 또한 여러 클래스에서 반복되는 공통 관심사가 있을 때 데코레이터를 사용하면 중복된 코드를 줄이고 코드를 모듈 단위로 관리하는 효과를 거둘 수 있습니다.

2. provider

공급자는 Nest의 기본 개념입니다. 많은 기본 Nest 클래스는 서비스, 리포지토리, 팩토리, 헬퍼 등 공급자로 취급될 수 있습니다. 공급자의 주요 아이디어는 종속성으로 주입 할 수 있다는 것입니다. 즉, 개체는 서로 다양한 관계를 만들 수 있으며 개체 인스턴스를 "연결"하는 기능은 대부분 Nest 런타임 시스템에 위임할 수 있습니다.

cats.service.ts 

import { Injectable } from '@nestjs/common';
import { Cat } from './interfaces/cat.interface';

@Injectable()
export class CatsService {
  private readonly cats: Cat[] = [];

  create(cat: Cat) {
    this.cats.push(cat);
  }

  findAll(): Cat[] {
    return this.cats;
  }
}

서비스에는 컨트롤러에서 사용할 메소드들을 만들어줍니다
서비스를 만들기 위해선 Injectable이라는 데코레이터를 만들어줘야 합니다.
Nest는 일반적으로 DI(Dependency injection)라는 디자인 패턴을 기반으로 구축되었습니다.
DI ?

클래스 모델이나 코드에는 런타임 시점의 의존관계가 드러나지 않는다. 그러기 위해서는 인터페이스만 의존하고 있어야 한다.
런타임 시점의 의존관계는 컨테이너나 팩토리 같은 제3의 존재가 결정한다.
의존관계는 사용할 오브젝트에 대한 레퍼런스를 외부에서 제공(주입)해줌으로써 만들어진다.

https://tecoble.techcourse.co.kr/post/2021-04-27-dependency-injection/

의존성을 줄어들게 하여 재사용성이 높고 가독성이 좋은 코드를 만들 수 있습니다 !

3. Module

각 애플리케이션에는 최사한 하나의 루트 모듈이 있고, 그래프를 구축하는 데 사용하는 시작점이 됩니다 !

import { Module } from '@nestjs/common';
import { CatsController } from './cats.controller';
import { CatsService } from './cats.service';

@Module({
  controllers: [CatsController],
  providers: [CatsService],
  exports: [CatsService]
})
export class CatsModule {}

일단 생성되면 모든 모듈에서 재사용 할 수 있습니다 !
모듈은 기본적으로 싱글톤 구조 이므로 여러 모듈 간에 동일한 인스턴스를 쉽게 공유할 수 있습니다.

이렇게 해당 모듈에 서비스와 컨트롤러를 연결할 수 있습니다 !

자 이렇게 해서 왜 Nest를 선택했고, 간단한 구조에 대해서 알아봤습니다. 너무 지식이 부족해서 제대로 정리했는지 모르겠지만, 앞으로 더 좋은 프로젝트를 만들기 위해서 더욱 공부 해야겠습니다 !

출처 Nest 공식문서 : https://docs.nestjs.com/controllers
[DI]이일민, 토비의 스프링 3.1, 에이콘(2012), p114
[데코레이터]https://toss.tech/article/nestjs-custom-decorator

profile
새로운 걸 배우는 것을 좋아하는 프론트엔드 개발자입니다!

0개의 댓글