diff --git a/Makefile b/Makefile index ae208a9..50761d1 100644 --- a/Makefile +++ b/Makefile @@ -10,8 +10,8 @@ PWD := $(shell pwd) .FORCE: ./inventory/group_vars/all/all_services.yml: .FORCE - tofu output --json \ - | yq -y '{all_services: with_entries(.value |= .value).services | to_entries | map(.value)}' \ + tofu output --json services \ + | yq -y '{all_services: .}' \ > ./inventory/group_vars/all/all_services.yml ./inventory/group_vars/all/opentofu.yml: .FORCE diff --git a/modules/infrastructure/scaleway.tf b/modules/infrastructure/scaleway.tf index d863c9d..f017a11 100644 --- a/modules/infrastructure/scaleway.tf +++ b/modules/infrastructure/scaleway.tf @@ -13,7 +13,7 @@ data "scaleway_iam_user" "serguzim" { resource "scaleway_iam_application" "service_applications" { for_each = local.services_s3 - name = each.value.name + name = each.key } resource "scaleway_iam_policy" "service_storage_policies" { @@ -28,7 +28,7 @@ resource "scaleway_iam_policy" "service_storage_policies" { resource "scaleway_object_bucket" "service_buckets" { for_each = local.services_s3 - name = "${each.value.name}.serguzim.me" + name = "${each.key}.serguzim.me" lifecycle { prevent_destroy = true } diff --git a/modules/infrastructure/variables.tf b/modules/infrastructure/variables.tf index d4d064c..a13813a 100644 --- a/modules/infrastructure/variables.tf +++ b/modules/infrastructure/variables.tf @@ -12,7 +12,6 @@ variable "default_ssh_key" { variable "services" { type = map(object({ - name = string host = string dns = optional(list(object({ domain = string diff --git a/modules/services/authentik.tf b/modules/services/authentik.tf index cf9cd2b..5523583 100644 --- a/modules/services/authentik.tf +++ b/modules/services/authentik.tf @@ -53,9 +53,9 @@ resource "authentik_group" "minio_users" { resource "authentik_provider_oauth2" "service_providers" { for_each = local.services_auth - name = each.value.name + name = each.key client_type = "confidential" - client_id = each.value.name + client_id = each.key authorization_flow = data.authentik_flow.default_authorization_flow.id redirect_uris = each.value.auth_redirects property_mappings = flatten([ @@ -69,7 +69,7 @@ resource "authentik_provider_oauth2" "service_providers" { resource "authentik_application" "service_applications" { for_each = local.services_auth - name = each.value.name + name = each.key slug = replace(each.value.dns[0].domain, ".", "-") protocol_provider = authentik_provider_oauth2.service_providers[each.key].id } diff --git a/modules/services/postgresql.tf b/modules/services/postgresql.tf index 982fecb..ca1ab84 100644 --- a/modules/services/postgresql.tf +++ b/modules/services/postgresql.tf @@ -6,13 +6,13 @@ resource "random_password" "postgresql_service_passwords" { resource "postgresql_role" "service_roles" { for_each = local.services_database - name = each.value.name + name = each.key login = true password = random_password.postgresql_service_passwords[each.key].result } resource "postgresql_database" "service_databases" { for_each = local.services_database - name = each.value.name + name = each.key owner = postgresql_role.service_roles[each.key].name } diff --git a/modules/services/variables.tf b/modules/services/variables.tf index fe72923..d7657e1 100644 --- a/modules/services/variables.tf +++ b/modules/services/variables.tf @@ -3,7 +3,6 @@ variable "authentik_url" { variable "services" { type = map(object({ - name = string host = string dns = optional(list(object({ domain = string diff --git a/playbooks/filter_plugins/gatus.py b/playbooks/filter_plugins/gatus.py index 3d3a347..08e8568 100644 --- a/playbooks/filter_plugins/gatus.py +++ b/playbooks/filter_plugins/gatus.py @@ -50,7 +50,7 @@ class FilterModule(object): "[CERTIFICATE_EXPIRATION] > 48h" ] - for service in services: + for name, service in services.items(): if mon := service.get("monitoring"): if service.get("dns"): url = f"https://{service["dns"][0]['domain']}" @@ -71,7 +71,7 @@ class FilterModule(object): conditions = default_conditions new_endpoint = { - "name": service["name"], + "name": name, "group": mon.get("group"), "url": url, "conditions": conditions, diff --git a/playbooks/filter_plugins/service_filters.py b/playbooks/filter_plugins/service_filters.py index 37befc6..91d6700 100644 --- a/playbooks/filter_plugins/service_filters.py +++ b/playbooks/filter_plugins/service_filters.py @@ -2,32 +2,38 @@ class FilterModule(object): def filters(self): return { 'services_for_host': self.services_for_host, - 'services_to_dnscontrol': self.services_to_dnscontrol, + 'services_names': self.services_names, + 'services_get_attr': self.services_get_attr, 'services_get_backups': self.services_get_backups, 'service_get_backups': self.service_get_backups, 'services_ports_to_docker': self.services_ports_to_docker, 'service_get_domain': self.service_get_domain, + 'services_to_dnscontrol': self.services_to_dnscontrol, } def services_for_host(self, services, host): - result = [] - for service in services: + result = {} + for name, service in services.items(): if not host: - result.append(service) + result[name] = service continue if service["host"] == host: - result.append(service) + result[name] = service continue if service["host"] == "*": - result.append(service) + result[name] = service continue return result - def find_service(self, services, name): - for service in services: - if service.get("name") == name: - return service - return None + def services_names(self, services): + return list(services.keys()) + + def services_get_attr(self, services, attr): + result = [] + for service in services.values(): + if value := service.get(attr): + result.append(value) + return result def services_get_backups(self, all_services, wanted_services): result = [] @@ -36,12 +42,12 @@ class FilterModule(object): return result def service_get_backups(self, all_services, wanted_service): - if service := self.find_service(all_services, wanted_service): + if service := all_services.get(wanted_service): return service.get("backup") or [] return [] def service_get_domain(self, all_services, wanted_service): - if service := self.find_service(all_services, wanted_service): + if service := all_services.get(wanted_service): if dns := service.get("dns"): if dns_0 := dns[0]: return dns_0.get("domain") @@ -55,11 +61,11 @@ class FilterModule(object): result.append(f"{port['port']}:{port['port']}/{port['protocol']}") return result - def services_to_dnscontrol(self, services): + def services_to_dnscontrol(self, all_services): result = {} - for service in services: + for svc_name, service in all_services.items(): for dns in service.get("dns") or []: - name = dns.get("name") or service["name"] + name = dns.get("name") or svc_name domain_parts = dns["domain"].split(".") target_parts = domain_parts[:-2] or ["@"] result[name] = { diff --git a/playbooks/roles/backup/vars/main.yml b/playbooks/roles/backup/vars/main.yml index 89d1d9c..1dfe3bf 100644 --- a/playbooks/roles/backup/vars/main.yml +++ b/playbooks/roles/backup/vars/main.yml @@ -1,6 +1,6 @@ --- -backup_list: "{{ host_services | map(attribute='backup') | flatten }}" -backup_list_all: "{{ all_services | map(attribute='backup') | flatten }}" +backup_list: "{{ host_services | services_get_attr('backup') | flatten }}" +backup_list_all: "{{ all_services | services_get_attr('backup') | flatten }}" backup_msg_start: "Backup started" backup_msg_fail: "Backup failed" diff --git a/playbooks/roles/caddy/vars/main.yml b/playbooks/roles/caddy/vars/main.yml index 40c8042..2f56a07 100644 --- a/playbooks/roles/caddy/vars/main.yml +++ b/playbooks/roles/caddy/vars/main.yml @@ -6,7 +6,7 @@ caddy_acmedns_url: "https://{{ acme_dns.host }}" caddy_ports_default: - "{{ host_vpn.ip }}:2019:2019" -caddy_ports_extra: "{{ host_services | map(attribute='ports') | flatten | services_ports_to_docker('reverse_proxy') }}" +caddy_ports_extra: "{{ host_services | services_get_attr('ports') | flatten | services_ports_to_docker('reverse_proxy') }}" caddy_ports: "{{ caddy_ports_default | union(caddy_ports_extra) }}" caddy_env: diff --git a/playbooks/roles/lego/vars/main.yml b/playbooks/roles/lego/vars/main.yml index d9884e5..d7c8564 100644 --- a/playbooks/roles/lego/vars/main.yml +++ b/playbooks/roles/lego/vars/main.yml @@ -1,5 +1,5 @@ --- -lego_host_certificates: "{{ host_services | map(attribute='certificates') | flatten }}" +lego_host_certificates: "{{ host_services | services_get_attr('certificates') | flatten }}" lego_env: ACME_DNS_API_BASE: https://{{ acme_dns.host }} diff --git a/playbooks/serguzim.net.yml b/playbooks/serguzim.net.yml index df28901..ade0cee 100644 --- a/playbooks/serguzim.net.yml +++ b/playbooks/serguzim.net.yml @@ -21,11 +21,11 @@ - name: Include service roles ansible.builtin.include_role: - name: "{{ services_item.name }}" + name: "{{ services_item }}" apply: - tags: "{{ services_item.name }}" + tags: "{{ services_item }}" tags: always - loop: "{{ host_services }}" + loop: "{{ host_services | services_names() }}" loop_control: loop_var: services_item diff --git a/playbooks/tasks/get-unused.yml b/playbooks/tasks/get-unused.yml index 598e222..ecaa098 100644 --- a/playbooks/tasks/get-unused.yml +++ b/playbooks/tasks/get-unused.yml @@ -14,4 +14,4 @@ - name: Set unused services ansible.builtin.set_fact: - unused_services: "{{ docker_compose_projects_result.stdout_lines | difference(host_services | map(attribute='name')) }}" + unused_services: "{{ docker_compose_projects_result.stdout_lines | difference(host_services | services_names()) }}" diff --git a/playbooks/tasks/reload-caddy.yml b/playbooks/tasks/reload-caddy.yml index b067ea1..e153b64 100644 --- a/playbooks/tasks/reload-caddy.yml +++ b/playbooks/tasks/reload-caddy.yml @@ -6,7 +6,7 @@ - name: Map exisiting/wanted caddy site configs ansible.builtin.set_fact: caddy_site_configs_have: "{{ find_result.files | map(attribute='path') }}" - caddy_site_configs_want: "{{ host_services | map(attribute='name') | list_prefix_path_suffix(caddy_config_path, '.conf') }}" + caddy_site_configs_want: "{{ host_services | services_names() | list_prefix_path_suffix(caddy_config_path, '.conf') }}" - name: Remove unwanted caddy site configs ansible.builtin.file: diff --git a/services.auto.tfvars b/services.auto.tfvars index 9a7e69d..98eb685 100644 --- a/services.auto.tfvars +++ b/services.auto.tfvars @@ -1,6 +1,5 @@ services = { "acme_dns" = { - name = "acme_dns" host = "node001" dns = [{ domain = "acme.serguzim.me" @@ -15,7 +14,6 @@ services = { }, "authentik" = { - name = "authentik" host = "node003" dns = [{ domain = "auth.serguzim.me" @@ -31,7 +29,6 @@ services = { }, "backup" = { - name = "backup" host = "*" auth = false database = false @@ -39,7 +36,6 @@ services = { }, "caddy" = { - name = "caddy" host = "*" ports = [ { @@ -65,7 +61,6 @@ services = { }, "extra_services" = { - name = "extra_services" host = "node001" auth = false database = false @@ -73,7 +68,6 @@ services = { }, "faas" = { - name = "faas" host = "node002" dns = [ { @@ -100,7 +94,6 @@ services = { }, "forgejo" = { - name = "forgejo" host = "node003" dns = [{ domain = "git.serguzim.me" @@ -120,7 +113,6 @@ services = { }, "forgejo_runner" = { - name = "forgejo_runner" host = "node003" auth = false database = false @@ -128,7 +120,6 @@ services = { }, "healthcheck" = { - name = "healthcheck" host = "node003" auth = false database = false @@ -136,7 +127,6 @@ services = { }, "gatus" = { - name = "gatus" host = "node003" dns = [{ domain = "status.serguzim.me" @@ -152,7 +142,6 @@ services = { }, "homebox" = { - name = "homebox" host = "node003" dns = [{ domain = "inventory.serguzim.me" @@ -175,7 +164,6 @@ services = { }, "immich" = { - name = "immich" host = "node002" dns = [{ domain = "gallery.serguzim.me" @@ -200,7 +188,6 @@ services = { }, "influxdb" = { - name = "influxdb" host = "node002" dns = [{ domain = "tick.serguzim.me" @@ -223,7 +210,6 @@ services = { }, "jellyfin" = { - name = "jellyfin" host = "node002" dns = [{ domain = "media.serguzim.me" @@ -246,7 +232,6 @@ services = { }, "lego" = { - name = "lego" host = "*" auth = false database = false @@ -254,7 +239,6 @@ services = { }, "linkwarden" = { - name = "linkwarden" host = "node003" dns = [{ domain = "bookmarks.serguzim.me" @@ -271,7 +255,6 @@ services = { }, mailcowdockerized = { - name = "mailcowdockerized" host = "node003" dns = [{ domain = "mail.serguzim.me" @@ -289,7 +272,6 @@ services = { }, "minio" = { - name = "minio" host = "node002" dns = [ { @@ -316,7 +298,6 @@ services = { }, "ntfy" = { - name = "ntfy" host = "node003" dns = [{ domain = "push.serguzim.me" @@ -339,7 +320,6 @@ services = { }, "postgresql" = { - name = "postgresql" host = "node002" backup = [{ name = "postgresql" @@ -359,7 +339,6 @@ services = { }, "reitanlage_oranienburg" = { - name = "reitanlage_oranienburg" host = "node003" dns = [ { @@ -384,7 +363,6 @@ services = { }, "shlink" = { - name = "shlink" host = "node001" dns = [ { @@ -410,7 +388,6 @@ services = { }, "synapse" = { - name = "synapse" host = "node003" dns = [ { @@ -444,7 +421,6 @@ services = { }, "tandoor" = { - name = "tandoor" host = "node003" dns = [{ domain = "recipes.serguzim.me" @@ -463,7 +439,6 @@ services = { }, "teamspeak_fallback" = { - name = "teamspeak_fallback" host = "node003" dns = [ { @@ -488,7 +463,6 @@ services = { } "telegraf" = { - name = "telegraf" host = "node003" auth = false database = true @@ -496,7 +470,6 @@ services = { }, "tinytinyrss" = { - name = "tinytinyrss" host = "node001" dns = [{ domain = "rss.serguzim.me" @@ -511,7 +484,6 @@ services = { }, "umami" = { - name = "umami" host = "node001" dns = [{ domain = "analytics.serguzim.me" @@ -526,7 +498,6 @@ services = { }, "vikunja" = { - name = "vikunja" host = "node001" dns = [{ domain = "todo.serguzim.me" @@ -546,7 +517,6 @@ services = { }, "watchtower" = { - name = "watchtower" host = "*" auth = false database = false @@ -554,7 +524,6 @@ services = { }, "wiki_js" = { - name = "wiki_js" host = "node001" dns = [{ domain = "wiki.serguzim.me" @@ -569,7 +538,6 @@ services = { }, "woodpecker" = { - name = "woodpecker" host = "node003" dns = [{ domain = "ci.serguzim.me" diff --git a/variables.tf b/variables.tf index 6be1ba9..89db8ea 100644 --- a/variables.tf +++ b/variables.tf @@ -142,7 +142,6 @@ variable "default_ssh_key" { variable "services" { type = map(object({ - name = string host = string dns = optional(list(object({ domain = string