대기열+웹 소켓 트러블 슈팅

김재익·2023년 9월 15일
0
post-thumbnail

개선 전 수강신청 로직
1. 클라이언트에서 수강 신청 요청 과 함께 웹 소켓 연결 요청 둘은 각각의 비동기 요청
2. 서버는 수강 신청 요청을 Redis 대기열로 등록
3. 서버에서 대기열에 등록된 요청을 처리, 처리와 함께 pub sub 구조로 해당 요청을 보낸 클라이언트에게 처리 결과 전송

문제

분산 서버로 확장시 웹 소켓 연결과 처리 결과 전송 로직에 문제가 발생함

원인

클라이언트로 부터 들어오는 모든 요청은 ALB에의해 라운드로빈 방식으로 모든 서버를 돌아가며 요청이 가게 되는데 이 때 /ws 요청을 받은 서버가 아닌 다른 서버가 대기열에 등록된 요청을 처리하고 /sub으로 전송했을 때 연결된 클라이언트가 없어 전송이 안됐다.

해결방안

웹 소켓 통신 전담 서버를 지정해 /ws 요청을 해당 서버만 받도록 ALB를 수정한다.
처리와 동시에 전송하는 것이 아닌 처리 결과를 캐시에 저장하고 전담 서버가 그것을 읽어 결과를 전송하도록 로직 분리
ALB 규칙을 이용하여 특정 경로 요청을 특정 서버로만 보내도록 하는법

문제 해결

하나의 서버가 웹 소켓 연결을 전담하고 해당 서버와 분산 서버는 처리 후 처리 결과를 캐시에 저장하고 웹 소켓 전담서버가 이를 주기적으로 읽어 결과를 전송해준다.

문제

규모있는 동시 트래픽이 발생했을 때 웹 소켓 통신이 불안정해지는 문제 + 그로인한 UX 문제 발생

원인

전담 서버도 웹 소켓 통신 외 조회, 신청 로직을 수행하므로 서버에 부하가 걸렸을 때 처리 결과 전송이 적용해놓은 주기대로 처리되지 않는 문제 발생

해결 방안

웹 소켓 전용 서버를 생성하여 웹 소켓 통신만 수행하도록 설계
(서버 비용을 줄이기 위해 기존 서버에 웹 소켓 통신을 전담했으나 UX에 문제가 발생하는 것은 궁극적으로 잘못된 것이기에 서버 비용을 부담하는 것이 옳다고 판단. 단, 수행 해야하는 업무가 간단하기 때문에 최대한 작은 서버로 비용절감)

문제 해결

웹 소켓 전용 서버는 요청을 대기열에 등록시키는 것과 스케줄러를 이용해 캐시에서 결과를 꺼내와 클라이언트에 전송하는 역할만 수행한다.

생각

어떻게든 서버 비용(지원금)을 아끼기위해 서버내 로직 수정으로 해결하려했지만 UX를 위해서는 타협이 필요하는 것을 알게되었다.
이 트러블 덕분에 ALB의 규칙 설정에 대해 알게 되었고 이는 나중에 MSA구조를 설계할 때도 사용할 수 있을 것 같다.
전체 로직에서 Redis 캐시 사용은 다른 팀원분이 구축하셨는데 이 트러블을 해결하면서 Redis를 사용해볼 수 있어서 좋은 경험이 되었다.

profile
개발자호소인

0개의 댓글

관련 채용 정보