Time flies with Terraform tries: a brief story about modules
I’ve been busy doing a few things in the background, like -not- adding content and being quiet.
All jokes aside, I have been transferring my cloud-side configuration to Terraform. Until recently I was using DigitalOcean as my hosting platform, but in the face of rising costs (and a weak GBP, where DigitalOcean charges in USD) I spent a few days last month building out a Kubernetes cluster in my homelab.
I’ll go into more detail another time, but for now let’s stick with cloud-side config. Specifically, DNS is something that has to be handled externally (well not quite, but it takes a a glutton for punishment to run their own DNS server at home).
So, I’m using Cloudflare to host my DNS zone, because it comes with a few web protection bells and whistles. My first attempt was to write out individual records using the Cloudflare record, like this:
resource "cloudflare_record" "website" {
name = "website"
type = "A"
proxied = false
value = 80.90.10.20
ttl = "600"
zone_id = var.zone_id
}
Terraform resources can be defined very simply, like this: WYSIWYG (what you see is what you get). It makes an A record for website.sierrana.co.uk
with a TTL of 600 seconds, and attaches it to the DNS zone via the zone_id variable. Every record is created this way, which takes up a lot of screen real-estate (virtual-estate?) and some duplication.
A much more efficient way to do this is using a Terraform module, which lets me define some defaults and variable handling.
I make a module with the file dns.tf
in the folder cloudflare
. There are some variables I have to define, and some of them have default values.
locals {
name = var.name
type = var.type
proxied = var.proxied
value = var.value
ttl = var.ttl
zone_id = var.zone_id
}
resource "cloudflare_record" "record" {
name = local.name
type = local.type
proxied = local.proxied
value = local.value
ttl = local.ttl
zone_id = local.zone_id
}
Back in my top-level main.tf
I can now call the module and give it a very small amount of information and it will create a record with all the default values I chose.
module "www" {
source = "./modules/cloudflare"
name = "website"
}
I can pass additional information in, and it will change the record creation values, but since most of my records are made this way, I can save some time and effort - and most of all, the satisfaction of making it work.