diff --git a/infra/.terraform.lock.hcl b/infra/.terraform.lock.hcl index 8927fa3..9c18879 100644 --- a/infra/.terraform.lock.hcl +++ b/infra/.terraform.lock.hcl @@ -33,6 +33,43 @@ provider "registry.opentofu.org/hashicorp/hcloud" { ] } +provider "registry.opentofu.org/hashicorp/local" { + version = "2.9.0" + constraints = "~> 2.5" + hashes = [ + "h1:1dtKYW/5a1qob3yneL6WzOlnSGfYtJ6a2XeejCk9yb4=", + "h1:5NseXq5wU8O20ersTtV4ocrLYFFtgFr7n0pRLO1W2Rw=", + "h1:5d22ZPPK4iiygPbwRz/PJF5Es/0axVpMlPRpCR0Padw=", + "h1:AnwyolirmIlBMjH6+tV8bKkvT+5axJNYxi2y2IguiX4=", + "h1:PBp+HeseY021Fw3sLznCG27idgwPoff4cBuNmKgPL2w=", + "h1:VDxIhe4GbzdOCdmt7mQaqdwERQW6GSI7Roonts42Gr0=", + "h1:ZO6eWWnf8LjjV1q/JNeL9WLtZ6fwIttOnyN5LjCNSEo=", + "h1:dPIAf8oUAz+vW2E0iZunMvpuPddRZIztRsPSY1u+VnY=", + "h1:fwTDVG9AhFVKQZIb1EXkHv4FqzsZNlLWgkyPGDmZZEE=", + "h1:kDc465XPC7/6XFCjrMC4mTqhA9ef0FHKuJ3ZgfGNfeg=", + "h1:kGbjxrI2P8MHeyVtE1U3Q1TbyF71ExnHxtkrE+Aj6UU=", + "h1:kcoK6Afbsj54u9zaEqpecWAFKytqjBijtguCNwV3d4M=", + "h1:rxomJjDwOo+YZ+WIPc25FqEgsz9orh/2MCyUcZmFjvw=", + "h1:t0CMn/Rkwquw8l2yQ+O4ApzbMZfY2UazbsDnZygzACA=", + "h1:tJwgm2BS4xCGlElCDQEFXQoefY9Y4t0JdSKTtsPBbBo=", + "zh:13ef7ecd1e397ec5b20ea588508dd3e3b8d6c50d809ae76b079abf9dd8d02e4b", + "zh:2190c9325980076489ce02b0f5dd2c0b91fc8711cefa99e714d8619a32827ad1", + "zh:2a0cfc5600730093705071707e4a4e4e953e7d9091859e0f66b46daa1060dd5d", + "zh:2ff53eac1af43ab9a2248a0e53c963d46e19cf04bc4c3f323591cfcebb218252", + "zh:4ebc3dee700f60af9da29970052fd02fa947813162b224716862dc9d7f1f7542", + "zh:5fe6dab84ceeaa8eb3f1567c5f05578333370c472240ca5c5bfc25e92d4d5586", + "zh:66bbec16367bbf440045502c9779b11f4ac5b022c8d8d17afe12d431950838b5", + "zh:7641e5c2e4b529e869cde29ab5b1de2fd1091489eb745b19ac2709bd7f4dfd84", + "zh:855bfba0756d17ce07595ff57d7cf664443d1495127cb88fb063362734b8b22a", + "zh:aaec10f237921d60c581d1b7a66f0a8a8019d9802dc04af11b5b981f6682e01d", + "zh:e460835a38ffa1e74f6929904bfd14ef473d217fd537b7ce834abe5ce5e2ce07", + "zh:ecc4295215db0e4aea3c9329611c31e09a853e1ae207d56742403bd4f5516703", + "zh:ee6d9fae63a612072e00402894e14826af7a3351c235b9c5b423b7629a77ca29", + "zh:f2b5c8db74aa7ebcf7cd423672358437d42401675069ef67b01ff910054e49d5", + "zh:f5aff74d3eb96d4592c7bca5cd3ea89b469e84efbf382944bd0f844a57059c09", + ] +} + provider "registry.opentofu.org/hetznercloud/hcloud" { version = "1.66.0" constraints = "~> 1.45" diff --git a/infra/main.tf b/infra/main.tf index 0c96d20..03ead0e 100644 --- a/infra/main.tf +++ b/infra/main.tf @@ -38,6 +38,7 @@ module "dev" { network_ip_range = var.network_ip_range bootstrap_script = local.bootstrap_script ssh_private_key_path = var.ssh_private_key_path + runner_count = var.dev_runner_count # module.network.id alone doesn't guarantee the subnet exists yet, and a server # can't join a network before it has a subnet. diff --git a/infra/modules/dev/main.tf b/infra/modules/dev/main.tf index 7c117a0..2aa4cbe 100644 --- a/infra/modules/dev/main.tf +++ b/infra/modules/dev/main.tf @@ -88,4 +88,19 @@ resource "hcloud_volume" "storage" { server_id = hcloud_server.this.id automount = true format = "ext4" + + lifecycle { + prevent_destroy = true + } +} + +# Renders services/dev/Runners/docker-compose.yml directly into the repo, with +# one runner service per var.runner_count. This only touches the local working +# tree - deploying the change still goes through the normal scp + spinup.sh flow. +resource "local_file" "runners_compose" { + filename = "${path.root}/../services/dev/Runners/docker-compose.yml" + content = templatefile("${path.module}/templates/runners-docker-compose.yml.tftpl", { + runner_count = var.runner_count + }) + file_permission = "0644" } diff --git a/infra/modules/dev/templates/runners-docker-compose.yml.tftpl b/infra/modules/dev/templates/runners-docker-compose.yml.tftpl new file mode 100644 index 0000000..1389842 --- /dev/null +++ b/infra/modules/dev/templates/runners-docker-compose.yml.tftpl @@ -0,0 +1,30 @@ +# Generated by OpenTofu from var.dev_runner_count - do not hand-edit. +# To change the number of runners, edit dev_runner_count in terraform.tfvars and +# run tofu apply. To change their shape, edit +# infra/modules/dev/templates/runners-docker-compose.yml.tftpl instead. +# +# GITEA_RUNNER_REGISTRATION_TOKEN is intentionally left as a compose variable +# (not baked in here) - services/dev/spinup.sh generates a fresh token and +# writes it to Runners/.env immediately before starting these containers. +services: +%{ for i in range(runner_count) ~} + runner-${i + 1}: + image: gitea/act_runner:latest + container_name: gitea_runner_${i + 1} + volumes: + - ./config.yaml:/config.yaml + - ./gitea_runner_${i + 1}:/data + - /var/run/docker.sock:/var/run/docker.sock + networks: + - proxy + environment: + CONFIG_FILE: /config.yaml + GITEA_INSTANCE_URL: "https://git.luke-else.co.uk" + GITEA_RUNNER_REGISTRATION_TOKEN: "$${GITEA_RUNNER_REGISTRATION_TOKEN}" + GITEA_RUNNER_NAME: "CICD#${i + 1}" + restart: unless-stopped +%{ endfor ~} + +networks: + proxy: + external: true diff --git a/infra/modules/dev/variables.tf b/infra/modules/dev/variables.tf index 9a2dec0..9828bfb 100644 --- a/infra/modules/dev/variables.tf +++ b/infra/modules/dev/variables.tf @@ -52,3 +52,8 @@ variable "ssh_private_key_path" { description = "Local path to the private key matching var.ssh_key_id, used to run the bootstrap script over SSH." type = string } + +variable "runner_count" { + description = "Number of Gitea Actions runner containers to render into services/dev/Runners/docker-compose.yml." + type = number +} diff --git a/infra/modules/prod/main.tf b/infra/modules/prod/main.tf index 1c5e5f0..f97ae0b 100644 --- a/infra/modules/prod/main.tf +++ b/infra/modules/prod/main.tf @@ -115,4 +115,8 @@ resource "hcloud_volume" "storage" { server_id = hcloud_server.this.id automount = true format = "ext4" + + lifecycle { + prevent_destroy = true + } } diff --git a/infra/terraform.tfvars.example b/infra/terraform.tfvars.example index 861f79c..1338581 100644 --- a/infra/terraform.tfvars.example +++ b/infra/terraform.tfvars.example @@ -22,3 +22,4 @@ ssh_private_key_path = "~/.ssh/id_ed25519" # prod_volume_size = 20 # allowed_ssh_source_ips = ["203.0.113.4/32"] # deploy_user = "deploy" +# dev_runner_count = 3 diff --git a/infra/variables.tf b/infra/variables.tf index a19472c..b962133 100644 --- a/infra/variables.tf +++ b/infra/variables.tf @@ -91,3 +91,9 @@ variable "deploy_user" { type = string default = "deploy" } + +variable "dev_runner_count" { + description = "Number of Gitea Actions runner containers to run on dev. Rendered into services/dev/Runners/docker-compose.yml on every tofu apply - see infra/modules/dev/templates/runners-docker-compose.yml.tftpl." + type = number + default = 1 +} diff --git a/infra/versions.tf b/infra/versions.tf index e01c365..d991f1e 100644 --- a/infra/versions.tf +++ b/infra/versions.tf @@ -6,6 +6,10 @@ terraform { source = "hetznercloud/hcloud" version = "~> 1.45" } + local = { + source = "hashicorp/local" + version = "~> 2.5" + } } }