본문 바로가기
Project 2

Devops Day 39 (4.28) Project 2 AWS 배포 자동화_Day2

by Jackykim 2023. 5. 3.

마일스톤4 : 이미지 ECS 배포
Goal

- ECS의 클러스터, 태스크 정의, 태스크, 서비스에 대한 개념을 이해합니다.

- ECR에 저장된 웹 서버 이미지를 ECS로 배포해 봅니다.

- ECS 태스크의 로그를 읽어봅니다.

- 로드 밸런서와 ECS 서비스를 연결해 봅니다.


1. AWS ECS
콘솔에 접속하여 태스크 정의에 들어가 새 태스크 정의 생성으로 들어갑니다.

- 필수 내용 기입

2. AWS ECS 콘솔에 클러스터 -> 클러스터 생성에 들어갑니다.

- 필수 값, 페이지 설정 등 기입 합니다.

- 클러스터 생성이 완료 됐으면 들어가 서비스 생성 선택합니다.
- 기본 유형으로 진행하고 그전에 생성한 패밀리 선택하여 진행합니다.

- 로드 밸런서 이름 지정하고 포트도 확인합니다.

단 진행 하다가 "Error occurred during operation 'ECS Deployment Circuit Breaker was triggered'."

이 error 는 마일스톤1~2 에 진행한 ECR 이미지 문제로 발생했습니다. ECR 이미지에 mongodb 이미지가 포함되면 error가 생겨 v.1.0 이미지로 연결 해야합니다.
이미지가 없거나 잘 못 삭제하였으면 Docker desktop에서 원하는 이미지를 ECR로 push가 가능합니다.

- docker tag <image-name>:<tag> <your-aws-account-id>.dkr.ecr.<your-region>.amazonaws.com/<ecr-repo-name>:<tag> 으로 원하는 이미지 선택
<image-name>, <tag>, <your-aws-account-id>, <your-region>, <ecr-repo-name> 변수는 수정
- docker push <your-aws-account-id>.dkr.ecr.<your-region>.amazonaws.com/<ecr-repo-name>:<tag> 으로 ECR에 push 하면 ECR에 생깁니다.

- 이미지 변경 및 수정 해도 동일한 error가 생겨 mongo 유 서비스 먼저 생산하는 방향 선택

 

Mongo DB 서비스 생성 방법

1. Mongo DB 위한 새로운 태스크 생성 후 필수 내용 기입

- URI 이미지는 자동으로 업로드 되어 Latest으로 설정하면 됩니다.

 

- 포트는 mongoDB에서 사용하는 27017 포트로 설정
- 개별적으로 추가에 MongoDB USER / PASSWORD 키 값 기입

 

2. EC2 에서 Mongo 위한 Target Group 생성합니다.

- Ip address으로 선택 후 포트는 27017로 지정합니다.

 

3. EC2 보안 그룹에 들어가 가장 많이 사용하는 보안 그룹 선택 후에 포트 설정합니다.

- 포트 3000 + 27017 인바운드 규칙 추가 해줍니다.

 

4. EC2 로드 벨런서에 들어가 mongo 위한 로드 벨런서 생성합니다.

- VPC mapping 모두 선택
- 포트 27017로 설정하고 Target Group 앞서 생성한 mongo-tg 선택하고 생성

 

5. 다시 helloworld-was-cluster 에 들어 새로운 서비스를 생성합니다.

- 시작 우형으로 선택하고 패밀리 선택

- 네트워크에서 업데이트한 보안 그룹 (wizard-3) 선택 후 로드 벨런서 (NLB) 선택 후 생성

6. 서비스 이상없이 생성하면 하단 이미지처럼 나와합니다.

7. MongoDB Compass 하고 연결 확인하기 위해 하단 프로세스 진행합니다

- ECS 생성한 서비스에 들어가 “구성 밑 태스트”에 들어가 태스크 선택 후 에 퍼블릭 IP 주소 복사합니다.
- MongoDB Compass 프로그램 에서 URI에 “mongodb://<퍼블릭 IP 주소>:27017
- Username + Password 기입하고 연결되면 MongoDB compass 하고 ECS 하고 연결이 정상적으로 작동하고 있습니다.

 

 

마일스톤5 : 서버 이미지 ECS 배포 자동화

연습과제 : WAS애서 mongodb 로의 접속

 

1. docker build -t project2_helloworld . 으로 이미지 다시 생성한후 docker compose up 했을때 하단 error 메시지가 나왔습니다.

- 로컬에서 dirname 관련 자료를 찾을 수 없어 이런 문제들이 생겼습니다.
- node -v 확인한 결과 node가 V14.21.3 구 버전을 사용하고 있어 dirname을 확인 못 하였습니다. 그래서 문제 해결하기 위해 sudo npm install -g n 한후 nvm install 18로 node ㅍ18.16.0으로 업데이트 했습니다.
- 다시 docker build + compose up 했지만 동일한 error 메시지가 떠서, 코드에 문제가 있는지 확인했습니다.

 

2. 그전에 작성한 코드 하나하나 보면서 수정하였습니다.
- 처음에는 app.js에도 문제가 있어 초기화 하였습니다.

- Docker-Compose,yml 파일 수정

- 그전에 services 밑에 project2라고 설정 하여지만 여기에서는 폴더명 “helloworld-was”으로 수정했습니다.
- Restart : ‘always; -> 다운 표 없는 always으로 수정했습니다.
- 그전에 env file에 “-.env”로 설정 되어서 -> “- .env” 로 변경했습니다.
- Mongo Environment에 HOSTNAME 추가 하였고 그전에 값을 기입하였지만 MONGO_INITDB_ROOT_@@ 값으로 모두 수정했습니다.

- .env 파일 업데이트

- Docker-compose.yml 파일 업데이트 하여 .env 파일도 같이 업데이트 하였습니다.
- HOSTNAME을 Mongo / Localhost가 아닌 IP 주소로 설정해야 하단 error 메시지를 극복 할 수 있습니다. (npm run start 했을 경우)

마막으로 plugin js 파일 수정하였습니다.

- require( ‘dotenv’ ).config() 추가 했습니다. 이 코드는 .env 환경 및 값을 가지고 오게 합니다. 

 

3. 모두 수정했으면 NPM run start 해야합니다.
- npm run start 할 경우 Plugin error가 계속 생겼습니다
.

- 이문제는 이미지 / 코드에 mongo 관련 내용 (backend / database) 가 없어 error가 뜨고 있어 mongo 설정 하여 docker container를 실행합니다.
- docker run --name some-mongo --env MONGO_INITDB_ROOT_USERNAME=<user> --env MONGO_INITDB_ROOT_PASSWORD=<password> -p 27017:27017 -d mongo:latest 으로 설정 완료 하고 npm run start 하면 문제 없이 진행됩니다.


연습과제 : ECS에서 민감 정보 다루기
Goal : 데이터베이스 연결 등에 필요한 민감정보를 어떻게 컨테이너에 주입시키는지 알아봅니다.


1. Fastify로 작성된 WAS의 routes/root.js 파일을 다음과 같이 수정합니다.

2. 민감 정보 입력 하기 위해 콘솔에서 AWS secrets manager로 이동한 후, 새로운 보안 암호를 만듭니다.
- 보안 암호 유형: 다른 유형의 보안 암호 선택

- 키/값 페어: 다음의 키/값들을 입력합니다.

- MONGO_HOSTNAME: mongodb의 엔드포인트

- MONGO_USERNAME: mongodb의 사용자 이름

- MONGO_PASSWORD: mongodb의 비밀번호

- 보안 암호 이름: 잘 알아볼 수 있게 짓도록 합시다.

- 자동 교체는 적용하지 않습니다.

3. 작업 정의 생성

1. 앞서 WAS의 소스 코드를 수정했으므로, 만일 빌드 및 push 자동화가 잘 되었다면, 새로운 태그를 가진 이미지가 ECR에 준비되어 있을 것입니다.

2. 새로운 작업 정의의 개정을 만듭니다. (최신 push된 이미지로 태그를 바꾸어야 합니다)

3. 환경 변수를 설정합니다.

4. 새로운 개정을 만듭니다.

 

3-1. AWS ECS 태스크 정의에 들어가 ECR에 새로 생성된 이미지에 태스크 / 변경된 환경 적용합니다. 컨테이너명, 이미지 URL, 컨테이너 포트, 환경 변수 기입합니다.

- 환경 변수 키 값 기입할 때 보안 암호 ARN 끝에 :키:값을 추가 해야 합니다.

4. 작업 정의의 최신 개정을 바탕으로 서비스 업데이트

기존에 만들어두었던 서비스를 선택합니다. [서비스 업데이트] 버튼을 클릭합니다.

 

5. 태스크에 접속 후, 환경변수 적용 확인

로드 밸런서나, 각 태스크의 퍼블릭 IP를 통해 WAS에 접근해 보면, 기대한 결과를 얻을 수 있습니다.

실습과제: 작업 정의 파일을 이용한 배포 자동화
GitHub Action을 이용해 ECS 배포 과정 workflow를 추가합니다.

민감 정보가 절대 Git에 노출되지 않아야 합니다.

 

1. 작업 정의 JSON 파일을 Git Repository에 추가합니다

- github/workflows 에 aws.yml 파일 추가하고 task_definition.json 파일은 루트 디렉토리에 저장합니다.
- task_definition_json 코드는 AWS ECS 태스크 정의에 들어가 JSON 항목을 선택하면 표시 되어 copy & paste 하면 됩니다.

2. AWS.yml 파일 작성 합합니다.

3. ECS로의 배포를 위한 GitHub Action workflow를 추가합니다.

4. Git pull / push 으로 내용 github에 업로드 합니다.
참고 : 기존의 ECR로의 빌드/push 작업 자동화 workflow가 있는 경우에 해당 내용이 중복이므로, 기존 workflow는 지워도 좋습니다.

- AWS.yml 수정 하여 빌드 및 이미지 push 는 가능하지만 Deploy 부분에 문제가 생겼습니다.

- 문제 미해결

 

마일스톤6 - 서버 애플리케이션의 HTTPS 적용
https://본인도메인.click의 트래픽이 서버 컨테이너, 즉 애플리케이션 로드 밸런서로 연결되도록 만들어야 합니다.


Hint

- DNS 주소에 따른 트래픽을 로드 밸런서로 보내려면 Route 53을 이용해야 합니다.

- HTTPS 적용을 위해서는, 구입한 도메인의 인증서가 필요합니다. AWS Certificate Manager(ACM)에서 발급받은 인증서를 활용해야 합니다.

- 로드 밸런서 구성에서 HTTPS 프로토콜을 선택하면 인증서 적용이 가능합니다.

 

1. 새로운 Load Balancer 생성 하고 SSL 인증은 그전 Route 53 에서 받은 인증서 그대로 사용

2. Route 53에 들어가 새로운 레코드 생성