ECS는 Docker를 사용하여 EC2 인스턴스 클러스터에 애플리케이션을 쉽게 배포하고 확장, 축소가 가능하도록 해주는 서비스이다. 이를 위해 각 EC2 인스턴스에 Docker 컨테이너를 어떻게 구성하여 띄울 것인지에 대한 작업 정의를 해 놓고, 이 작업정의를 기반으로 클러스터에 어떻게 실행하고 유지 관리할지에 대한 정의가 포함되어 있는 서비스를 생성한다. 이 때 작업 정의에서 사용되는 Docker 컨테이너의 이미지는 ECR의 각 리포지터리를 사용한다. 서비스에 대한 정의에 따라 ELB와 Auto Scaling이 구성되어 클러스터 내 EC2 인스턴스들이 확장되거나 축소될 수 있다.
주요 구성 요소
Container Instance
- Amazon ECS 에이전트를 실행 중이며 클러스터에 등록된 Amazon EC2 인스턴스
- 각 인스턴스가 EC2 서버 한대라고 생각하면 됨
Container
- Task의 일부로 작성된 Linux 컨테이너
Cluster
Container Instance의 논리적인 그룹
Task Definitions
작업 정의 : 컨테이너에 대한 정의
Tasks
정의 해놓은 작업을 Container Instance로 배포 (작업 정의의 단일 인스턴스)
Service
배포된 각 작업들이 Container Instance에서 구동된 것을 서비스라고 함.
서비스 (Service)
Amazon ECS는 단일 ECS 클러스터에서 작업 정의에 지정된 수("원하는 개수")의 인스턴스를 동시에 실행 및 관리할 수 있게 해줌
서비스에서 작업이 중지되는 경우 해당 작업은 종료되었다가 다시 시작됨.
- 이 프로세스는 원하는 실행 작업 수에 도달할 때까지 계속 됨
- 해당 컨테이너 인스턴스의 docker 컨테이너가 제거되었다가 다시 생성됨.
필요한 경우 ELB를 사용하여 서비스의 작업에 트래픽을 균등하게 분산하도록 구성할 수 있음
- 서비스 로드 밸런싱 참조
서비스 스케쥴러가 최소 상태 백분율 및 최대 백분율 파라미터를 사용하여 배포 전략 결정
- 서비스 정의 파라미터 참조
서비스 스케쥴러 동작 방식 (다음의 로직으로 가용 영역 간의 작업을 밸런싱)
- 클러스터에서 어느 컨테이너 인스턴스가 서비스의 작업 정의를 지원할 수 있는지 판단
- 필요한 CPU, 메모리, 포트 및 컨테이너 인스턴스 속성과 같은 것들로
- 인스턴스와 동일한 가용영역에서 이 서비스의 최소 실행 작업 수를 기준으로 유효한 컨테이너 인스턴스를 정렬.
- 여기서 최소 실행 작업수라는 것은 각 컨테이너 인스턴스가 구동 중인 작업수가 제일 작은 컨테이너 인스턴스가 우선순위가 높다는 것을 의미
- 위에서 결정된 컨테이너 인스턴스로 작업을 배치
- 클러스터에서 어느 컨테이너 인스턴스가 서비스의 작업 정의를 지원할 수 있는지 판단
작업 정의 (Task Definistions)의 컨테이너 설정
고급 컨테이너 구성
- CPU 단위 : ECU 값
- CPU 코어마다 1024개의 cpu 단위가 존재
- docker run —cpu-shares 옵션에 매핑됨
- 필수 (essential) : true인 경우 컨테이너가 중지되면 작업의 일부인 다른 모든 컨테이너도 중지됨
- 진입점 (entryPoint) : docker run의 —entrypoint 옵션에 매핑
- 명령 (command) : 컨테이너로 전달되는 명령
- docker run의 command 파라미터에 매핑
- 작업 디렉터리 (workingDirectory) : docker run의 —workdir에 매핑
- Env 변수 (environment) : docker run의 —env 옵션에 매핑
네트워크 설정
- 네트워킹 비활성화 (disableNetworking) : true일 경우 컨테이너 내에서 네트워킹이 비활성화됨
- 링크 (links) : 포트 매핑 필요 없이 컨테이너 간 통신이 가능하도록 함.
- docker run 의 —link와 매핑
- 호스트 이름 (hostname) : 컨테이너에 사용할 호스트 이름
- docker run의 —hostname 옵션에 매핑
- DNS 서버 (dnsServers) : 컨테이너에 제공되는 DNS 서버 목록
- docker run의 —dns 옵션에 매핑
- DNS 검색 도메인 (dnsSearchDomains) : 컨테이너에 제공되는 DNS 검색 도메인의 목록
- docker run의 —dns-search 옵션에 매핑
- 추가 호스트 (extraHosts) : 컨테이너의 /etc/hosts 파일에 추가할 호스트 이름 및 IP 주소 매핑의 목록
- docker run의 —add-host 옵션에 매핑
스토리지 및 로깅
읽기 전용 루트 파일 시스템 (readonlyRootFilesystem) : true일 경우 루트 파일 시스템에 대한 읽기 전용 엑세스 부여
- docker run의 —ready-only 옵션에 매핑
탑재 지점 (mountPoints) : 컨테이너에서 데이터 볼륨의 탑재 지점
docker run의 —volume 옵션에 매핑
볼륨이 존재하지 않을 경우 작업에서 데이터 볼륨 사용 참조
소스 볼륨 (sourceVolume) : 탑재할 볼륨의 이름
컨테이너 경로 (containerPath) : 호스트 볼륨을 탑재할 컨테이너의 경로
읽기 전용 (readyOnly) : true 일 경우 컨테이너에는 볼륨에 대한 읽기 전용 엑세스가 부여됨
- 기본 값 false
볼륨 출저 (volumesFrom) : 다른 컨테이너로부터 탑재할 데이터 볼륨
- docker run의 —volumes-from 옵션에 매핑
- 소스 컨테이너 (sourceContainer) : 탑재할 볼륨이 위치한 컨테이너의 이름
- 읽기 전용 (readOnly) : true일 경우 컨테이너에는 볼륨에 대한 읽기 전용 엑세스가 부여됨
- 기본 값 false
로그 구성 (logConfiguration) : 컨테이너의 로그 구성 사항
- docker run 의 —log-driver 옵션에 매핑
- 기본적으로 Docker 데몬이 사용하는 것과 동일한 로깅 드라이버를 사용
- 작업 정의에서 awslogs 로그 드라이버를 사용하여 CloudWatch Logs로 컨테이너 로그를 보낼 수 있음
- awslogs 로그 드라이버 사용 참조
- 아래 로그 드라이버를 선택해서도 awslogs를 사용할 수 있음
로그 드라이버 (logDriver) : 컨테이너에 사용할 로그 드라이버
- Amazon ECS 컨테이너 에이전트가 기본적으로 통신할 수 있는 로그 드라이버
로그 옵션 (options) : 로그 드라이버로 보낼 구성 옵션
보안/리소스 제한/DOCKER 레이블
- 권한이 있음 (privileged) : true일 경우 컨테이너에는 호스트 컨테이너 인스턴스에 대한 승격된 권한을 부여 받음(root 사용자와 비슷)
- docker run의 —privileged 옵션에 매핑
- 사용자 (user) : 컨테이너 내부에서 사용할 사용자 이름
- docker run의 —user 옵션에 매핑
- Docker 보안 옵션 (dockerSecurityOptions) : SELinux 및 AppArmor 다중 수준 보안 시스템에 사용자 지정 레이블을 제공할 문자열 목록
- docker run의 —security-opt 옵션에 매핑
- Amazon ECS 컨테이너 에이전트는
ECS_SELINUX_CAPABLE=true
또는ECS_APPARMOR_CAPABLE=true
환경 변수를 사용하여 해당 인스턴스에서 사용 가능한 로깅 드라이버를 등록해야 해당 인스턴스에 배치된 컨테이너가 이들 보안 옵션을 사용할 수 있음 - Amazon ECS 컨테이너 에이전트 구성 참조
- 사용자 제한 (ulimits) : 컨테이너에 설정하 ulimits의 목록
- docker run의 —ulimit 옵션에 매핑
- Docker 레이블 (dockerLabels) : 컨테이너에 추가할 레이블의 키/값 맵
- docker run의 —label 옵션에 매핑
ECU(Elastic Compute Units)
AWS에서는 EC2 머신의 성능을 표현하기 위해 ECU(Elastic Compute Units)라는 단위로 표현
1ECU = 1 core 1.0-1.2 GHz 2007 Opteron or 2007 Xeon processor로 정의
ECU = Virtual Core 개수 * Physical CPU에 따른 ECU 값
EC2의 각 인스턴스 타입별로 vCPU 수가 정해져 있지만 이는 계열(family)에 따라 호스트의 사양이 다르기 때문에 vCPU 수가 같다고 해서 같은 성능을 보장하지는 않음.
- 그래서 표준적인 CPU 성능이 필요했기 때문에 AWS에서는 이를 위해 ECU라는 CPU 성능 단위를 만들었음
- 1ECU는 PassMark-CPU 라는 성능점수로 400점이며, 쿼드코어 CPU 1개의 PassMark-CPU 성능점수가 8800점.
- 22개의 ECU가 일반적으로 포털에서 사용하는 쿼드코어 CPU1개와 동일
- 일반적으로 웹서버가 평균 10% 미만을 사용한다고 할 때 2.2개의 ECU면 충분하며, 피크치를 고려해도 10ECU정도면 충분
EC2 인스턴스에서 사양 확인
$ lscpu
참고
ECS의 AMI(Amazon Machine Image)
- Amazon ECS-Optimized Amazon Linux AMI
- 아마존에서 docker를 사용하기에 최적화 된 환경을 Amazon Linux에 구축한 AMI
- Amazon Linux인데 CoreOS인 것처럼 리소스를 최소화 시킴
ELB(Elastic Load Balancer)
ALB (Application Load Balancer)
OSI 모델의 일곱 번째 계층인 응용 프로그램 계층에서 작동
요청을 받으면 우선 순위에 따라 리스너의 규칙을 검토하여 적용 할 규칙을 결정한 후 라운드 로빈 라우팅 알고리즘을 사용하여 작업 대상 그룹에서 대상을 선택함.
- 여기서 작업 대상은 ECS에서 작업 대상에 자동으로 추가해주는 컨테이너 인스턴스를 말함
라운드 로빈 방식이 아닌 트래픽 기반의 로드 밸런싱을 하도록 리스너 규칙을 구성할 수도 있음
대상 그룹 내의 특정 대상이 여러 대상 그룹에 등록되어 있더라도 각 대상 그룹에 대한 라우팅은 독립적으로 수행됨
- 즉, 속해있는 대상 그룹의 규칙 따라 각각 라우팅 됨
ELB 특성 상 대상 그룹에서 비정상적인 대상을 탐지하고 정상적인 대상에만 트래픽을 라우팅함
응용 프로그램에 대한 요청의 흐름을 방해하지 않고 로드 밸런서에 대상을 추가 및 제거할 수 있기 때문에 자동으로 확장이 가능
오토 스케일링 설정이 안되어 있는 경우에는 작업의 수를 증가시키거나 감소시키는 작업을 수동으로 수행해야 한다.
- 작업 개수를 늘리는 경우
- ECS => 클러스터 => 서비스 선택 후 업데이트 버튼 클릭 => 작업 개수 폼의 값 조정
- ECS => 클러스터 => ECS 인스턴스 => ECS 인스턴스 조정 => 원하는 인스턴스 개수 폼의 값 조정
- EC2 => Instances 에서 인스턴스 생성 확인
- EC2 => Load Balancing에서 TargetGroup 선택 => Target Group 리스트 중 해당 EC2 컨테이너 인스턴스에 해당하는 TargetGroup 선택 후 Targets 탭 선택 => Edit 버튼을 클릭 하여 새로 추가된 EC2 인스턴스를 TargetGroup에 추가
- 작업 개수를 줄이는 경우
- ECS => 클러스터 => 서비스 선택 후 업데이트 버튼 클릭 => 작업 개수 폼의 값 조정
- ECS => 클러스터 => ECS 인스턴스 => ECS 인스턴스 조정 => 원하는 인스턴스 개수 폼의 값 조정
- 인스턴스 개수를 줄이면 자동으로 EC2 인스턴스를 terminated 시킴
- 완벽히 제거하려면 수동으로
- EC2 => Load Balancing에서 TargetGroup 선택 => Target Group 리스트 중 해당 EC2 컨테이너 인스턴스에 해당하는 TargetGroup 선택 후 Targets 탭 선택 => Edit 버튼을 클릭 하여 제거된 EC2 인스턴스를 TargetGroup에서 제거
ALB를 사용할 때의 이점 (CLB 사용 시 보다)
- 경로(URL) 기반 라우팅 지원
- 단일 EC2 인스턴스에 여러 포트를 사용하여 여러 서비스로 요청 라우팅을 지원
- CLB는 하나의 EC2 인스턴스에 하나의 포트만 사용 가능
- 컨테이너화 된 애플리케이션 지원
- ECS는 작업 예약 시 사용하지 않는 포트를 동적으로 선택하여 대상 그룹에 작업을 등록할 수 있음
- 상태 검사가 대상 그룹 단위로 정의되기 때문에 CloudWatch에서 메트릭을 대상 그룹 단위로 모니터링 할 수 있음
- 액세스 로그는 추가 정보를 포함하여 압축 된 형식으로 저장됨
- 로드 밸런서 성능이 향상됨
Auto Scaling
- CloudWatch 경보에 의해 서비스를 확장하고 축소하는 조정 정책을 만들어서 서비스 Auto Scaling을 구성할 수 있음
- ECS => 클러스터 => Service => 서비스 리스트 중 해당 서비스 선택 => 업데이트 버튼 클릭 => Auto Scaling 설정 선택
- Minimum number of tasks : 최소로 유지할 작업의 개수
- Desired number of tasks : 원하는 작업의 개수
- Maximum number of tasks : 최대로 확장될 수 있는 작업의 개수
- IAM role for Service Auto Scaling : IAM 역할과 서비스 조정 정책을 구성할 수 있음
- 새 경보 생성을 선택하여 경보에 대한 구성을 한다.
- 경보 임계 값을 위와 같이 설정하면 CPU 사용률이 1분동안 75%를 넘으면 CloudWatch 경보가 트리거 된다.
- 경보 설정을 저장한 후 정책에 대한 설정을 한다.
- 위와 같이 설정하면 Cloud Watch에서 경보가 트리거 될 때 원하는 서비스의 작업이 설정된만큼 추가된다.
- 추가될 작업 수가 1이상인 경우 휴지 시간에 설정된 시간에 따라 조정 작업간의 딜레이가 생긴다.
ECR (EC2 Container Registry)
- Docker Container Registry
- ECR에 저장된 이미지는 ECS에서 사용할 수 있음.
- IAM 롤 사용 가능
- HTTPS를 통해 컨테이너 이미지를 송수신
- 이미지는 S3로 저장이 되며, S3 서버측 암호화를 사용해서 자동으로 이미지를 암호화함
- 사용을 위해서는 awscli 필요
- Amazon ECR API를 사용해서도 이미지를 푸시하고 가져올 수 있지만 docker 명령을 사용할 것을 권장
비용
- 초기 비용이나 약정은 없음
- 리포지토리에 저장한 데이터와 인터넷으로 전송한 데이터양에 대한 요금만 지불
- 프리티어 유저인 경우 해당 기간 동안 매월 500MB의 스토리지를 무료 제공
- 프리티어 유저인 경우 해당 기간 동안 매월 15GB의 데이터 전송을 무료 제공
- 스토리지는 월별 GB당 0.10 USD
- 수신 데이터는 무료
- 같은 리전에 있는 EC2에서 ECR을 사용하는 경우에는 무료
리포지토리
- 레지스트리가 여러 리포지토리를 포함하고 있는 개념
- 각 리포지토리에 이미지를 푸시하거나 가져올 수 있음.
- 리포지토리 이름은 네임스페이스를 지원
- 이를 통해 리포지토리를 그룹화 할 수 있음
- 즉, 동일한 레지스트리를 여러 팀이 사용하는 경우 네임스페이스로 구분하여 리포지토리를 분리할 수 있다. 이렇게 구성하면 같은 이름의 이미지를 사용하더라도 네임스페이스가 다르기 때문에 간섭없이 사용 가능
- ecr:GetAuthorizationToken 권한이 있는 사용자만 레지스트리에 인증할 수 있고, 리포지토리를 사용할 수 있음.
사용하기
registry에 접속하기 위한 docker login 인증 정보 얻기
$ aws ecr get-login
- 반환된 텍스트를 복사하여 명령 실행
- 텍스트에 포함된 패스워드는 12시간 동안 유효한 권한 부여 토큰
- GetAuthorizationToken API를 통해 base64로 인코딩된 토큰을 가져올 수 있지만 docker login 명령에서 디코딩해서 사용해야함.
- 위의 AWS CLI 명령을 사용하면 자동으로 토큰을 가져오고 디코딩하고 docker login 명령으로 변환해 주기 때문에 이를 사용하면 편리
- 위 명령 수행 시 반환되는 텍스트에서 마지막 인자에 해당하는 주소가 레지스트리 주소.
- 명령을 그대로 복사하여 실행할 경우 ps -e 명령을 통해 password를 볼 수가 있음.
- 안전하지 않은 시스템일 경우 docker login시 -p 옵션을 생략하고 대화형으로 로그인해야함.
- 반환된 텍스트를 복사하여 명령 실행
이후 해당 ECR 주소를 사용하여 docker push 명령으로 이미지를 푸시할 수 있음.
참고
'Programming > AWS' 카테고리의 다른 글
[AWS] EC2 종료 시 filebeat 정상 종료 확인 및 대기 (2) | 2017.09.26 |
---|---|
[AWS] Elastic Beanstalk 생성과 Hook, .ebextensions를 통해 EC2 인스턴스 설정 (2) | 2017.06.12 |
[AWS] EC2 인스턴스에서 docker swarm 서비스를 통해 웹서버 구동 및 확장 (0) | 2017.06.11 |
[AWS] EC2 인스턴스에 Docker Swarm 구성 (1) | 2017.05.31 |
[AWS] Docker for AWS의 CloudFormation 설정 살펴보기 (0) | 2017.05.21 |
댓글