add static ip note to readme
fix readme issues
add version flag
Terrafirma is a composable alternative to Terraform. Like Terraform, Terrafirma deploys infrastructure. It abstracts away the cloud provider and provides a CLI that reliably creates and destroys servers.
Unlike Terraform, Terrafirma is designed to work alongside and with other tools. It is very much designed in the UNIX philosphy of doing one thing well.
tf
. Works alongside everything else
using json. jq
to your heart's content.Note that this is not a "batteries-included" tool. Terrafirma provides the bare minimum to interface with cloud providers and manage infrastructure.
Currently only Google Cloud (GCP) is supported. Patches for additional features and cross-cloud support are welcome.
Terrafirma deploys infrastructure in 3 steps:
Unlike Terraform which executes a plan in a single command, Terrafirma
separates the create
and destroy
steps.
This is because Terrafirma is designed to compose well with other tools and doesn't make any assumptions around how you provision servers, start your services, check their health, or notify your reverse proxy of new IPs.
In a high-availability production environment, all of that must happen after create but before destroy. A single step that both creates and destroys would require Terrafirma to handle that logic, which would greatly complicate the tool's code, configuration, and use.
Instead, ensure your new servers are provisioned, services are running, and your reverse proxy is directing traffic to the new instances prior to deleting old instances. Usually this can be accomplished with a simple bash script gluing everything together.
Terrafirma requires a services.json
file describing the services you want to
deploy and the types of boxes you'll use. Here's an example:
{
"requirements": {
"app-1": {
"cpu": 2,
"ram": "12 GB",
"disk": "20 GB",
"net": {
"ports": [5000, 5001],
"mbps": 300
}
},
"app-2": {
"cpu": 3,
"ram": "4 GB",
"disk": "30 GB"
},
"redis": {
"cpu": 1,
"ram": "2 GB",
"disk": "10 GB"
}
},
"counts": {
"openbsd": {
"app-1": 2,
"app-2": 4
},
"debian": {
"redis": 1
}
},
"providers": {
"gcp:my-project:us-central1:us-central1-b": {
"openbsd": {
"machineType": "n1-standard-4",
"disk": "100 GB",
"image": "projects/{your-project}/global/images/openbsd-67"
},
"debian": {
"machineType": "n1-highmem-4",
"disk": "10 GB",
"image": "projects/gce-uefi-images/global/images/family/debian-11"
}
},
}
}
Since using Terrafirma requires several steps, you'll probably use a short bash script to automate your particular workflow. An example script might look like this:
#!/usr/bin/env bash
set -efux
GCP_TOKEN=$(gcloud auth print-access-token)
export GCP_TOKEN
# Plan the number of servers to be created and destroyed. This creates a
# tf_plan.json file which the remaining steps use.
#
# binp is a binpacking tool that minimizes the number of servers for our box
# type.
terrafirma -b "$(binp)" plan > tf_plan.json
# Create any new servers, wait for them to boot, then use terrafirma to build
# an inventory file mapping the new IPs to each of the services running on
# them. Other tools can convert this inventory.json file to an SSH config file,
# etc.
#
# Terrafirma will automatically create and assign static IP addresses as
# needed.
if terrafirma create; then
echo "waiting 60s for servers to boot..." && sleep 60
fi
# Get our new inventory only containing our future state
terrafirma -i inventory > inventory.json
# Provision our servers using our usual deployment tools (cup, ansible, etc.).
up -t 100.0.0.1 -c provision_openbsd
up -t 100.0.0.2 -c provision_debian
# Now we know our reverse proxy is sending traffic to these new boxes, so we
# can bring down our old ones and clean up any temporary files when we're done.
#
# Note that Terrafirma will not delete static IPs, so you don't need to worry
# about affecting IP whitelists. Static IPs must be manually deleted.
terrafirma destroy
rm tf_plan.json
If you wanted to wipe out your Terrafirma-managed infrastructure (except for any static IPs):
GCP_TOKEN=... terrafirma -b '{}' plan > tf_plan.json
GCP_TOKEN=... terrafirma destroy
Patches for the following would be greatly appreciated: