✍️ 글쓰기/💻 배우고

3-1. AWS Elastic Beanstalk + AWS S3로 웹 어플리케이션 배포하기

ddubimoon 2022. 4. 22. 09:18

 React + Flask + GraphQL 웹 어플리케이션 프로젝트 전체 로드맵

 

React & Flask & GraphQL 웹앱 프로젝트 시작 🏁

이번에 리액트와 플라스크를 활용해 프로젝트를 할 기회가 생겼다. 거기에 GraphQL API에서 필요한 데이터들을 CRUD 해야 했는데, 이런 조합의 프로젝트 예시를 찾아보는 것이 쉽지 않았다 🥺 언젠

joy-able.tistory.com


* 이 글의 전체 프로세스는 이 링크를 토대로 진행되었습니다. 

AWS 계정 셋업

AWS 유저 만들기

1. AWS Management Console 에 로그인

2. IAM 콘솔을 연다

3. Users -> Add users

4. User 이름을 설정하고, 엑세스 방식 설정

- API, AWS CLI 에 대한 엑세스 권한이 필요한 경우, Programmatic access 방식 선택. 엑세스 키는 사용자 추가가 완료 되고 나면 확인 후 다운로드가 가능하다. 하지만 이후 해당 엑세스 키를 잊어버렸을 때는 재발급해야 하니, 확인 후 어딘가에 기록해두는 것을 추천한다.  

- AWS Management Console 에 대한 엑세스 권한이 필요한 경우엔 AWS Management Console access 선택.

5. 권한(Permission) 설정

- 기존 정책에 직접 연결하기 (Attach existing policies directly)

현재 추가하고자 하는 사용자에게 모든 엑세스를 넘겨주어도 괜찮다면 AdministorAccess (관리자) 정책을 연결

6. 필요한 경우 Tag 설정

7. 최종 리뷰 후 Create User

8. 새로운 User가 추가되었다. 여기에 기재된 Access Key ID와 Secret access key 를 다운 받거나 기록해두기.


Frontend 배포하기

AWS S3 버킷 만들기

1. Amazon S3 -> Buckets -> Create bucket

🌟 주의: bucket 만들 때 aws 지역 (e.g. us-west-2) 기억해두기. 이후 다른 단계에서도 지역을 통일해주어야 서로를 검색하고 연결할 수 있음.

2. 우선 Public Access가 가능하도록 Block all public access 체크 해제 후, 맨 아래에 주의 메시지에 체크.

나중에 모든 업로드가 끝난 후 다시 block 할 예정이다.

React Build 후 S3 Bucket에 업로드하기

1. Frontend로 만들어 둔 리액트 앱을 build 하기

아래의 your-web-frontend 대신 위에서 설정한 bucket 이름을 쓴다.

- s3 sync 명령을 실행하면서 public permission을 유지하기 위해 --acl public-read 를 뒤에 붙여준다.

cd frontend
export REACT_APP_API_URL=/api
npm run build
aws s3 sync build/ s3://your-web-frontend --acl public-read

2. S3 Bucket에서 성공적으로 업로드 된 파일과 폴더들을 확인할 수 있다. 이때 다시 전체 선택 후, Actions -> Make public using ACL 을 눌러 파일들이 모두 확실히 public일 수 있도록 설정해준다.


 Backend 배포하기

Docker란?

Docker는 어플리케이션을 신속하게 구축, 테스트 및 배포할 수 있는 소프트웨어 플랫폼이다. Docker는 소프트웨어를 컨테이너라는 표준화된 유닛으로 패키징하며, 이 컨테이너에는 라이브러리, 시스템 도구, 코드, 런타임 등 소프트웨어를 실행하는 데 필요한 모든 것이 포함되어 있다. Docker를 사용하면 환경에 구애받지 않고 어플리케이션을 신속하게 배포 및 확장할 수 있어 코드가 문제 없이 실행될 수 있는지 테스트할 수 있다. 특히 AWS에서 Docker를 이용하면 보다 저렴한 비용으로 어플리케이션을 배포할 수 있다. 

 

Docker를 사용해야 하는 이유

Docker를 사용하면 코드를 더 빨리 전달하고, 어플리케이션 운영을 표준화하고, 코드를 원활하게 이동하고, 리소스 사용률을 높여 배포 비용을 절감할 수 있다. 또한 Docker를 사용하면 어디서나 안정적으로 실행할 수 있는 단일 객체를 확보하게 된다. 만약 어플리케이션 아키텍쳐가 더 복잡해지거나, 좀더 구체화된 환경 설정을 요구한다면 만들어진 Docker 이미지를 원하는 서비스로 유연하게 연동시킬 수 있다. 

 

Docker 이미지 만들어 AWS ECR에 푸시하기

Step 1: Docker file 만들기

1. backend 디렉토리 아래 Dockerfile 을 새로 만든다.

확장자 없이 Dockerfile 이름을 가진 파일을 만들면 된다.

2. Dockerfile 에 아래와 같이 코드 작성

FROM python:3.7
WORKDIR /backend
COPY requirements.txt requirements.txt
RUN pip install -r requirements.txt
EXPOSE 8080
COPY . .
CMD ["gunicorn", "wsgi:app", "-w 2", "-b 0.0.0.0:8080", "-t 30"]

Step 2: AWS ECR 리포지토리 만들고 Docker 이미지 만들어 푸시하기

1. Amazon ECR -> Repositories -> Create repository

🌟 주의: 앞서 만든 S3 bucket과 지역 동일할 수 있도록 확인

2. 방금 만든 리포지토리에 들어가서 View push commands 에서 아래의 command들을 확인할 수 있다.

- 플라스크 웹 어플리케이션을 작업하던 디렉토리에서 위의 command를 입력하면 된다.

차례대로 아래와 같은 단계이다:

(1) 인증 토큰을 받아 Docker 클라이언트를 레지스트리에 로그인

(2) Docker 이미지를 만들기

(3) 이미지에 태그 붙이기

(4) 새로 만든 AWS 리포지토리에 해당 이미지 푸시하기

 

- 만들어진 Docker 컨테이너 실행해보기

실행을 멈추려면 control + C 누르기

docker run -p 8080:8080 <your-backend>

Step 3: AWS Elastic Beanstalk 플랫폼 만들기

 

Step 4: AWS ECR과 EB 연결하기

ECR에서 EB를 읽을 수 있도록 허용해주어야 한다. 그렇지 않으면 error: Instance deployment: The ECR service failed to authenticate your private repository 라는 에러 메시지를 발견하게 될 것.

 

1. 앞서 만들어두었던 유저의 IAM 콘솔로 다시 들어가, aws-elasticbeanstalk-ec2-role을 선택. AmazonEC2ContainerRegistryReadOnly 정책을 첨부해준다. 

Step 5: Dockerrun.aws.json 파일 추가해주기

1. 어플리케이션의 backend 디렉토리에 aws_deploy라는 폴더를 만들고, 거기에 Dockerrun.aws.json 파일을 생성해준다.

.elasticbeanstalk 폴더는 나중에 deploy를 실행하면 생기는 폴더이니, 우선 무시하자.

2. 파일 안에는 아래와 같이 쓴다.

<your-ecr-uri> 라고 쓰인 부분에는 말 그대로 위에서 생성해던 ECR에 들어가 URI 값을 복사해주면 된다.

{
  "AWSEBDockerrunVersion": "1",
  "Image": {
    "Name": "<your-ecr-uri>",
    "Update": "true"
  },
  "Ports": [
    {
      "ContainerPort": 8080,
      "HostPort": 8080
    }
  ]
}

Step 6: 배포 실행

# aws eb cli 설치. 실행 시 최초에 한 번 설치해주면 된다.
pip install awsebcli

# backend 폴더의 aws_deploy 폴더로 이동
cd backend/aws_deploy 

eb init
eb deploy

제대로 배포가 되었다면 아래와 같이 Health 부분에 초록색으로 OK 사인을 확인할 수 있다.

문제가 생겼다면 Elastic Beanstalk -> Yourwebapp-env -> Logs 에 들어가 로그 데이터를 다운 받아 어디에서 에러가 생겼는지 확인할 수 있다. 


S3에 배포된 frontend를 더욱 효율적으로 활용할 수 있게 Cloudfront를 사용하는 방법과, 백엔드를 불러오는 방법은 다음 글에서 다룰 예정이다. 

이 글의 가장 처음에 올려둔 웹 어플리케이션의 전체 로드맵을 참고!

References

Docker란 무엇입니까?

How to deploy a website on AWS with Docker, Flask, & React from scratch

How to deploy a Docker container to AWS Elastic Beanstalk using AWS CLI

AWS 사용자 추가