서버리스가 확장성에 대해 당신에게 거짓말을 하고 있습니다
서버리스 컴퓨팅은 무한한 확장성과 제로 오버헤드를 약속합니다. AWS Lambda나 Google Cloud Run과 같은 플랫폼은 컴퓨팅 레이어를 즉각적으로 확장합니다.
하지만 당신의 백엔드는 여전히 다운됩니다.
문제는 컴퓨팅이 아닙니다. 문제는 데이터베이스입니다.
함수가 확장될 때, '커넥션 스톰(connection storm)'이 발생합니다. 새로운 함수 인스턴스가 생성될 때마다 데이터베이스에 새로운 연결을 시도하기 때문입니다. 만약 1,000개의 함수가 있다면, 1,000개의 연결 요청이 동시에 Postgres 또는 MySQL 인스턴스에 몰리게 됩니다.
관계형 데이터베이스에는 엄격한 한계가 있습니다. 이 한계에 도달하면 새로운 연결은 실패합니다. 이는 높은 지연 시간(latency)과 5xx 에러로 이어집니다. 컴퓨팅은 준비되었지만, 데이터베이스가 버티지 못하는 것입니다.
다음 세 가지 전략으로 이 문제를 해결할 수 있습니다:
커넥션 프록시(Connection Proxy) 사용하기 함수를 데이터베이스에 직접 연결하지 마세요. AWS RDS Proxy 또는 Google Cloud SQL Proxy와 같은 프록시를 사용하세요. 이 레이어는 함수와 데이터베이스 사이에 위치합니다. 소수의 지속적인 연결 풀(persistent connection pool)을 관리하며, 이를 수많은 함수가 공유할 수 있도록 합니다.
데이터 프록시 레이어 구현하기 고급 프록시는 단순히 연결을 관리하는 것 이상의 역할을 수행합니다. 다음과 같은 작업이 가능합니다:
- 읽기(read)와 쓰기(write)를 서로 다른 데이터베이스 인스턴스로 분산합니다.
- 빈번한 쿼리를 캐싱하여 데이터베이스 부하를 줄입니다.
- 쿼리가 데이터베이스에 도달하기 전에 최적화합니다.
- 비동기 쓰기(Asynchronous Writes)로 전환하기 모든 사용자 액션을 동기식 데이터베이스 쓰기로 처리하지 마세요. 많은 작업이 즉각적인 일관성(consistency)을 필요로 하지는 않습니다.
기존 방식: User Action -> Function -> Sync DB Write -> Response
권장 방식: User Action -> Function -> Push Event to Queue -> Fast Response
별도의 함수가 해당 이벤트를 가져와 나중에 데이터베이스에 기록할 수 있습니다. 이를 통해 갑작스러운 트래픽 급증으로부터 데이터베이스를 보호할 수 있습니다.
진정한 확장성은 단순히 컴퓨팅을 확장하는 것 그 이상을 요구합니다. 탄력적인 데이터 액세스(elastic data access)를 고려하여 설계해야 합니다. 이론적인 최대치를 기준으로 프로비저닝하는 것을 멈추세요. 급증하는 함수와 데이터 사이에 버퍼(buffer)를 구축하기 시작해야 합니다.
Source: https://dev.to/prabashanadev/your-serverless-is-lying-to-you-about-scale-4cga