ec2에서 서버리스로의 교체기

요약

  1. (많은 경우) 람다는 ec2보다 싸다
  2. 람다는 한동안 접속하지 않을 시 콜드스타트가 적용된다. 따라서 느릴 수도 있다

계기

개인 웹서비스를 ec2에서 제공하고 있었다. 월 29,000원 정도 요금이 나오고 있었는데 비용을 더 줄이고 싶었다. 다른 대안을 알아보다가 서버리스의 존재를 알게된다. 솔깃했다. 어떤 개발자가 ec2에서 서버리스로 전환후 비용을 절약할 수 있었다는 말을 듣고 갈아탈 작정을 한다

aws lambda

aws도 람다(lambda)라는 이름으로 서버리스 서비스를 제공하고 있었다. 같은 aws인지 거부감도 없었고 바로 람다로 갈아타려고 했는데 몇가지 걸림돌이 있었다. 중앙 서버가 없으므로 정적파일을 cdn으로 제공하거나 api를 모듈 함수화 해야했는데 대단히 손이 많이가는 작업이었다. 당시 내 서비스는 next.js 기반이었는데 매번 디플로이를 할때마다 수동으로 이런 작업들을 한다는게 엄두가 나지 않았다. 다행이 서버리스(serverless)라는 프레임웍이 있었고 정적파일화 && 단일함수화 작업은 자동으로 수행되었다.
그렇게 써보니 작동은 잘 되었고 요금은 월 2,500원 가량으로 약 2만원 이상 줄어들었다. 이정도면 요금의 관점에서는 바꾼 보람이 있었다. 그런데 없던 문제가 생겼다. db에서 데이터를 가져오는 시간이 너무 길었다

서버리스 === 느린 db요청?

그 서버리스 함수는 DBaaS의 일종인 MongoDB Atlas(이하 아틀라스)에서 데이터를 가져오고 있었다. 그래서 처음에는 이 아틀라스를 의심했지만 문제는 서버리스 함수의 콜드스타트였다. 이용자가 거의 없는 내 서비스는 람다의 입장에서 메모리에 함수를 계속 상주시킬 이유가 없었다. 요청이 뜸한 함수는 메모리에서 해제되는데 이 상황을 게으른 상태(idle state)라고 하는 모양이다. 게으른 상태에서 누군가 함수를 요청하면 해야할 일이 참 많다. 먼저 함수를 메모리에 적재한다. 이후 함수가 실행될 워커 스레드를 생성한다. 생성된 워커 스레드는 db 서버와 연결이 안되어있는 상태이므로 재연결을 요청한다. 재연결이 허가되면 그제서야 데이터를 요청한다. 여기까지 걸리는 시간은 약 4초였다. 1초도 느리다고 취급받는 세상에서 4초는 넌센스였다. 역시 싼건 이유가 있었다.

콜드스타트 제거가 가능한가?

콜드스타트에 한번 걸리면 느려진다는 불만이 나한테만 있었을까. 당연히 aws측도 인지하고 있었던 문제였다. 그래서 그들은 2019년 12월, 함수가 게으른 상태(idle state)로 진입하지 않도록 하는 서비스인 프로비전드 컨커런시(provisioned concurrency)를 공개한다. 결론부터 말하면 본인은 이걸 사용하지 않았다. 프로비전드 컨커런시를 알아보던 도중 렘(realm)이라는 더 좋은 솔루션을 발견했다. 나는 이것에 미혹되었고 결국 서버리스 기반의 db통신은 버렸다. 따라서 내가 써보지 않은 프로비전드 컨커런시에 대한 이야기는 어렵다. 다만 납득할 수 있는 가격대였고 괜찮은 해결책으로 보였다. 만일 내가 렘을 몰랐다면 이것을 사용했을지는 분명하다

서버리스의 또다른문제, db커넥션 제한

여기서부터는 소규모 프로젝트에 대한 이야기는 아니다. 그래도 중요한 토픽이다.
많은 db가 최대연결 설정을 제한한다. 그런 환경에서 서버리스를 사용할 때 기존에 없던 문제가 생긴다. 서버리스 환경의 각 함수는 각각의 db 세션을 가진다. 고전적인 서버 모델과 다른 이러한 특성은 많은 수의 동시 커넥션을 생성한다. 특히 서버리스 함수가 몇분간 호출되지 않아 게으른 상태(idle state)로 진입할 때 db와 커넥션을 종료하지 않는다. 이런 좀비 커넥션은 가용 커넥션의 수를 크게 제한한다. 이런 db커넥션 제한 문제도 콜드스타트 못지않은 서버리스의 문제점이었다. 과거형을 쓰는 이유는 해결책이 나왔기 때문이다. AWS의 RDS Proxy는 db연결 전용 프록시 함수를 생성하여 이 함수를 경유하도록 문제를 해결했다. 이렇게 되면 각각의 함수가 db커넥션 상태일 필요가 없어 총 db커넥션 수가 크게 줄어든다.
db프록시의 장점은 이것만이 아니다. 이미 연결되어 있는 db세션을 재활용하는 것이므로 함수가 콜드스타트 되었을 때 서버에 재연결을 시도하는 시간을 없앨 수 있다. 따라서 서버리스의 약점인 느린 레이턴시를 극복할 수 있다

결론

콜드스타트와 db커넥션 제한은 서버리스의 고질적인 문제였다. 하지만 aws는 이에대한 해결책을 제공했다. 이로서 서버리스를 경유한 db참조 문제는 대부분 해결된 셈이므로 서버리스 이용에 큰 부담을 덜 수 있게 되었다.

홈으로