코딩하고 싶을 땐, 타자를 두드리자

[Spring Boot/AWS] SQS 연결 및 Spring 서버에서 메세지 수신 구현기 본문

0x3 프로젝트/Caring

[Spring Boot/AWS] SQS 연결 및 Spring 서버에서 메세지 수신 구현기

[BE]모리 2025. 9. 12. 17:15

Caring 팀프로젝트에서 SQS를 이용하기까지의 과정

 Caring 프로젝트를 진행하면서, 새로운 기능 도입에 들어가게 되었다.
해당 기능은 바로 장애인 정책 검색 관련 RAG 챗봇이었다. 해당 챗봇을 만들면서 여러 AWS 서비스를 사용하여 구현을 하였고 이는 나중에 포스트를 통해 제대로 여정을 돌아볼 예정이다.
 
 이 장애인 혜택 지원 챗봇을 만들면서 기능 자체에 대한 의문이 PM 및 팀원에게 들었다. 그래서 이 챗봇이 과연 현재 열풍인 ChatGPT 보다 좋은가? 그리고 장애인의 타깃에 맞는 UX를 제공하고 있는가? 였다. 그래서 장애인 혜택 지원 챗봇의 기능을 보강하면서도 다른 것이 필요했다. 그렇게 생각한 것이, 기존에 설계한 DB를 이용하여 거주하는 지역에 맞게 신규 정책에 대한 정보를 공지하는 기능의 추가였다.
 

공지 챗봇 관련 아키텍처 설계

 
그래서 현 상황에 맞게 아키텍처 설계를 시작하였고, Lambda에서 EC2안에 있는 Spring 서버 사이의 통신이 필요했고, 이를 AWS SQS로 해결하려 하였다. 
 

Q1. 왜 Lambda에서 알림 전송까지의 처리를 담당하지 않고, Spring 서버와 일을 분담하였는가?

 가장 큰 이유는 아무래도 서비스의 책임 분리라 생각한다. 같은 서비스 내에 모든 기능을 한 번에 넣게 되면은 구현하기는 정말 쉽다. 그러나 시스템의 안정성, 이후에 추가될 기능에 관한 확장성을 생각하면 각 기능을 다른 서비스에서 처리하는 것이 이후 개발에 더 효율적이라 생각하였다.
 또한 아키텍처를 보다시피 두개의 RDS를 이용 중인데, 현재 MySQL 기반 RDS는 VPC에 소속되어 있고, PostgreSQL은 VPC에 소속되어 있지 않다. User RDS가 VPC에 소속되어 있기 때문에, 이를 VPC 밖 Lambda가 이용하기 위해선 VPC Endpoint가 필수이다. VPC Endpoint는 데이터 전송 비용뿐만 아니라 추가로 시간당 비용이 청구되기 때문에, 현 MVP 단계에선 과한 아키텍처라 생각하였고, 이를 해결할 방법으로 VPC 내부에 EC2를 두어서 해당 DB를 접근하자는 생각에 이르렀다.
 따라서, Lambda는 신규 정책 조회 및 해당 정책을 SQS에 메시지로 전달하는 단순 기능으로 구현하고, Spring 서버에서 SQS에 있는 메시지를 수신하여 처리하는 비즈니스 로직을 담당하는 것으로 결정하였다.

Q2. 왜 메시지큐를 Lambda와 Spring 서버 사이의 통신 기술로 사용하였는가?

 기능의 분리를 결정한 순간부터, 두 시스템의 통신을 고민하기 시작하였다.
처음에는 흔하게 Lambda에서 API 호출을 통해 Spring 서버와 통신하는 동기 방식을 선택하려고 했었다.
그런데, 동기 방식으로 구현하게 되면 만약 Spring 서버가 잠시 점검 중이거나, 갑작스러운 트래픽 증가로 응답이 느려지면 Lambda의 API 호출이 실패하게 되고, 이는 새로운 정책 데이터 처리 자체가 누락되는 심각한 문제로 이어질 수 있었다.
 그래서 두 서비스를 완벽히 분리하기 위해 비동기 방식인 메세지 큐라는 기술의 도입을 결정하였다. 메세지 큐를 도입하면, Lambda는 정책을 보내는데만 집중할 수 있고, 반대로 Spring 서버는 자신의 상태에 맞게 적절히 메시지를 수신하여 이를 공지로 만들어 전송하는 기능에만 집중할 수 있게 된다.

Q3. 왜 메시지 큐 구현 기술 중에 Kafka나 RabbitMQ가 아닌 SQS를 사용하였는가?

@<마녀 배달부 키키> 지브리 스튜디오

 
MVP 기능 구현을 하면서도 중요시 여기는 게 있다. 바로 코스트 대비 효율이다. 이 코스트는 여러 의미가 될 수 있다 생각한다. 사람의 시간 및 노력이 될 수도 있고, 아니면 말 그대로 요금이 될 수도 있다. 여러 프로젝트를 경험하면서, 이런 부분에는 더 많은 코스트가 생기고 이런 식으로 아키텍처를 바꾸면 효율이 더 증대되는 경험을 하였다. 그러다 보니 이번 프로젝트에서도, 해당 기능을 구현하기 위해 가장 적절한 아키텍처를 구상하는데 시간을 들였다. SQS는 그 기반에서 나온 선택이다. Kafka와 RabbitMQ도 훌륭한 메시지 큐 구현 기술이다. 다만, SQS와 다르게 서버리스 방식이 아니기 때문에, 별도의 서버가 필요하게 된다. 서버 비용보다 서버리스 방식으로 구현된 SQS가 더 저렴할 수밖에 없다.

심지어 100만 건 까지는 무료....

 
또한, 현재 Lambda에서 메시지 큐로 보내고, 이를 단순히 수신하여 이를 Spring 서버에서 처리하는 로직에서 RabbitMQ의 라우팅 기능이나 Kafka의 메세지 정책 이력 변경 내역 저장 및 스트리밍 기능은 오버스펙이라 생각하였다. 따라서, 이런 부분을 고려하여 SQS를 선택하게 되었다.
 
지금까지, Spring Boot에 SQS를 연결하게 된 여정을 아키텍처 기반으로 설명해보았다.