1. 조건문

# <조건 정의> ? <옳은 경우> : <틀린 경우>
var.a != "" ? var.a : "default-a"
# 조건식 형태 권장 사항 
var.example ? 12 : "hello"            # 비권장
var.example ? "12" : "hello"          # 권장
var.example ? tostring(12) : "hello"  # 권장
variable "enable_file" {
  default = true
}

resource "local_file" "foo" {
  count    = var.enable_file ? 1 : 0
  content  = "foo!"
  filename = "${path.module}/foo.bar"
}

output "content" {
  value = var.enable_file ? local_file.foo[0].content : ""
}

위와 같이 TF_VAR_enable_file 를 false로 지정하면 foo파일이 생성되지 않는다.

 

그러나 변수 내용을 없애면 다음과같이 foo파일이 생성된다.

 

 

2.함수

upper라는 함수를 사용해본다.

resource "local_file" "foo" {
  content  = upper("foo! bar!")
  filename = "${path.module}/foo.bar"
}

위와같이 소문자로 적었던 foo bar가 대문자로 변환됐다.

 

3.terraform_data

null_resource를 사용하는 것은 마치 코딩 없이도 버튼을 누르거나 스위치를 켜는 것과 유사합니다. 이 버튼이나 스위치 자체는 그다지 특별한 기능을 하지 않지만, 다른 기기나 프로세스가 이 버튼 눌림이나 스위치 켜짐을 감지하고 특정 행동을 취합니다.

예를 들어, 가정에서 가습기가 있고 그 가습기는 물이 다 떨어지면 자동으로 꺼집니다. 하지만 가습기에 물을 채웠을 때 자동으로 켜지지는 않습니다. 이런 경우에 버튼을 설치해 물을 채운 후 버튼을 누르면 가습기가 자동으로 켜지도록 설정할 수 있습니다.

이 버튼은 실제로 "가습기를 켜다"라는 행동을 직접 수행하지는 않습니다. 그저 누군가가 물을 채웠다는 사실을 가습기에 알리는 신호일 뿐입니다. 그리고 가습기는 이 신호를 받고 작동을 시작합니다.

이와 비슷하게 null_resource는 특정 상황에서 어떤 일이 일어나야 한다는 것을 알리는 '버튼'이나 '스위치' 같은 역할을 합니다. 이것 자체로는 아무 일도 하지 않지만, 이것이 트리거되면 연결된 다른 작업(예를 들어, 스크립트 실행)이 실행됩니다.

이에 더해서 terraform_data는 추가 프로바이더 없이 테라폼 자체에 포함된 기본 수명주기 관리자가 제공

 

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

resource "aws_instance" "ec2_example" {
  ami           = "ami-091aca13f89c7964e"
  instance_type = "t2.micro"
}

resource "terraform_data" "tf_data_resource_ip" {
  triggers_replace = [aws_instance.ec2_example.public_ip]

  provisioner "local-exec" {
    command = "echo New Public IP: ${aws_instance.ec2_example.public_ip}"
  }
}

 

4. moved 블럭

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

module "ec2_module" {
  source = "./ec2_module"

  ami           = "ami-091aca13f89c7964e"
  instance_type = "t2.micro"
}

module "terraform_data_module" {
  source = "./terraform_data_module"

  ec2_public_ip = module.ec2_module.public_ip
}

moved {
  from = aws_instance.ec2_example
  to   = module.ec2_module.aws_instance.ec2_example
}

moved {
  from = terraform_data.tf_data_resource_ip
  to   = module.terraform_data_module.terraform_data.tf_data_resource_ip
}

ec2 모듈

variable "ami" {}
variable "instance_type" {}

resource "aws_instance" "ec2_example" {
  ami           = var.ami
  instance_type = var.instance_type

  output "public_ip" {
    value = aws_instance.ec2_example.public_ip
  }
}

terrform data 모듈

variable "ec2_public_ip" {}

resource "terraform_data" "tf_data_resource_ip" {
  triggers_replace = [var.ec2_public_ip]

  provisioner "local-exec" {
    command = "echo New Public IP: ${var.ec2_public_ip}"
  }
}

 

5. 프로바이더

헬름 프로바이더를 사용하여 nginx를 배포해보았다.

 

terraform {
  required_providers {
    architech-http = {
      source = "architect-team/http"
      version = "~> 3.0"
    }
    http = {
      source = "hashicorp/http"
    }
    aws-http = {
      source = "terraform-aws-modules/http"
    }
  }
}

data "http" "example" {
  provider = aws-http
  url = "https://checkpoint-api.hashicorp.com/v1/check/terraform"

  request_headers = {
    Accept = "application/json"
  }
}

이런식으로 여러개의 프로바이더도 정의가 가능하다.

 

# region 1
provider "aws" {
  region = "ap-southeast-1"
}

# region 2
provider "aws" {
  alias = "seoul"
  region = "ap-northeast-2"
}

resource "aws_instance" "app_server1" {
  ami           = "ami-06b79cf2aee0d5c92"
  instance_type = "t2.micro"
}

resource "aws_instance" "app_server2" {
  provider      = aws.seoul
  ami           = "ami-0ea4d4b8dc1e46212"
  instance_type = "t2.micro"
}

아니면 이런식으로 리전별로 프로바이더를 다르게 정의할수가 있다.

+ Recent posts