더보기

★★cloudNet@ 팀의 가시다 님이 진행하는 Terraform 101 Study 4기 내용과

한빛미디어 테라폼으로 시작하는 IaC 책을 참고하여 정리하였습니다.

 

★ Terraform, IaC 이란?

  • 하시코프(Hashicorp)에서 Go 언어로 개발한 오픈소스 IaC(Infrastructure as Code) 도구
  • IaC(Infrastructure as Code)는 코드로 인프라를 관리
  • HCL(Hashicorp Configuration Language)를 사용해 클라우드 리소스를 선언
    (코드로 클라우드 인프라 서버를 더 효율적으로 구축하고, 운영할 수 있는 오픈소스 소프트웨어)

★ 실습 환경 구성(윈도우)

  1. 윈도우에 WSL2 설치
    : Powershell 관리자 권한으로 실행 [vscode 에서 TERMINAL 실행]
    : wsl --install 입력
    : username, password 입력
    : 원하는 리눅스 접속시 d 옵션 (wsl -d Ubuntu)
    : 리눅스 종료 시 t 옵션 (wsl -t)
    : 리스트 확인 l 옵션 (wsl -l)

WSL 설치

 

현재 설치된 리눅스 확인

 

생성한 Ubuntu로 접속

 

3. Terraform 설치 및 확인

설치한 테라폼 버전 확인

 

4. VS Code 설치 후 아래 설치 필요

  • HashiCorp HCL : syntax highlighting for HCL files
  • HashiCorp Terraform : Highlighting syntax from Terraform 등

 

★ (실습) AWS CLI 설치 및 자격증명

[ 환경 구성 ] - default VPC를 사용

  1. AWS Free-Tier
  2. AWS IAM User 생성 : AdministratorAccess, 프로그래밍 방식 액세스 권한 부여(Access/Secret Key)
  3. AWS CLI v2 설치 (LINUX 사용)

[명령어]

# curl "https://awscli.amazonaws.com/awscli-exe-linux-x86_64.zip" -o "awscliv2.zip"
# unzip awscliv2.zip
# sudo ./aws/install

 

[결과] aws --version 으로 확인

 

4. aws configure 입력

* Acess Key, Secret Access Key 만드는 방법
1) aws 관리 콘솔 접속 - 보안 자격 증명

2) 액세스 키 만들기

3) 발급 후 CSV 파일 다운로드

 

5. 필요 옵션 및 필요 툴 설치 

# export AWS_PAGER=""
# sudo apt install -y tree jq

 

6. AWS 서울 리전에 default VPC 확인

aws ec2 describe-vpcs --filter 'Name=isDefault,Values=true' | jq
{
...

aws ec2 describe-vpcs --filter 'Name=isDefault,Values=true' | jq '.Vpcs[0].VpcId'
"vpc-3912a952"


#aws ec2 describe-subnets --filter 'Name=vpc-id,Values=vpc-3912a952' --output table
aws ec2 describe-subnets --filter 'Name=vpc-id,Values=vpc-<자신의VPC ID>' --output table

 

 

★ (실습) AWS CLI 설치 및 자격증명

1. 배포 전 준비

  • 작업 디렉터리 생성 및 이동

디렉터리 생성

  • Amazon Linux 2 최신 ami id 찾기 

 

  • EC2 생성 모니터링
# [터미널1] EC2 생성 모니터링
export AWS_PAGER=""
while true; do aws ec2 describe-instances --query "Reservations[*].Instances[*].{PublicIPAdd:PublicIpAddress,InstanceName:Tags[?Key=='Name']|[0].Value,Status:State.Name}" --filters Name=instance-state-name,Values=running --output text ; echo "------------------------------" ; sleep 1; done

 

  • EC2 1대 배포 실행 (코드 파일 작성)
cat <<EOT > main.tf
provider "aws" {
  region = "ap-northeast-2"
}

resource "aws_instance" "example" {
  ami           = "$AL2ID"
  instance_type = "t2.micro"
}
EOT

 

  • 배포실행 : 터미널2에서 실행
# 초기화
terraform init
ls -al
tree .terraform

# plan 확인
terraform plan

# apply 실행
terraform apply
 Enter a value: yes 입력

# ec2 생성 확인 : aws 웹 관리 콘솔에서도 확인 - 서울 리전 선택
export AWS_PAGER=""
aws ec2 describe-instances --output table

 

영상과 같이 따라했지만 여러 에러메시지 발생하여 main.tf 수정하여 재배포 ㅠㅠ

 

1. InvalidParameterValue: Value (ap-northeast-2a) for parameter availabilityZone is invalid. Subnet 'subnet-0f87ce2a29c053566' is in the availability zone ap-northeast-2d

 

해결 : main.tf 파일에서 availability_zone을 ap-northeast-2d 로 지정하여 적용

 

2. 배포는 성공하였으나 Public IP 확인 불가

 

해결 : 기본VPC 서브넷에서 자동 할당IP 설정 옵션 체크 후 재배포

 

 

  • EC2 태그 정보 수정 > 배포 실행

terraform plan
terraform apply --auto-aprove

  • EC2 삭제
# 리소스 삭제
terraform destroy
 Enter a value: yes 입력

혹은
terraform destroy -auto-approve

 


★ 기본 사용법

  • 실습 디렉터리 생성
# 실습 디렉터리 생성 후 이동 : workspaces 혹은 각자 편한 이름으로 생성
mkdir workspaces
cd workspaces

# 테라폼 실행
terraform
Usage: terraform [-version] [-help] <command> [args]
...

 

  • main.tf 파일 생성
resource "local_file" "abc" {
content  = "abc!"
filename = "${path.module}/abc.txt"
}

 

  • plan 계획 & apply 실행
    : terraform plan 명령은 테라폼으로 적용할 인프라의 변경 사항에 관한 실행 계획을 생성하는 동작. 
    또한 출력되는 결과를 확인하여 어떤 변경이 적용될지 사용자가 미리 검토하고 이해하는데 도움을 줌.(변경을 실제 적용X)
    : terraform apply는 plan 계획을 기반으로 작업을 실행

terraform plan
terraform apply

 

  • main.tf 코드 파일 추가

main.tf 파일 수정 후 terraform apply

 

 

  • destroy 제거
    : 코드파일이 있는 경로에서 terraform destroy 명령어 입력 (main.tf 파일이 있는 경로)
    : 기존에 있던 abc.txt, def.txt 파일이 삭제된 걸 확인할 수 있음
    : terraform state list (확인)

terraform destory

 


★ (실습) EC2 1대 배포 & 웹 서버 설정

1. EC2 1대를 배포하면서 userdata에 웹 서버 설정 -> 간단한 애플리케이션 설정 자동화 (Ubuntu 22.04 LTS 사용)

# 각자 편한 디렉터리를 생성해주시면 됩니다
cd ..
mkdir t101-1week-web
cd t101-1week-web

# Ubuntu 22.04 최신 AMI ID 확인
aws ec2 describe-images --owners 099720109477 \
    --filters "Name=name,Values=ubuntu/images/hvm-ssd/ubuntu-jammy-22.04-amd64-server-*" "Name=state,Values=available" \
    --query 'Images|sort_by(@, &CreationDate)[-1].[ImageId, Name]' --output text

# 변수 지정
UBUNTUID=ami-0572f73f0a5650b33

 

  • 코드 파일 작성 : user_data에 실행 명령어 작성
cat <<EOT > main.tf
provider "aws" {
  region = "ap-northeast-2"
}

resource "aws_instance" "example" {
  ami                    = "$UBUNTUID"
  instance_type          = "t2.micro"

  user_data = <<-EOF
              #!/bin/bash
              echo "Hello, T101 Study" > index.html
              nohup busybox httpd -f -p 8080 &
              EOF

  tags = {
    Name = "terraform-Study-101"
  }
}
EOT

 

  • default VPC 생성
    # aws ec2 create-default-vpc
    : default VPC 에러가 계속 발생하여 기존 VPC 삭제 후에 위 명령어로 default VPC 재생성
  • 배포 실행
# init
terraform init

# plan
terraform plan
+ user_data                            = "d91ca31904077f0b641b5dd5a783401396ffbf3f"

# apply 실행
terraform apply -auto-approve

terraform apply

 

  • 웹 서버 접속 시도
# [터미널3] 변수 지정
PIP=43.203.153.49
while true; do curl --connect-timeout 1  http://$PIP:8080/ ; echo "------------------------------"; date; sleep 1; done

 

웹 서버 접속 실패

  • 웹 서버 접속 문제 해결 : 보안그룹 생성 후 연동 필요 (코드 수정하여 보안그룹 생성 및 연동 확인)

보안그룹 추가 후 접속 성공

 

 

  • 8080포트가 아닌 다른 포트로 변경하여 웹 서버 접속

terraform apply


: terraform apply 시 기존 ec2 destory 후 새로 생성하여 연결이 끊어졌다가 ec2 생성이 완료되었을 때 다시 running 상태 확인 가능

 


★ HCL (HashiCorp configuration Language)

: 하시코프사에서 IaC와 구성 정보를 명시하기 위해 개발된 오픈 소스 도구
: IaC는 수동 프로세스가 아닌 코드를 통해 인프라를 관리하고 프로비저닝
: 테라폼에서 HCL이 코드의 영역을 담당 (확장자 tf)
: HCL 언어는 구성내용을 작성하는 목적 (블록 단위로 구성 되어 있음- {}로 감싸진 하나의 단위를 블록이라 하며 로 정의) 

 

★ 테라폼 블록

  • 테라폼 버전이나 프로바이더 버전과 같은 값들은 자동으로 설정되지만, 함께 작업할 때는 버전을 명시적으로 선언하고 필요한 조건을 입력하여 실행 오류를 최소화할 것을 권장
  • 시간이 지난 후 테라폼 코드를 실행하여도 동일한 결과를 얻어야 함
  • 테라폼, 프로바이더, 모듈이 항상 의도한 정의대로 실행되는 것을 목적
  • 버전 체계 - 시맨틱 버전관리 방식을 따름
    - Major 버전 : 내부 동작의 API가 변경 또는 삭제되거나 하위 호환이 되지 않는 버전
    - Minor 버전 : 신규 기능이 추가되거나 개선되고 하위 호환이 가능한 버전
    - Patch 버전 : 버그 및 일부 기능이 개선된 하위 호환이 가능한 버전
  • 테라폼 버전
    : required_version ="< 1.0.0" 일 경우 error 발생
terraform {
  required_version = ">= 1.0.0"
}

resource "local_file" "abc" {
  content  = "abc!"
  filename = "${path.module}/abc.txt"
}

 

terraform init

 

  • 백엔드 블록 : State
    : 백엔드 블록의 구성은 테라폼 실행 시 저장되는 State(상태 파일)의 저장 위치를 선언
    : 하나의 백엔드만 허용
    : State의 데이터를 사용해 코드로 관리된 리소스를 탐색하고 추적
    : 외부 백엔드 저장소 필요
    • State 잠금 동작
      : 기본적으로 활성화되는 백엔드는 local
      : 상태를 작업자의 로컬 환경에 저장하고 관리하는 방식
      : 여러 작업자가 접근해 사용할 수 있도록 공유 스토리지 같은 개념
      : 공유되는 백엔드에 State가 관리되면 테라폼이 실행되는 동안 .terraform.tfstate.lock.info 파일이 생성되면서 해당 State를 동시에 사용하지 못하도록 잠금 처리

    • 다른 터미널에서 terraform apply 시 아래와 같이 .terraform.tfstate.lock.info 확인 가능

terraform apply

 

★ 리소스 블록

- 컴퓨팅 인스턴스, 가상 네트워크, 데이터베이스, 버킷 또는 DNS와 같은 리소스 관리

- 실제 리소스를 나타내기 때문에 중요

 

  • 리소스 구성
    - 리소스 선언 : 리소스 유형(프로바이더 이름_제공리소스유형), 동일한 유형에 대한 식별자 역할로 고유한 이름, 구성 인수들이 이름 뒤에 중괄호 내에 선언
resource "<리소스 유형>" "<이름>" {
  <인수> = <값>
}

 

  • 리소스 동작 보조 추가 메타인수
depends_on 종속성을 선언하며, 선언된 구성요소와의 생성 시점에 대해 정의
count 선언된 개수에 따라 여러 리소스를 생성
for_each map 또는 set 타입의 데이터 배열의 값을 기준으로 여러 리소스 생성
provider 동일한 프로바이더가 다수 정의되어 있는 경우 지정
lifecycle 리소스의 수명주기 관리
provisioner 리소스 생성 후 추가 작업 정의
timeouts 프로바이더에서 정의한 일부 리소스 유형에서는 create, update, delete에 대한 허용 시간 정의 가능

 

  • 종속성
    - resource, module 선언으로 프로비저닝되는 각 요소의 생성 순서를 구분
    - 기본적으로 자동으로 연관 관계가 정의되는 암시적 종속성을 갖게 되고, 강제로 리소스 간 명시적 종속성을 부여할 경우에는 메타인수인 depends_on을 활용

  • 리소스 속성 참조
    - 리소스 구성에서 참조 가능한 값은 인수와 속성
    : 인수 > 리소스 생성 시 사용자가 선언하는 값
    : 속성 > 사용자가 설정하는 것은 불가능하지만 리소스 생성 이후 획득 가능한 리소스 고유 값
더보기

kubernetes_namespace.example.metadata.0.name #namespace 리소스 인수 참조

 


★ help & init 초기화

  • help 옵션

# terraform console -help

# terraform init -help

  • init 초기화
# 테라폼 실행을 위해 코드 파일이 있는 디렉터리로 이동
# (참고) 테라폼이 실행되는 디렉터리 = 모듈(테라폼 코드 파일과 변수 파일), 기본 작업디렉터리는 '루트 모듈', 호출 모듈은 '자식 모듈'
cd 03.start/

# plan 실행 시 에러 출력 > 에러 메시지의 의미는?
terraform plan
│ Error: Inconsistent dependency lock file
│ 
│ The following dependency selections recorded in the lock file are inconsistent with the current configuration:
│   - provider registry.terraform.io/hashicorp/local: required by this configuration but no version is selected
│ 
│ To make the initial dependency selections that will initialize the dependency lock file, run:
│   terraform init

# 초기화 : 코드 사용 구문 기반으로 필요한 프로바이더 플러그인을 찾고 설치, 추가로 '프로바이더/모듈/백엔드' 구성 설정/변경 시 수행 필요
terraform init
ls -al
tree .terraform  # VS Code에서 탐색기 확인

 

 

★ validate 테라폼 구성 파일 유효성 확인

  • 디렉터리에 있는 테라폼 구성 파일의 유효성 확인. API작업은 발생하지 않고 코드적인 유효성만 검토
  • API 작업이 발생하는 테라폼 Plan 동작과 달리 작성된 구성의 문법, 종속성, 속성 이름이나 연결된 값의 정확성 확인

 

★ terraform fmt

  • fmt : format 또는 reformat 줄임 표시로 terraform tmt 명령어로 수행, 코드 가독성 높임

terraform fmt

 

★ terraform 명령어

terraform init 프로젝트 초기화하는데 사용
(실행한 경로에 .terraform파일이 생성되며 지정한 Provider에 해당하는 파일 다운로드)
terraform plan HCL로 작성한 인프라에 대한 생성 계획을 보여줌
terraform apply HCL로 작성한 인프라에 대한 생성 계획을 보여주고, 생성 여부 확인(yes 입력 시 인프라 생성)
(인프라가 생성, 변경되었을 경우 해당 상태를 terraform.state라는 파일을 통해서 관리)
terraform destory 만들어진 인프라 삭제
apply와 반대로 삭제되는 리소스 조회 후 yes 입력하면 삭제 진행