[FastAPI] 16. Pulumi๋ฅผ ์ด์ฉํด FastAPI Serverless ํ๊ฒฝ ๊ตฌ์ถํด๋ณด๊ธฐ
์ฐ๋ฆฌ๋ ์ง๋ ๊ธ์์ FastAPI, Magnum, AWS Serverless Stack(Lambda, API Gateway)์ ์ด์ฉํ์ฌ FastAPI ์๋ฒ๋ฆฌ์ค ํ๊ฒฝ์ ๊ตฌ์ถํ์ต๋๋ค.
ํ์ง๋ง AWS Lambda์ API Gateway๋ฅผ ํตํด ์๋ฒ๋ฆฌ์ค ํ๊ฒฝ์ ์ผ์ผ์ด ๊ตฌ์ถํ๋ ๊ฒ์ ์ฐ๋ฆฌ๊ฐ AWS GUI Console์ ์ตํ๊ณ , ์ ์ํ๋๋ฐ ๋ง์ ๋ฌ๋ ์ปค๋ธ ์์๋ฅผ ํ์๋ก ํ๊ณ , ์ค๋ น ๊ทธ๋ฐ ๊ฒ ์ด๋ฏธ ์๋ฌ๋ ์ํ์๋ค. ํ๋๋ผ๋ ์์ด ๋ง์ด ๊ฐ๋ ์์ (์์ฃผ ์ค๊ณ ๊ฐ๋ ์ฝ์ ๋ฉ๋ด)๋ค ๋๋ฌธ์ ์คํ๋ ค ๋นํจ์จ์ ์ธ ๊ตฌ์ถ ๋ฐฐ๊ฒฝ์ด๋ผ๊ณ ์๊ฐํ์ จ๋ ๋ถ๋ค๋ ๊ณ์ จ์ ๊ฒ์ ๋๋ค.
Automation
๊ทธ๋ฌ๋ ๊ตณ์ด ๋ง์ฐ์ค๋ฅผ ํด๋ฆญํ์ง ์๊ณ ๋ YAML ์ฝ๋๋ ํ๋ก๊ทธ๋๋ฐ ์ธ์ด์ ์ฝ๋๋ฅผ ์ฌ์ฉํด์ ๊ตฌ์ถํ ์ ์๋ ๋ฐฉ๋ฒ๋ค์ด ์์ต๋๋ค.
- AWS SAM CLI
- Terraform (ํ ๋ผํผ)
- Pulumi (ํ๋ฃจ๋ฏธ)
AWS SAM์ Serverless Application Model์ ์ฝ์๋ก AWS์ ์๋ฒ๋ฆฌ์ค ํ๋ซํผ์ ๋ช ๋ น์ด๋ก ๊ตฌ์ถํ๋ ํ๋ ์์ํฌ์ ๋๋ค.
Terraform์ ์๋ฒ๋ฆฌ์ค ์ธ์ AWS, GCP, Azure ๋ฑ์ ํด๋ผ์ฐ๋ ๋ฆฌ์์ค๋ฅผ HCL ์ธ์ด๋ก ์์ฑํด ๋ฐฐํฌํ๋ ๋๊ตฌ์ ๋๋ค.
Pulumi๋ Terraform์ ๊ทธ ๊ธฐ๋ฅ์ด ์ ์ฌํ์ง๋ง HCL์ด ํ๋ก๊ทธ๋๋ฐ ์ธ์ด(Go, Python ๋ฑ)๋ก ์์ฑํด ๋ฐฐํฌํ๋ ๋๊ตฌ์ ๋๋ค.
์ฐ๋ฆฌ๋ ์ฌ๊ธฐ์ Pulumi๋ฅผ ์ด์ฉํด Python ์ธ์ด๋ฅผ ์ด์ฉํ์ฌ AWS ์๋ฒ๋ฆฌ์ค ํ๊ฒฝ์ ๊ตฌ์ถํด๋ณด๋๋ก ํ๊ฒ ์ต๋๋ค.
AWS IAM
๋จผ์ ๋ฐฐํฌ ๋๊ตฌ(Pulumi)๊ฐ AWS ๋ฆฌ์์ค๋ฅผ ์ด์ฉํด ์๋ฒ๋ฆฌ์ค ํ๊ฒฝ์ ๋ง๋ค์ด์ค ์ ์๋ ๊ถํ์ด ํ์ํฉ๋๋ค. AWS ์ฝ์์ ๋ก๊ทธ์ธ ํ ํ IAM์ ์ ์ํฉ๋๋ค.
Pulumi๊ฐ ๋ด AWS ๋ฆฌ์์ค์ ์ ๊ทผํ ์ ์๋๋ก ์๋ก์ด ์ ์ ๋ฅผ ์ถ๊ฐํ ๊ฒ์ ๋๋ค. Add users๋ฅผ ํด๋ฆญํฉ๋๋ค.
์ ์ ์ด๋ฆ์ ์ ๋ ฅํ๊ณ access type์ Access Key๋ก ์ง์ ํฉ๋๋ค.
๋ค์์ผ๋ก ๋์ด๊ฐ๋ฉด User Group์ ์ง์ ํด์ผ ํฉ๋๋ค. ์ฐ๋ฆฌ๋ ๋ง๋ค์ด๋ User Group์ด ์์ผ๋ฏ๋ก Create group์ ํตํด ์๋ก์ด ์ฌ์ฉ์ ๊ทธ๋ฃน์ ๋ง๋ค์ด์ค๋๋ค.
์ฌ์ฉ์ ๊ทธ๋ฃน์๋ ํด๋น ๊ทธ๋ฃน์ด ๊ฐ์ง ๊ถํ์ ์ง์ ํ๊ณ , ๊ทธ ๊ถํ์ ์์๋ ์ฌ์ฉ์๊ฐ ์์ ๋ฐ๋ ๊ตฌ์กฐ์ ๋๋ค.
์๋ฒ๋ฆฌ์ค ๊ตฌ์ถ์๋ ์๋์ 3๊ฐ์ง ๊ถํ ์ ์ฑ ์ด ํ์ํฉ๋๋ค.
- IAMFullAccess
- AmazonAPIGatewayAdministrator
- AWSLambdaFullAccess
์์ ์ ์ฑ ์ด ํ์ํ ์ด์ ๋ฅผ ๊ฐ๋ตํ ์ค๋ช ํ์๋ฉด ์ง๋ ๊ธ์์ ์ฐ๋ฆฌ๋ Lambda๋ฅผ ํตํด ์ ํ๋ฆฌ์ผ์ด์ ์ฝ๋๋ฅผ ๋ฐฐํฌํ์๊ณ , API Gateway๋ฅผ ์ฌ์ฉํด Lambda์ Proxy๋ก ์ฐ๊ฒฐํ์์ต๋๋ค. ๊ทธ๋ค์ ์ฐ๊ฒฐํ๋๋ฐ, API Gateway๊ฐ Lambda์ ๋ฆฌ์์ค๋ฅผ ์ฌ์ฉํ ์ ์๋๋ก ๊ถํ์ ๋ถ์ฌํ์์ฃ . ๋ฐ๋ผ์ IAMFullAccess ์ ์ฑ ๊น์ง ํ์๋ก ํฉ๋๋ค.
๊ทธ๋ ๊ฒ 3๊ฐ์ง ์ ์ฑ ์ ์ฃผ๊ณ ์ฌ์ฉ์ ๊ทธ๋ฃน์ ๋ง๋ค๋ฉด ์์ ๊ฐ์ด ์์ฑ๋ ์ฌ์ฉ์ ๊ทธ๋ฃน์ด ๋์ฌ ๊ฒ์ ๋๋ค. ํด๋น ๊ทธ๋ฃน์ ์ฒดํฌ ๋ฐ์ค๋ฅผ ํด๋ฆญํ ํ ๋ค์ ๊ณผ์ ์ผ๋ก ๋์ด๊ฐ๋๋ค.
3๋จ๊ณ ๊ณผ์ ์ ์ ํ ์ฌํญ์ด๋ฏ๋ก ์๋ตํ๊ณ 4๋จ๊ณ๋ก ๋์ด๊ฐ๋๋ค. access type์ด access key์ด๊ณ , User Group์ด ์ ์ค์ ๋์ด ์๋์ง ํ์ธํ ํ ์ฌ์ฉ์ ์์ฑ์ ์งํํฉ๋๋ค.
์ ์ ์์ฑ์ด ์๋ฃ๋๋ฉด Access Key ID์ Secret Access Key๊ฐ ๋ถ์ฌ๋ฉ๋๋ค. ํ ๋ฒ ์์ฑ๋ Secret access key๋ ์ฝ์์์ ๋ ๋ฒ ๋ค์ ๋ณผ ์ ์์ผ๋ฏ๋ก .csv ํ์ผ์ ๋ค์ด๋ก๋ ๋ฐ์ ๋ณ๋๋ก ์ ์ฅํด๋์ผ์๋ ๊ฑธ ์ถ์ฒํฉ๋๋ค.
Set environment Access Key
Pulumi์์ ๋ฐฉ๊ธ ๋ถ์ฌํ AWS ๊ณ์ ์ ์ฌ์ฉํ ์ ์๋๋ก ํ๊ฒฝ ๋ณ์์ Access Key์ Secret Access Key ๊ฐ์ ์ถ๊ฐํด์ผ ํฉ๋๋ค.
$ export AWS_ACCESS_KEY_ID=${ACCESS_KEY_ID}โ
$ export AWS_SECRET_ACCESS_KEY=${SECRET_ACCESS_KEY}
OS X, Linux์์ ํฐ๋ฏธ๋์ ์ด๊ณ export ๋ช ๋ น์ด๋ฅผ ํตํด ํ๊ฒฝ ๋ณ์๋ฅผ ์ถ๊ฐํ ์ ์์ต๋๋ค.
> $Env:AWS_ACCESS_KEY_ID = ${ACCESS_KEY_ID}
> $Env:AWS_SECRET_ACCESS_KEY = ${SECRET_ACCESS_KEY}
Windows์์๋ PowerShell ํน์ Windows Terminal์ ์ด๊ณ $Env ์คํฌ๋ฆฝํธ๋ฅผ ์ด์ฉํด ํ๊ฒฝ ๋ณ์๋ฅผ ์ถ๊ฐํ ์ ์์ต๋๋ค.
Install Pulumi
์ด์ AWS์ ๋ํ ์ ํ ์ ๋ชจ๋ ๋๋ฌ์ต๋๋ค. ์์ ์ ์ปดํจํฐ์ pulumi CLI๋ฅผ ์ค์นํ๊ณ , ์๋ก์ด Pulumi ํ๋ก์ ํธ๋ฅผ ๋ง๋ค๋ฉด ๋ฉ๋๋ค.
https://www.pulumi.com/docs/get-started/install/
$ curl -sSL https://get.pulumi.com | sh
Linux์์๋ curl์ ํตํด ์ต์ ๋ฒ์ ์ pulumi๋ฅผ ์ค์นํ ์ ์์ต๋๋ค.
$ brew install pulumi/tap/pulumi
OS X์์๋ Homebrew๋ฅผ ์ด์ฉํ์ฌ pulumi๋ฅผ ์ค์นํฉ๋๋ค.
> choco install pulumi
Windows์์๋ Chocolatey ํน์ WinGet ํจํค์ง ๊ด๋ฆฌ์์์ pulumi๋ฅผ ์ ๊ณตํฉ๋๋ค.
Create Project
Pulumi๋ ํ๋ก์ ํธ ๋จ์๋ก ํด๋ผ์ฐ๋ ๋ฆฌ์์ค๋ฅผ ๊ด๋ฆฌํ ์ ์์ต๋๋ค. ์ด์ ๊ธ์์ ์ฐ๋ฆฌ๋ FastAPI ํ๋ก์ ํธ๋ฅผ ์์ฑํ๊ณ , ํด๋น ํ๋ก์ ํธ ์์ ๋๋ ํฐ๋ฆฌ์ infra ๋๋ ํฐ๋ฆฌ์ pulumi ํ๋ก์ ํธ๋ฅผ ๋ง๋ค์ด๋ณด๋๋ก ํ๊ฒ ์ต๋๋ค.
api ๋ฐ์ผ๋ก infra ๋๋ ํฐ๋ฆฌ๋ฅผ ๋ง๋ญ๋๋ค. ์ฐ๋ฆฌ๋ ์ฌ๊ธฐ์ AWS๋ฅผ ์ฌ์ฉํ ๊ฒ์ด๋ฏ๋ก AWS ํด๋๋ฅผ ํ ๊ฐ ๋ ์ถ๊ฐํฉ๋๋ค. ๊ทธ๋ฆฌ๊ณ ์ด์ ๊ธ์์ ๋ง๋ค์ด๋์๋ ํ๋ก์ ํธ ๋ชจ๋ ์์ถ ํ์ผ์ fastapi-serverless-layer.zip ์ด๋ฆ์ผ๋ก ์์ ํ ํ ์ต์์ ๋๋ ํฐ๋ฆฌ์ ์ด๋์ํต๋๋ค.
$ pulumi new aws-python
infra/aws ๋๋ ํฐ๋ฆฌ ๊ฒฝ๋ก์์ ์ ๋ช ๋ น์ด๋ฅผ ์ ๋ ฅํ๋ฉด ์๋ก์ด Pulumi ํ๋ก์ ํธ๋ฅผ ์์ฑํฉ๋๋ค.
๊ทธ๋ฌ๋ฉด __main__.py, Pulumi.yaml, Pulumi.${stack}.yaml ์ด๋ ๊ฒ 3๊ฐ๊ฐ ์์ฑ๋ฉ๋๋ค. ๋ฌผ๋ก venv ํด๋ ๋ฑ๋ ์์ฑ๋๊ฒ ์ง๋ง ์ฐ๋ฆฌ๊ฐ ์ดํด๋ณผ ๊ฒ์ ์ด 3๊ฐ์ง ํ์ผ์ ๋๋ค.
Pulumi stack ํ์ผ์์๋ ํด๋น ์คํ์ ๋ํ ํด๋ผ์ฐ๋ ํ๊ฒฝ์ ์ค์ ํฉ๋๋ค. ์ฐ๋ฆฌ๋ AWS๋ฅผ ์ฌ์ฉํ ๊ฒ์ด๊ณ ์์ธ ๋ฆฌ์ (ap-northeast-2)์ ํ๊ฒฝ์ ๊ตฌ์ถํฉ๋๋ค.
์ฝ๋ ์์ฑ
aws ์๋ฒ๋ฆฌ์ค ํ๊ฒฝ์ ๋ง๋๋ ์ฝ๋๋ฅผ ์์ฑํ๊ธฐ ์ ์, ์ฐ๋ฆฌ๊ฐ ์ด๋ค ๊ฒ์ ์ด๋ค ๋ฐฉ๋ฒ์ผ๋ก ์๋ฒ๋ฆฌ์ค ํ๊ฒฝ์ ๊ตฌ์ถํ๋์ง ์ดํดํด์ผ ํฉ๋๋ค. ๋จผ์ Lambda ํ๋ก์ ํธ๋ AWS์ Cloudwatch๋ก ์ด๋ฒคํธ ๋ก๊ทธ๋ฅผ ๋ง๋ค๊ณ ๊ด๋ฆฌํ๊ธฐ ๋๋ฌธ์ ์ด์ ๋ํ ๊ถํ์ ๋ถ์ฌํด์ค์ผ ํฉ๋๋ค.
aws ๋๋ ํฐ๋ฆฌ์ iam.py ํ์ผ์ ๋ง๋ค๊ณ ์์ฒ๋ผ LambdaRole๊ณผ Role ์ ์ฑ ์ Cloudwatch๋ก ๋ก๊ทธ ๊ทธ๋ฃน์ ๋ง๋ค๊ณ ์ด๋ฒคํธ๋ฅผ ๊ธฐ๋กํ๋ ๊ถํ์ ์ฃผ๋๋ก ํฉ๋๋ค.
์์์ ๋ง๋ค์ด๋๋ iam.py๋ฅผ importํ์ฌ Lambda_ ์ธ์คํด์ค์ ์ฃผ์ ํฉ๋๋ค. ๊ทธ๋์ผ๋ง Pulumi์์ ํด๋น ๊ถํ์ ์์๋ฐ๊ณ Lambda ํจ์๋ฅผ ๋ง๋ค ๋ Cloudwatch์ ํด๋น ํจ์์ ๋ํ ๋ก๊ทธ ๊ทธ๋ฃน์ ๋ง๋ค ์ ์์ต๋๋ค.
Deploy
์ด์ ๋ง์ง๋ง์ผ๋ก ์์์ ์์ฑํ ์ฝ๋๋ฅผ AWS์ ๋ฐฐํฌ๋ง ํ๋ฉด ๋ฉ๋๋ค.
$ pulumi preview
Pulumi๋ ๋ฐฐํฌํ๊ธฐ ์ ๋ด๊ฐ ์์ฑํ ์ฝ๋์ ๋ฌธ์ ๊ฐ ์๋์ง๋ฅผ ๊ฒ์ฌํด์ฃผ๋ ์ ํจ์ฑ ์ฒดํฌ ๊ธฐ๋ฅ์ด ์์ต๋๋ค. preview ๋ช ๋ น์ ํตํด ์ฐ๋ฆฌ๊ฐ ์์ฑํ ์ฝ๋๊ฐ ์ด๋ค ์ด๋ฒคํธ๊ฐ ๋ฐ์ํ๋์ง ์ฝ๋์ ๋ฌธ์ ๊ฐ ์๋์ง๋ฅผ ์ดํด๋ด ๋๋ค.
PASSPHRASE๋ ์ฒ์ Pulumi ํ๋ก์ ํธ๋ฅผ ์์ฑํ์ ๋ ์ค์ ํ PASSPHRASE ๊ฐ์ ๋ฃ์ด์ฃผ๋ฉด ๋ฉ๋๋ค.
์์ ๊ฐ์ด lambda Role๋ก ์์ํ์ฌ Lambda Layer๋ฅผ ์์ฑํ๊ณ , ํจ์๋ฅผ ๋ฃ๊ณ , API Gateway๋ฅผ ๋ง๋๋ ์์๋๋ก ์งํํ๋ฉด ์ ๋ ๊ฒ์ ๋๋ค.
$ pulumi up
๋ชจ๋ ๊ฒ์ฆ์ด ๋๋ฌ์ผ๋ฉด up ๋ช ๋ น์ด๋ฅผ ํตํด ์์ ์ AWS์ ๋ฐฐํฌํ๋๋ก ํฉ๋๋ค.
์ด ๋, ์ ๊ณผ์ ์ด ๋ง๋์ง๋ฅผ ๋ค์ ๋ฌผ์ด๋ด ๋๋ค. ๋ง์ผ๋ฉด yes ์๋ชป๋ ๊ฒ์ด ์๋ค๋ฉด no๋ฅผ ํ์๋ฉด ๋ฉ๋๋ค.
์์ ๊ฐ์ด API Gateway ์๋ํฌ์ธํธ ์ฃผ์๊ฐ ์์ฑ์ด ๋์์ผ๋ฉด ์ ์์ ์ผ๋ก ์๋ฒ๋ฆฌ์ค ์คํ์ด ์์ฑ๋ ๊ฒ์ ๋๋ค.
API๊ฐ ์ ํธ์ถ๋ ๋ชจ์ต์ ๋๋ค.
๋ง์น๋ฉฐ...
์ฌ๊ธฐ๊น์ง Pulumi๋ฅผ ์ฌ์ฉํด์ AWS ํ๊ฒฝ์ ์ฝ๋๋ก ์์ฑํ๋ ๊ฒ๊น์ง ์งํํด๋ดค์ต๋๋ค.
๊ฐ์ธ์ ์ผ๋ก FastAPI๋ฅผ Serverless๋ก ๊ตฌ์ถํ๋ ๊ฒ์ ๋ํด์๋ ๊ธฐ์กด์ FaaS ํ๊ฒฝ์ ์ ์ง๋ณด์์ ๋ํ ๋ถํธํจ์ ๋ง์ด ๋์ด์คฌ๋ค๊ณ ์๊ฐํฉ๋๋ค.
์ด์ ์ FaaS๋ ํจ์๋ณ๋ก API๋ฅผ ๋ง๋ค๊ณ ์ด๋ฅผ API Gateway EndPoint์ ์ผ์ผ์ด ๋์ ํ๋ ํํ์๋ค๋ฉด ์ง๊ธ์ API Gateway์์ Lambda ์ฝ๋ ํ๋๋ฅผ Proxy๋ก ๊ฑธ์ด๋๊ณ , ์๋ํฌ์ธํธ๋ฅผ ํด๋น ์ฝ๋์๊ฒ ๋งก๊ธฐ๊ฒ ๋ค๋ ๊ฒ์ด ๋ฉ๋๋ค.
์ด๋ ๊ฒ ํจ์ผ๋ก์จ ์ถ๊ฐ API๋ฅผ ๋ง๋ค ๋๋ง๋ค Lambda ํจ์๋ฅผ ๋ณ๋๋ก ๋ง๋๋ ๊ฒ์ ํ์ง ์์๋ ํ๋์ Lambda ํ๋ก์ ํธ์์ ์งํํ ์ ์๊ณ , ๋ ๋์๊ฐ์๋ CI/CD์ ์ ์ฉํ ๋ Lambda ์ฝ๋ ํ์ผ์ ์ฌ๋ฐฐํฌํ๋ ํํ๋ก๋ง ๊ตฌํํ๋ฉด ๋๊ธฐ ๋๋ฌธ์ ๊ณผ์ ์์ฒด๊ฐ ๊ฐ์ํ ๋ ์ ์์ต๋๋ค.
์ถ๊ฐ๋ก ํ์ฌ Lambda๋ ์ฝ๋๋ฅผ ์ง์ ํ์ผ๋ก ์ฌ๋ฆฌ๋ ๊ฒ ๋ฟ ์๋๋ผ Docker Image๋ก๋ ์์ฑํ ์ ์๋ ๋ฐฉ๋ฒ์ด ์์ต๋๋ค. ์ฌ์ค ๊ตณ์ด Docker Image๊น์ง ์จ์ผ ํ๋๋ผ๋ ์ ์ฅ์ด์ง๋ง ํ์ผ ์ ๋ก๋๊ฐ ์์ง ์ด์ํ๋ค๋ฉด Docker Image๋ฅผ ์ฌ์ฉํ๋ ๊ฒ๋ ๋์์ง ์๋ค๊ณ ์๊ฐํฉ๋๋ค.