From 1404c46d27ba86155ac44d20f9ef43096b310b24 Mon Sep 17 00:00:00 2001 From: Michael Walker Date: Tue, 10 Dec 2024 21:49:24 +0000 Subject: [PATCH] Split some website configuration into a host template This will be used to geographically distribute barrucadu.co.uk. --- hosts/_templates/barrucadu-website-mirror.nix | 228 ++++++++++++++++++ .../memo-barrucadu-co-uk.caddyfile | 0 .../www-barrucadu-co-uk.caddyfile | 0 hosts/carcosa/configuration.nix | 115 +-------- hosts/carcosa/secrets.yaml | 6 +- 5 files changed, 237 insertions(+), 112 deletions(-) create mode 100644 hosts/_templates/barrucadu-website-mirror.nix rename hosts/{carcosa/caddy => _templates/barrucadu-website-mirror}/memo-barrucadu-co-uk.caddyfile (100%) rename hosts/{carcosa/caddy => _templates/barrucadu-website-mirror}/www-barrucadu-co-uk.caddyfile (100%) diff --git a/hosts/_templates/barrucadu-website-mirror.nix b/hosts/_templates/barrucadu-website-mirror.nix new file mode 100644 index 00000000..3f301ad7 --- /dev/null +++ b/hosts/_templates/barrucadu-website-mirror.nix @@ -0,0 +1,228 @@ +# Configures a webserver for the following domains: +# +# - {www,bookdb,bookmarks,memos,weeknotes,}barrucadu.co.uk +# - {www,}barrucadu.com +# - {www,}barrucadu.dev +# - {www,}barrucadu.uk +# +# The state of each website (static files, databases) needs to be synchronised +# to this machine for the sites to work. +{ config, lib, pkgs, ... }: + +with lib; +let + httpDir = + if config.nixfiles.eraseYourDarlings.enable + then "${toString config.nixfiles.eraseYourDarlings.persistDir}/srv/http" + else "/srv/http"; + + certDirFor = domain: + if config.nixfiles.eraseYourDarlings.enable + then "${toString config.nixfiles.eraseYourDarlings.persistDir}/var/lib/acme/${domain}" + else "/var/lib/acme/${domain}"; + + copyCertsFor = domain: '' + mkdir -p ${toString config.nixfiles.eraseYourDarlings.persistDir}/var/lib/acme || true + rm -r ${toString config.nixfiles.eraseYourDarlings.persistDir}/var/lib/acme/${domain} || true + cp -a /var/lib/acme/${domain} ${toString config.nixfiles.eraseYourDarlings.persistDir}/var/lib/acme/${domain} + ''; + + caddyConfigWithTlsCert = certDomain: '' + encode gzip + + header Permissions-Policy "interest-cohort=()" + header Referrer-Policy "strict-origin-when-cross-origin" + header Strict-Transport-Security "max-age=31536000; includeSubDomains" + header X-Content-Type-Options "nosniff" + header X-Frame-Options "SAMEORIGIN" + + header -Server + + tls ${certDirFor certDomain}/cert.pem ${certDirFor certDomain}/key.pem { + protocols tls1.3 + } + ''; +in +{ + ############################################################################### + ## Certificates + ############################################################################### + + # Provision certificates via DNS challenge + security.acme = { + acceptTerms = true; + + defaults = { + email = "mike@barrucadu.co.uk"; + dnsProvider = "route53"; + dnsPropagationCheck = true; + environmentFile = config.sops.secrets."services/acme/env".path; + reloadServices = [ "caddy" ]; + }; + + certs."barrucadu.co.uk" = { + group = config.services.caddy.group; + domain = "barrucadu.co.uk"; + extraDomainNames = [ "*.barrucadu.co.uk" ]; + postRun = if config.nixfiles.eraseYourDarlings.enable then copyCertsFor "barrucadu.co.uk" else ""; + }; + + certs."barrucadu.com" = { + group = config.services.caddy.group; + domain = "barrucadu.com"; + extraDomainNames = [ "*.barrucadu.com" ]; + postRun = if config.nixfiles.eraseYourDarlings.enable then copyCertsFor "barrucadu.com" else ""; + }; + + certs."barrucadu.dev" = { + group = config.services.caddy.group; + domain = "barrucadu.dev"; + extraDomainNames = [ "*.barrucadu.dev" ]; + postRun = if config.nixfiles.eraseYourDarlings.enable then copyCertsFor "barrucadu.dev" else ""; + }; + + certs."barrucadu.uk" = { + group = config.services.caddy.group; + domain = "barrucadu.uk"; + extraDomainNames = [ "*.barrucadu.uk" ]; + postRun = if config.nixfiles.eraseYourDarlings.enable then copyCertsFor "barrucadu.uk" else ""; + }; + }; + sops.secrets."services/acme/env" = { }; + + + ############################################################################### + ## HTTP + ############################################################################### + + # http + services.caddy.enable = true; + + # redirects + services.caddy.virtualHosts."barrucadu.co.uk".extraConfig = '' + ${caddyConfigWithTlsCert "barrucadu.co.uk"} + + redir https://www.barrucadu.co.uk{uri} + ''; + + services.caddy.virtualHosts."barrucadu.com".extraConfig = '' + ${caddyConfigWithTlsCert "barrucadu.com"} + + redir https://www.barrucadu.co.uk{uri} + ''; + + services.caddy.virtualHosts."www.barrucadu.com".extraConfig = '' + ${caddyConfigWithTlsCert "barrucadu.com"} + + redir https://www.barrucadu.co.uk{uri} + ''; + + services.caddy.virtualHosts."barrucadu.dev".extraConfig = '' + ${caddyConfigWithTlsCert "barrucadu.dev"} + + redir https://www.barrucadu.co.uk + ''; + + services.caddy.virtualHosts."www.barrucadu.dev".extraConfig = '' + ${caddyConfigWithTlsCert "barrucadu.dev"} + + redir https://www.barrucadu.co.uk + ''; + + services.caddy.virtualHosts."barrucadu.uk".extraConfig = '' + ${caddyConfigWithTlsCert "barrucadu.uk"} + + redir https://www.barrucadu.co.uk{uri} + ''; + + services.caddy.virtualHosts."www.barrucadu.uk".extraConfig = '' + ${caddyConfigWithTlsCert "barrucadu.uk"} + + redir https://www.barrucadu.co.uk{uri} + ''; + + # real sites + services.caddy.virtualHosts."www.barrucadu.co.uk".extraConfig = '' + ${caddyConfigWithTlsCert "barrucadu.co.uk"} + + header /fonts/* Cache-Control "public, immutable, max-age=31536000" + header /*.css Cache-Control "public, immutable, max-age=31536000" + + file_server { + root ${httpDir}/barrucadu.co.uk/www + } + + ${fileContents ./barrucadu-website-mirror/www-barrucadu-co-uk.caddyfile} + ''; + + services.caddy.virtualHosts."bookdb.barrucadu.co.uk".extraConfig = '' + ${caddyConfigWithTlsCert "barrucadu.co.uk"} + + reverse_proxy http://127.0.0.1:${toString config.nixfiles.bookdb.port} + ''; + + services.caddy.virtualHosts."bookmarks.barrucadu.co.uk".extraConfig = '' + ${caddyConfigWithTlsCert "barrucadu.co.uk"} + + reverse_proxy http://127.0.0.1:${toString config.nixfiles.bookmarks.port} + ''; + + services.caddy.virtualHosts."memo.barrucadu.co.uk".extraConfig = '' + ${caddyConfigWithTlsCert "barrucadu.co.uk"} + + header /fonts/* Cache-Control "public, immutable, max-age=31536000" + header /mathjax/* Cache-Control "public, immutable, max-age=7776000" + header /*.css Cache-Control "public, immutable, max-age=31536000" + + root * ${httpDir}/barrucadu.co.uk/memo + file_server + + handle_errors { + @410 { + expression {http.error.status_code} == 410 + } + rewrite @410 /410.html + file_server + } + + ${fileContents ./barrucadu-website-mirror/memo-barrucadu-co-uk.caddyfile} + ''; + + services.caddy.virtualHosts."weeknotes.barrucadu.co.uk".extraConfig = '' + ${caddyConfigWithTlsCert "barrucadu.co.uk"} + + header /fonts/* Cache-Control "public, immutable, max-age=31536000" + header /*.css Cache-Control "public, immutable, max-age=31536000" + + file_server { + root ${httpDir}/barrucadu.co.uk/weeknotes + } + ''; + + + ############################################################################### + ## Miscellaneous + ############################################################################### + + # bookdb + nixfiles.bookdb.enable = true; + nixfiles.bookdb.readOnly = true; + + # bookmarks + nixfiles.bookmarks.enable = true; + nixfiles.bookmarks.readOnly = true; + + # Firewall + networking.firewall.allowedTCPPorts = [ 80 443 ]; + + # Concourse access + users.extraUsers.concourse-deploy-robot = { + home = "/var/lib/concourse-deploy-robot"; + createHome = true; + isSystemUser = true; + openssh.authorizedKeys.keys = + [ "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIFilTWek5xNpl82V48oQ99briJhn9BqwCACeRq1dQnZn concourse-worker@cd.barrucadu.dev" ]; + shell = pkgs.bashInteractive; + group = "nogroup"; + }; +} diff --git a/hosts/carcosa/caddy/memo-barrucadu-co-uk.caddyfile b/hosts/_templates/barrucadu-website-mirror/memo-barrucadu-co-uk.caddyfile similarity index 100% rename from hosts/carcosa/caddy/memo-barrucadu-co-uk.caddyfile rename to hosts/_templates/barrucadu-website-mirror/memo-barrucadu-co-uk.caddyfile diff --git a/hosts/carcosa/caddy/www-barrucadu-co-uk.caddyfile b/hosts/_templates/barrucadu-website-mirror/www-barrucadu-co-uk.caddyfile similarity index 100% rename from hosts/carcosa/caddy/www-barrucadu-co-uk.caddyfile rename to hosts/_templates/barrucadu-website-mirror/www-barrucadu-co-uk.caddyfile diff --git a/hosts/carcosa/configuration.nix b/hosts/carcosa/configuration.nix index abd41fbf..5630cdcb 100644 --- a/hosts/carcosa/configuration.nix +++ b/hosts/carcosa/configuration.nix @@ -24,6 +24,10 @@ let httpdir = "${toString config.nixfiles.eraseYourDarlings.persistDir}/srv/http"; in { + imports = [ + ../_templates/barrucadu-website-mirror.nix + ]; + ############################################################################### ## General ############################################################################### @@ -97,7 +101,7 @@ in ## Services ############################################################################### - # WWW + # WWW - there are more websites, see barrucadu-website-mirror services.caddy.enable = true; services.caddy.extraConfig = '' (common_config) { @@ -113,80 +117,11 @@ in } ''; - services.caddy.virtualHosts."barrucadu.co.uk".extraConfig = '' - import common_config - redir https://www.barrucadu.co.uk{uri} - ''; - - services.caddy.virtualHosts."barrucadu.com".extraConfig = '' - import common_config - redir https://www.barrucadu.co.uk{uri} - ''; - - services.caddy.virtualHosts."www.barrucadu.com".extraConfig = '' - import common_config - redir https://www.barrucadu.co.uk{uri} - ''; - - services.caddy.virtualHosts."barrucadu.uk".extraConfig = '' - import common_config - redir https://www.barrucadu.co.uk{uri} - ''; - - services.caddy.virtualHosts."www.barrucadu.uk".extraConfig = '' - import common_config - redir https://www.barrucadu.co.uk{uri} - ''; - - services.caddy.virtualHosts."www.barrucadu.co.uk".extraConfig = '' - import common_config - - header /fonts/* Cache-Control "public, immutable, max-age=31536000" - header /*.css Cache-Control "public, immutable, max-age=31536000" - - file_server { - root ${httpdir}/barrucadu.co.uk/www - } - - ${fileContents ./caddy/www-barrucadu-co-uk.caddyfile} - ''; - - services.caddy.virtualHosts."bookdb.barrucadu.co.uk".extraConfig = '' - import common_config - reverse_proxy http://127.0.0.1:${toString config.nixfiles.bookdb.port} - ''; - - services.caddy.virtualHosts."bookmarks.barrucadu.co.uk".extraConfig = '' - import common_config - reverse_proxy http://127.0.0.1:${toString config.nixfiles.bookmarks.port} - ''; - services.caddy.virtualHosts."foundry.barrucadu.co.uk".extraConfig = '' import common_config reverse_proxy http://localhost:${toString config.nixfiles.foundryvtt.port} ''; - services.caddy.virtualHosts."memo.barrucadu.co.uk".extraConfig = '' - import common_config - - header /fonts/* Cache-Control "public, immutable, max-age=31536000" - header /mathjax/* Cache-Control "public, immutable, max-age=7776000" - header /*.css Cache-Control "public, immutable, max-age=31536000" - - root * ${httpdir}/barrucadu.co.uk/memo - file_server - - handle_errors { - @410 { - expression {http.error.status_code} == 410 - } - rewrite @410 /410.html - file_server - } - - ${fileContents ./caddy/memo-barrucadu-co-uk.caddyfile} - ''; - services.caddy.virtualHosts."misc.barrucadu.co.uk".extraConfig = '' import common_config basicauth /_site/* { @@ -216,27 +151,6 @@ in reverse_proxy http://localhost:${toString config.services.prometheus.port} ''; - services.caddy.virtualHosts."weeknotes.barrucadu.co.uk".extraConfig = '' - import common_config - - header /fonts/* Cache-Control "public, immutable, max-age=31536000" - header /*.css Cache-Control "public, immutable, max-age=31536000" - - file_server { - root ${httpdir}/barrucadu.co.uk/weeknotes - } - ''; - - services.caddy.virtualHosts."barrucadu.dev".extraConfig = '' - import common_config - redir https://www.barrucadu.co.uk - ''; - - services.caddy.virtualHosts."www.barrucadu.dev".extraConfig = '' - import common_config - redir https://www.barrucadu.co.uk - ''; - services.caddy.virtualHosts."cd.barrucadu.dev".extraConfig = '' import common_config reverse_proxy http://127.0.0.1:${toString config.nixfiles.concourse.port} { @@ -377,14 +291,6 @@ in # Docker registry services.dockerRegistry.enable = true; - # bookdb - nixfiles.bookdb.enable = true; - nixfiles.bookdb.readOnly = true; - - # bookmarks - nixfiles.bookmarks.enable = true; - nixfiles.bookmarks.readOnly = true; - # concourse nixfiles.concourse.enable = true; nixfiles.concourse.environmentFile = config.sops.secrets."nixfiles/concourse/env".path; @@ -443,17 +349,6 @@ in services.prometheus.webExternalUrl = "https://prometheus.carcosa.barrucadu.co.uk"; - # Concourse access - users.extraUsers.concourse-deploy-robot = { - home = "/var/lib/concourse-deploy-robot"; - createHome = true; - isSystemUser = true; - openssh.authorizedKeys.keys = - [ "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIFilTWek5xNpl82V48oQ99briJhn9BqwCACeRq1dQnZn concourse-worker@cd.barrucadu.dev" ]; - shell = pkgs.bashInteractive; - group = "nogroup"; - }; - # Extra packages users.extraUsers.barrucadu.packages = with pkgs; [ irssi diff --git a/hosts/carcosa/secrets.yaml b/hosts/carcosa/secrets.yaml index ff460b9b..729d76e6 100644 --- a/hosts/carcosa/secrets.yaml +++ b/hosts/carcosa/secrets.yaml @@ -12,6 +12,8 @@ nixfiles: umami: env: ENC[AES256_GCM,data:FDH0WI/eUDeuylLoL0xNgLawV6ROVTyK3iW25a7z7wesEBPrH1ffs/mQlBiCVG4a0KsC6QCcsCyJxXA2kFrFNm2ktVDouJd4ECuN,iv:SYzk1s24nFgiKswkXiTLSPIBW6v0JoeN6J5o89zzZuQ=,tag:LAwSKw+9GaqHWo9A9gQjsw==,type:str] services: + acme: + env: ENC[AES256_GCM,data:7TXbgIK8VNXxlJxcxUDwfpqE2Si7L9P1jG+Xhus+ikOB1LN118ZFOQv89fAgWVuQEB52uFhRLphIJHhmXIyRh0CSIVfXAJXPOjZC7CyjIrYRx3+saZGgK1a05vE4b7wI4PNVnXcb,iv:FoGAQl7Bu41wskZI4TCEkhBXLir2lyJRaHdLG7YYR4U=,tag:D+mBP9eYsPhHdJyCzcaJvw==,type:str] alertmanager: env: ENC[AES256_GCM,data:0XJmdUlSzYnfKrovd/MpjXpSmazltAc8mgalp8U1nv30ek7OIZJS2ehih26UiwMf9pa/yx4lfoWQlU4Zx4eF7kep/rcr74sznFGRAYxvfVs1DTaWOuvSUqs1ZQOk8xTv5MAxBgP/,iv:F5aHKGSAJO762dXdwhWSCMhanLE/Z/Kbt2rqy+BFSLk=,tag:+/cZRlSzpGjgNQmr8f7dlQ==,type:str] caddy: @@ -45,8 +47,8 @@ sops: dTQwclBRU3JmQ2hBOFVlaVIxZHN4cVEKvVR1bSH4yo2Td8YGNI2hmflT0M3hcYu8 qyYoWd5MFP9VBYKxrF8W2naQSY6Ax4IiVuNbKDDLFooTC93V+oxNDA== -----END AGE ENCRYPTED FILE----- - lastmodified: "2024-01-26T23:48:26Z" - mac: ENC[AES256_GCM,data:Ay1JpYoj+XRBPoPwuy5QJ8jmbxfzyBKe0p1F/Twp/F4nMstPv65+W7D+KLOJg66ki2/3j2nuhJnhsypmG20bAHA+Yr3nRPwO/0NHNQCuTxLmjFI4TjTlqHfofUzjAajXHSThm2bCz4nuqSpI+UVL9VOTJl1OR05jhYclozrZacw=,iv:V3vVrISCkFaLP/67IAd1VLVNpHkzZwtni6ace5kTWIk=,tag:LUCeYK2M85u/aUl3cdBNpQ==,type:str] + lastmodified: "2024-12-10T14:10:21Z" + mac: ENC[AES256_GCM,data:KfkSC9PlfNiMPiVnmormjFRuLP7Fc3DNsSk5nKm9+UdmD+XbxpfKRI9F7pzXs/tSNUn51PKOPz62mhgCpGl3hUcQkzRxdcxVp2+TrVkCx+Oc6EOGsAt7u8Qidki+M3gDYUFoFLFJDSwOGMWNo4Lu8yUjK3B/Y8ZxJRRNLFlQBzQ=,iv:QPgx+Hz73Cm5cjlcAC4wmvVvFV2zr+YyNcRdLrdQgZA=,tag:0gQ1qrbfUS9/dIaEIe5Ksg==,type:str] pgp: [] unencrypted_suffix: _unencrypted version: 3.8.1