배경
Terraform을 로컬에서만 사용하다가 Cloud 환경으로 옮기면, 누가 어느 환경에 apply했는지와 state를 어디에서 관리하는지가 중요해진다. 이 노트는 Terraform Cloud를 사용하면서 workspace, 변수, run, import를 어떻게 연결해서 이해하면 되는지 정리한다.
Terraform Cloud는 현재 HCP Terraform이라는 이름으로 제공된다. 여기서는 기존에 익숙한 Terraform Cloud라는 표현을 사용하되, 공식 문서의 HCP Terraform과 같은 서비스를 가리킨다.
개념
HCP Terraform은 Terraform 실행, state, 변수, 실행 이력을 workspace 단위로 관리하는 협업 환경이다. AWS CLI의 profile이 계정·region·자격 증명 대상을 나누는 데 도움을 주듯, HCP Terraform에서는 organization과 workspace를 통해 어떤 인프라 묶음에 대해 작업하는지 명확히 한다.
다만 workspace는 단순한 CLI profile이나 Jenkins Pipeline 하나와 완전히 같지는 않다. 하나의 workspace는 특정 인프라 구성의 코드, 입력 변수, state, run 이력을 함께 관리하는 단위다.
Terraform Cloud 장점
- state를 개인 로컬 파일이 아니라 workspace별로 관리하고 이전 버전도 확인할 수 있다.
- VCS와 연결하면 변경 사항을 기준으로 plan과 apply 흐름을 남길 수 있다.
- Terraform 변수와 환경 변수를 workspace에서 관리하고 민감값을 분리할 수 있다.
- run 로그와 변경 이력을 한 곳에서 확인할 수 있어, 팀에서 “누가 어떤 코드로 적용했는가”를 추적하기 쉽다.
- 지원되는 Provider와 요금제에서는 Plan 기준으로 예상 월 비용과 증감분을 유추할 수 있다. 실제 청구 금액과 동일하다는 뜻은 아니다.
처음 CLI를 연결할 때는 terraform login을 사용한다. 브라우저가 열리면 account settings에서 발급한 user token을 CLI에 등록한다.
terraform loginroot module에는 organization과 workspace를 연결하는 cloud block을 둔다.
terraform {
cloud {
organization = "example-org"
workspaces {
name = "network-dev"
}
}
}# Terraform 설정이 있는 환경 경로에서 실행
terraform initLocal Plan
CLI-driven 방식에서는 로컬에서 terraform plan을 실행한다. 다만 이 말이 무조건 로컬에서 Plan이 동작한다는 뜻은 아니다.
- Workspace의 실행 모드가
Remote이면 로컬 명령을 통해 HCP Terraform에 Run을 만들고 실제 Plan과 Apply는 Remote 환경에서 실행한다. - 실행 모드가
Local이면 Terraform CLI가 로컬에서 실행되고 State만 HCP Terraform Workspace에 저장된다.
실무에서는 Pull Request에서 plan 결과를 확인하고, 승인된 변경만 apply하도록 나누는 흐름이 안전하다. 로컬에서 plan을 보더라도 같은 workspace의 state를 사용하므로, 어떤 workspace를 대상으로 실행하는지 먼저 확인해야 한다.
Terraform 단일 사용과의 차이점
| 항목 | Terraform CLI만 사용 | HCP Terraform 사용 |
|---|---|---|
| 실행 위치 | 로컬 개발자 환경 또는 별도 CI | workspace의 remote run 또는 연결한 CLI |
| state | 로컬 또는 별도 backend를 직접 구성 | workspace별 state와 이전 version 관리 |
| 변수·비밀값 | .tfvars, 환경 변수, CI secret 등으로 관리 | workspace 변수와 sensitive 설정으로 관리 |
| 실행 이력 | CI 로그와 개별 로컬 기록에 의존 | run별 plan/apply 로그와 구성 버전을 함께 확인 |
Projects
Project는 관련 workspace를 묶는 상위 단위다. 예를 들어 하나의 서비스에서 network, application, monitoring을 각각 workspace로 나누고, 같은 팀이나 서비스 단위의 Project로 묶을 수 있다. Project 단위의 권한을 이용하면 workspace를 하나씩 관리하지 않아도 되는 경우가 있다.
Workspaces
Workspace는 하나의 인프라 구성 단위를 관리한다. Jenkins Pipeline 하나와 비슷하게 보일 수 있지만, Pipeline 자체라기보다 해당 인프라의 state·변수·실행 이력을 가진 작업 공간에 가깝다.
Bitbucket 같은 VCS와 연결하면 저장소와 working directory를 지정할 수 있다. 지정한 경로의 Terraform 코드가 변경되면 run을 만들고, plan 결과와 알림을 확인하는 흐름으로 사용할 수 있다. 환경별로 디렉터리를 나눈 경우에는 dev와 prod가 같은 workspace를 공유하지 않도록 working directory와 workspace를 명확히 분리한다.
States
State는 Terraform 코드와 실제 리소스의 연결 정보를 보관한다. HCP Terraform에서는 workspace별 state와 이전 state version을 관리한다. state에 민감 정보가 포함될 수 있으므로, workspace 접근 권한과 state 다운로드 권한을 필요한 인원으로 제한해야 한다.
Import
기존에 만들어져 있지만 Terraform이 아직 관리하지 않는 리소스는 import로 state에 등록한다. 먼저 resource block을 코드에 작성하고 import block을 추가한 뒤, plan으로 예상 변경을 확인하고 apply한다.
resource "aws_s3_bucket" "logs" {
bucket = "example-logs"
}
import {
to = aws_s3_bucket.logs
id = "example-logs"
}import와 moved는 목적이 다르다. import는 새로 state에 등록하는 작업이고, moved는 이미 state에 있는 리소스의 주소를 리팩터링으로 바꿨을 때 사용한다.
moved {
from = aws_s3_bucket.legacy_logs
to = aws_s3_bucket.logs
}HCP Terraform에서는 Search & Import 기능으로 여러 미관리 리소스를 찾고 resource·import block 초안을 만들 수도 있다. 이 기능은 workspace에서 Terraform 1.14 이상을 사용해야 하며, provider가 지원하는 list block을 구성해야 한다. 생성된 코드와 plan 결과는 적용 전에 반드시 검토한다.
Variables
Workspace에는 Terraform 입력 변수와 환경 변수를 등록할 수 있다. 비밀값은 sensitive로 등록해 화면과 로그 노출을 줄이고, 코드나 저장소의 .tfvars에 장기 자격 증명을 직접 넣지 않는다.
Dynamic Provider Credentials
AWS IAM access key를 workspace 변수에 장기간 저장하는 대신, OIDC 기반 dynamic provider credentials를 사용하면 run마다 짧은 수명의 자격 증명을 발급받을 수 있다. 이 방식은 workspace와 AWS IAM role의 권한을 분리하고, 어떤 workspace가 어떤 role을 사용할 수 있는지 제어하기 좋다.
Runs
Run은 구성 변경부터 plan, 정책 검사(사용 시), apply까지의 한 실행 단위다. VCS 연결 workspace에서는 저장소 변경으로 run을 만들 수 있고, CLI·API·UI에서도 시작할 수 있다. 모든 Terraform plan과 apply를 확인할 수 있으므로, 적용 전에는 plan의 변경 리소스와 destroy 여부를 확인하는 습관이 필요하다.
- 공식 문서: HCP Terraform Workspaces
- Import: Import existing resources
- Cost Estimation: HCP Terraform Plans and Features