안녕하세요, 오늘은 테라폼 cidrsubnet, cidrsubnets에 대해서 정리한 내용을 가지고 포스팅합니다.
‘테라폼으로 시작하는 IaC’를 기준으로 내용 정리하였으며, Cloudnet의 테라폼 스터디 내용을 기반으로 하고 있습니다.
CIDR 표기법에 대한 설명 및 새로운 네트워크 프리픽스 비트 추가 방법
이 글에서는 RFC 4632 섹션 3.1에서 정의한 CIDR (Classless Inter-Domain Routing) 표기법을 사용하여 네트워크 주소 범위를 어떻게 분할하는지 설명합니다.
CIDR 표기법
CIDR 표기법은 IP 주소를 더 효율적으로 할당하고 라우팅 할 수 있도록 하는 방법입니다. CIDR 주소는 'IP 주소/프리픽스 길이' 형식으로 작성되며, 여기서 프리픽스 길이는 서브넷 마스크를 나타내는 비트 수를 의미합니다.
cidrsubnets 함수
cidrsubnet(prefix, newbits, netnum)
cidrsubnets 함수는 주어진 네트워크 프리픽스에서 여러 개의 서브넷 주소를 계산할 수 있도록 합니다. 이 함수는 다음과 같은 인수를 받습니다:
- prefix: CIDR 표기법으로 주어진 네트워크 프리픽스.
- newbits: 추가할 각 네트워크 프리픽스 비트의 수를 지정하는 인수.
반환값은 각 newbits 인수에 대해 하나씩, CIDR 표기법으로 작성된 주소 범위를 포함하는 문자열 목록입니다.
IP 주소 공간 분할
이 함수를 사용하여 네트워크 주소 계획의 일환으로 주소 공간을 분할할 때, 네트워크 주소가 실제 인프라에 할당된 후에는 기존 인수를 변경하면 안 됩니다. 그렇지 않으면 나중에 할당된 주소가 무효화될 수 있습니다. 그러나 주소 공간이 충분히 남아 있는 한 기존 호출에 새 인수를 추가하는 것은 안전합니다.
IPv4 및 IPv6 지원
이 함수는 IPv4와 IPv6 프리픽스를 모두 지원하며, 결과는 항상 주어진 프리픽스와 동일한 주소 체계를 사용합니다.
예시
예를 들어, cidrsubnets(" 172.16.0.0/12", 4, 2 )를 호출하면, /12 및 /16 서브넷 크기로 네트워크 주소 범위를 분할하는 두 개의 서브넷 주소가 반환됩니다.
cidrsubnet("172.16.0.0/12", 4, 2)
- prefix: "172.16.0.0/12" (기존 CIDR 블록)
- newbits: 4 (추가할 비트 수)
- netnum: 2 (생성할 서브넷의 인덱스)
-
결과: 172.18.0.0/16
- (원래 블록: 172.16.0.0/12 서브넷 비트 추가: 4 서브넷 인덱스: 2 (세 번째 서브넷) 결과: 172.18.0.0/16)
cidrsubnet("10.1.2.0/24", 4, 15)
- prefix: "10.1.2.0/24" (기존 CIDR 블록)
- newbits: 4 (추가할 비트 수)
- netnum: 15 (생성할 서브넷의 인덱스)
-
결과: 10.1.2.240/28
- (원래 블록: 10.1.2.0/24 서브넷 비트 추가: 4 서브넷 인덱스: 15 (열여섯 번째 서브넷) 결과: 10.1.2.240/28)
cidrsubnet("fd00:fd12:3456:7890::/56", 16, 162)
- prefix: "fd00:fd12:3456:7890::/56" (기존 CIDR 블록)
- newbits: 16 (추가할 비트 수)
- netnum: 162 (생성할 서브넷의 인덱스)
- (원래 블록: fd00:fd12:3456:7890::/56 서브넷 비트 추가: 16 서브넷 인덱스: 162 (163번째 서브넷) 결과: fd00:fd12:3456:7800:a200::/72)
추가 정보
- cidrsubnet 함수: 단일 서브넷 주소를 계산할 수 있으며, 서브넷 번호를 지정할 수 있습니다.
- cidrsubnets 함수: 여러 개의 서브넷 주소를 한 번에 계산할 수 있으며, 서브넷 번호를 자동으로 할당합니다.
cidrsubnet 함수를 사용해서 리소스를 직접 배포해 보겠습니다.
variables.tf
variable "vpc_cidr" {
description = "The CIDR block for the VPC"
type = string
default = "10.0.0.0/16"
}
variable "subnet_bits" {
description = "The number of bits to add to the VPC CIDR block for subnets"
type = number
default = 4
}
variable "subnet_count" {
description = "The number of subnets to create"
type = number
default = 3
}
variable "ami_id" {
description = "The AMI ID for the EC2 instances"
type = string
default = "ami-0edc5427d49d09d2a"
}
variable "instance_type" {
description = "The type of instance to use"
type = string
default = "t2.micro"
}
variable "valid_azs" {
description = "List of valid availability zones"
type = list(string)
default = ["ap-northeast-2a", "ap-northeast-2c"]
}
main.tf
provider "aws" {
region = "ap-northeast-2"
}
data "aws_availability_zones" "available" {}
resource "aws_vpc" "main" {
cidr_block = var.vpc_cidr
tags = {
Name = "main-vpc"
}
}
resource "aws_subnet" "subnets" {
count = var.subnet_count
vpc_id = aws_vpc.main.id
cidr_block = cidrsubnet(var.vpc_cidr, var.subnet_bits, count.index)
availability_zone = var.valid_azs[count.index % length(var.valid_azs)]
tags = {
Name = "subnet-${count.index}"
}
}
resource "aws_instance" "example" {
count = var.subnet_count
ami = var.ami_id
instance_type = var.instance_type
subnet_id = aws_subnet.subnets[count.index].id
tags = {
Name = "example-instance-${count.index + 1}"
}
}
output.tf
output "vpc_id" {
description = "The ID of the VPC"
value = aws_vpc.main.id
}
output "subnet_ids" {
description = "The IDs of the subnets"
value = aws_subnet.subnets[*].id
}
output "instance_ids" {
description = "The IDs of the EC2 instances"
value = aws_instance.example[*].id
}
앞서 설명한 것처럼, cidrsubnet 함수를 사용하여 CIDR 블록(10.0.0.0/16)에 4비트를 추가해 서브넷을 생성하려고 합니다.
cidrsubnet("10.0.0.0/16", 4, 0)
이렇게 하면 원래의 /16 블록이 더 작은 /20 블록으로 나누어집니다. 또한, 특정 가용 영역에서 인스턴스 유형이 지원되지 않는 문제를 해결하기 위해서 valid_azs를 추가해 (ap-northeast-2b와 ap-northeast-2d를 피하여) 유효한 서브넷과 인스턴스를 생성합니다.
수행 결과 :
생성된 서브넷과 인스턴스가 의도한 바와 같이 서브넷과 인스턴스를 생성한 것을 확인하실 수 있습니다.
'DevOps > Terraform' 카테고리의 다른 글
[Terraform] 조건식을 활용한 태깅 (0) | 2024.06.29 |
---|---|
[Terraform] for_each, for, dynamic의 사용법 (0) | 2024.06.29 |
[Terraform] count 사용하기 (0) | 2024.06.23 |
[Terraform] 로컬 변수 사용하기 (0) | 2024.06.23 |
[Terraform] 입력 변수 사용하기 (0) | 2024.06.23 |