"서버 어떻게 만들었더라?" - IaC(Infrastructure as Code)란 무엇인가

댓글 0
댓글을 작성하려면 로그인이 필요합니다.
아직 댓글이 없습니다. 첫 번째 댓글을 작성해보세요!
AWS 콘솔에 접속해서 EC2를 하나 만들었다. 보안 그룹도 설정하고, S3 버킷도 만들었다. 잘 돌아간다. 그런데 같은 환경을 하나 더 만들어야 한다면? 콘솔을 열어서 똑같은 작업을 처음부터 다시 해야 한다.
여기서 문제가 시작된다. 클릭으로 만든 인프라는 기록이 남지 않는다. 무엇을 어떤 순서로 설정했는지 기억에 의존해야 하고, 사람이 반복하면 실수가 생긴다. IaC는 이 문제를 해결하기 위한 접근 방식이다.
이 글에서는 IaC가 무엇인지, 왜 필요한지, 그리고 어떤 도구들이 있는지 기초부터 정리한다.

클라우드 콘솔에서 리소스를 직접 만드는 방식은 처음에는 직관적이다. 화면에서 옵션을 선택하고 버튼을 누르면 된다. 하지만 이 방식은 규모가 커질수록 문제가 드러난다.
첫째, 재현이 어렵다. 동일한 환경을 다시 만들려면 이전에 어떤 설정을 했는지 정확히 기억해야 한다. 문서로 남겨둔다 해도 콘솔 UI가 바뀌거나 옵션이 추가되면 문서가 금방 낡는다.
둘째, 변경 추적이 안 된다. 누가, 언제, 어떤 설정을 바꿨는지 알 수 없다. 장애가 발생했을 때 원인을 추적하기 어렵고, 이전 상태로 되돌리는 것도 쉽지 않다.
셋째, 협업이 힘들다. 한 사람이 콘솔에서 작업하는 동안 다른 사람이 같은 리소스를 건드리면 충돌이 생긴다. 리뷰 과정도 없기 때문에 실수가 그대로 반영된다.

IaC(Infrastructure as Code)는 서버, 네트워크, 데이터베이스 같은 인프라를 코드 파일로 정의하고 관리하는 방식이다. 콘솔에서 클릭하는 대신, 텍스트 파일에 원하는 인프라 상태를 선언한다.
예를 들어 "t3.micro 인스턴스를 ap-northeast-2에 만들고, 80번 포트를 열어라"를 코드로 작성하면, 도구가 이를 읽고 실제 인프라를 생성한다.
인프라가 코드가 되면 소프트웨어 개발에서 당연하게 쓰는 방식들을 그대로 적용할 수 있다.
IaC 도구는 크게 두 가지 접근 방식으로 나뉜다.
**"이런 상태가 되어야 한다"**를 정의한다. 현재 상태가 어떻든, 도구가 알아서 원하는 상태로 맞춰준다.
resource "aws_instance" "web" {
ami = "ami-0c55b159cbfafe1f0"
instance_type = "t3.micro"
tags = {
Name = "web-server"
}
}
위 코드는 Terraform 문법이다. "이 스펙의 EC2 인스턴스가 존재해야 한다"고 선언하면, Terraform이 현재 상태를 확인하고 필요한 변경만 수행한다. 이미 존재하면 건드리지 않고, 없으면 생성하고, 스펙이 다르면 수정한다.
**"이 순서대로 실행해라"**를 정의한다. 어떤 동작을 어떤 순서로 수행할지 직접 지정한다.
- name: Install nginx
apt:
name: nginx
state: present
- name: Start nginx
service:
name: nginx
state: started
위는 Ansible의 플레이북 예시다. "nginx를 설치하고, 서비스를 시작해라"는 절차를 순서대로 기술한다.

선언형과 명령형이 완전히 분리되는 건 아니다. 대부분의 도구가 두 가지 특성을 어느 정도 함께 갖고 있다. 다만 일반적으로 인프라 프로비저닝에는 선언형, 서버 내부 설정에는 명령형이 더 자주 쓰인다.
| 구분 | 선언형 | 명령형 |
|---|---|---|
| 관점 | 원하는 상태 | 실행할 절차 |
| 멱등성 | 도구가 보장 | 직접 관리 필요 |
| 대표 도구 | Terraform, CloudFormation | Ansible, Shell Script |
| 주 용도 | 인프라 리소스 생성/관리 | 서버 설정/배포 |
HashiCorp에서 만든 오픈소스 도구로, IaC 하면 가장 먼저 떠오르는 도구다. AWS, GCP, Azure 등 다양한 클라우드 프로바이더를 하나의 문법(HCL)으로 관리할 수 있다.
특징:
plan 명령으로 실제 적용 전에 어떤 변경이 일어날지 미리 확인할 수 있다.AWS에서 제공하는 IaC 서비스다. AWS 리소스만 다루지만, AWS와의 통합이 가장 깊다.
특징:
서버 설정 관리에 강점이 있는 도구다. SSH로 접속해서 명령을 실행하는 방식이라 에이전트 설치가 필요 없다.
특징:

정답은 없지만, 인프라 리소스를 코드로 관리하는 경험을 쌓고 싶다면 Terraform부터 시작하는 게 무난하다. 클라우드에 종속되지 않고, 커뮤니티와 레퍼런스가 풍부하며, plan → apply의 워크플로우가 IaC의 핵심 개념을 이해하기에 적합하다.
실제로 IaC가 어떻게 동작하는지 Terraform의 기본 흐름으로 살펴본다.
원하는 인프라를 .tf 파일에 정의한다.
provider "aws" {
region = "ap-northeast-2"
}
resource "aws_s3_bucket" "assets" {
bucket = "my-app-assets-bucket"
tags = {
Environment = "production"
}
}
terraform init
프로바이더 플러그인을 다운로드하고 작업 디렉토리를 초기화한다.
terraform plan
현재 상태와 코드를 비교해서 어떤 변경이 일어날지 보여준다. 실제로 반영되는 건 아니다. 이 단계에서 의도하지 않은 변경이 없는지 확인할 수 있다.
terraform apply
plan에서 확인한 변경 사항을 실제로 적용한다. 승인을 거쳐 인프라가 생성되거나 수정된다.
terraform destroy
코드로 관리 중인 인프라를 전부 삭제한다. 테스트 환경을 빠르게 만들었다가 정리할 때 유용하다.
이 init → plan → apply 사이클이 Terraform 사용의 기본이고, IaC 워크플로우의 핵심이다.
Terraform은 상태 파일(.tfstate)로 현재 인프라가 어떤 상태인지 추적한다. 이 파일이 꼬이면 실제 인프라와 코드가 어긋나게 된다. 혼자 작업할 때는 로컬에 두어도 되지만, 팀으로 작업한다면 S3 같은 원격 저장소에 상태 파일을 관리하는 것이 좋다.
비슷한 인프라 구성이 반복되면 모듈로 분리한다. 예를 들어 VPC 구성, EC2 인스턴스 구성을 모듈로 만들어두면 여러 환경(dev, staging, production)에서 재사용할 수 있다.
IaC를 도입한 뒤에 콘솔에서 직접 리소스를 수정하면 상태 파일과 실제 인프라가 달라진다. 이걸 **드리프트(drift)**라고 한다. IaC로 관리하기로 한 리소스는 반드시 코드를 통해서만 변경해야 한다.
인프라를 콘솔에서 클릭으로 관리하는 건 빠르고 직관적이지만, 규모가 커지면 한계가 분명하다. IaC는 인프라를 코드로 정의해서 버전 관리, 리뷰, 재현, 자동화를 가능하게 하는 접근 방식이다.
처음부터 모든 인프라를 코드로 옮길 필요는 없다. 지금 관리하고 있는 리소스 중 하나를 골라서 Terraform 코드로 작성해보는 것부터 시작하면 된다. terraform plan을 한 번 실행해보면, 콘솔에서는 볼 수 없었던 인프라의 전체 그림이 보이기 시작한다.