Infra Architecture/Datacenter & Cloud

Datacenter & Cloud - 07. Infrastructure as Code 실천

인프라를 코드로 만드는 도구 — Terraform 실천

2014년, HashiCorp의 Mitchell Hashimoto는 — "인프라를 코드로 관리하자"는 아이디어를 담아 Terraform을 발표했다. 클라우드 콘솔에서 마우스로 VPC를 만들고 EC2를 띄우는 대신 — 텍스트 파일에 "VPC 하나, EC2 세 대"라고 적고 — terraform apply 한 줄로 전부 만드는 것. foundations 06에서 본 IaC(Infrastructure as Code) 철학이 — Terraform이라는 도구로 구체화된다. 이 글은 Terraform의 실천 — HCL 문법·state 관리·모듈·drift 감지 — 을 다룬다.

Terraform의 작동 원리

Terraform은 선언적(declarative) IaC 도구다. "내가 원하는 상태(desired state)를 코드로 적으면 — Terraform이 현재 상태(current state)를 그 목표로 맞춘다." 비유하자면 — 건축 도면(HCL 코드)을 주면 — 시공사(Terraform)가 도면대로 건물(인프라)을 짓는 것. 도면을 고치면 — 건물도 고쳐지고, 도면을 버리면 — 건물도 철거된다.

flowchart LR
    CODE["HCL 코드<br/>(.tf 파일)"] --> PLAN["terraform plan<br/>(변경 계획)"]
    PLAN --> APPLY["terraform apply<br/>(실행)"]
    APPLY --> CLOUD["클라우드<br/>(AWS/GCP/Azure)"]
    CLOUD --> STATE["state 파일<br/>(.tfstate)"]
    STATE --> CODE

HCL — Terraform의 언어

HCL(HashiCorp Configuration Language) 은 Terraform 전용 구성 언어다. JSON보다 읽기 쉽고, 프로그래밍 언어(JavaScript·Python)보다 제한적이다 — 반복문·조건문이 제한적이고, 주로 "선언"에 집중한다.

# main.tf — VPC와 EC2를 만드는 예시

provider "aws" {
  region = "ap-northeast-2"
}

resource "aws_vpc" "main" {
  cidr_block           = "10.0.0.0/16"
  enable_dns_hostnames = true

  tags = {
    Name = "my-vpc"
  }
}

resource "aws_subnet" "web" {
  vpc_id                  = aws_vpc.main.id
  cidr_block              = "10.0.1.0/24"
  availability_zone       = "ap-northeast-2a"
  map_public_ip_on_launch = true

  tags = {
    Name = "web-subnet"
  }
}

resource "aws_instance" "web" {
  ami           = "ami-0abcdef1234567890"
  instance_type = "t3.micro"
  subnet_id     = aws_subnet.web.id

  tags = {
    Name = "web-server"
  }
}

HCL의 핵심 구성 요소:

  • provider — 어느 클라우드(AWS·GCP·Azure·...)에 만들 것인가
  • resource — 만들 인프라 객체(VPC·EC2·RDS·...). 리소스 타입 + 이름 + 속성
  • variable — 입력 변수 (환경별로 다른 값)
  • output — 출력 값 (다른 모듈에서 참조)
  • data — 이미 존재하는 리소스를 읽어오기 (만드는 게 아니라 참조)

terraform plan — "무엇이 바뀔지" 미리 보기

terraform plan은 — 코드와 현재 인프라(state)를 비교해서 — "이렇게 바뀔 것"을 보여준다. 실제로 실행하지 않고 — 추가(+)/변경(~)/삭제(-)를 미리 본다.

# terraform plan 출력 예시
Terraform will perform the following actions:

  # aws_instance.web will be created
  + resource "aws_instance" "web" {
      + ami           = "ami-0abcdef1234567890"
      + instance_type = "t3.micro"
      + id            = (known after apply)
    }

  # aws_vpc.main will be created
  + resource "aws_vpc" "main" {
      + cidr_block = "10.0.0.0/16"
      + id         = (known after apply)
    }

Plan: 2 to add, 0 to change, 0 to destroy.

이 "미리 보기"가 Terraform의 핵심 안전장치다 — 실행 전에 무엇이 바뀌는지 확인하고, 실수를 잡는다.

terraform apply — 실제 실행

terraform apply는 — plan에서 보여준 변경사항을 클라우드에 실제로 적용한다. 클라우드 API를 호출해서 VPC를 만들고, EC2를 띄운다. 이 과정은 — 수십 초에서 수분(리소스 수에 따라).

state — Terraform의 기억

state 파일(terraform.tfstate) 은 — Terraform이 "내가 만든 리소스가 뭔지"를 기억하는 파일이다. 코드(HCL)와 클라우드 사이의 다리다.

  • 코드는 "이렇게 되어야 한다"를 정의
  • state는 "현재 어떻게 되어 있다"를 기록
  • Terraform은 — 코드와 state를 비교해서 차이를 만든다

state 파일이 없으면 — Terraform은 "어떤 리소스를 내가 만들었는지"를 모른다. 클라우드에 리소스가 있어도 — state에 없으면 "없는 것"으로 취급하고 — 코드에 있으면 "새로 만든다". 이 참사를 막으려면 — state를 안전하게 관리해야 한다.

원격 백엔드 — state를 클라우드에

state 파일을 로컬(terraform.tfstate)에 두면 — 팀원 간 공유가 안 되고, 잃어버리면 재앙이다. 그래서 — 원격 백엔드(remote backend) 에 state를 둔다.

# backend 설정 (S3에 state 저장)
terraform {
  backend "s3" {
    bucket         = "my-terraform-state"
    key            = "prod/terraform.tfstate"
    region         = "ap-northeast-2"
    dynamodb_table = "terraform-locks"    # 동시 실행 방지 (locking)
  }
}

S3에 state를 두면 — 팀원이 공유할 수 있고, DynamoDB로 locking하면 — 두 사람이 동시에 terraform apply하는 것을 막는다. Terraform Cloud·GitLab Managed Terraform·AWS Terraform Cloud 같은 관리형 백엔드도 있다.

state 파일에 비밀번호가 들어 있을 수 있다. VPC ID·AMI ID 같은 무해한 정보뿐 아니라 — DB 비밀번호·인증서 키 같은 민감 정보가 state에 저장될 수 있다. state 파일을 Git에 커밋하면 안 된다(보안 위험). 원격 백엔드 + 접근 제한이 필수다.

모듈 — 재사용 가능한 인프라 단위

모듈(module) 은 — Terraform 코드를 재사용 가능한 단위로 묶는 것이다. 함수나 클래스처럼 — 한 번 정의하고 여러 번 사용한다.

# 모듈 사용 예시
module "vpc" {
  source  = "terraform-aws-modules/vpc/aws"
  version = "5.0.0"

  cidr            = "10.0.0.0/16"
  azs             = ["ap-northeast-2a", "ap-northeast-2b"]
  public_subnets  = ["10.0.1.0/24", "10.0.2.0/24"]
  private_subnets = ["10.0.3.0/24", "10.0.4.0/24"]
}

Terraform Registry(registry.terraform.io)에는 — 커뮤니티가 만든 수천 개의 모듈이 있다. AWS VPC·EKS·RDS·ALB 같은 표준 패턴을 — 모듈 하나로 불러온다. 모듈은 — 일관성(모든 환경이 같은 VPC 구조)과 효율(코드 중복 감소)을 제공한다.

모듈 접근 source 형태 전형 사례
로컬 source = "./modules/vpc" 같은 저장소 내 모듈
Terraform Registry source = "terraform-aws-modules/vpc/aws" 커뮤니티 검증 모듈
Git source = "git::https://github.com/org/infra-modules" 사내 모듈 저장소
S3 source = "s3::https://s3.amazonaws.com/bucket/key" 아카이브된 모듈

drift — 코드와 현실이 어긋날 때

드리프트(drift) 는 — 코드(HCL)가 정의한 상태와 실제 클라우드의 상태가 어긋나는 현상이다. 누군가 콘솔에서 수동으로 보안 그룹을 바꾸거나, 다른 도구(Ansible)가 인스턴스를 수정하면 — drift가 발생한다.

# drift 감지 (코드와 실제 상태 비교)
terraform plan -refresh-only

-refresh-only는 — 클라우드의 실제 상태를 state에 갱신하고 — 변경 계획을 보여준다. drift가 있으면 — "~가 코드와 다르다"가 표시된다.

드리프트 관리 전략:

  • 코드로 다시 맞추기 — 콘솔 변경을 취소하고 코드를 source of truth로 복원. terraform apply가 덮어씀.
  • 코드에 반영 — 콘솔에서 한 변경이 맞으면 — 코드에 반영(commit). 둘을 일치시킴.
  • 지속적 감지 — Terraform Cloud·Atlantis 같은 도구로 정기적으로 drift를 감지.

Pulumi와 CDK — 대안 IaC 도구

Terraform이 HCL(전용 언어)을 쓰는 반면 — Pulumi(2018)와 AWS CDK(2019)는 — 범용 프로그래밍 언어(JavaScript·Python·Go·C#)로 인프라를 정의한다.

// Pulumi (TypeScript)
const vpc = new aws.ec2.Vpc("main", {
  cidrBlock: "10.0.0.0/16",
  enableDnsHostnames: true,
});
// AWS CDK (TypeScript)
const vpc = new ec2.Vpc(this, "MainVpc", {
  cidr: "10.0.0.0/16",
});

Pulumi/CDK의 장점 — 프로그래밍 언어의 전체 기능(반복문·조건문·함수·타입 시스템)을 쓸 수 있다. HCL의 제한적인 for_each·count보다 자유롭다. 단점 — 프로그래밍 능력이 필요하고, HCL보다 학습 곡선이 가파르다. Terraform이 여전히 점유율 1위지만, Pulumi/CDK가 성장 중이다.

특성 Terraform (HCL) Pulumi (Python/TS/Go) AWS CDK (TS/Python)
언어 HCL (전용) 범용 언어 범용 언어
멀티 클라우드 지원 지원 AWS 전용
학습 곡선 완만 중간 중간
점유율 1위 성장 중 AWS 생태계
상태 관리 state 파일 Pulumi Service CloudFormation

실습 — Terraform 기본

1. Terraform 설치 및 버전 확인

terraform version
terraform --help | head -5

2. 코드 검증

# 코드 문법 검사
terraform validate
# 포맷 확인
terraform fmt -check -diff
# 초기화 (provider 다운로드)
terraform init

3. 계획 및 적용

# 변경 계획 미리 보기
terraform plan
# 실제 적용
terraform apply
# 리소스 삭제
terraform destroy

4. state 확인

# state에 있는 리소스 목록
terraform state list
# 특정 리소스의 상세 정보
terraform state show aws_vpc.main

미검증: Terraform은 별도 설치 필요(apt install terraform 또는 다운로드). 클라우드 자격증명(AWS CLI 설정)이 있어야 apply가 동작.

Terraform은 "코드로 인프라를"의 실천이다

Terraform을 이해하면 — foundations 06의 IaC 철학이 어떻게 실제 도구로 구현되는지가 보인다. 코드로 VPC를 만들고, state로 상태를 추적하고, 모듈로 재사용하고, plan으로 안전하게 변경한다. "콘솔에서 클릭하는" 방식과 비교해 — 일관성·추적 가능성·재현 가능성을 얻는다. 단점은 — HCL 학습과 state 관리의 복잡성. 하지만 — 현대 인프라 관리에서 Terraform(또는 동급 IaC 도구)은 선택이 아닌 기본이다.

다음 글에서는 — Terraform으로 만든 인프라 위에서 동작하는 애플리케이션 패러다임을 다룬다 — Cloud Native 플랫폼. CNCF 생태·선언적 인프라·GitOps·Service Mesh가 "왜 클라우드 네이티브로 가나"라는 질문에 답한다.


참고

  • HashiCorp, "Terraform Documentation" — 공식 문서. 접근 2026-07-21. URL: https://developer.hashicorp.com/terraform/docs
  • Brikman, Y. "Terraform: Up & Running" 3rd ed, O'Reilly, 2022 — Terraform 실전 가이드. 접근 2026-07-21
  • Pulumi, "Pulumi Documentation" — 범용 언어 IaC. 접근 2026-07-21. URL: https://www.pulumi.com/docs/
  • AWS, "AWS CDK Documentation" — 클라우드 개발 키트. 접근 2026-07-21
  • Morris, K. "Infrastructure as Code" 2nd ed, O'Reilly, 2020 — IaC 철학. 접근 2026-07-21
  • Terraform Registry — 커뮤니티 모듈. 접근 2026-07-21. URL: https://registry.terraform.io/