Redis Queue vs AWS SQS in NestJS

NestJS에서 Queue를 사용하는 방식에는 대표적으로 Bull을 통한 Redis, aws-sdk를 통한 AWS SQS(Simple Queue Service) 등이 있다. 공식문서 레시피에서는 Queue를 사용 시Redis/Bull를 사용하는 것을 권장하고 있다.

 

여기서 Redis는 뭔지 알겠는데 Bull이 뭔지 모르겠다고 생각이 들수도 있다. 잠시 Bull이 뭔지 알아보자.

Bull Github 주소에 들어가면 ReadMe 소개에 아래와 같이 적혀있다.

The fastest, most reliable, Redis-based queue for Node. Carefully written for rock solid stability and atomicity.

 

소개글을 그대로 확인해보면 Bull은 Node 환경에서 동작하는 Redis 기반의 Queue 시스템 라이브러리이다. Bull을 사용하면 Redis로 Queue를 직접 구현 및 ioredis로 nestjs에 맞게 연동하는 시간을 단축할 수 있는 메리트가 있다.

 

이에 비해 AWS SQS는 AWS에서 사용 가능한 Queue 시스템으로 작업 대기열 및 배치,버퍼, 순차 입력등 여러 용도로 활용 가능하다. AWS SQS에서는 표준 대기열/FIFO 대기열 의 두 가지 대기열 방식을 지원한다.

 

FIFO 대기열의 경우, Redis Queue와 대부분 동일하지만, 중복된 메세지가 들어오면 처리하지 않고 큐에서 제외시켜버린다. 표준 대기열은 메세지 배치를 비롯해 실시간 처리 용도로 사용하는 Queue라 선입선출이 지켜지지 않을 가능성이 있고, 최소한 한번 이상의 메세지 전달을 보장하여 동일한 메세지가 두 번 전달될 가능성이 있다.

 

Redis/Bull

Bull/Redis로 Queue를 구현하면 몇 가지 장점이 있다.

  1. Queue가 이미 구현되어있다.
  2.  공식 문서의 레시피 예시를 비롯해서 찾아볼 수 있는 레퍼가 있어 적용이 쉽다.

장점만 있다면 좋았을텐데 몇 가지 단점도 있다.

  1. Redis Cache를 사용하려면 추가적으로 cache-manager와 같은 라이브러리를 추가적으로 설치해줘야한다.
  2. 외부 인스턴스에 설치되어 있는 redis를 사용하는데 접속 및 세팅에 이슈가 있다.
    1. nestjs/bull 사용 시 동일 호스트의 redis에는 정상 접근/작동하지만, 외부 redis에는 Port/Auth 모두 정상으로 되고도 연결되지않는 이슈가 있다.( 로컬 환경에서 Redis-cli 통해 해당 인스턴스로 정상 접근/연결은 된다. )
      1. https://github.com/OptimalBits/bull/issues/2402 
      2. https://github.com/nestjs/bull/issues/1010
    2.  위의 이슈들을 체크해보면 해당 이슈에 대한 양측 moderator 의견은 "우리 패키지 문제가 아닌 거 같다."로 맺음된다. 

Bull 측 moderator 답변
NestJs 측 moderator 답변

 

AWS SQS

AWS SQS로 Queue를 구현하면 아래와 같은 장점이 있다.

  1. 중복 가능성이 있는 메세지를 서버측의 중복 로직 구현없이도 Queue에서 알아서 중복 제거한다.
  2. Batch로 묶어서 한번에 메세지 처리가 가능하다.
  3. aws-sdk를 사용하여 연동/적용하는 과정이 단순하다.

몇 가지 장점이 있으면 언제나 몇 가지 단점도 있다.

  1. Queue 이상의 역할은 할 수 없어 Cache 사용이 필요하면 Redis 세팅이 불가피하다.
  2. 서버에서 Queue 상태를 확인할 수 없어서 aws-cli나 aws 콘솔에서 체크해야한다.

 

마무리

현재 쓰고 있는 기술 스택 및 상황에 따라 Redis Queue 또는 AWS SQS를 잘 골라서 사용하면 될 거 같다.