AWS Lambda/CDK - Docker - Fastapi를 통해 서버리스 백앤드 배포하기(1)

Joey Kim·2023년 5월 25일
1
post-thumbnail

Serverless

우리는 API 앱 하나를 배포하기 위해 서버 구축, 네트워크 환경 구축, 보안 환경 구축 등 수동으로 진행합니다. 하지만 Serverless는 이러한 구축 리소스 없이 API를 구현하는 코드만 있다면 누구나 배포할 수 있습니다.
많은 서버리스 서비스들이 있지만 우리는 그 중 AWS Lambda 서비스와 도커를 통해 API를 배포하는 간단한 방법을 소개하고자 합니다.
전체 코드는 아래 깃허브에서 확인하실 수 있습니다.
Github: https://github.com/hyoj0942/lambda-docker-fastapi


사용 Skills

1. AWS Lambda

  • 서버를 프로비저닝하거나 관리하지 않고도 코드를 실행할 수 있게 해주는 컴퓨팅 서비스

2. AWS API Gateway

  • API 게이트웨이는 실제 백엔드 서비스 또는 데이터와 접속하고 API 호출에 대한 정책, 인증 및 일반 액세스 제어를 적용하여 중요한 데이터를 보호하는 트래픽 관리자

3. AWS CDK(Cloud Development Kit)

  • 프로그래밍 언어를 사용하여 클라우드 애플리케이션 리소스를 모델링 및 프로비저닝 해주는 도구.
    즉 터미널 코드 몇 줄로 Lambda에 배포하고 관리하는 툴

4. Docker

  • Lambda와 CDK만 사용해도 CICD하는데에는 큰 문제가 없으나, 치명적인 단점으로 함수 하나당 250MB라는 용량 제한이 있습니다. 이 용량에는 모듈 용량도 포함되어 있으며, Docker 이미지 배포는 10GB의 용량을 제공합니다. 뒤에 언급하겠지만 우리는 Fastapi, Mangum 라이브러리를 통해 여러 개의 API를 하나의 함수로 배포할 것이기 때문에 넉넉한 공간이 필요합니다.

5. Fastapi

  • 파이썬 백앤드 프레임워크 삼대장(django, flask, fastapi)중 하나입니다. 어떤 프레임워크를 사용하셔도 따라 하는데 무방합니다.

로컬 pc에 세팅되어야 하는 것

먼저 필자는 MacOS M1칩을 사용합니다. 어느 OS에서 해도 무방합니다. (Linux에서는 안 해봤는데 될 겁니다)

1. AWS-cli

2. docker

  • https://hub.docker.com/
    도커 데스크탑 설치해 줍니다. 터미널에서 docker --version 명령어가 정상적으로 작동하면 잘 된 겁니다.

3. npm

4. python3

  • 필자는 3.9 버전을 사용합니다.
  • 핵심 modules: poetry, mangum, FastAPI, uvicorn

5. poetry


프로젝트 생성

먼저 프로젝트의 디렉터리를 생성합니다.

mkdir lambda-docker-fastapi
cd lambda-docker-fastapi

두 개의 디렉토리를 생성합니다. 하나는 CDK 코드용이고 다른 하나는 Python 코드용입니다.

mkdir cdk python

Part 1: Python

먼저 Lambda 함수에 대한 Python 코드를 생성합니다(python 3.9). 위에서 언급했듯이 종속성을 관리하기 위해 Poetry를 사용합니다.

Poetry로 Python 환경을 시작하려면 다음을 실행합니다.

cd python
poetry init

필요한 종속성 라이브러리들을 설치합니다.

poetry add uvicorn
poetry add fastapi
poetry add mangum

가상 환경을 설치합니다.

poetry install

로컬에서 사용하는 종속성이 나중에 Dockerfile에서도 사용되는 파일이 되도록 파일이 생성됩니다. 이제 Python 함수를 작성하고 Dockerfile을 만들어야 합니다.
첫 번째 단계부터 시작하겠습니다.
다음과 같이 폴더 구조를 만듭니다.

└── cdk
└── python
    ├── poetry.lock
    ├── pyproject.toml
    └── app
        ├── __init__.py
        ├── main.py
        └── api
            ├── __init__.py
            └── order.py

기본적인 CRUD API들을 작성합니다. 따로 API에 대한 설명은 생략하겠습니다.

# python/app/api/order.py
from fastapi import APIRouter, Path

router = APIRouter(prefix="/orders", tags=["Orders"])
metadata_order = {"name": "Order API Version 1", "description": "Version 1 ORDER API"}


@router.get(path="", summary="GET Orders")
async def get_orders():
    return {"message": "Get Orders"}


@router.post(path="", summary="POST Orders")
async def register_order():
    return {"message": "Register Order"}


@router.patch(path="/{order_id}", summary="PATCH Orders")
async def update_order(order_id: int = Path(..., title="Order Number")):
    return {"message": f"Update Order by {order_id}"}


@router.delete(path="/{order_id}", summary="DELETE Orders")
async def delete_order(order_id: int = Path(..., title="Order Number")):
    return {"message": f"Delete Order by {order_id}"}
# python/app/main.py
from fastapi import FastAPI, APIRouter
from mangum import Mangum
from api.order import router as order_router

app = FastAPI(
    title="FastAPI Serverless",
    description="FastAPI를 활용한 서버리스",
    version="0.1.0",
    root_path="/v1",
)

api_router = APIRouter(prefix="/api")


@app.get("/test")
async def health_check():
    return {"code": 200, "message": "success", "data": None}


api_router.include_router(order_router)
app.include_router(api_router)

handler = Mangum(app)

이번 포스트에서는 로컬 환경을 세팅하고, python 예시 API를 작성하는 것까지 했습니다.

다음 포스트에서는 Dockerfile을 통해 도커를 빌드하고, CDK를 통해 코드로 람다를 배포하는 것까지 진행 해 보겠습니다.


📚 참고문헌

profile
Software Engineer

0개의 댓글