가상면접 사례로 배우는 대규모 시스템 설계 기초(1) - 사용자 수에 따른 규모 확장성

1장 사용자 수에 따른 규모 확장성
김주혁's avatar
Mar 09, 2024
가상면접 사례로 배우는 대규모 시스템 설계 기초(1) - 사용자 수에 따른 규모 확장성
 

 
가상면접 사례로 배우는 대규모 시스템 설계 기초를 읽으면서, 트래픽을 감당하기 위한 기본적 서버 설계에 관하여, ppt 방식으로 어떻게 쉽고 잘 설명할 수 있을까 고민하다 AWS 기반으로 설명한다면 실무적으로 도움이 될 것 같아 AWS 기반 아키텍쳐를 설명하기로 했다.
 

1. DNS

일반적인 시스템 구성을 이해하기 위해서는 사용자 요청인 트래픽 처리과정의 흐름을 먼저 이해할 필요가 있다.
 
사용자로부터 전달된 요청은 특정 도메인으로의 요청이다. 도메인으로 AWS의 컴퓨팅 네트워크와 매핑된 주소를 찾기 위해서는 먼저 DNS 쿼리를 해결해야 한다. 해당 DNS 쿼리를 통한 질의는 AWS의 Route 53 Resolver에 연결된 VPC에 있는 VPC+2로 전송된다.
 
notion image
 
  1. Client가 AWS DNS resolver에 도메인 주소인 www.example.com으로 쿼리를 질의
  1. DNS resolver 서버는 DNS root name server에 도메인관련 정보 질의
  1. DNS root name server는 다시 DNS resolver server로 .com을 관리하는 name server의 정보를 응답
  1. DNS resolver server는 다시 .com을 관리하는 서버로 www.example.com 관련 쿼리 질의
  1. .com을 관리하는 name server는 www.example.com을 route53 name server로 다시 응답
  1. DNS resolver server는 route 53 name server로 질의해 ip 주소를 얻게되고, 해당 ip 주소를 client에 전달함으로 써 DNS 관련 정보를 얻어 해당 주소로 이동
 
하는 순으로, AWS DNS resolver를 통해 사용자는 DNS 관련 정보를 얻어 해당 주소로 이동할 수 있다.
아웃바운드 건, 인바운드 건 결국 DNS resolver를 통하여 DNS 질의를 수행하고, 이 질의를 기반으로 얻은 정보를 토대로 움직인다는 것은 변함이 없다.
 
이것이 하나의 트래픽을 이해하기 위한, 기본 동작 DNS 질의 과정이다.
 

2. Load Balancer

이제 DNS 쿼리 질의 과정을 통해 정보를 취득하고, 도메인이 가리키는 IP 주소를 알아냈다.
 
위와 같은 과정을 통해 수 많은 사용자가 서버에 요청을 보내게 되면, CPU나 메모리 사용량이 증가해 서버가 다운될 수 있고 느려질 수 있다.
 
부하 분산 문제를 해결하기 위해, 서비스 운영자는 수직적 Scale up과 수평적 Scale out 정책을 선택할 수 있다.
 
책에서는 이런 문제를 해결하기 위해 사용되는 것이 부하 분산기인 로드 밸런서라고 소개하고 있다. 물론 Scale out 정책인 로드 밸런서 뿐만 아니라, 점유율과 사용량 그리고 트래픽 추세를 통해 Sclae up을 진행할 수도 있지만, 여기서는 책에서 나온대로 Scale out을 위한 AWS 로드 밸런서를 토대로 말하게 됐다.
notion image
Without Load Balancing
notion image
With Load Balancing
 
로드 밸런서는 부하 분산 집합에 속한 웹서버에 트래픽을 고르게 분산하는 역할을 한다. Route 53을 사용하는 경우 로드 밸런서를 도메인에 설정할 때 레코드가 생성되는데, DNS를 통해 얻은 정보를 토대로 해당 레코드와 매핑된 Public IP에 접근하게 된다.
 
notion image
해당 로드 밸런서는 VPC와 네트워크 매핑을 수행할 수 있고, 선택한 AZ와 매핑된 네트워크 VPC의 라우팅 테이블을 통해 target이 되는 컴퓨팅 리소스로 트래픽을 각 가용영역으로 부하 분산시킨다.
 
notion image
그리고 Scale out 전략을 위해 해당 컴퓨팅 네트워크에 ASG group이 설정됐다면, 기본적인 트래픽에 대한 대비는 된 것이다.
 

3. Database

이제 유저의 트래픽을 감당하기 위한 기본 준비가 완료 됐다.
 
하지만, 데이터 베이스는 어떠한가?
 
현재 데이터베이스는 유저의 수 많은 요청에 대한 처리를 대비할 준비가 전혀 돼있지 않다. 책에서는 많은 데이터베이스 시스템이 주(master)-부(slayer) 관계를 설정하고 있다고 한다. 데이터 원본 및 쓰기 작업은 주 서버에, 읽기 및 사본은 부 서버에 두는 것을 저장하는 방식이 보통이라고 한다.
notion image
 
이제 책에서 나온대로 master와 slave를 rds로 설정했다. rds는 같은 vpc안에 있을 수도 있고, 다른 vpc로 연결된 상태로 피어링이 걸려있을 수도 있지만, 일단은 단순하게 같은 vpc안에 있다.
 
master와 slave가 설정된 위 구조에 다중화를 적용하는 방식으로 하나의 read 데이터베이스에 장애나 부하가 생겨도, 다른 read 데이터베이스를 사용하면 되기 때문에 가용성과 재해 복구에 더 수월해질 것이다. aws에서는 해당 기능을 위해 multi a-z와 read replica를 계속해서 생성해주는 방식을 제공하는데, 이번에는 read replica 방식을 간단하게 설명할 것이다.
 
https://aws.amazon.com/ko/blogs/database/automate-amazon-rds-for-postgresql-horizontal-scaling-and-system-integration-with-amazon-eventbridge-and-aws-lambda/
 
위 이미지는 AWS 공홈에 올라와 있는 RDS 수평 확장 및 Amazon EventBridge 및 AWS Lambda와의 시스템 통합을 위해 Amazon RDS 자동화다. 관련 지식이 부족하여 간단한 예시를 들어 이런식으로 scale out이 가능하다만 보여주기 위해 가져왔다.
 
아직 해당 RDS scale out에 대한 정보가 없어, 가능하다는 정도로 대략적인 설명만 하면
  1. AWS CloudWatch가 RDS의 I/O를 모니터링 하고 있다 특정 임계점이 넘으면,
  1. AWS EventBridge에 이벤트가 발생하고 해당 이벤트로 AWS Lambda를 실행시켜
  1. AWS Lambda에서 RDS 읽기전용 slave replica를 생성하고
  1. replica 생성 후 SNS로 메세지를 발행한다.
  1. Application에서는 SNS 주제를 구독하고 있다 이벤트를 전달받아
  1. 해당 구독 이벤트를 기반으로 기존 RDS와 새로 생성된 read replica에 offload, 즉 읽기 작업을 분산시킨다.
 
위와 같은 과정으로 rds의 부하와 장애를 예방하고 가용성을 올리는 노력을 통해 서버뿐만 아니라 데이터베이스의 부하와 장애까지 극복했다.
 
그렇다면 이제, 부피가 크거나 참조가 빈번하게 일어나는 데이터는 어떻게 처리하면 좋을까?
 

4. Cache / CDN

  • Cache
    •  
      위에서의 작업 결과로, 일종의 트래픽 부하는 예방 됐다.
       
      하지만 동일한 요청이 반복된다거나, 리소스를 많이 소모하며 시간이 오래 걸리는 작업이 있다면 서버의 성능이 줄어들고, 데이터 베이스 성능 또한 저하 될 것이다.
       
      또한, 데이터베이스 다중화같은 기술을 사용할 수 없다면 많은 트래픽이 데이터베이스에 집중 됐을 때 장애를 겪을 확률이 높다.
       
      notion image
      이럴 때 사용할 수 있는게, 바로 캐시 서버다.
       
      읽기 주도형 캐시 전략을 통해 자주 사용되거나, 비용이 큰 요청을 캐시서버에 저장한 뒤 그러한 요청이 들어오면 캐시서버에 저장된 데이터를 보내주는 식으로 부하를 줄일 수 있다.
       
      이를 통해 응답시간을 개선할 수 있다.
 
  • CDN
    •  
      이제 응답시간을 개선했는데, 만약 서버에 동영상과 이미지 등 정적 콘텐츠를 많이 사용한다면 예를들어 페이지를 열 때마다 같은 동영상이 계속해서 로드되는데 그 때마다 동영상을 새로 불러오고 있다면 트래픽과 비용을 많이 차지하는 정적 콘텐츠 특성상 리소스 낭비가 심할 것이다.
       
      이럴 때 사용할 수 있는 것이 바로 CDN이다.
       
      CDN은 정적 콘텐츠를 사용하는데 쓰인다. 이미지, 비디오, CSS, javascript 파일 등을 캐시할 수 있다.
       
      AWS에는 CDN으로 사용할 수 있는 리소스로, CloudFront가 있고 이 CloutFront를 통해 정적 컨텐츠인 이미지 동영상, 그리고 js와 css까지 캐싱할 수 있기 때문에 이제 프론트엔드는 CDN으로 배포한다.
 
여기까지 왔을 때 나올 수 있는 아키텍쳐는 아래와 같다.
notion image
 

5. 그 외

  1. 무상태 웹 계층
    1.  
      이제 서버와 데이터베이스의 수평 확장을 도모했다.
       
      책에서는 웹 계층의 stateless 성을 지향해야 한다고 나와 있는데, AWS의 리소스들은 이미 각 리소스간 서로 stateless하다. scale out을 위해 ec2의 리소스를 계속해서 모니터링하고 있는 클라우드 와치를 비롯한 scale out 전략 흐름을 제외하면 이미 무상태 웹 계층을 지향한 상태로 아키텍쳐가 존재한다.
       
      하지만, VPC는 stateful한 것과 stateless한 개념의 차이가 있다. VPC의 security groups은 stateful하고 VPC의 ACL은 stateless하다.
       
      • security groups
        • stateful 네트워크 트래픽 처리는 VPC의 기본 동작
        • VPC의 보안그룹에 설정된 상태에 따라, 트래픽 흐름 제어를 위해 인바운드 규칙을 제어하게 되며 아웃바운드는 암시적 자동적으로 허용된다.
        • 하나의 서버 단위 네트워크 정책
        •  
          일반적으로 보안그룹은 같은 서브넷이나 다른 서브넷에서의 I/O를 제어하게 된다. 허용된 트래픽을 기억하고 해당 트래픽에 대한 응답을 허용하는 것이기 때문에, 특정 IP로 들어오는 것이 허용된다면 당연히 그 IP로 나가는 것도 허용된다.
           
      • ACL
        • stateless 트래픽 처리로 AWS VPC에서 ACL의 기본 동작
        • stateless 네트워크에서 ACL은 인바운드 및 아운바운드에 대한 명시적 규칙이 필요
        • 서브넷 단위 네트워크 정책
        •  
          ACL은 기본적으로 인바운드/아웃바운드 모두 차단된다. 예를들어 80 포트를 허용했다고 하더라도, 아웃바운드가 차단된다면 응답이 허용되지 않는다.
           
      보안그룹과 ACL은 어떤 상황에서 적용될까?
       
      보안그룹은 같은 서브넷인 경우 서브넷 내에서는 같은 네트워크 ACL이 적용되기 때문에 트래픽이 서브넷 내에서 자유롭게 이동할 수 있다. 따라서, 서브넷 간 트래픽을 조율하려면 보안 그룹을 조정해야 한다.
       
      ACL은 다른 서브넷과 외부에서의 요청에 적용에 사용되고, 다른 네트워크 ACL이 적용되기 때문에 다른 서브넷과 외부와의 트래픽을 조율하려면 ACL을 수정해야 한다.
       
  1. 데이터 센터(지리적 라우팅)
    1.  
      AWS는 지리적 위치 라우팅을 Route 53을 통해 DNS 쿼리가 시작되는 위치 기반으로 트래픽에 제공하는 리소스를 선택할 수 있다.
       
      Route 53으로 DNS 쿼리는 지리적 라우팅된 IP로 요청을 보내게 되고, 지역에 따라 다른 데이터 센터에 요청을 보낼 수 있다.
       
  1. 메세지 큐
    1.  
      메세지 큐는 Pub/Sub 기반으로 메세지를 게시한 Publisher와 구독하고 게시된 메세지를 사용하는 Subscriber로 나뉜다.
       
      메세지는 다음과 같은 상황에 쓰인다.
    2. 비동기 작업 처리: 메시지 큐는 비동기 작업을 지원하므로, 작업을 비동기적으로 처리하고 결과를 나중에 가져올 수 있다. 예를 들어, 이메일 발송, 파일 처리, 알림 전송 등의 작업을 비동기적으로 처리할 때 메시지 큐를 사용할 수 있다.
    3. 시스템 간 통신 및 통합: 서로 다른 시스템 간에 메시지 큐를 사용하여 데이터를 안전하게 교환하고 통합할 수 있습니다. MSA 아키텍쳐에서 주로 메세지 기반의 설계를 주도하며, 각 서버간 의존성을 줄이고 독립적으로 동작할 수 있도록 도와준다.
    4. 이벤트 드리븐 아키텍처: 메시지 큐는 이벤트 기반 아키텍처를 구현하는 데 사용된다. 이벤트를 생성하고 이벤트를 구독하는 서비스 간의 통신을 용이하게 만들어, 느슨하게 결합된 시스템을 구축할 수 있다.
    5. 작업 조절 및 스케쥴링: 메시지 큐는 작업을 예약하고 스케줄링할 때 유용하다. 일정한 간격으로 주기적인 작업을 실행하거나, 특정 이벤트가 발생했을 때 특정 작업을 수행하는 데 사용할 수 있다.
    6. 고가용성 및 확장성: 메시지 큐는 대량의 작업을 처리하고 여러 서버 간에 작업을 분산하여 확장성을 갖출 수 있다. 또한, 메시지 큐를 사용하면 일부 서버가 다운되더라도 메시지는 안전하게 보관되어, 시스템이 고가용성을 유지할 수 있다.
    7. 버퍼 역할: 메시지 큐는 서로 다른 작업 속도를 조절하는 데 사용될 수 있다. 빠른 생산자와 느린 소비자 간의 데이터 흐름을 조절하고, 시스템에 유입되는 트래픽을 조절할 수 있다.
    8.  
      notion image
      다양한 상황에서 메세지를 기반으로 서비스를 구축할 수 있다. AWS에는 SQS라는 메세지 리소스가 있고, 이를 기반으로 고가용성 및 확장성을 구축하는 간단한 예시를 들면
       
      특정 작업에 의해 메세지 큐로 메세지가 전송되고 해당 메세지의 일정 숫자 이상 늘어나면 큐를 모니터링하고 있는 CloudWatch의 특정 메트릭 정보로 알람이 울려 EC2가 scale out되는 형태로 간단하게 메세지 기반 서비스의 확장성을 노릴 수 있다.
 
  1. 로그, 메트릭 그리고 자동화
    1.  
      일반적으로 규모가 작거나, 유저가 아직 이용중인 서비스가 아니라면 로그나 메트릭 자동화 같은 것들은 하면 좋지만, 꼭 필요하진 않다. 하지만, 규모가 커지면 반드시 필요해진다.
       
      notion image
      로그는 시스템이나 프로그램의 동작에 관한 정보를 기록하는 것을 의미한다. 가장 간단하게 node.js의 로그 라이브러리를 사용한다면 이런식으로 로그를 기록할 수 있다.
       
       
      notion image
      메트릭은 CPU 사용량, 메모리 등 네트워크 자원의 사용량과 서비스의 응답시간 및 지연시간 및 트래픽에 대한 총체적인 정보들을 메트릭이라고 부릅니다.
       
      notion image
      notion image
      AWS는 CloudWatch란 리소스로 각 리소스별 사용에 관한( 예를들면 메세지, 람다) 내역을 기록하여 볼 수 있다.
       
      아니면, AWS와 결합하여 Data dog이나 Grapana와 같은 로그 및 메트릭을 수집하여 GUI 형태나 그래프 형태로 제공하는 서드파티 툴을 사용해서 로그 메트릭 정보를 수집할 수 있다.
 
Share article
RSSPowered by inblog