diff --git a/README.md b/README.md index 1b20119..c40c863 100644 --- a/README.md +++ b/README.md @@ -2,11 +2,9 @@ Work-in-progress NixOS Server Infrastructure based on [valerie's NixOS setup](https://git.dessa.dev/valnyx/nixos/src/commit/fe5d9a5d2275157d3c8da527fe467e1587a86bfe). -## WIP +## Checklist -This is a work-in-progress and currently is not production ready. Please check back later. - -### Checklist +Stage 1: - [x] Get basic install working - [x] Configure reverse proxy @@ -15,7 +13,7 @@ This is a work-in-progress and currently is not production ready. Please check b - [x] Configure NFS mount - [x] Configure Traefik & its dashboard - [x] Configure Caddy for internal service port forwarding (difficult!) - - [ ] Install Tailscale + - [x] Install Tailscale - [x] Install Portainer for other servers & basic admin tasks - [x] Install Forgejo - [x] Install Personal Website @@ -23,13 +21,26 @@ This is a work-in-progress and currently is not production ready. Please check b - [x] Install Passbolt - [x] Install Pterodactyl Panel - [x] Install Immich - - [ ] Install Synapse + - [x] Install Synapse - [x] Restore Forgejo - [ ] Restore Synapse - [x] Restore Passbolt - - [ ] Restore Pterodactyl Panel - - [ ] Restore Immich (difficult!) (halfway done. DB needs restoration but images copied) - - [ ] Get myself a treat :3 + - [x] Restore Pterodactyl Panel + - [x] Restore Immich + +Stage 2: + + - [ ] Bootstrap `milkyway` server + - [ ] Set up WireGuard + +Stage 3: + + - [ ] Migrate main computer config NixOS tree to here + - [ ] Rebrand NixOS repo to be more generic (Pheonix/`pheonix-iac` -> PheoNIX referencing both the concept of Pheonixes and NixOS) + +Stage 4: + + - [ ] Party ## Manifesto diff --git a/hosts/andromeda/configuration.nix b/hosts/andromeda/configuration.nix index 83e0c84..3e73f27 100755 --- a/hosts/andromeda/configuration.nix +++ b/hosts/andromeda/configuration.nix @@ -20,6 +20,7 @@ ./stacks/traefik/docker-compose.nix ./stacks/caddy/docker-compose.nix ## Internal + ./stacks/tailscale/docker-compose.nix ./stacks/portainer/docker-compose.nix ./stacks/passbolt/docker-compose.nix ./stacks/pterodactyl/docker-compose.nix @@ -28,6 +29,7 @@ ./stacks/terah.dev/docker-compose.nix ./stacks/mcaptcha/docker-compose.nix ./stacks/forgejo/docker-compose.nix + ./stacks/synapse/docker-compose.nix ]; users.mutableUsers = false; @@ -90,6 +92,12 @@ }; }; + # Tailscale fixer-uppers + boot.kernel.sysctl = { + "net.ipv4.ip_forward" = 1; + "net.ipv6.conf.all.forwarding" = 1; + }; + # Volumes fileSystems."/mnt/NASBox" = { device = "192.168.0.3:/mnt/Diskette/KubeData"; diff --git a/hosts/andromeda/stacks/synapse/docker-compose.nix b/hosts/andromeda/stacks/synapse/docker-compose.nix new file mode 100644 index 0000000..10c8070 --- /dev/null +++ b/hosts/andromeda/stacks/synapse/docker-compose.nix @@ -0,0 +1,147 @@ +# Auto-generated using compose2nix v0.3.1. +{ config, pkgs, lib, ... }: + +{ + imports = [ + ../../../../system/sops.nix + ]; + + # Containers + virtualisation.oci-containers.containers."synapse-db" = { + image = "docker.io/postgres:17.5"; + environmentFiles = [ config.sops.secrets.synapse_db_docker_env.path ]; + environment = { + "POSTGRES_INITDB_ARGS" = "--encoding=UTF-8 --lc-collate=C --lc-ctype=C"; + "POSTGRES_USER" = "synapse"; + }; + volumes = [ + "synapse_db:/var/lib/postgresql/data:rw" + ]; + log-driver = "journald"; + extraOptions = [ + "--network-alias=db" + "--network=synapse_default" + ]; + }; + + systemd.services."docker-synapse-db" = { + serviceConfig = { + Restart = lib.mkOverride 90 "no"; + }; + after = [ + "docker-network-synapse_default.service" + "docker-volume-synapse_db.service" + ]; + requires = [ + "docker-network-synapse_default.service" + "docker-volume-synapse_db.service" + ]; + partOf = [ + "docker-compose-synapse-root.target" + ]; + wantedBy = [ + "docker-compose-synapse-root.target" + ]; + }; + + virtualisation.oci-containers.containers."synapse-synapse" = { + image = "docker.io/matrixdotorg/synapse:latest"; + environment = { + "SYNAPSE_CONFIG_PATH" = "/data/homeserver.yaml"; + }; + volumes = [ + "synapse_synapse:/data:rw" + "/mnt/NASBox/synapse/uploads:/data/media_store:rw" + "${config.sops.secrets.synapse_synapse_docker_env.path}:/data/homeserver.yaml:ro" + "${config.sops.secrets.synapse_synapse_signing_docker_env.path}:/data/matrix.terah.dev.signing.key:ro" + ]; + labels = { + "traefik.enable" = "true"; + "traefik.http.routers.http-synapse.entryPoints" = "http"; + "traefik.http.routers.http-synapse.rule" = "Host(`matrix.terah.dev`)"; + }; + dependsOn = [ + "synapse-db" + ]; + log-driver = "journald"; + extraOptions = [ + "--network-alias=synapse" + "--network=synapse_default" + ]; + }; + + systemd.services."docker-synapse-synapse" = { + serviceConfig = { + Restart = lib.mkOverride 90 "always"; + RestartMaxDelaySec = lib.mkOverride 90 "1m"; + RestartSec = lib.mkOverride 90 "100ms"; + RestartSteps = lib.mkOverride 90 9; + }; + after = [ + "docker-network-synapse_default.service" + "docker-volume-synapse_synapse.service" + ]; + requires = [ + "docker-network-synapse_default.service" + "docker-volume-synapse_synapse.service" + ]; + partOf = [ + "docker-compose-synapse-root.target" + ]; + wantedBy = [ + "docker-compose-synapse-root.target" + ]; + }; + + # Networks + systemd.services."docker-network-synapse_default" = { + path = [ pkgs.docker ]; + serviceConfig = { + Type = "oneshot"; + RemainAfterExit = true; + ExecStop = "docker network rm -f synapse_default"; + }; + script = '' + docker network inspect synapse_default || docker network create synapse_default + ''; + partOf = [ "docker-compose-synapse-root.target" ]; + wantedBy = [ "docker-compose-synapse-root.target" ]; + }; + + # Volumes + systemd.services."docker-volume-synapse_db" = { + path = [ pkgs.docker ]; + serviceConfig = { + Type = "oneshot"; + RemainAfterExit = true; + }; + script = '' + docker volume inspect synapse_db || docker volume create synapse_db + ''; + partOf = [ "docker-compose-synapse-root.target" ]; + wantedBy = [ "docker-compose-synapse-root.target" ]; + }; + + systemd.services."docker-volume-synapse_synapse" = { + path = [ pkgs.docker ]; + serviceConfig = { + Type = "oneshot"; + RemainAfterExit = true; + }; + script = '' + docker volume inspect synapse_synapse || docker volume create synapse_synapse + ''; + partOf = [ "docker-compose-synapse-root.target" ]; + wantedBy = [ "docker-compose-synapse-root.target" ]; + }; + + # Root service + # When started, this will automatically create all resources and start + # the containers. When stopped, this will teardown all resources. + systemd.targets."docker-compose-synapse-root" = { + unitConfig = { + Description = "Root target generated by compose2nix."; + }; + wantedBy = [ "multi-user.target" ]; + }; +} diff --git a/hosts/andromeda/stacks/tailscale/docker-compose.nix b/hosts/andromeda/stacks/tailscale/docker-compose.nix new file mode 100644 index 0000000..9ea781f --- /dev/null +++ b/hosts/andromeda/stacks/tailscale/docker-compose.nix @@ -0,0 +1,91 @@ +# Auto-generated using compose2nix v0.3.1. +{ config, pkgs, lib, ... }: + +{ + imports = [ + ../../../../system/sops.nix + ]; + + # Containers + virtualisation.oci-containers.containers."tailscale-tailscale" = { + image = "tailscale/tailscale:latest"; + environmentFiles = [ config.sops.secrets.tailscale_docker_env.path ]; + environment = { + "TS_EXTRA_ARGS" = "--advertise-tags=tag:container --advertise-routes=192.168.0.0/24 --advertise-routes=192.168.1.0/24 --advertise-routes=192.168.2.0/24 --advertise-routes=192.168.3.0/24 --advertise-routes=192.168.4.0/24 --advertise-exit-node"; + "TS_STATE_DIR" = "/var/lib/tailscale"; + "TS_USERSPACE" = "false"; + }; + volumes = [ + "tailscale_tailscale:/var/lib/tailscale:rw" + ]; + log-driver = "journald"; + extraOptions = [ + "--cap-add=net_admin" + "--device=/dev/net/tun:/dev/net/tun:rwm" + "--network-alias=tailscale" + "--network=tailscale_default" + ]; + }; + + systemd.services."docker-tailscale-tailscale" = { + serviceConfig = { + Restart = lib.mkOverride 90 "always"; + RestartMaxDelaySec = lib.mkOverride 90 "1m"; + RestartSec = lib.mkOverride 90 "100ms"; + RestartSteps = lib.mkOverride 90 9; + }; + after = [ + "docker-network-tailscale_default.service" + "docker-volume-tailscale_tailscale.service" + ]; + requires = [ + "docker-network-tailscale_default.service" + "docker-volume-tailscale_tailscale.service" + ]; + partOf = [ + "docker-compose-tailscale-root.target" + ]; + wantedBy = [ + "docker-compose-tailscale-root.target" + ]; + }; + + # Networks + systemd.services."docker-network-tailscale_default" = { + path = [ pkgs.docker ]; + serviceConfig = { + Type = "oneshot"; + RemainAfterExit = true; + ExecStop = "docker network rm -f tailscale_default"; + }; + script = '' + docker network inspect tailscale_default || docker network create tailscale_default + ''; + partOf = [ "docker-compose-tailscale-root.target" ]; + wantedBy = [ "docker-compose-tailscale-root.target" ]; + }; + + # Volumes + systemd.services."docker-volume-tailscale_tailscale" = { + path = [ pkgs.docker ]; + serviceConfig = { + Type = "oneshot"; + RemainAfterExit = true; + }; + script = '' + docker volume inspect tailscale_tailscale || docker volume create tailscale_tailscale + ''; + partOf = [ "docker-compose-tailscale-root.target" ]; + wantedBy = [ "docker-compose-tailscale-root.target" ]; + }; + + # Root service + # When started, this will automatically create all resources and start + # the containers. When stopped, this will teardown all resources. + systemd.targets."docker-compose-tailscale-root" = { + unitConfig = { + Description = "Root target generated by compose2nix."; + }; + wantedBy = [ "multi-user.target" ]; + }; +} diff --git a/secrets b/secrets index 4cc9a1c..b1a2a6a 160000 --- a/secrets +++ b/secrets @@ -1 +1 @@ -Subproject commit 4cc9a1c088cd9c651b485e340eac6fdb26912d14 +Subproject commit b1a2a6a7a4c8b75bfcbf8d5cd066dcc201441332 diff --git a/system/sops.nix b/system/sops.nix index de10eb3..7ab3ce8 100755 --- a/system/sops.nix +++ b/system/sops.nix @@ -23,6 +23,7 @@ in }; reverse_proxy_client_privkey = {}; caddy_docker_env = {}; + tailscale_docker_env = {}; forgejo_db_docker_env = {}; forgejo_server_docker_env = {}; mcaptcha_db_docker_env = {}; @@ -33,6 +34,9 @@ in pterodactyl_pterodactyl_docker_env = {}; immich_db_docker_env = {}; immich_immich_docker_env = {}; + synapse_db_docker_env = {}; + synapse_synapse_docker_env = {}; + synapse_synapse_signing_docker_env = {}; }; }; }