업무시간에만 사용하는 서비스인 경우 사용하지 않는 시간에 인스턴스를 중지시켜 두면 사용 요금을 반으로 줄일 수 있다. 하지만 수동으로 하다보면 중지하는걸 까먹는게 대부분이다.
자동으로 사용시간에는 EC2를 시작하고 미사용시간에는 EC2를 중지하는 Lambda 함수를 사용하면 요금을 줄일 수 있다.
이전글에서 설명한 Tag 강제하기와 같이 사용하여 사용요금을 최대한 줄여보자.
엄청나게 간단한 Lambda 함수로 자동화를 할 수 있다.
Key값은 'AutoSchedule' 이고 Value값은 'Y' 인 Tag 를 가진 인스턴스의 상태를 시작 시키는 Lambda 함수이다.
import boto3
region = 'ap-northeast-2'
instances = []
ec2_r = boto3.resource('ec2')
ec2 = boto3.client('ec2', region_name=region)
for instance in ec2_r.instances.all():
for tag in instance.tags:
if tag['Key'] == 'AutoSchedule':
if tag['Value'] == 'Y':
instances.append(instance.id)
def lambda_handler(event, context):
ec2.start_instances(InstanceIds=instances)
print('started your instances: ' + str(instances))
python코드를 살펴보자.
- region = 'ap-northeast-2'
: AWS 리전을 'ap-northeast-2' (서울 리전)로 설정- instances = []
: 중지할 EC2 인스턴스의 ID를 저장할 빈 리스트를 생성- ec2_r = boto3.resource('ec2')
: EC2 리소스를 사용하기 위해 Boto3 리소스 객체를 생성- ec2 = boto3.client('ec2', region_name=region)
: EC2 클라이언트를 생성하고 지정된 리전으로 설정- for instance in ec2_r.instances.all():
: 모든 EC2 인스턴스를 반복- for tag in instance.tags:
: 각 인스턴스의 태그를 반복- if tag['Key'] == 'AutoSchedule':
: 태그 키가 'AutoSchedule'인 경우- if tag['Value'] == 'Y':
: 태그 값이 'Y'인 경우- instances.append(instance.id)
: 해당 인스턴스의 ID를 instances 리스트에 추가- def lambda_handler(event, context):
: Lambda 함수의 핵심 핸들러 함수를 정의 이 함수는 Lambda 서비스에 의해 호출- ec2.start_instances(InstanceIds=instances)
: instances 리스트에 있는 모든 EC2 인스턴스를 시작- print('started your instances:' + str(instances))
: 시작된 인스턴스의 ID를 출력
Lambda 함수를 매번 자동으로 돌릴 수 있도록 트리거 설정을 해주자.
구성에서 EventBrigde 트리거 추가를 해준다. rule만 추가해 주면 제 시간에 알아서 함수가 작동해서 EC2를 시작시켜 줄 것이다.
트리거 소스는 EventBridge를 선택하고 새로운 Rule을 만들어 준다.
Rule Type은 Schedule expression으로 하여 Cron값을 넣어주어 시간을 지정한다.
Key값은 'AutoSchedule' 이고 Value값은 'Y' 인 Tag 를 가진 인스턴스의 상태를 중지 시키는 Lambda 함수이다.
import boto3
region = 'ap-northeast-2'
instances = []
ec2_r = boto3.resource('ec2')
ec2 = boto3.client('ec2', region_name=region)
for instance in ec2_r.instances.all():
for tag in instance.tags:
if tag['Key'] == 'AutoSchedule':
if tag['Value'] == 'Y':
instances.append(instance.id)
def lambda_handler(event, context):
ec2.stop_instances(InstanceIds=instances)
print('stopped your instances: ' + str(instances))
ec2.stop_instances(InstanceIds=instances)
: instances 리스트에 있는 모든 EC2 인스턴스를 중지
EC2 중지는 매일 오후7시 Off 하도록 시간 설정하였다. 시간은 UTC기준이니 현지시간대를 꼭 확인하자.
트리거 까지 완성 했는대 지정한 날짜에 실행이 안되었다.
cloudwatch 로그그룹에서 로그를 확인해 보았더니 권한이 없다는것 같다.
role을 만들어 주고 EC2에 접근할 수 있도록 작업권한을 준다.
{
"Version": "2012-10-17",
"Statement": [
{
"Sid": "VisualEditor0",
"Effect": "Allow",
"Action": [
"ec2:Describe*",
"ec2:Start*",
"ec2:Stop*",
],
"Resource": "*"
}
]
}
실행 역할 권한까지 추가한다면 Lambda 실행이 된다.