Terraform 및 Terraform IBM Provider

클라우드 시스템이 도입 되기 전에는 하나의 서비스를 운영하기 위해 하드웨어를 설치하고, 그 위에 OS, WAS, DB 등의 소프트웨어 플랫폼 및 기타 필요한 소프트웨어를 설치한 후 서비스를 위한 어플리케이션을 설치하였습니다. 그러나, 클라우드 환경에서는 하드웨어의 경우 몇번의 클릭만을 통해 생성할 수 있는 VM이나 컨테이너 형태가 많이 사용되고 있고, 소프트웨어 또한 PaaS나 SaaS 형태로 제공되는 서비스들을 클릭 몇 번을 통하여 생성하여 사용할 수 있게 되었습니다. 또한, 서비스 개발 방법도 최근에는 기존의 덩치가 큰 하나의 어플리케이션(Monolithic)으로 작성되던 것들이 개발 편의성, 효율성, 성능 등의 이유로 작은 독립적인 서비스로 만들어서 운영하는 MSA(Micro-Service Architecture) 형태로 변화하게 되었습니다. 이런 MSA 환경은 단일 서비스가 아니라 여러개의 다양한 서비스들이 배포되어야 하고, 이러한 서비스들이 시스템 부하에 따라 동적으로 증가했다가 감소하도록 할 수 있습니다. 하지만, 이로 인한 VM 및 컨테이너를 위한 인프라웨어 관리 및 개발된 서비스들을 관리하기 위한 복잡도가 증가하게 되었습니다. 이러한 복잡도 문제를 해결하기 위해 코드로 인프라를 관리하는 Infrastructure as code(IaC)에 대한 개념이 등장하게 되었고, 이러한 IaC는 아래와 같은 장점을 가지고 기존의 문제를 보완하고 있습니다.

  • 상황에 맞는 다양한 인프라 및 PaaS 등을 동적으로 구성할 수 있음.
  • 자동화를 통해 사람에 의해 수동으로 구성시 발생하는 실수를 줄일 수 있음.
  • 형상 관리가 가능해져서 변경 관리 및 재사용이 용이함.

이러한 IaC를 지원하는 아래와 같은 다양한 툴들이 등장하게 되었습니다.

  • Terraform
  • Ansible
  • Chef
  • Puppet

본 문서에서는 이러한 IaC 툴들 중 Terraform에 대해 살펴보고 Terraform을 이용하여 IBM Cloud 서비스를 관리하는 방법에 대해 알아보려 합니다.

Terraform

Terraform(https://www.terraform.io) 은 HashiCorp(https://www.hashicorp.com) 에서 만든 오픈소스(https://github.com/hashicorp/terraform) 인프라 관리 도구 입니다. Terraform은 아래와 같은 기능을 지원하고 있습니다.

  • HCL(Hashicorp Configuration Language) 및 json을 이용하여 configuration파일을 작성하여 인프라를 정의 할 수 있음.
  • Terraform과 여러 외부 서비스를 연결해주는 provider라고 불리는 plugin 모듈이 있으며, 여러 종류의 Provider를 통해 IBM Cloud, AWS, Azure 등의 다양한 클라우드 지원 가능. (https://www.terraform.io/docs/providers/index.html)
  • state파일을 통해 기존에 프로비저닝한 상태를 저장하고, configuration파일에서 변경된 내용만 반영하여 효율적인 프로비저닝이 가능하며, state file의 공유를 통해 협업이나 자동화가 가능함.
  • 플래닝 단계를 가지고 있어서 어떤 부분이 변경될지 미리 확인할 수 있음.
  • 리소스간의 디펜던시를 명시할 수 있어서, 연관되지 않은 리소스는 병렬로 프로비저닝할 수 있음.

Terrafrom 설치 방법

설치는 binary를 직접 받아서 path를 지정하거나 소스를 받아 빌드하는 수동 설치 방법과 각 OS 별 패키지 설치 툴을 이용하는 방법이 있습니다. 자세한 설치는 링크 를 확인하시기 바랍니다.

수동 설치

  • 사용하시는 플랫폼에 맞는 파일을 다운로드 사이트(https://www.terraform.io/downloads.html) 에서 받으신 후 압축을 풀고 해당 디렉토리를 PATH에 추가해 주시면 됩니다.

  • github(https://github.com/hashicorp/terraform) 에서 소스를 직접 받으셔서 컴파일 하여 설치할 수도 있습니다. 테라폼은 go language를 사용하여 구현이 되어 있습니다. 따라서, 컴파일을 하기 위해서는 go language를 빌드하기 위한 GOPATH등의 빌드 환경이 구성되어 있어야 합니다. 설치는 다운 받으신 git 디렉토리로 이동하여 아래의 명령어를 통해 하실 수 있습니다.

go install

OS의 패키지 툴을 이용한 설치

  • MAC OSX : osx 머신의 경우 아래와 같이 homebrew를 이용하여 설치할수 있습니다.
brew install terraform
  • Windows : windows 머신의 경우 아래와 choloatey를 이용하여 설치할 수 있습니다.
choco install terraform

Terraform 실행

terraform은 아래 과정을 통해 실행이 됩니다..

  1. 우선 infrastucture를 정의한 configuration file을 생성합니다.
  2. “terraform init”을 통해 플러그인 설정 및 terraform 실행 준비합니다.
  3. “terraform plan” 명령어를 이용하여 변경되는 정보 확인할 수 있습니다.
  4. “terraform apply” 명령어로 인프라 생성 및 변경합니다. 최종적으로 tfstate 파일이 생성이 되며, 이를 통해 추가 및 변경에 대한 관리가 가능합니다.

Terraform configration file

인프라에 대한 정의를 담고 있는 configuration 파일은 variable, provider, data, resource, output 과 같은 항목으로 구성이 됩니다. 각각에 대해 좀 더 자세히 살펴 보겠습니다.

variable

변수 정의

인프라 관리시 필요한 정보를 변수를 통해 설정 할수 있습니다. 이러한 변수는 아래의 여러가지 방법을 통해 정의 될 수 있습니다.

  • variable 키워드를 통한 정의
variable "test_variable" {}
  • terrafrom.tfvars, terraform.tfvars.json, .auto.tfvars, .auto.tfvars.json 파일 정의
variable_from_file = "This is variable test from file"
  • command line에서의 -var 옵션을 통한 직접 정의 및 -var-file을 통한 var file 지정 정의
terraform apply -var foo=bar
terraform apply -var-file=foo.tfvars
  • TFVAR prefix를 이용한 환경 변수로 정의
export TF_VAR_variable_from_env="variable from env"
변수 사용

변수는 configuration file에서 var.* 를 통해 변수에 접근할수 있습니다.

output "variable_from_env" { 
  value = var.variable_from_env
}

provider

대부분의 cloud를 위한 provider들이 존재하고 있습니다. 이러한 provider에 대한 설정은 아래와 같이 지정하실수 있습니다.

provider "ibm" {
  ibmcloud_api_key = var.ibmcloud_api_key
  region = var.region
}

IBM provider의 경우 ibmcloud_api_key를 이용하여 login 할수 있으며, 클래식 infrastructure를 사용하실 때에는 iaas_classic_username/iaas_classic_api_key를 입력하셔야 합니다. 또한, region 을 통해 resource를 만들기 위한 region을 설정 할 수 있습니다.

data

각 provider는 data를 위해 미리 정의된 값들이 있습니다. 이런 data를 이용하여 provider에서 정의된 값들을 읽어 올 수 있습니다. 예를 들어 아래 코드는 IBM provider 에서 제공하는 Cloud Foundry의 data를 이용하여 organization과 space 이름을 입력하여 각각의 id를 얻어 오는 예제입니다.

variable ibmcloud_api_key {}
variable region {}
variable org {}
variable space {}

provider "ibm" {
  ibmcloud_api_key = var.ibmcloud_api_key
  region = var.region
}

data "ibm_org" "org" {
  org = var.org
}

data "ibm_space" "space" {
  space = var.space
  org   = var.org
}

output "orgdata" { 
  value = data.ibm_org.org.id
}

output "spacedata" { 
  value = data.ibm_space.space.id
}

resource

인프라를 구성하는 요소인 네트워크, 인스턴스, 블럭 스토리지, DNS, DB서비스 등을 정의하기 위한 것입니다. 리소스로 정의된 내용은 apply를 통해 새로 생성이 되거나 이미 생성된 내용이 있으면 변경이 됩니다. 아래의 예는 IBM Cloud에서 사용자 인증 관련 appid 서비스를 생성하는 코드입니다.

variable resource_name {}
variable resource_plan {}
variable resource_location {}

resource "ibm_resource_instance" "appid_instance" {
  name     = var.resource_name
  service  = "appid"
  plan     = var.resource_plan
  location = var.resource_location
}

output "appid_id" {
  depends_on = ["ibm_resource_instance.appid_instance"]
  value      = "${ibm_resource_instance.appid_instance.id}"
}

output

variable, data, resource에 대한 실행 결과 중 필요한 내용을 output으로 저장할수 있습니다. 이러한 저장된 내용은 다른 시스템에서 활용할 수 있습니다. 예를 들어, terrafrom으로 생성된 인프라에 자동적으로 연결하기 위한 시스템이 구축되어 있다면, output을 통해 시스템에 인프라의 내용을 자동으로 추가하기 위한 구현을 할 수 있습니다. ouput에 대한 예제는 위의 다른 확인하실 수 있습니다.

terraform 명령어

terraform 사용시 자주사용하는 명령어는 아래와 같습니다.

  • terraform init : terraform 디렉토리를 초기화 합니다. 사용된 plugin 등을 설치하여 terraform 실행을 위한 준비를 합니다.
  • terraform apply : tf 파일을 기반으로 인프라를 생성을 하거나 변경을 반영합니다.
  • terraform plan : terraform 디렉토리에 대한 변경 내용을 확입할 수 있습니다.
  • terraform validate : terraform 디렉토리의 유효성을 검증합니다.
  • terraform destory : tf 파일을 통해 만들어진 인프라를 모두 삭제 합니다.

일반적으로 terraform init 실행 후 terraform apply를 이용하여 인프라를 생성하거나 업데이트를 하고, terraform destroy를 이용하여 인프라를 삭제하는 명령어를 많이 사용합니다.

이 외에도 여러가지 명령어 들이 있습니다. “terraform” 명령어를 이용하여 다른 명령어들을 확인 하실수 있습니다.

Terraform IBM Provider

terraform provider중에 IBM Cloud제품 (https://cloud.ibm.com) 을 지원하기 위한 provider가 있습니다. (https://github.com/IBM-Cloud/terraform-provider-ibm) IBM Cloud에서 제공하는 classic infrastructure, Cloun foundary(CF)와 IAM 서비스들, IBM Cloud functions, kubernetes 와 파워 시스템, VPC infrastructure 등을 생성하실수 있습니다.

설치 방법

설치는 빌드된 provider를 다운 받거나 빌드를 통해 설치할수 있습니다.

  • provider 다운로드 : https://github.com/IBM-Cloud/terraform-provider-ibm/releases 으로 가셔서 사용하시는 플랫폼에 맞는 바이너리를 다운로드 받습니다. zip 파일 압축을 해제하시면 terraform-provider-ibm_vX.Y.Z 형태의 바이너리가 있고, 이를 아래의 플랫폼에 맞는 plugin 디렉토리로 복사를 하시면 됩니다.
Linux/Unix/OS X: ~/.terraform.d/plugins
Windows: %APPDATA%\terraform.d\plugins
  • 빌드 통한 설치 : 빌드는 terraform과 마찬가지로 go language를 사용합니다. $GOPATH/src/github.com/IBM-Cloud 에 git clone을 이용하여 git@github.com:IBM-Cloud/terraform-provider-ibm.git의 소스를 받으신 후 make biuld를 하시면 됩니다. 자세한 명령어는 아래 참고 하시기 바랍니다.
mkdir -p $GOPATH/src/github.com/IBM-Cloud; cd $GOPATH/src/github.com/IBM-Cloud
git clone git@github.com:IBM-Cloud/terraform-provider-ibm.git
Enter the provider directory and build the provider

cd $GOPATH/src/github.com/IBM-Cloud/terraform-provider-ibm
make build

.tf 파일 생성 방법

인증 설정

생성을 위한 리소스에 따라 인증에 필요한 정보가 다릅니다. 필요한 리소스에 따라 각 정보를 확인하시기 바랍니다.

  • class infrastructure 를 위한 인증 정보
provider "ibm" {
    ibmcloud_api_key = <IBM Cloud API key>
    iaas_classic_username = <user name for classic infrastructure>
    iaas_classic_api_key = <API Key for class infrastructure>
    region = <IBM Cloud region>
}
  • CF 및 IAM 서비스를 위한 인증 정보
provider "ibm" {
  ibmcloud_api_key = <IBM Cloud API key>
  region = <IBM Cloud region>
}
  • IBM Cloud Functions
provider "ibm" {
  function_namespace = <Namespace in IBM Cloud Function>
  ibmcloud_api_key = <IBM Cloud API key>
  region = <IBM Cloud region>
}
  • Kubernetes 서비스
provider "ibm" {
  ibmcloud_api_key = <IBM Cloud API key>
  generation = <VPC generation>
}
  • Power sysetm
provider "ibm" {
  zone = <IBM Cloud zone>
  ibmcloud_api_key = <IBM Cloud API key>
  region = <IBM Cloud region>
}
  • VPC infrasturcture for Gen 1 and Gen2 Compute
provider "ibm" {
  ibmcloud_api_key = <IBM Cloud API key>
  generation = <VPC generation>
  region = <IBM Cloud region>
}
  • multiple provider 사용시에는 alias 사용
provider "ibm" {
  ibmcloud_api_key    = var.ibmcloud_api_key
  region = "us-south"
}

provider "ibm" {
  alias = "east"
  ibmcloud_api_key    = var.ibmcloud_api_key
  region = "us-east"
}

resource "ibm_container_cluster" "cluster" {
  provider = ibm.east
...
}

IBM Terraform Provider 기본 기능들

tf configuration 파일에서 사용되는 IBM Terraform Provider의 주요 resource 및 data는 아래 링크들을 통해 확인 하실 수 있습니다.

이 외에도 많은 기능들이 있으니 Official Document에서 확인하시기 바랍니다. 또한 Sample의 sample 링크에서 구체적인 사용법을 샘플을 통해 확인 하실 수 있습니다.

결론

본 문서에서 InfraStructure를 코드로 관리하는 기술 중 Terraform과 IBM Cloud를 관리 할 수 있는 IBM Terraform Plugin에 대하여 살펴 봤습니다. 프로젝트에서 InfraStructure가 동적으로 자주 변경되거나 비슷한 환경을 지속적으로 만드는 경우가 있다면 Terraform을 활용해 보시기 바랍니다. 수동으로 생성했을때 보다 편리하고 관리하기 쉽다는 것을 느끼실 겁니다.