Setting up my Micro.blog sub-domain using IaC, Terraform and Cloudflare
The last step to setting up my new Micro.blog was to use it from my own domain.
I debated using it exclusively at paultibbetts.uk
but I want to work on my own blog for that address.
So I’m going to use Micro.blog as… my microblog… at micro.paultibbetts.uk
.
Instead of doing it by hand on Cloudflare’s website I wrote it down as code.
Infrastructure as Code
Writing down your infrastructure as code has a lot of benefits:
- it’s in one central place instead of spread out in different UIs on different sites
- it can be version controlled
- it can be readable by robots as well as other humans
You can use tools like Terraform, OpenTofu or Pulumi to do this.
Terraform
I’m using Terraform at the moment. I might look into Pulumi in the future.
Terraform uses HCL for its configuration.
main.tf
terraform {
required_providers {
cloudflare = {
source = "cloudflare/cloudflare"
version = "~> 4.0"
}
}
}
My domain is managed by Cloudflare so at the start of my code I tell Terraform to use the cloudflare/cloudflare
provider. This means I can manage different things in Cloudflare using a few settings.
provider "cloudflare" {
api_token = var.cloudflare_api_token
}
Next I tell the Cloudflare provider to use a variable for my API token.
data "cloudflare_zone" "paultibbetts_dot_uk" {
name = "paultibbetts.uk"
}
Originally I asked ChatGPT how to do this, and it was technically correct, but it wanted me to go on the Cloudflare site, go to my domain, and copy the zone_id
to pass in as a variable. Which is missing the point of doing this with code.
Instead, using data
means this block is a data source, called paultibbetts_dot_uk
, which uses Cloudflare’s cloudflare_zone
module to get a zone (domain) with a name of paultibbetts.uk
.
I don’t know or care what the ID is and I can automate the process of finding it out.
resource "cloudflare_record" "microblog" {
zone_id = data.cloudflare_zone.paultibbetts_dot_uk.id
name = "micro"
type = "CNAME"
value = "paultibbetts.micro.blog"
ttl = 300
}
When I create a cloudflare_record
resource, called microblog
, I can use the data source to get the ID of the zone for which domain the CNAME
record should be added to.
vars.tf
variable "cloudflare_api_token" {
type = string
description = "api token"
}
Because I don’t want to write down my API token in my code I set it up as a variable.
I can now pass in the token when I run Terraform:
terraform apply \
-var cloudflare_api_token="********" \
but I prefer loading it in as an environment variable.
You can do this by prefixing the variable with TF_VAR
:
# secrets.sh
export TF_VAR_cloudflare_api_token=********
and remembering to source this file before you run Terraform commands
source secrets.sh
terraform apply
apply
Now I can run terraform apply
, confirm the proposed changes, and Terraform will use the Cloudlfare API to add the CNAME to my domain for me.
After making a quick change in Micro.blog I’m live at my own domain 🥳