Frontend 리팩토링과 아키텍처에 대해서 깊게 고민하던 도중 우연히 만났다. 흥미로워서 프론트엔드 영상보다 먼저 보게되었다.
레거시 리팩토링이나 운영에 관한 이야기가 정말 많았는데 너무나 흥미로웠고 인사이트도 많이 얻어서 글로 기록해둔다.
1. 5천만 전국민 요청에도 끄떡없는 네이버 검색 만들기 - 검색 SRE와 비상대응 시스템
2. 네이버페이 결제 시스템의 성장과 변화
5천만 전국민 요청에도 끄떡없는 네이버 검색 만들기 - 검색 SRE와 비상대응 시스템
플레이 네이버(PLAY NAVER)
[팀네이버 컨퍼런스 DAN 24] 5천만 전국민 요청에도 끄떡없는 네이버 검색 만들기 - 검색 SRE와 비상대응 시스템
tv.naver.com
[ 왜 필요했는가? ]


대통령 선거, 국가 재난 상황 등 전국민의 관심이 일정 시간동안 집중되는 경우가 있다. 이 때, 네이버 검색의 트래픽이 10배 가까이 오르고 가용성이 바닥나는 상황이 생긴다. 이는 API 응답 오류와 신뢰성 저하로 이어지게 된다.
당연히 서버 증설을 하면 좋지만, 이런 예측 불가능한 상황(트래픽 폭증)에서 무제한의 장비 증설은 불가능하다. 그래서, 네이버는 이에 대한 비상 대응 시스템을 설계 및 적용했다.
[ 비상 대응 모드 ]


네이버 검색은 비상 대응 모드를 생성하여 이 문제를 해결하기로 하였다. 비상 대응 중에는 캐시와 병목 지점이 생기는 부분에 대한 복잡한 요청을 Degrade시키고(신뢰성 감소), 이를 통해서 트래픽의 가용성을 신속히 확보하는 것에 집중한다.
그럼 여기서 질문이 생긴다.
"검색 서비스의 중단 없이 어떻게 비상모드를 서버에 적용할 것인가?"
"서버가 터지지 않게, 비상모드를 얼마나 신속하게 적용할 것인가?"
"비상 대응모드가 필요한 상황을 어떻게 정의할 것인가?"
[ Dynamic Configuration Management ]


Spring Cloud Config 와 같이 서버에 설정값을 중앙에서 관리하고 이를 각 Client가 가져와서 쓰는 방법이다. 그리고, 설정값이 변경되면 이를 알려주어서 변경 사항을 전파하여 각 Client가 다시 설정에 맞게 구성되도록 한다.
이렇게하면 설정값과 같은 간단한 케이스는 중단 없이 바로 배포가 가능하며, 비상모드를 바로 실행할 수 있게된다.
다만, 이 설정값이 잘못될 경우 바로 장애가 발생할 수 있으므로 배포 전 data validation 과정이 필수로 필요해진다.
이를 통하여, 네이버는 서비스 중단없이 비상모드를 즉시 적용할 수 있게된다.
[ 비상대응모드 정의 ]


비상대응은 결국 트래픽의 증가로 결정된다.
트래픽의 증가가 판별될 경우, 자동적으로 비상대응을 발동시켜서 서비스의 안정성을 높인 뒤 주요 서비스의 핵심 지표를 수집한다.
핵심 지표들이 괜찮다고 판별될 경우, CDCM을 이용하여 다시 원상 복구를 시킨다.
[ 느낀점과 인사이트 ]
- 별도의 배포없이 설정을 바꿀 수 있다는 점이 굉장히 재밌었다.
- 위에서 설명은 안했지만, 네이버 검색은 "지진", "선거" 등 정말 사람들과 함께 숨쉬는 서비스구나 느껴져서 부러웠다.
- SRE를 막연하게 사이트 신뢰성으로 알고 있었는데 저렇게 일하시는구나 느껴져서 정말 재밌었다.
네이버페이 결제 시스템의 성장과 변화
플레이 네이버(PLAY NAVER)
[팀네이버 컨퍼런스 DAN 24] 네이버페이 결제 시스템의 성장과 변화
tv.naver.com
[ 분산 DB로의 전환 ]

Read Replica를 늘린다면 단일 DB로도 부담이 줄어들었을 수도 있다. 하지만, 주문 도메인의 특성에 의해서 Write가 많은 서비스이기 때문에 해당 방법으로는 해결할 수 없었고 Sharding을 통한 분산 DB적용이 필요했다.
강연자님 말로는 Read 트래픽은 해결책이 정말 다양하게 있기 때문에 분산 DB가 꼭 필요한 지는 잘 생각해서 적용해보라 하셨다.
[ 점진적 DB 전환 ]

Strangler Facade는 점진적 전환을 위한 패턴입니다.
legacy 시스템과 modern 시스템을 모두 운용하면서, 문제가 생길경우 legacy 시스템의 결과를 가져와서 유저에게는 안정적인 답변을 줍니다. 또한, 마이그레이션 완료된 부분에 대해서는 기존 시스템과 결과를 비교하여 제대로 동작하는 지 확인을 합니다.
이렇게 한 부분씩 마이그레이션을 진행하고 테스트를 진행하면서 점진적 전환을 가능하게 해줍니다.
[ 단일 DB와 분산 DB 듀얼 운영]
분산 DB로 모두 전향하면 좋겠지만, 네이버에서는 분산DB로는 효율이 너무 좋지 않은 서비스들이 있다. 예를 들면, 패밀리 계정 등으로 가족들을 묶어야하는 경우다. 이 경우 브로드캐스팅 쿼리를 날려야하며 이 경우는 오히려 단일 DB보다 부하를 급증시킨다. 그래서, 단일 DB를 유지해야한다.
하지만, 단일 DB와 분산DB를 모두 운영하면 DB가 두 개이므로 다음 문제가 생겼다한다.
- 각 DB가 서로의 변경사항을 알아야한다.
- 다른 DB에 복제가 지연되면 문제가 생길 수 있다.

- 각 DB가 서로의 변경사항을 적용하기 위해서 Dual Write Driver를 만들어서 애플리케이션 단에서 두 개의 DB와 커넥션을 유지하고 write 요청을 합니다. (애플리케이션의 상대적인 부담이 생깁니다.)
- 복제를 할 때, 하나의 DB에 먼저 업데이트를 적용합니다. 해당 DB가 제대로 완료되었다면 그 결과값을 바탕으로 다른 DB를 업데이트합니다. 이 때, 완료된 최종 데이터를 문제가 생기지 않습니다.
- 복제 중이여서 분산 DB에 해당 데이터가 없을 경우, 단일 DB에서 데이터를 조회하여옵니다. 업데이트가 완료되었다면 단일 DB에 값이 있습니다.
[ EDA(Event Driven Architecture) 도입 ]

결제 시스템은 카드사와 은행권을 사용해야하는데, 이는 확장할 수 없다. 즉, 트래픽이 폭주하는 것을 감당할 방법이 없다.
이런 경우, EDA를 사용하는 것이 좋은 솔루션이 된다.
장점은 이런 트래픽 증가를 해결하고 유연한 구조를 가져갈 수 있는 것이다. 단점은 비동기에서 생기는 개발과 운영의 복잡성이다.
[ EDA 이벤트 검증 프로세스 ]

메시지를 발송하고 n분 후, 제대로 처리되었는 지 확인하는 장치를 도입했다. EDA에서 필요없으나, 초기 도입 시에 유용한 안정 장치가 된다.
[ DLQ ]

네트워크가 안 좋아서 실패하거나 메세지의 순서 보장이 필요한 경우가 있다.
이 때, 지속적인 에러를 발생시키는 메시지들은 전체 시스템의 지연을 만들기 때문에 DLQ로 빼주어서 별도 관리를 진행한다.
이 부분을 더 자세히 설명하면
1. Queue에서 메시지 방출 및 소비
2. Error가 발생하면, retry (Redis에 기록하여 빠르게 읽기에 보관할 것들은 여기에 임시 보관)
3. 지속적으로 실패한 데이터는 DLQ로 보내서 시스템 지연을 막음고 상황에 맞게 DLQ에 데이터를 넣고 빼서 처리
[ 이벤트 처리 지연 현상 ]

증설하면 해결되지만 불가능하다면 작업시간이나 주제에 따라서 토픽을 분리하면 좋다.
토픽에 따라 우선순위를 부여하면 가벼운 이벤트나 급한 이벤트들을 우선적으로 해결하면서 이득을 볼 수 있다.
또한, 장애 시 너무 장기간 쌓여진 정상적인 이벤트들도 제거한다 (보통 이 경우 요청이 만료되어서 쓸모가 없다.)
[ 느낀점과 인사이트 ]
- 점진적 전환에 대해서 굉장히 회의적이었는데, Strangler Facade라는 장치가 굉장히 맘에 들었다. 나중에 써봐야겠다.
- EDA와 비슷한 부분에 대해서 최근에 궁금했었다. 그리고 저거 도입했을 때, 메시지 손실 처리가 정말 궁금하고 불안했는데 안전 장치를 별도로 만들어서 천천히 도입하는 부분이 재밌었다.
- 토픽을 분리하는 건 뭔가 페이지 교체 알고리즘이나 JS 비동기 방식이랑 비슷해보여서 아이디어 하나만 잘 알고 확장시켜도 되겠구나 많이 느끼는 중이다.
'책과 강연 > 온라인 강연' 카테고리의 다른 글
| [구름 강연] 시야가 넓은 개발자는 무엇이 다를까? _ 김영재님 (LINE 기술임원) 후기 3편 (2) | 2024.02.15 |
|---|---|
| [구름 강연] 시야가 넓은 개발자는 무엇이 다를까? _ 김영재님 (LINE 기술임원) 후기 2편 (0) | 2024.02.14 |
| [구름 강연] 시야가 넓은 개발자는 무엇이 다를까? _ 김영재님 (LINE 기술임원) 후기 1편 (1) | 2024.02.14 |
| [유튜브] 소프트웨어 아키텍처의 중요성 (2) | 2023.12.28 |