Windows 10 환경에서 Terraform을 이용한 AWS 자원 배포 - 4. ASG 및 ALB 연동
이전에 파일로 나눠서 사용한 AWS 환경에 ASG(AutoScale Group)와 ALB를 연동해 구성하는 방법을 실습
1. ALB 및 ALB 리스너, ALB 대상그룹 생성
// ALB 및 ALB 리스너, ALB 대상그룹 생성
echo resource "aws_lb" "ersia_alb" { > alb.tf
echo name = "t101-alb" >> alb.tf
echo load_balancer_type = "application" >> alb.tf
echo subnets = [aws_subnet.ersia_subnet1.id, aws_subnet.ersia_subnet2.id] >> alb.tf
echo security_groups = [aws_security_group.ersia_sg.id] >> alb.tf
echo. >> alb.tf
echo tags = { >> alb.tf
echo Name = "t101-alb" >> alb.tf
echo } >> alb.tf
echo } >> alb.tf
echo. >> alb.tf
echo resource "aws_lb_listener" "ersia_http" { >> alb.tf
echo load_balancer_arn = aws_lb.ersia_alb.arn >> alb.tf
echo port = 80 >> alb.tf
echo protocol = "HTTP" >> alb.tf
echo. >> alb.tf
echo # By default, return a simple 404 page >> alb.tf
echo default_action { >> alb.tf
echo type = "fixed-response" >> alb.tf
echo. >> alb.tf
echo fixed_response { >> alb.tf
echo content_type = "text/plain" >> alb.tf
echo message_body = "404: page not found - T101 Study" >> alb.tf
echo status_code = 404 >> alb.tf
echo } >> alb.tf
echo } >> alb.tf
echo } >> alb.tf
echo. >> alb.tf
echo resource "aws_lb_target_group" "ersia_albtg" { >> alb.tf
echo name = "t101-alb-tg" >> alb.tf
echo port = 80 >> alb.tf
echo protocol = "HTTP" >> alb.tf
echo vpc_id = aws_vpc.ersia_vpc.id >> alb.tf
echo. >> alb.tf
echo health_check { >> alb.tf
echo path = "/" >> alb.tf
echo protocol = "HTTP" >> alb.tf
echo matcher = "200-299" >> alb.tf
echo interval = 5 >> alb.tf
echo timeout = 3 >> alb.tf
echo healthy_threshold = 2 >> alb.tf
echo unhealthy_threshold = 2 >> alb.tf
echo } >> alb.tf
echo } >> alb.tf
echo. >> alb.tf
echo output "ersia_alb_dns" { >> alb.tf
echo value = aws_lb.ersia_alb.dns_name >> alb.tf
echo description = "The DNS Address of the ALB" >> alb.tf
echo } >> alb.tf
type alb.tf
// terraform plan 및 apply 수행
terraform plan && terraform apply -auto-approve
ALB 대상그룹까지 생성했으나, 아직 아무 대상과도 연결하지 않은 상태이며,
리스너 규칙도 404 고정응답 반환만 추가된 상태임
2. ASG 생성 및 ALB 대상그룹과의 연결
// AGS 생성
echo data "aws_ami" "ersia_amazonlinux2" { > asg.tf
echo most_recent = true >> asg.tf
echo filter { >> asg.tf
echo name = "owner-alias" >> asg.tf
echo values = ["amazon"] >> asg.tf
echo } >> asg.tf
echo. >> asg.tf
echo filter { >> asg.tf
echo name = "name" >> asg.tf
echo values = ["amzn2-ami-hvm-*-x86_64-ebs"] >> asg.tf
echo } >> asg.tf
echo. >> asg.tf
echo owners = ["amazon"] >> asg.tf
echo } >> asg.tf
echo. >> asg.tf
echo resource "aws_launch_configuration" "ersia_lauchconfig" { >> asg.tf
echo name_prefix = "t101-lauchconfig-" >> asg.tf
echo image_id = data.aws_ami.ersia_amazonlinux2.id >> asg.tf
echo instance_type = "t2.micro" >> asg.tf
echo security_groups = [aws_security_group.ersia_sg.id] >> asg.tf
echo associate_public_ip_address = true >> asg.tf
echo. >> asg.tf
echo user_data = "${file("ec2-userdata-web.tftpl")}" >> asg.tf
echo. >> asg.tf
echo # Required when using a launch configuration with an auto scaling group. >> asg.tf
echo lifecycle { >> asg.tf
echo create_before_destroy = true >> asg.tf
echo } >> asg.tf
echo } >> asg.tf
echo. >> asg.tf
echo resource "aws_autoscaling_group" "ersia_asg" { >> asg.tf
echo name = "ersia_asg" >> asg.tf
echo launch_configuration = aws_launch_configuration.ersia_lauchconfig.name >> asg.tf
echo vpc_zone_identifier = [aws_subnet.ersia_subnet1.id, aws_subnet.ersia_subnet2.id] >> asg.tf
echo min_size = 2 >> asg.tf
echo max_size = 10 >> asg.tf
echo health_check_type = "ELB" >> asg.tf
echo target_group_arns = [aws_lb_target_group.ersia_albtg.arn] >> asg.tf
echo. >> asg.tf
echo tag { >> asg.tf
echo key = "Name" >> asg.tf
echo value = "terraform-asg" >> asg.tf
echo propagate_at_launch = true >> asg.tf
echo } >> asg.tf
echo } >> asg.tf
type asg.tf
// asg.tf에서 사용할 userdata 파일 선언
echo #!/bin/bash > ec2-userdata-web.tftpl
echo wget https://busybox.net/downloads/binaries/1.31.0-defconfig-multiarch-musl/busybox-x86_64 >> ec2-userdata-web.tftpl
echo mv busybox-x86_64 busybox >> ec2-userdata-web.tftpl
echo chmod +x busybox >> ec2-userdata-web.tftpl
echo RZAZ=^$(curl http://169.254.169.254/latest/meta-data/placement/availability-zone-id) >> ec2-userdata-web.tftpl
echo IID=^$(curl 169.254.169.254/latest/meta-data/instance-id) >> ec2-userdata-web.tftpl
echo LIP=^$(curl 169.254.169.254/latest/meta-data/local-ipv4) >> ec2-userdata-web.tftpl
echo echo "<h1>RegionAz($RZAZ) : Instance ID($IID) : Private IP($LIP) : Web Server</h1>" ^> index.html >> ec2-userdata-web.tftpl
echo nohup ./busybox httpd -f -p 80 ^& >> ec2-userdata-web.tftpl
type ec2-userdata-web.tftpl
// terraform plan 및 apply 수행
terraform plan && terraform apply -auto-approve
3-1. ALB에 ASG로 이어주는 리스너 규칙 추가
// ALB에 ASG로 이어주는 리스너 규칙 추가
echo resource "aws_lb_listener_rule" "ersia_albrule" { > alb_rule.tf
echo listener_arn = aws_lb_listener.ersia_http.arn >> alb_rule.tf
echo priority = 100 >> alb_rule.tf
echo. >> alb_rule.tf
echo condition { >> alb_rule.tf
echo path_pattern { >> alb_rule.tf
echo values = ["*"] >> alb_rule.tf
echo } >> alb_rule.tf
echo } >> alb_rule.tf
echo. >> alb_rule.tf
echo action { >> alb_rule.tf
echo type = "forward" >> alb_rule.tf
echo target_group_arn = aws_lb_target_group.ersia_albtg.arn >> alb_rule.tf
echo } >> alb_rule.tf
echo } >> alb_rule.tf
echo. >> alb_rule.tf
echo output "ersia_alb_dns2" { >> alb_rule.tf
echo value = aws_lb.ersia_alb.dns_name >> alb_rule.tf
echo description = "The DNS Address of the ALB" >> alb_rule.tf
echo } >> alb_rule.tf
type alb_rule.tf
// terraform plan 및 apply 수행
terraform plan && terraform apply -auto-approve
3-2. 정상 수행 및 ALB를 통한 EC2 접속 확인
// ALB DNS로 접속 수행 결과
c:\terraform_study\study2>
c:\terraform_study\study2>curl -s http://t101-alb-56454306.ap-northeast-2.elb.amazonaws.com
<h1>RegionAz(apne2-az3) : Instance ID(i-01ac1da56a73cd0b7) : Private IP(10.10.2.237) : Web Server</h1>
c:\terraform_study\study2>curl -s http://t101-alb-56454306.ap-northeast-2.elb.amazonaws.com
<h1>RegionAz(apne2-az3) : Instance ID(i-01ac1da56a73cd0b7) : Private IP(10.10.2.237) : Web Server</h1>
c:\terraform_study\study2>curl -s http://t101-alb-56454306.ap-northeast-2.elb.amazonaws.com
<h1>RegionAz(apne2-az1) : Instance ID(i-00f51e5956842fba7) : Private IP(10.10.1.199) : Web Server</h1>
c:\terraform_study\study2>curl -s http://t101-alb-56454306.ap-northeast-2.elb.amazonaws.com
<h1>RegionAz(apne2-az3) : Instance ID(i-01ac1da56a73cd0b7) : Private IP(10.10.2.237) : Web Server</h1>
c:\terraform_study\study2>
접속 시 ASG에서 생성된 2개의 서버로 로드밸런싱이 되는 것을 확인
4. ASG 서버 대수 변경 후 접속 테스트
// asg.tf 파일의 min_size를 2에서 3으로 변경
...
...
...
vpc_zone_identifier = [aws_subnet.ersia_subnet1.id, aws_subnet.ersia_subnet2.id]
min_size = 2 <----- 해당 부분을 3으로 변경
max_size = 10
health_check_type = "ELB"
target_group_arns = [aws_lb_target_group.ersia_albtg.arn]
tag {
key = "Name"
...
...
...
// terraform plan 및 apply 수행
terraform plan && terraform apply -auto-approve
// ALB DNS로 접속 수행 결과
c:\terraform_study\study2>
c:\terraform_study\study2>curl -s http://t101-alb-56454306.ap-northeast-2.elb.amazonaws.com
<h1>RegionAz(apne2-az3) : Instance ID(i-01ac1da56a73cd0b7) : Private IP(10.10.2.237) : Web Server</h1>
c:\terraform_study\study2>curl -s http://t101-alb-56454306.ap-northeast-2.elb.amazonaws.com
<h1>RegionAz(apne2-az3) : Instance ID(i-01ac1da56a73cd0b7) : Private IP(10.10.2.237) : Web Server</h1>
c:\terraform_study\study2>curl -s http://t101-alb-56454306.ap-northeast-2.elb.amazonaws.com
<h1>RegionAz(apne2-az1) : Instance ID(i-00f51e5956842fba7) : Private IP(10.10.1.199) : Web Server</h1>
c:\terraform_study\study2>curl -s http://t101-alb-56454306.ap-northeast-2.elb.amazonaws.com
<h1>RegionAz(apne2-az1) : Instance ID(i-03c7932edea8884a6) : Private IP(10.10.1.138) : Web Server</h1>
c:\terraform_study\study2>curl -s http://t101-alb-56454306.ap-northeast-2.elb.amazonaws.com
<h1>RegionAz(apne2-az1) : Instance ID(i-00f51e5956842fba7) : Private IP(10.10.1.199) : Web Server</h1>
c:\terraform_study\study2>curl -s http://t101-alb-56454306.ap-northeast-2.elb.amazonaws.com
<h1>RegionAz(apne2-az1) : Instance ID(i-03c7932edea8884a6) : Private IP(10.10.1.138) : Web Server</h1>
c:\terraform_study\study2>
10.10.1.138 / 10.10.1.199 / 10.10.2.237의 IP를 가진 3대 EC2로 로드 밸런싱되는 것을 확인할 수 있음
5. 실습이 완료된 자원 삭제
// 테라폼으로 생성한 AWS 자원 삭제
terraform destroy -auto-approve
-> 삭제의 경우 apply 때와 마찬가지로 auto-approve 옵션 사용 시 주의가 필요함
참고자료
- 테라폼 공식 홈페이지 : https://developer.hashicorp.com/terraform/intro
- 테라폼 레지스트리 : https://registry.terraform.io/providers/hashicorp/aws/latest/docs/data-sources
- 테라폼 variable, data 참고 : https://kim-dragon.tistory.com/219