Reputation: 143
Is it possible to concatonate / join variables in terraform? I am struggling to find a reference to correct syntax.
I would like to do something like this:
variable "env" {
default = "production"
}
variable "vpc_name" {
default = "cloudy"
}
resource "aws_subnet" "${var.env}_${var.vpc_name}_pub1" {
vpc_id = "${aws_vpc.${var.vpc_name}.id}"
cidr_block = "10.0.1.0/24"
availability_zone = "us-east-1a"
}
Which would effectively achieve something like this:
resource "aws_subnet" "production_cloudy_pub1" {
vpc_id = "${aws_vpc.cloudy.id}"
cidr_block = "10.0.1.0/24"
availability_zone = "us-east-1a"
}
Upvotes: 4
Views: 3184
Reputation: 56877
As the comments mention you can't interpolate variables like that in Terraform or do things like default a variable to another variable you could achieve your stated aim using data sources.
In the example case you could do something like the following:
variable "env" {
default = "production"
}
variable "vpc_name" {
default = "cloudy"
}
data "aws_vpc" "selected" {
tags {
Name = "${var.vpc_name}"
}
}
resource "aws_subnet" "pub1" {
vpc_id = "${data.aws_vpc.selected.id}"
cidr_block = "10.0.1.0/24"
availability_zone = "us-east-1a"
}
That would create the subnet in the "cloudy" VPC automatically.
This also allows for pulling more information than just the VPC id back so you could do something like this instead:
variable "env" {
default = "production"
}
variable "vpc_name" {
default = "cloudy"
}
data "aws_vpc" "selected" {
tags {
Name = "${var.vpc_name}"
}
}
resource "aws_subnet" "public" {
vpc_id = "${data.aws_vpc.selected.id}"
cidr_block = "${cidrsubnet(data.aws_vpc.selected.cidr_block, 8, 1)}"
availability_zone = "us-east-1a"
}
The cidrsubnet
function calculates a subnet from a given CIDR range. In this case if your VPC was a 10.0.0.0/16
this would return 10.0.1.0/24
.
The above examples solve your main stated problem but it doesn't allow for dynamically named Terraform resources. In your short example there doesn't seem to be a need for it but if you wanted something dynamic then you could also combine this with something like a count on the resource:
variable "env" {
default = "production"
}
variable "vpc_name" {
default = "cloudy"
}
data "aws_vpc" "selected" {
tags {
Name = "${var.vpc_name}"
}
}
data "aws_availability_zones" "all" {}
resource "aws_subnet" "public" {
count = "${length(data.aws_availability_zones.all.names)}"
vpc_id = "${data.aws_vpc.selected.id}"
cidr_block = "${cidrsubnet(data.aws_vpc.selected.cidr_block, 8, count.index)}"
availability_zone = "${data.aws_availability_zones.all.names[count.index]}"
}
This now dynamically creates a subnet in each availability zone in the region for your VPC. Obviously you can take this pretty far and I'd recommend reading up on data sources in general plus all of the AWS specific data sources.
Upvotes: 2