데이터 엔지니어 · AI 엔지니어를 위한 핵심 요약
Terraform은 HashiCorp에서 개발한 오픈소스 IaC(Infrastructure as Code) 도구로, 선언형 언어(HCL)를 사용하여 클라우드 및 온프레미스 인프라를 안전하고 반복 가능하게 프로비저닝합니다. 데이터 엔지니어와 AI 엔지니어는 복잡한 인프라를 코드로 관리하고, 멀티 클라우드 환경에서 일관된 워크플로를 유지할 수 있습니다.
원하는 상태를 코드로 작성하면 Terraform이 현재 상태와 비교하여 필요한 변경만 실행합니다. 멱등성(Idempotent) 보장.
.tfstate 파일로 인프라의 실제 상태를 추적합니다. 팀 협업 시 원격 백엔드(S3, Terraform Cloud)와 함께 사용.
AWS, Azure, GCP, Kubernetes 등 2000+ 프로바이더를 단일 워크플로로 관리. 데이터 파이프라인, AI 클러스터를 유연하게 구성.
기존 방법(수동 설정, 스크립트, 구성 관리 도구)과 비교한 Terraform의 강점을 표로 정리했습니다.
| 기능 | 수동 설정 | Ansible / Puppet | AWS CloudFormation | Terraform |
|---|---|---|---|---|
| 선언형 | ❌ | 절차형 혼합 | ✅ | ✅ (HCL) |
| 멀티 클라우드 | 매우 어려움 | 가능 (별도 모듈) | AWS 전용 | ✅ 내장 |
| 상태 관리 | ❌ | ❌ (일부) | 스택 기반 | ✅ .tfstate |
| Dry-run (계획) | ❌ | --check | Change Set | ✅ terraform plan |
| 모듈 재사용 | ❌ | Role/Playbook | Nested Stack | ✅ Registry |
Terraform의 워크플로우와 주요 구성 요소를 ASCII 다이어그램으로 시각화했습니다.
핵심 용어
hashicorp/aws).aws_s3_bucket).macOS (Homebrew), Linux (apt/yum), Windows (choco) 등 환경에 맞게 설치합니다.
# macOS
brew install hashicorp/tap/terraform
# Linux (Debian/Ubuntu)
wget -O- https://apt.releases.hashicorp.com/gpg | sudo gpg --dearmor -o /usr/share/keyrings/hashicorp-archive-keyring.gpg
echo "deb [signed-by=/usr/share/keyrings/hashicorp-archive-keyring.gpg] https://apt.releases.hashicorp.com $(lsb_release -cs) main" | sudo tee /etc/apt/sources.list.d/hashicorp.list
sudo apt update && sudo apt install terraform
# 버전 확인
terraform --version
main.tf 파일을 생성하고 아래 내용을 작성합니다.
# main.tf
terraform {
required_providers {
aws = {
source = "hashicorp/aws"
version = "~> 5.0"
}
}
}
provider "aws" {
region = "ap-northeast-2"
}
resource "aws_s3_bucket" "data_lake" {
bucket = "my-data-lake-202603"
tags = {
Name = "DataLake"
Environment = "dev"
}
}
# 초기화 (프로바이더 다운로드)
terraform init
# 실행 계획 확인
terraform plan
# 인프라 적용
terraform apply # "yes" 입력
# 리소스 확인
terraform state list
# 인프라 제거 (주의!)
terraform destroy
다음은 Python 서브프로세스로 Terraform output을 읽어서 S3 버킷 이름을 가져오는 예제입니다.
import subprocess
import json
def get_terraform_output(output_name):
result = subprocess.run(
["terraform", "output", "-json"],
capture_output=True,
text=True,
check=True
)
outputs = json.loads(result.stdout)
return outputs.get(output_name, {}).get("value")
bucket_name = get_terraform_output("bucket_arn")
print(f"생성된 버킷 ARN: {bucket_name}")
파이썬 라이브러리 python-terraform을 사용하면 더 정교한 제어가 가능합니다:
# pip install python-terraform
from python_terraform import Terraform
tf = Terraform()
return_code, stdout, stderr = tf.plan()
print(stdout)
Terraform 코드를 작성할 때 자주 사용하는 블록과 그 역할을 요약한 표입니다.
| 블록 | 설명 | 예시 |
|---|---|---|
terraform {} |
백엔드, 프로바이더 버전, 필수 설정 정의 | backend "s3" { bucket = "tfstate" } |
provider |
클라우드 프로바이더 인증 및 리전 설정 | provider "aws" { region = "us-east-1" } |
resource |
실제 인프라 리소스 생성 | resource "aws_instance" "web" { ... } |
data |
기존 리소스 정보 조회 (읽기 전용) | data "aws_ami" "ubuntu" { ... } |
variable |
입력 변수 선언 (유효성 검사 가능) | variable "env" { default = "dev" } |
output |
적용 후 결과값 노출 (예: IP, ARN) | output "bucket_arn" { value = aws_s3_bucket.data.arn } |
module |
외부 모듈 호출 (재사용) | module "vpc" { source = "terraform-aws-modules/vpc/aws" } |
locals |
지역 변수로 반복 계산 방지 | locals { name_prefix = "myapp-${var.env}" } |
resource 블록의 prevent_destroy = true 속성을 사용하면 실수로 중요한 리소스가 삭제되는 것을 방지할 수 있습니다.
| 문제 | 원인 | 해결 방법 |
|---|---|---|
| State Lock 충돌 | 여러 사용자가 동시에 apply | DynamoDB 테이블을 lock 대상으로 설정 (S3 백엔드) |
| Provider 호환성 오류 | 버전 제약이 너무 좁음 | version = "~> 5.0"처럼 유연한 범위 사용 |
| 민감 정보 노출 | state 파일에 plain text로 저장 | sensitive = true 변수 사용, state 암호화 |
| 리소스 의존성 누락 | 명시적 의존성이 없음 | depends_on 메타 인자로 강제 연결 |
| terraform plan/apply 느림 | 리소스 수가 많거나 refresh 병목 | -refresh=false 또는 target 사용 |
terraform import.subprocess로 terraform output -json을 호출해 인프라 정보를 파이썬 애플리케이션에 전달하거나, python-terraform 라이브러리로 plan/apply를 자동화할 수 있습니다.
Terraform을 더 깊이 학습하기 위한 공식 문서와 유용한 링크입니다.