brunch

You can make anything
by writing

C.S.Lewis

by 강수빈 Dec 04. 2023

백엔드 초보자가 무조건 NestJS를 써야 하는 이유

NestJS lifecycle

Masterpiece of JS Backend Framework


NestJS를 사용해야 하는 이유


NestJS는 타입스크립트를 기본으로 지원하며 다양한 데코레이터와 인핸서를 만들고 활용할 수 있어 생산성과 안정성이 뛰어나다.

하지만 내가 초보 개발자에게 NestJS를 추천하는 이유는 이런 이유가 아니다.

데코레이터와 인핸서가 있어도 쓸 줄 모르면 그만이기 때문이다.

초보 개발자가 NestJS를 사용해야 하는 가장 큰 이유는 의존성 주입을 몰라도 저절로 쓰게 된다는 것이다.


의존성 주입이 뭔지 모르겠다고? 그래도 일단 시작해보자.

우선 NestJS를 시작하면 자동으로 Controller와 Service, Module이 생성된다.

이제 막 입문한 초보 개발자는 공식 홈페이지의 튜토리얼대로 Controller에서 라우터를 설정하고 Service에서 TypeORM을 활용해 데이터를 다룰 수 있다.

이때 데이터를 다루기 위해서는 Service에 InjectRepository로 Model을 주입해줘야 하고 Injectable된 해당 Service를 Module에서 주입받아야 Controller에서 사용할 수 있기에 의존성 주입이라는 것을 원치 않아도 익히게 된다.

지금 설명이 이해되지 않아도 괜찮다.

다시말해 의존성 주입을 활용하지 않으면 작동하지 않게 만들었으니 발생하는 에러를 해결하다 보면 저절로 의존성 주입을 활용하게 되고, 이는 결과적으로 초보 개발자도 유지보수와 협업이 쉬운 코드를 작성하게 된다.


NestJS의 기초, 라이프사이클


라이프사이클은 NestJS를 시작하는 초보 개발자가 가장 먼저 짚고 가야 할 부분이다.

Middleware, Guards, interceptors, Pipes, Controller, Exception filters를 활용하는 법을 알면 백엔드 개발이 엄청나게 간단해진다.

백엔드 개발을 처음 접한 사람이라면 이걸 왜 다 알아야하는지 그 이유에 공감하지 못할 수 있다.

그렇다면 지금 당장은 Controller만 알면 된다.

Controller에서 Request를 받아 처리하고 Response 하는게 자연스러워지는 것이 먼저다.

유저의 회원가입과 로그인 인증, 게시글 CRUD를 처리하는 백엔드를 구성해보자.

그 과정에서 Request를 처리하기 위한 잡다한 코드를 많이 작성하게 된다.

복잡하게 작성된 읽기 힘든 Controller를 접하고서 라이프사이클을 공부한다면 그 필요성과 유용성에 공감할 수 있을 것이다.


NestJS 라이프사이클


위 이미지는 NestJS의 라이프사이클을 그림으로 나타낸 것이다.

공식 문서, NestJS 라이프사이클을 검색했을 때 나오는 이미지와 약간의 차이가 있는데 어떤 부분이 다른지 확인해보고 여러분은 어떻게 생각하는지 댓글로 의견을 남겨주길 바란다.


아래는 각 라이프사이클의 특성과 간단한 활용법을 적은 글이다.


Middleware

라이프사이클 내의 모든 역할을 Middleware로 구현할 수 있다

어떤 역할이든 수행할 수 있지만 모든 동작을 Middleware로 구현하면 해당 Middleware가 어떤 역할을 하는지, 어디에 적용되어 있는지, Request와 Response 중 언제 작동하는지 매번 코드를 읽고 확인해야 한다.

HTTP 통신에서만 동작하는 것도 단점이다.

따라서 Middleware는 웬만하면 사용하지 말고 이외의 라이프사이클을 활용하는 것을 추천한다.


Guards

Request를 확인하고 수정할 수 있다.

User Guard를 만들어 헤더에 포함된 토큰의 유효성과 권한을 확인하고 인증된 유저의 정보를 Request에 포함하면 이후 유저 정보를 쉽게 활용할 수 있다.

토큰 검증에 실패할 경우 Exception filters를 활용해 에러를 Response 할 수 있다.


Request Interceptors

Guards처럼 Request를 확인하고 수정할 수 있다.

Guards의 검증을 통과한 Request를 처리하며 Pipes와 Controller에서 사용할 기능을 Request에 미리 정의할 수 있다.


Pipes

Controller에서 사용되는 데이터를 해당 파이프에 맞게 변환 혹은 예외 처리한다.

params에 ParseintPipe를 쓰면 값을 Number로 변환할 수 있다.


Controller

Request를 확인해 라우팅하고 처리한 결과를 Response한다.

유저 커스텀 데코레이터를 만들어 사용하면 Request 내의 유저 정보를 간단히 활용할 수 있다.


Response Interceptors

Request 처리 간 생성된 정보를 Response에 활용할 수 있다.

Guard의 검증을 통과해 정상적으로 처리된 Response에 대한 로그를 남길 수 있다.

RxJS의 catchError로 Pipes, Controller에서 try / catch 없이 발생한 에러를 catch해 처리 후 Exception filters를 실행할 수 있다.


Exception filters

try / catch로 처리하지 않은 오류 발생 시 실행된다.

라이프사이클 내의 어떤 단계에서든 Exception filters가 실행될 수 있다.

Exception filters 실행 시 이후 모든 단계를 스킵하고 해당 Exception을 Response한다.

에러에 대한 로그를 남길 수 있다.


글만 봐서는 이해하기 어렵다면 공식문서를 보고 간단한 프로젝트를 시작해보길 바란다.

아래 링크해 둔 강의를 보고 공부하는 것도 좋다.

라이프사이클을 이해하고어느정도 다룰 수 있게 되었다면 드디어 NestJS의 시동을 걸었다고 할 수 있겠다.

나도 이제 막 시동을 건 초급 개발자이기에 앞으로 나아갈 수 있도록 더 열심히 공부할 것이다.


마치며


NestJS 라이프사이클을 대략적으로는 알고 있었는데 이번에 글로 정리하며 완전히 이해할 수 있었다.

이 글을 계기로 여러분이 NestJS에 관심을 갖게 됐다면 더할나위없이 기쁜 일이다.

혹시 내가 잘못 이해하고 있는 점을 짚어준다면 굉장히 큰 도움이 될 것이다.


읽을거리


Request lifecycle | NestJS


NestJS Intereptor와 Lifecycle | 슈퍼브 블로그


관련 강의


NestJS로 API 만들기 | 노마드 코더


10개 프로젝트로 끝내는 Node.js의 모든 것(Express & Nest.js) 초격차 패키지 Online. | 패스트캠퍼스


NestJS REST API 백엔드 완전 정복 마스터 클래스 - Part 1 NestJS Core | 인프런


작가의 이전글 단 6개월만에 풀스택 개발자가 되는 과정
브런치는 최신 브라우저에 최적화 되어있습니다. IE chrome safari