migrate hetzner-vm to hetzner-arm; piped currently dead

This commit is contained in:
chaos 2023-09-21 05:06:27 +01:00
parent 4206a3f07e
commit 90f450d7d9
No known key found for this signature in database
78 changed files with 650 additions and 678 deletions

View file

@ -7,30 +7,24 @@ in rec {
hosts = { hosts = {
# map of hostname to config for cluster node # map of hostname to config for cluster node
"piped-fi" = rec { "piped-fi" = rec {
ip = "${internalWireGuard.hosts.hetzner-vm.ip}"; ip = "${internalWireGuard.hosts.hetzner-arm.ip}";
# ssh -L 3014:127.0.0.1:3014 -L 26257:127.0.0.1:26257 hetzner-vm # ssh -L 3014:127.0.0.1:3014 -L 26257:127.0.0.1:26257 hetzner-arm
joinString = "${ip}:${toString ports.cockroachDB}"; joinString = "${ip}:${toString ports.cockroachDB}";
advertiseAddr = joinString; advertiseAddr = joinString;
resticName = "piped-finland";
resticBucket = "Piped-Finland"; resticBucket = "Piped-Finland";
vaultUserName = "hetzner-vm-container-piped-fi";
baseDomain = "piped-fi.owo.monster"; baseDomain = "piped-fi.owo.monster";
}; };
"piped-uk" = rec { "piped-uk" = rec {
ip = "${internalWireGuard.hosts.raspberry.ip}"; ip = "${internalWireGuard.hosts.raspberry.ip}";
# ssh -L 3014:127.0.0.1:3014 -L 26257:127.0.0.1:26257 raspberry # ssh -L 3014:127.0.0.1:3014 -L 26257:127.0.0.1:26257 raspberry
joinString = "${ip}:${toString ports.cockroachDB}"; joinString = "${ip}:${toString ports.cockroachDB}";
advertiseAddr = joinString; advertiseAddr = joinString;
resticName = "piped-uk";
resticBucket = "Piped-UK"; resticBucket = "Piped-UK";
vaultUserName = "rapsberry-container-piped-uk";
baseDomain = "piped-uk.owo.monster"; baseDomain = "piped-uk.owo.monster";
}; };
}; };

View file

@ -1,8 +1,4 @@
rec { rec {
"hetzner-vm" = {
ipv4 = "65.21.182.73";
ipv6 = "2a01:4f9:c010:8beb::1";
};
"hetzner-arm" = { "hetzner-arm" = {
ipv4 = "65.21.145.62"; ipv4 = "65.21.145.62";
ipv6 = "2a01:4f9:c012:9dbf::1"; ipv6 = "2a01:4f9:c012:9dbf::1";

View file

@ -2,10 +2,10 @@ let
pubkeys = builtins.fromJSON (builtins.readFile ./chaosInternalWireGuardPubKeys.json); pubkeys = builtins.fromJSON (builtins.readFile ./chaosInternalWireGuardPubKeys.json);
in rec { in rec {
hosts = { hosts = {
"hetzner-vm" = { "hetzner-arm" = {
ip = "10.69.42.1"; ip = "10.69.42.1";
public = pubkeys."hetzner-vm"; public = pubkeys."hetzner-arm";
endpoint = "hetzner-vm.servers.genderfucked.monster:51820"; endpoint = "hetzner-arm.servers.genderfucked.monster:51820";
}; };
"vault" = { "vault" = {
ip = "10.69.42.2"; ip = "10.69.42.2";
@ -25,11 +25,5 @@ in rec {
public = pubkeys."raspberry"; public = pubkeys."raspberry";
endpoint = "raspberry.servers.genderfucked.monster:51820"; endpoint = "raspberry.servers.genderfucked.monster:51820";
}; };
# TODO: make this .1 again after migration like hetzner-vm
"hetzner-arm" = {
ip = "10.69.42.6";
public = pubkeys."hetzner-arm";
endpoint = "hetzner-arm.servers.genderfucked.monster:51820";
};
}; };
} }

View file

@ -1,5 +1,4 @@
{ {
"hetzner-vm": "xgOQQcZQXftPC25+A7Iyf/XK6/iSo3Osyx6kTrZKdzw=",
"vault": "u8hSeht8xR48O9AN+0cSsXPK0ZZFNcnPhOxdc+rsrlI=", "vault": "u8hSeht8xR48O9AN+0cSsXPK0ZZFNcnPhOxdc+rsrlI=",
"raspberry": "Ghrs0ps2RCsg0My9seLq+8ZFZCM4NLZWE8RiY3g9/RU=", "raspberry": "Ghrs0ps2RCsg0My9seLq+8ZFZCM4NLZWE8RiY3g9/RU=",
"lappy-t495": "8aZBM3f8/qThiHvGlGP1IHLoe61m/3VTwNzCi7CrhF8=", "lappy-t495": "8aZBM3f8/qThiHvGlGP1IHLoe61m/3VTwNzCi7CrhF8=",

View file

@ -93,11 +93,11 @@
] ]
}, },
"locked": { "locked": {
"lastModified": 1694643239, "lastModified": 1695224363,
"narHash": "sha256-pv2k/5FvyirDE8g4TNehzwZ0T4UOMMmqWSQnM/luRtE=", "narHash": "sha256-+hfjJLUMck5G92RVFDZA7LWkR3kOxs5zQ7RPW9t3eM8=",
"owner": "nix-community", "owner": "nix-community",
"repo": "home-manager", "repo": "home-manager",
"rev": "d9b88b43524db1591fb3d9410a21428198d75d49", "rev": "408ba13188ff9ce309fa2bdd2f81287d79773b00",
"type": "github" "type": "github"
}, },
"original": { "original": {
@ -134,11 +134,11 @@
}, },
"nixpkgs-unstable": { "nixpkgs-unstable": {
"locked": { "locked": {
"lastModified": 1694669921, "lastModified": 1694959747,
"narHash": "sha256-6ESpJ6FsftHV96JO/zn6je07tyV2dlLR7SdLsmkegTY=", "narHash": "sha256-CXQ2MuledDVlVM5dLC4pB41cFlBWxRw4tCBsFrq3cRk=",
"owner": "nixos", "owner": "nixos",
"repo": "nixpkgs", "repo": "nixpkgs",
"rev": "f2ea252d23ebc9a5336bf6a61e0644921f64e67c", "rev": "970a59bd19eff3752ce552935687100c46e820a5",
"type": "github" "type": "github"
}, },
"original": { "original": {
@ -150,11 +150,11 @@
}, },
"nur": { "nur": {
"locked": { "locked": {
"lastModified": 1694778311, "lastModified": 1695239195,
"narHash": "sha256-Hu5U9pXwMqUjWF7uh4SKqdKy1QMy9RVGxmst11srSgA=", "narHash": "sha256-0wA8qj7pssnjYAHyt57Js+i96qycM6b0cYXy/nzpBCc=",
"owner": "nix-community", "owner": "nix-community",
"repo": "NUR", "repo": "NUR",
"rev": "7a673ac1f35648a908730206a2793b0e3818bc25", "rev": "e088ab8be212d3c2c5eeb36bac25d384b4dda779",
"type": "github" "type": "github"
}, },
"original": { "original": {
@ -176,11 +176,11 @@
] ]
}, },
"locked": { "locked": {
"lastModified": 1695142252, "lastModified": 1695255877,
"narHash": "sha256-rcYxKVb6Mpna3xNSwRHMw/Yzw3tky0+JuMLM5qoBiUw=", "narHash": "sha256-QKRrwgVS0hHP34IqxjdTC0Lpp7mBVeqFNX22Lbqgmh8=",
"owner": "ChaotiCryptidz", "owner": "ChaotiCryptidz",
"repo": "piped-flake", "repo": "piped-flake",
"rev": "994a8e983eef9071d73c9b2daad9bd42aac0b1aa", "rev": "76f688b1e63ce9ef2b2435cd64e30d10d98fa9cd",
"type": "gitlab" "type": "gitlab"
}, },
"original": { "original": {

View file

@ -7,22 +7,22 @@
inherit (lib.lists) forEach; inherit (lib.lists) forEach;
inherit (builtins) attrNames; inherit (builtins) attrNames;
containerAddresses = import "${self}/hosts/hetzner-vm/data/containerAddresses.nix"; containerAddresses = import "${self}/hosts/hetzner-arm/data/containerAddresses.nix";
in { in {
programs.ssh.enable = true; programs.ssh.enable = true;
programs.ssh.matchBlocks = programs.ssh.matchBlocks =
mkMerge mkMerge
((forEach ["hetzner-vm" "vault" "raspberry" "vault-decrypt"] (hostname: { ((forEach ["hetzner-arm" "hetzner-arm-decrypt" "vault" "vault-decrypt" "raspberry"] (hostname: {
"${hostname}" = { "${hostname}" = {
user = "root"; user = "root";
hostname = "${hostname}.servers.genderfucked.monster"; hostname = "${hostname}.servers.genderfucked.monster";
}; };
})) }))
++ (forEach (attrNames containerAddresses.containers) (name: { ++ (forEach (attrNames containerAddresses.containers) (name: {
"hetzner-vm-container-${name}" = { "hetzner-arm-container-${name}" = {
user = "root"; user = "root";
hostname = "${containerAddresses.containers.${name}}"; hostname = "${containerAddresses.containers.${name}}";
proxyJump = "hetzner-vm"; proxyJump = "hetzner-arm";
}; };
})) }))
++ [ ++ [

View file

@ -8,8 +8,7 @@
hostPath, hostPath,
... ...
}: let }: let
inherit (lib.modules) mkMerge; inherit (lib.modules) mkMerge mkForce;
inherit (lib.lists) forEach;
ports = [ ports = [
# SMTP # SMTP
@ -26,20 +25,6 @@
4190 4190
]; ];
containerLib = import "${self}/lib/containerLib.nix" {
inherit lib;
};
# Using secrets from Host
secrets = config.services.secrets.secrets;
secretsList = [
"mail_restic_password"
"mail_restic_env"
"private_mail_aliases"
"chaos_mail_passwd"
"system_mail_passwd"
"gotosocial_mail_passwd"
];
sharedFiles = [ sharedFiles = [
"/var/lib/acme/mail.owo.monster/fullchain.pem" "/var/lib/acme/mail.owo.monster/fullchain.pem"
"/var/lib/acme/mail.owo.monster/key.pem" "/var/lib/acme/mail.owo.monster/key.pem"
@ -48,74 +33,51 @@ in {
containers.mail = { containers.mail = {
autoStart = true; autoStart = true;
bindMounts = mkMerge [ bindMounts = mkMerge (map (file: {
(containerLib.genBindHostsForSecrets secrets secretsList)
(mkMerge (forEach sharedFiles (file: {
"${file}" = { "${file}" = {
hostPath = "${file}"; hostPath = "${file}";
}; };
}))) })
]; sharedFiles);
specialArgs = { specialArgs = {
inherit inputs; inherit inputs;
inherit tree; inherit tree;
inherit self; inherit self;
inherit hostPath; inherit hostPath;
hostSecrets = secrets;
}; };
config = {config, ...}: { config = {...}: {
nixpkgs.pkgs = pkgs; nixpkgs.pkgs = pkgs;
imports = with tree; imports = with tree;
[ [
profiles.base presets.nixos.containerBase
inputs.home-manager-unstable.nixosModules.home-manager
profiles.nginx profiles.nginx
modules.nixos.secrets
users.root ./secrets.nix
] ]
++ (with hosts.hetzner-vm.containers.mail; [ ++ (with hosts.hetzner-arm.containers.mail; [
modules.mailserver modules.mailserver
profiles.mailserver profiles.mailserver
profiles.restic profiles.restic
]); ]);
# For Shared Secrets
systemd.tmpfiles.rules = [ systemd.tmpfiles.rules = [
"d ${config.services.secrets.secretsDir} - root root"
"d /var/lib/acme - root root" "d /var/lib/acme - root root"
"d /var/lib/acme/mail.owo.monster - root root" "d /var/lib/acme/mail.owo.monster - root root"
]; ];
networking.firewall = { networking.firewall = {
enable = false; enable = mkForce false;
}; };
home-manager.users.root = { home-manager.users.root.home.stateVersion = "23.05";
imports = with tree; [home.base home.dev.small];
home.stateVersion = "23.05";
};
# Manually configure nameserver. Using resolved inside the container seems to fail
# currently
environment.etc."resolv.conf".text = "nameserver 8.8.8.8";
system.stateVersion = "23.05"; system.stateVersion = "23.05";
}; };
}; };
# users for secrets
users.users."dovecot2" = {
uid = config.ids.uids.dovecot2;
group = "dovecot2";
};
users.groups."dovecot2".gid = config.ids.gids.dovecot2;
# ssl for mail # ssl for mail
services.nginx = { services.nginx = {
enable = true; enable = true;

View file

@ -1,9 +1,9 @@
{ {
pkgs, pkgs,
hostSecrets, config,
... ...
}: let }: let
secrets = hostSecrets; secrets = config.services.secrets.secrets;
in { in {
services.mailserver = { services.mailserver = {
enable = true; enable = true;

View file

@ -1,11 +1,12 @@
{ {
pkgs, pkgs,
config, config,
hostSecrets,
... ...
}: let }: let
secrets = hostSecrets; secrets = config.services.secrets.secrets;
mailConfig = config.services.mailserver; mailConfig = config.services.mailserver;
backupPrepareCommand = "${ backupPrepareCommand = "${
(pkgs.writeShellScriptBin "backupPrepareCommand" '' (pkgs.writeShellScriptBin "backupPrepareCommand" ''
systemctl start postgresqlBackup-roundcube --wait systemctl start postgresqlBackup-roundcube --wait
@ -16,8 +17,8 @@ in {
restic restic
(pkgs.writeShellScriptBin "restic-mail" '' (pkgs.writeShellScriptBin "restic-mail" ''
env \ env \
RESTIC_PASSWORD_FILE=${secrets.mail_restic_password.path} \ RESTIC_PASSWORD_FILE=${secrets.restic_password.path} \
$(cat ${secrets.mail_restic_env.path}) \ $(cat ${secrets.restic_env.path}) \
${pkgs.restic}/bin/restic $@ ${pkgs.restic}/bin/restic $@
'') '')
]; ];
@ -36,8 +37,8 @@ in {
# repository is overrided in environmentFile to contain auth # repository is overrided in environmentFile to contain auth
# make sure to keep up to date when changing repository # make sure to keep up to date when changing repository
repository = "rest:https://storage-restic.owo.monster/Mail"; repository = "rest:https://storage-restic.owo.monster/Mail";
passwordFile = "${secrets.mail_restic_password.path}"; passwordFile = "${secrets.restic_password.path}";
environmentFile = "${secrets.mail_restic_env.path}"; environmentFile = "${secrets.restic_env.path}";
pruneOpts = [ pruneOpts = [
"--keep-last 5" "--keep-last 5"

View file

@ -0,0 +1,75 @@
{pkgs, ...}: {
services.secrets = {
enable = true;
vaultLogin = {
enable = true;
loginUsername = "hetzner-arm-container-mail";
};
autoSecrets = {
enable = true;
};
requiredVaultPaths = [
"api-keys/data/storage/restic/Mail"
"api-keys/data/chaos_mail/system"
"api-keys/data/chaos_mail/gotosocial"
"passwords/data/mail"
"private-public-keys/data/restic/Mail"
"infra/data/private-mail-aliases"
];
packages = with pkgs; [
apacheHttpd
];
secrets = {
vault_password = {
manual = true;
};
restic_password = {
fetchScript = ''
simple_get "/private-public-keys/restic/Mail" .password > "$secretFile"
'';
};
restic_env = {
fetchScript = ''
RESTIC_USERNAME=$(simple_get "/api-keys/storage/restic/Mail" .username)
RESTIC_PASSWORD=$(simple_get "/api-keys/storage/restic/Mail" .password)
echo "RESTIC_REPOSITORY=rest:https://$RESTIC_USERNAME:$RESTIC_PASSWORD@storage-restic.owo.monster/Mail" > "$secretFile"
'';
};
private_mail_aliases = {
fetchScript = ''
kv_get "/infra/private-mail-aliases" | jq .data.data | jq -r 'to_entries|map("\(.key) \(.value.to)")[]' > "$secretFile"
'';
};
chaos_mail_passwd = {
user = "dovecot2";
group = "dovecot2";
fetchScript = ''
password=$(simple_get "/passwords/mail" .password)
htpasswd -nbB "" "$password" 2>/dev/null | cut -d: -f2 > "$secretFile"
'';
};
system_mail_passwd = {
user = "dovecot2";
group = "dovecot2";
fetchScript = ''
password=$(simple_get "/api-keys/chaos_mail/system" .password)
htpasswd -nbB "" "$password" 2>/dev/null | cut -d: -f2 > "$secretFile"
'';
};
gotosocial_mail_passwd = {
user = "dovecot2";
group = "dovecot2";
fetchScript = ''
password=$(simple_get "/api-keys/chaos_mail/gotosocial" .password)
htpasswd -nbB "" "$password" 2>/dev/null | cut -d: -f2 > "$secretFile"
'';
};
};
};
}

View file

@ -4,50 +4,40 @@
tree, tree,
lib, lib,
inputs, inputs,
config,
pkgs, pkgs,
config,
... ...
}: let }: let
inherit (lib.modules) mkMerge; inherit (lib.modules) mkMerge;
inherit (lib.lists) forEach; inherit (lib.lists) forEach;
containerName = "music";
containerAddresses = import "${hostPath}/data/containerAddresses.nix"; containerAddresses = import "${hostPath}/data/containerAddresses.nix";
hostIP = containerAddresses.host; hostIP = containerAddresses.host;
containerIP = containerAddresses.containers.${containerName}; containerIP = containerAddresses.containers.${containerName};
containerName = "music";
containerConfig = config.containers.${containerName}.config;
containerLib = import "${self}/lib/containerLib.nix" {
inherit lib;
};
# Using secrets from Host
secrets = config.services.secrets.secrets;
secretsList = [
"mpd_control_password"
"slskd_env"
];
ports = import ./data/ports.nix; ports = import ./data/ports.nix;
# these secrets should probs be in host but im lazy
containerSecrets = config.containers.${containerName}.config.services.secrets.secrets;
pathInContainer = path: "/var/lib/nixos-containers/${containerName}" + path;
in { in {
containers.music = { containers.music = {
autoStart = true; autoStart = true;
privateNetwork = true; privateNetwork = true;
hostAddress = hostIP; hostAddress = hostIP;
localAddress = containerIP; localAddress = containerIP;
bindMounts = containerLib.genBindHostsForSecrets secrets secretsList;
specialArgs = { specialArgs = {
inherit inputs; inherit inputs;
inherit tree; inherit tree;
inherit self; inherit self;
inherit hostPath; inherit hostPath;
hostSecrets = secrets;
}; };
config = {config, ...}: { config = {...}: {
nixpkgs.pkgs = pkgs; nixpkgs.pkgs = pkgs;
imports = with tree; imports = with tree;
@ -58,8 +48,10 @@ in {
profiles.nginx profiles.nginx
profiles.firewallAllow.httpCommon profiles.firewallAllow.httpCommon
./secrets.nix
] ]
++ (with hosts.hetzner-vm.containers.music; [ ++ (with hosts.hetzner-arm.containers.music; [
profiles.mpd profiles.mpd
profiles.musicSync profiles.musicSync
profiles.soulseek profiles.soulseek
@ -75,11 +67,6 @@ in {
slskd-web slskd-web
]; ];
# For Shared Secrets
systemd.tmpfiles.rules = [
"d ${config.services.secrets.secretsDir} - root root"
];
home-manager.users.root.home.stateVersion = "23.05"; home-manager.users.root.home.stateVersion = "23.05";
system.stateVersion = "23.05"; system.stateVersion = "23.05";
}; };
@ -97,7 +84,7 @@ in {
services.nginx.virtualHosts."stream.owo.monster" = let services.nginx.virtualHosts."stream.owo.monster" = let
extraConfig = '' extraConfig = ''
auth_basic "Music Password"; auth_basic "Music Password";
auth_basic_user_file ${secrets.music_stream_passwd.path}; auth_basic_user_file ${pathInContainer containerSecrets.music_stream_passwd.path};
''; '';
in { in {
forceSSL = true; forceSSL = true;
@ -118,15 +105,6 @@ in {
}))); })));
}; };
# For permissions of secrets
users.users."mpd" = {
uid = containerConfig.ids.uids.mpd;
group = "mpd";
};
users.groups."mpd" = {
gid = containerConfig.ids.gids.mpd;
};
networking = { networking = {
nat.forwardPorts = [ nat.forwardPorts = [
{ {

View file

@ -1,14 +1,14 @@
{ {
lib, lib,
pkgs, pkgs,
hostSecrets, config,
... ...
}: let }: let
inherit (lib.strings) concatStringsSep; inherit (lib.strings) concatStringsSep;
inherit (lib.lists) forEach; inherit (lib.lists) forEach;
ports = import ../data/ports.nix; ports = import ../data/ports.nix;
secrets = hostSecrets; secrets = config.services.secrets.secrets;
in { in {
environment.systemPackages = with pkgs; [ environment.systemPackages = with pkgs; [
mpc_cli mpc_cli

View file

@ -1,10 +1,10 @@
{ {
lib, lib,
hostSecrets, config,
... ...
}: let }: let
ports = import ../data/ports.nix; ports = import ../data/ports.nix;
secrets = hostSecrets; secrets = config.services.secrets.secrets;
inherit (lib.modules) mkForce; inherit (lib.modules) mkForce;
in { in {

View file

@ -0,0 +1,57 @@
{pkgs, ...}: {
services.secrets = {
enable = true;
vaultLogin = {
enable = true;
loginUsername = "hetzner-arm-container-music";
};
autoSecrets = {
enable = true;
};
requiredVaultPaths = [
"api-keys/data/mpd"
"api-keys/data/music-stream"
"passwords/data/soulseek"
"passwords/data/slskd"
];
packages = with pkgs; [
apacheHttpd
];
secrets = {
vault_password = {
manual = true;
};
mpd_control_password = {
user = "mpd";
group = "mpd";
fetchScript = ''
simple_get "/api-keys/mpd" .password > "$secretFile"
'';
};
music_stream_passwd = {
user = "nginx";
group = "nginx";
fetchScript = ''
username=$(simple_get "/api-keys/music-stream" .username)
password=$(simple_get "/api-keys/music-stream" .password)
htpasswd -bc "$secretFile" "$username" "$password" 2>/dev/null
'';
};
slskd_env = {
fetchScript = ''
soulseek_password=$(simple_get "/passwords/soulseek" .password)
slskd_password=$(simple_get "/passwords/slskd" .password)
echo > "$secretFile"
echo "SLSKD_SLSK_PASSWORD=$soulseek_password" >> "$secretFile"
echo "SLSKD_PASSWORD=$slskd_password" >> "$secretFile"
'';
};
};
};
}

View file

@ -5,10 +5,12 @@
inputs, inputs,
config, config,
pkgs, pkgs,
lib,
... ...
}: let }: let
inherit (lib.modules) mkForce;
containerName = "piped-fi"; containerName = "piped-fi";
containerConfig = config.containers.${containerName}.config;
pipedSocketForComponent = ( pipedSocketForComponent = (
component: "/var/lib/nixos-containers/${containerName}/var/sockets/piped-${component}.sock" component: "/var/lib/nixos-containers/${containerName}/var/sockets/piped-${component}.sock"
@ -28,26 +30,23 @@ in {
config = {...}: { config = {...}: {
nixpkgs.pkgs = pkgs; nixpkgs.pkgs = pkgs;
imports = with tree; imports = with tree; [
[ presets.nixos.containerBase
presets.nixos.containerBase
profiles.nginx profiles.nginx
profiles.firewallAllow.httpCommon profiles.firewallAllow.httpCommon
profiles.pipedCluster profiles.pipedCluster
./secrets.nix ./secrets.nix
] ];
++ (with hosts.hetzner-vm.containers.piped-fi.profiles; [
restic
]);
# For Shared Secrets
systemd.tmpfiles.rules = [ systemd.tmpfiles.rules = [
"d /var/lib/cockroachdb-certs - root root" "d /var/lib/cockroachdb-certs - root root"
]; ];
networking.firewall.enable = mkForce false;
home-manager.users.root.home.stateVersion = "23.05"; home-manager.users.root.home.stateVersion = "23.05";
system.stateVersion = "23.05"; system.stateVersion = "23.05";
}; };

View file

@ -4,7 +4,7 @@
vaultLogin = { vaultLogin = {
enable = true; enable = true;
loginUsername = "hetzner-vm-container-piped-fi"; loginUsername = "hetzner-arm-container-piped-fi";
}; };
autoSecrets = { autoSecrets = {

View file

@ -2,7 +2,6 @@
self, self,
hostPath, hostPath,
tree, tree,
lib,
inputs, inputs,
config, config,
pkgs, pkgs,
@ -11,34 +10,21 @@
containerAddresses = import "${hostPath}/data/containerAddresses.nix"; containerAddresses = import "${hostPath}/data/containerAddresses.nix";
hostIP = containerAddresses.host; hostIP = containerAddresses.host;
containerIP = containerAddresses.containers.quassel; containerIP = containerAddresses.containers.quassel;
containerLib = import "${self}/lib/containerLib.nix" {
inherit lib;
};
# Using secrets from Host
secrets = config.services.secrets.secrets;
secretsList = [
"quassel_restic_env"
"quassel_restic_password"
];
in { in {
containers.quassel = { containers.quassel = {
autoStart = true; autoStart = true;
privateNetwork = true; privateNetwork = true;
hostAddress = hostIP; hostAddress = hostIP;
localAddress = containerIP; localAddress = containerIP;
bindMounts = containerLib.genBindHostsForSecrets secrets secretsList;
specialArgs = { specialArgs = {
inherit inputs; inherit inputs;
inherit tree; inherit tree;
inherit self; inherit self;
inherit hostPath; inherit hostPath;
hostSecrets = secrets;
}; };
config = {config, ...}: { config = {...}: {
nixpkgs.pkgs = pkgs; nixpkgs.pkgs = pkgs;
imports = with tree; imports = with tree;
@ -46,17 +32,14 @@ in {
presets.nixos.containerBase presets.nixos.containerBase
profiles.sshd profiles.sshd
profiles.firewallAllow.ssh profiles.firewallAllow.ssh
./secrets.nix
] ]
++ (with hosts.hetzner-vm.containers.quassel.profiles; [ ++ (with hosts.hetzner-arm.containers.quassel.profiles; [
quassel quassel
restic restic
]); ]);
# For Shared Secrets
systemd.tmpfiles.rules = [
"d ${config.services.secrets.secretsDir} - root root"
];
networking.firewall.allowedTCPPorts = [4242]; networking.firewall.allowedTCPPorts = [4242];
home-manager.users.root.home.stateVersion = "23.05"; home-manager.users.root.home.stateVersion = "23.05";

View file

@ -1,9 +1,9 @@
{ {
pkgs, pkgs,
hostSecrets, config,
... ...
}: let }: let
secrets = hostSecrets; secrets = config.services.secrets.secrets;
backupPrepareCommand = "${ backupPrepareCommand = "${
(pkgs.writeShellScriptBin "backupPrepareCommand" '' (pkgs.writeShellScriptBin "backupPrepareCommand" ''
@ -15,8 +15,8 @@ in {
restic restic
(pkgs.writeShellScriptBin "restic-quassel" '' (pkgs.writeShellScriptBin "restic-quassel" ''
env \ env \
RESTIC_PASSWORD_FILE=${secrets.quassel_restic_password.path} \ RESTIC_PASSWORD_FILE=${secrets.restic_password.path} \
$(cat ${secrets.quassel_restic_env.path}) \ $(cat ${secrets.restic_env.path}) \
${pkgs.restic}/bin/restic $@ ${pkgs.restic}/bin/restic $@
'') '')
]; ];
@ -31,8 +31,8 @@ in {
# repository is overrided in environmentFile to contain auth # repository is overrided in environmentFile to contain auth
# make sure to keep up to date when changing repository # make sure to keep up to date when changing repository
repository = "rest:https://storage-restic.owo.monster/Quassel"; repository = "rest:https://storage-restic.owo.monster/Quassel";
passwordFile = "${secrets.quassel_restic_password.path}"; passwordFile = "${secrets.restic_password.path}";
environmentFile = "${secrets.quassel_restic_env.path}"; environmentFile = "${secrets.restic_env.path}";
pruneOpts = [ pruneOpts = [
"--keep-last 5" "--keep-last 5"

View file

@ -0,0 +1,38 @@
{...}: {
services.secrets = {
enable = true;
vaultLogin = {
enable = true;
loginUsername = "hetzner-arm-container-quassel";
};
autoSecrets = {
enable = true;
};
requiredVaultPaths = [
"api-keys/data/storage/restic/Quassel"
"private-public-keys/data/restic/Quassel"
];
secrets = {
vault_password = {
manual = true;
};
restic_password = {
fetchScript = ''
simple_get "/private-public-keys/restic/Quassel" .password > "$secretFile"
'';
};
restic_env = {
fetchScript = ''
RESTIC_USERNAME=$(simple_get "/api-keys/storage/restic/Quassel" .username)
RESTIC_PASSWORD=$(simple_get "/api-keys/storage/restic/Quassel" .password)
echo "RESTIC_REPOSITORY=rest:https://$RESTIC_USERNAME:$RESTIC_PASSWORD@storage-restic.owo.monster/Quassel" > "$secretFile"
'';
};
};
};
}

View file

@ -0,0 +1,70 @@
{
self,
hostPath,
tree,
inputs,
config,
pkgs,
...
}: let
containerAddresses = import "${hostPath}/data/containerAddresses.nix";
hostIP = containerAddresses.host;
containerIP = containerAddresses.containers.social;
in {
containers.social = {
autoStart = true;
privateNetwork = true;
hostAddress = hostIP;
localAddress = containerIP;
specialArgs = {
inherit inputs;
inherit tree;
inherit self;
inherit hostPath;
};
config = {...}: {
nixpkgs.pkgs = pkgs;
imports = with tree;
[
presets.nixos.containerBase
profiles.sshd
profiles.firewallAllow.ssh
./secrets.nix
]
++ (with hosts.hetzner-arm.containers.social.profiles; [
gotosocial
restic
]);
networking.firewall = {
enable = true;
allowedTCPPorts = [8080];
};
home-manager.users.root.home.stateVersion = "23.05";
system.stateVersion = "23.05";
};
};
services.nginx.virtualHosts."gts-01.owo.monster" = {
forceSSL = true;
enableACME = true;
locations."/" = {
proxyPass = "http://${containerIP}:8080";
proxyWebsockets = true;
extraConfig = ''
# uncomment if running nginx without recommendedProxySettings
# proxy_set_header Host $host;
# proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
# proxy_set_header X-Forwarded-Proto $scheme;
'';
};
extraConfig = ''
client_max_body_size 128M;
'';
};
}

View file

@ -1,18 +1,18 @@
{ {
hostPath, hostPath,
hostSecrets, config,
... ...
}: let }: let
containerAddresses = import "${hostPath}/data/containerAddresses.nix"; containerAddresses = import "${hostPath}/data/containerAddresses.nix";
hostIP = containerAddresses.host; hostIP = containerAddresses.host;
containerIP = containerAddresses.containers.social; containerIP = containerAddresses.containers.social;
secrets = hostSecrets; secrets = config.services.secrets.secrets;
in { in {
services.gotosocial = { services.gotosocial = {
enable = true; enable = true;
setupPostgresqlDB = true; setupPostgresqlDB = true;
environmentFile = secrets.social_env_secrets.path; environmentFile = secrets.env_secrets.path;
settings = { settings = {
application-name = "chaos-gts"; application-name = "chaos-gts";

View file

@ -2,13 +2,12 @@
pkgs, pkgs,
config, config,
lib, lib,
hostSecrets,
... ...
}: let }: let
inherit (lib.strings) concatStringsSep; inherit (lib.strings) concatStringsSep;
inherit (lib.lists) forEach; inherit (lib.lists) forEach;
secrets = hostSecrets; secrets = config.services.secrets.secrets;
# Because gotosocial-admin isn't a seporate package we need to generate a seperate config # Because gotosocial-admin isn't a seporate package we need to generate a seperate config
# and duplicate the wrapper for use in a systemd unit # and duplicate the wrapper for use in a systemd unit
@ -48,8 +47,8 @@ in {
restic restic
(pkgs.writeShellScriptBin "restic-social" '' (pkgs.writeShellScriptBin "restic-social" ''
env \ env \
RESTIC_PASSWORD_FILE=${secrets.social_restic_password.path} \ RESTIC_PASSWORD_FILE=${secrets.restic_password.path} \
$(cat ${secrets.social_restic_env.path}) \ $(cat ${secrets.restic_env.path}) \
${pkgs.restic}/bin/restic $@ ${pkgs.restic}/bin/restic $@
'') '')
]; ];
@ -64,8 +63,8 @@ in {
# repository is overrided in environmentFile to contain auth # repository is overrided in environmentFile to contain auth
# make sure to keep up to date when changing repository # make sure to keep up to date when changing repository
repository = "rest:https://storage-restic.owo.monster/Social"; repository = "rest:https://storage-restic.owo.monster/Social";
passwordFile = "${secrets.social_restic_password.path}"; passwordFile = "${secrets.restic_password.path}";
environmentFile = "${secrets.social_restic_env.path}"; environmentFile = "${secrets.restic_env.path}";
pruneOpts = [ pruneOpts = [
"--keep-last 10" "--keep-last 10"

View file

@ -0,0 +1,47 @@
{...}: {
services.secrets = {
enable = true;
vaultLogin = {
enable = true;
loginUsername = "hetzner-arm-container-social";
};
autoSecrets = {
enable = true;
};
requiredVaultPaths = [
"private-public-keys/data/restic/Social"
"api-keys/data/storage/restic/Social"
"api-keys/data/chaos_mail/gotosocial"
];
secrets = {
vault_password = {
manual = true;
};
restic_password = {
fetchScript = ''
simple_get "/private-public-keys/restic/Social" .password > "$secretFile"
'';
};
restic_env = {
fetchScript = ''
RESTIC_USERNAME=$(simple_get "/api-keys/storage/restic/Social" .username)
RESTIC_PASSWORD=$(simple_get "/api-keys/storage/restic/Social" .password)
echo "RESTIC_REPOSITORY=rest:https://$RESTIC_USERNAME:$RESTIC_PASSWORD@storage-restic.owo.monster/Social" > "$secretFile"
'';
};
env_secrets = {
fetchScript = ''
smtp_password=$(simple_get "/api-keys/chaos_mail/gotosocial" .password)
echo "GTS_SMTP_PASSWORD=$smtp_password" > "$secretFile"
'';
};
};
};
}

View file

@ -8,7 +8,8 @@
rclone_serve_restic_social = 4212; rclone_serve_restic_social = 4212;
rclone_serve_restic_quassel = 4213; rclone_serve_restic_quassel = 4213;
rclone_serve_restic_piped_finland = 4214; rclone_serve_restic_piped_finland = 4214;
rclone_serve_restic_mail = 4215; rclone_serve_restic_piped_uk = 4215;
rclone_serve_restic_mail = 4216;
rclone_serve_http_music = 4220; rclone_serve_http_music = 4220;
rclone_serve_http_public = 4221; rclone_serve_http_public = 4221;

View file

@ -36,20 +36,14 @@ in {
imports = with tree; imports = with tree;
[ [
profiles.base presets.nixos.containerBase
inputs.home-manager-unstable.nixosModules.home-manager
profiles.sshd profiles.sshd
profiles.firewallAllow.ssh
modules.nixos.rclone-serve
modules.nixos.rclone-sync
modules.nixos.secrets
./secrets.nix ./secrets.nix
users.root
] ]
++ (with hosts.hetzner-vm.containers.storage.profiles; [ ++ (with hosts.hetzner-arm.containers.storage.profiles; [
rcloneConfigs rcloneConfigs
rcloneServe rcloneServe
rcloneSync rcloneSync
@ -58,20 +52,12 @@ in {
environment.systemPackages = with pkgs; [rclone]; environment.systemPackages = with pkgs; [rclone];
home-manager.users.root = {
imports = with tree; [home.base home.dev.small];
home.packages = with pkgs; [vault-bin];
home.stateVersion = "23.05";
};
networking.firewall = { networking.firewall = {
enable = true; enable = true;
allowedTCPPorts = attrValues ports; allowedTCPPorts = attrValues ports;
}; };
# Manually configure nameserver. Using resolved inside the container seems to fail home-manager.users.root.home.stateVersion = "23.05";
# currently
environment.etc."resolv.conf".text = "nameserver 8.8.8.8";
system.stateVersion = "23.05"; system.stateVersion = "23.05";
}; };
}; };
@ -110,6 +96,7 @@ in {
"/Social/".proxyPass = "http://${containerIP}:${toString ports.rclone_serve_restic_social}"; "/Social/".proxyPass = "http://${containerIP}:${toString ports.rclone_serve_restic_social}";
"/Quassel/".proxyPass = "http://${containerIP}:${toString ports.rclone_serve_restic_quassel}"; "/Quassel/".proxyPass = "http://${containerIP}:${toString ports.rclone_serve_restic_quassel}";
"/Piped-Finland/".proxyPass = "http://${containerIP}:${toString ports.rclone_serve_restic_piped_finland}"; "/Piped-Finland/".proxyPass = "http://${containerIP}:${toString ports.rclone_serve_restic_piped_finland}";
"/Piped-UK/".proxyPass = "http://${containerIP}:${toString ports.rclone_serve_restic_piped_uk}";
"/Mail/".proxyPass = "http://${containerIP}:${toString ports.rclone_serve_restic_mail}"; "/Mail/".proxyPass = "http://${containerIP}:${toString ports.rclone_serve_restic_mail}";
}; };
extraConfig = '' extraConfig = ''

View file

@ -126,6 +126,16 @@ in {
"--baseurl=/Piped-Finland/" "--baseurl=/Piped-Finland/"
]; ];
} }
{
id = "restic-piped-uk";
remote = "StorageBox:Backups/Restic/Piped-UK";
type = "restic";
extraArgs = [
"--addr=0.0.0.0:${toString ports.rclone_serve_restic_piped_uk}"
"--htpasswd=${secrets.restic_piped_uk_htpasswd.path}"
"--baseurl=/Piped-UK/"
];
}
{ {
id = "restic-mail"; id = "restic-mail";
remote = "StorageBox:Backups/Restic/Mail"; remote = "StorageBox:Backups/Restic/Mail";

View file

@ -1,17 +1,10 @@
{ {pkgs, ...}: {
config,
pkgs,
...
}: let
cfg = config.services.secrets;
in {
services.secrets = { services.secrets = {
enable = true; enable = true;
vaultLogin = { vaultLogin = {
enable = true; enable = true;
loginUsername = "hetzner-vm-container-storage"; loginUsername = "hetzner-arm-container-storage";
loginPasswordFile = cfg.secrets.vault_password.path;
}; };
autoSecrets = { autoSecrets = {
@ -36,6 +29,7 @@ in {
"api-keys/data/storage/restic/Social" "api-keys/data/storage/restic/Social"
"api-keys/data/storage/restic/Quassel" "api-keys/data/storage/restic/Quassel"
"api-keys/data/storage/restic/Piped-Finland" "api-keys/data/storage/restic/Piped-Finland"
"api-keys/data/storage/restic/Piped-UK"
"api-keys/data/storage/restic/Mail" "api-keys/data/storage/restic/Mail"
"api-keys/data/storage/webdav/main" "api-keys/data/storage/webdav/main"
@ -51,14 +45,6 @@ in {
rclone rclone
]; ];
uidMap = {
"storage" = config.users.users."storage".uid;
};
gidMap = {
"storage" = config.users.groups."storage".gid;
};
extraFunctions = '' extraFunctions = ''
replace_slash_for_sed() { replace_slash_for_sed() {
sed "s#/#\\\/#" sed "s#/#\\\/#"
@ -142,6 +128,16 @@ in {
''; '';
}; };
restic_piped_uk_htpasswd = {
user = "storage";
group = "storage";
fetchScript = ''
username=$(simple_get "/api-keys/storage/restic/Piped-UK" .username)
password=$(simple_get "/api-keys/storage/restic/Piped-UK" .password)
htpasswd -bc "$secretFile" "$username" "$password" 2>/dev/null
'';
};
restic_mail_htpasswd = { restic_mail_htpasswd = {
user = "storage"; user = "storage";
group = "storage"; group = "storage";

View file

@ -5,6 +5,5 @@
social = "192.168.100.12"; social = "192.168.100.12";
music = "192.168.100.13"; music = "192.168.100.13";
quassel = "192.168.100.14"; quassel = "192.168.100.14";
piped = "192.168.100.15";
}; };
} }

View file

@ -3,4 +3,4 @@
systemd-boot.enable = true; systemd-boot.enable = true;
efi.canTouchEfiVariables = true; efi.canTouchEfiVariables = true;
}; };
} }

View file

@ -11,25 +11,24 @@ in {
presets.nixos.serverHetzner presets.nixos.serverHetzner
presets.nixos.serverEncryptedDrive presets.nixos.serverEncryptedDrive
#profiles.nginx profiles.nginx
#profiles.firewallAllow.httpCommon profiles.firewallAllow.httpCommon
#profiles.chaosInternalWireGuard profiles.chaosInternalWireGuard
./hardware.nix ./hardware.nix
./secrets.nix ./secrets.nix
] ]
++ (forEach [ ++ (forEach [
#"social" "social"
#"storage" "storage"
#"music" "music"
#"quassel" "quassel"
#"piped-fi" "piped-fi"
#"mail" "mail"
] (name: ./containers + "/${name}")) ] (name: ./containers + "/${name}"))
++ (with hosts.hetzner-vm.profiles; [ ++ (with hosts.hetzner-arm.profiles; [
#vaultUI gitlabStaticSites
#gitlabStaticSites
]); ]);
# For Containers # For Containers

View file

@ -1,4 +1,4 @@
{pkgs, ...}: { {...}: {
services.secrets = { services.secrets = {
enable = true; enable = true;
@ -9,12 +9,13 @@
autoSecrets = { autoSecrets = {
enable = true; enable = true;
#affectedSystemdServices = [ affectedSystemdServices = [
# "wg-quick-wg0" "wg-quick-wg0"
#]; ];
}; };
requiredVaultPaths = [ requiredVaultPaths = [
"private-public-keys/data/ssh/root@hetzner-arm"
"private-public-keys/data/ssh/root@hetzner-arm-decrypt" "private-public-keys/data/ssh/root@hetzner-arm-decrypt"
"api-keys/data/gitlab/gitlab_pages_serve" "api-keys/data/gitlab/gitlab_pages_serve"
@ -25,11 +26,28 @@
manual = true; manual = true;
}; };
ssh_host_ed25519_key = {
path = "/etc/ssh/ssh_host_ed25519_key";
permissions = "600";
fetchScript = ''
[ ! -d "$SYSROOT/etc/ssh" ] && mkdir -p "$SYSROOT/etc/ssh/"
simple_get "/private-public-keys/ssh/root@hetzner-arm" .private | base64 -d > "$secretFile"
'';
};
ssh_host_ed25519_key_pub = {
path = "/etc/ssh/ssh_host_ed25519_key.pub";
permissions = "600";
fetchScript = ''
[ ! -d "$SYSROOT/etc/ssh" ] && mkdir -p "$SYSROOT/etc/ssh/"
simple_get "/private-public-keys/ssh/root@hetzner-arm" .private | base64 -d > "$secretFile"
'';
};
# this doesn't need to be a secret and can be generated at install time # this doesn't need to be a secret and can be generated at install time
# but it makes it easier to install. # but it makes it easier to install.
# it's stored in /nix store anyway # it's stored in /nix store anyway
ssh_host_ed25519_key = { initrd_ssh_host_ed25519_key = {
path = "/ssh_host_ed25519_key"; path = "/initrd_ssh_host_ed25519_key";
permissions = "600"; permissions = "600";
fetchScript = '' fetchScript = ''
simple_get "/private-public-keys/ssh/root@hetzner-arm-decrypt" .private | base64 -d > "$secretFile" simple_get "/private-public-keys/ssh/root@hetzner-arm-decrypt" .private | base64 -d > "$secretFile"

View file

@ -1,105 +0,0 @@
{
self,
hostPath,
tree,
inputs,
config,
pkgs,
...
}: let
containerAddresses = import "${hostPath}/data/containerAddresses.nix";
hostIP = containerAddresses.host;
containerIP = containerAddresses.containers.social;
# Using secrets from Host
secrets = config.services.secrets.secrets;
in {
containers.social = {
autoStart = true;
privateNetwork = true;
hostAddress = hostIP;
localAddress = containerIP;
bindMounts = {
"${secrets.social_restic_password.path}" = {
hostPath = "${secrets.social_restic_password.path}";
};
"${secrets.social_restic_env.path}" = {
hostPath = "${secrets.social_restic_env.path}";
};
"${secrets.social_env_secrets.path}" = {
hostPath = "${secrets.social_env_secrets.path}";
};
};
specialArgs = {
inherit inputs;
inherit tree;
inherit self;
inherit hostPath;
hostSecrets = secrets;
};
config = {config, ...}: {
nixpkgs.pkgs = pkgs;
imports = with tree;
[
profiles.base
inputs.home-manager-unstable.nixosModules.home-manager
profiles.sshd
modules.nixos.secrets
users.root
]
++ (with hosts.hetzner-vm.containers.social; [
profiles.gotosocial
profiles.restic
]);
environment.systemPackages = with pkgs; [
rclone
restic
];
# For Shared Secrets
systemd.tmpfiles.rules = [
"d ${config.services.secrets.secretsDir} - root root"
];
networking.firewall = {
enable = true;
allowedTCPPorts = [22 8080];
};
home-manager.users.root = {
imports = with tree; [home.base home.dev.small];
home.stateVersion = "23.05";
};
# Manually configure nameserver. Using resolved inside the container seems to fail
# currently
environment.etc."resolv.conf".text = "nameserver 8.8.8.8";
system.stateVersion = "23.05";
};
};
services.nginx.virtualHosts."gts-01.owo.monster" = {
forceSSL = true;
enableACME = true;
locations."/" = {
proxyPass = "http://${containerIP}:8080";
proxyWebsockets = true;
extraConfig = ''
# uncomment if running nginx without recommendedProxySettings
# proxy_set_header Host $host;
# proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
# proxy_set_header X-Forwarded-Proto $scheme;
'';
};
extraConfig = ''
client_max_body_size 128M;
'';
};
}

View file

@ -1,15 +0,0 @@
{...}: {
boot.loader = {
grub = {
enable = true;
device = "/dev/sda";
};
};
boot.initrd.kernelModules = ["nvme"];
fileSystems."/" = {
device = "/dev/sda1";
fsType = "ext4";
};
}

View file

@ -1,46 +0,0 @@
{
tree,
lib,
...
}: let
inherit (lib.lists) forEach;
in {
imports = with tree;
[
presets.nixos.serverBase
presets.nixos.serverHetzner
profiles.nginx
profiles.firewallAllow.httpCommon
profiles.cross.arm64
profiles.chaosInternalWireGuard
./hardware.nix
./secrets.nix
]
++ (forEach [
"social"
"storage"
"music"
"quassel"
"piped-fi"
"mail"
] (name: ./containers + "/${name}"))
++ (with hosts.hetzner-vm.profiles; [
vaultUI
gitlabStaticSites
]);
# For Containers
networking.nat = {
enable = true;
internalInterfaces = ["ve-+"];
externalInterface = "enp1s0";
};
networking.hostName = "hetzner-vm";
home-manager.users.root.home.stateVersion = "23.05";
system.stateVersion = "23.05";
}

View file

@ -1,171 +0,0 @@
{pkgs, ...}: {
services.secrets = {
enable = true;
vaultLogin = {
enable = true;
loginUsername = "hetzner-vm";
};
autoSecrets = {
enable = true;
affectedSystemdServices = [
"wg-quick-wg0"
"container@music"
"container@social"
"container@quassel"
"container@piped-fi"
];
};
packages = with pkgs; [
# for music & mail passwd files
apacheHttpd
];
requiredVaultPaths = [
"api-keys/data/mpd"
"api-keys/data/music-stream"
"api-keys/data/gitlab/gitlab_pages_serve"
"api-keys/data/storage/restic/Mail"
"api-keys/data/storage/restic/Social"
"api-keys/data/storage/restic/Quassel"
"api-keys/data/chaos_mail/system"
"api-keys/data/chaos_mail/gotosocial"
"passwords/data/soulseek"
"passwords/data/slskd"
"passwords/data/mail"
"private-public-keys/data/restic/Mail"
"private-public-keys/data/restic/Social"
"private-public-keys/data/restic/Quassel"
"infra/data/private-mail-aliases"
];
secrets = {
vault_password = {
manual = true;
};
# Used directly by server
# for fetching gitlab static sites
gitlab_env = {
user = "gitlab_artifacts_sync";
group = "gitlab_artifacts_sync";
fetchScript = ''
token=$(simple_get "/api-keys/gitlab/gitlab_pages_serve" .token)
echo "GITLAB_TOKEN=$token" > "$secretFile"
'';
};
# Container: music
mpd_control_password = {
user = "mpd";
group = "mpd";
fetchScript = ''
simple_get "/api-keys/mpd" .password > "$secretFile"
'';
};
music_stream_passwd = {
user = "nginx";
group = "nginx";
fetchScript = ''
username=$(simple_get "/api-keys/music-stream" .username)
password=$(simple_get "/api-keys/music-stream" .password)
htpasswd -bc "$secretFile" "$username" "$password" 2>/dev/null
'';
};
slskd_env = {
fetchScript = ''
soulseek_password=$(simple_get "/passwords/soulseek" .password)
slskd_password=$(simple_get "/passwords/slskd" .password)
echo > "$secretFile"
echo "SLSKD_SLSK_PASSWORD=$soulseek_password" >> "$secretFile"
echo "SLSKD_PASSWORD=$slskd_password" >> "$secretFile"
'';
};
# Container: mail
mail_restic_password = {
fetchScript = ''
simple_get "/private-public-keys/restic/Mail" .password > "$secretFile"
'';
};
mail_restic_env = {
fetchScript = ''
RESTIC_USERNAME=$(simple_get "/api-keys/storage/restic/Mail" .username)
RESTIC_PASSWORD=$(simple_get "/api-keys/storage/restic/Mail" .password)
echo "RESTIC_REPOSITORY=rest:https://$RESTIC_USERNAME:$RESTIC_PASSWORD@storage-restic.owo.monster/Mail" > "$secretFile"
'';
};
private_mail_aliases = {
fetchScript = ''
kv_get "/infra/private-mail-aliases" | jq .data.data | jq -r 'to_entries|map("\(.key) \(.value.to)")[]' > "$secretFile"
'';
};
chaos_mail_passwd = {
user = "dovecot2";
group = "dovecot2";
fetchScript = ''
password=$(simple_get "/passwords/mail" .password)
htpasswd -nbB "" "$password" 2>/dev/null | cut -d: -f2 > "$secretFile"
'';
};
system_mail_passwd = {
user = "dovecot2";
group = "dovecot2";
fetchScript = ''
password=$(simple_get "/api-keys/chaos_mail/system" .password)
htpasswd -nbB "" "$password" 2>/dev/null | cut -d: -f2 > "$secretFile"
'';
};
gotosocial_mail_passwd = {
user = "dovecot2";
group = "dovecot2";
fetchScript = ''
password=$(simple_get "/api-keys/chaos_mail/gotosocial" .password)
htpasswd -nbB "" "$password" 2>/dev/null | cut -d: -f2 > "$secretFile"
'';
};
# Container: social
social_restic_password = {
fetchScript = ''
simple_get "/private-public-keys/restic/Social" .password > "$secretFile"
'';
};
social_restic_env = {
fetchScript = ''
RESTIC_USERNAME=$(simple_get "/api-keys/storage/restic/Social" .username)
RESTIC_PASSWORD=$(simple_get "/api-keys/storage/restic/Social" .password)
echo "RESTIC_REPOSITORY=rest:https://$RESTIC_USERNAME:$RESTIC_PASSWORD@storage-restic.owo.monster/Social" > "$secretFile"
'';
};
social_env_secrets = {
fetchScript = ''
smtp_password=$(simple_get "/api-keys/chaos_mail/gotosocial" .password)
echo "GTS_SMTP_PASSWORD=$smtp_password" > "$secretFile"
'';
};
# Container: quassel
quassel_restic_password = {
fetchScript = ''
simple_get "/private-public-keys/restic/Quassel" .password > "$secretFile"
'';
};
quassel_restic_env = {
fetchScript = ''
RESTIC_USERNAME=$(simple_get "/api-keys/storage/restic/Quassel" .username)
RESTIC_PASSWORD=$(simple_get "/api-keys/storage/restic/Quassel" .password)
echo "RESTIC_REPOSITORY=rest:https://$RESTIC_USERNAME:$RESTIC_PASSWORD@storage-restic.owo.monster/Quassel" > "$secretFile"
'';
};
};
};
}

View file

@ -9,7 +9,7 @@
presets.nixos.encryptedUSB presets.nixos.encryptedUSB
profiles.cross.arm64 profiles.cross.arm64
#profiles.remote-builders profiles.remoteBuilders
profiles.chaosInternalWireGuard profiles.chaosInternalWireGuard
./secrets.nix ./secrets.nix

View file

@ -7,7 +7,7 @@
}; };
music_stream_password = { music_stream_password = {
user = 1000; user = "chaos";
group = "users"; group = "users";
fetchScript = '' fetchScript = ''
simple_get "/api-keys/music-stream" .password > "$secretFile" simple_get "/api-keys/music-stream" .password > "$secretFile"
@ -17,8 +17,6 @@
# Required for home.apps.manualBackupApps # Required for home.apps.manualBackupApps
gitlab_archiver_token = { gitlab_archiver_token = {
user = "chaos"; user = "chaos";
group = "users";
fetchScript = '' fetchScript = ''
simple_get "/api-keys/gitlab/gitlab_archiver" .token > "$secretFile" simple_get "/api-keys/gitlab/gitlab_archiver" .token > "$secretFile"
''; '';
@ -27,8 +25,6 @@
# Required for home.apps.manualBackupApps # Required for home.apps.manualBackupApps
restic_music_env = { restic_music_env = {
user = "chaos"; user = "chaos";
group = "users";
fetchScript = '' fetchScript = ''
api_username=$(simple_get "/api-keys/storage/restic/Music" .username) api_username=$(simple_get "/api-keys/storage/restic/Music" .username)
api_password=$(simple_get "/api-keys/storage/restic/Music" .password) api_password=$(simple_get "/api-keys/storage/restic/Music" .password)

View file

@ -81,16 +81,6 @@ in {
modules = defaultModules ++ [./hetzner-arm/hetzner-arm.nix]; modules = defaultModules ++ [./hetzner-arm/hetzner-arm.nix];
}; };
hetzner-vm = nixosUnstableSystem {
specialArgs =
defaultSpecialArgs
// {
hostPath = ./hetzner-vm;
};
system = "x86_64-linux";
modules = defaultModules ++ [./hetzner-vm/hetzner-vm.nix];
};
vault = nixosUnstableSystem { vault = nixosUnstableSystem {
specialArgs = specialArgs =
defaultSpecialArgs defaultSpecialArgs

View file

@ -5,10 +5,12 @@
inputs, inputs,
config, config,
pkgs, pkgs,
lib,
... ...
}: let }: let
inherit (lib.modules) mkForce;
containerName = "piped-uk"; containerName = "piped-uk";
containerConfig = config.containers.${containerName}.config;
pipedSocketForComponent = ( pipedSocketForComponent = (
component: "/var/lib/nixos-containers/${containerName}/var/sockets/piped-${component}.sock" component: "/var/lib/nixos-containers/${containerName}/var/sockets/piped-${component}.sock"
@ -39,11 +41,12 @@ in {
./secrets.nix ./secrets.nix
]; ];
# For Shared Secrets
systemd.tmpfiles.rules = [ systemd.tmpfiles.rules = [
"d /var/lib/cockroachdb-certs - root root" "d /var/lib/cockroachdb-certs - root root"
]; ];
networking.firewall.enable = mkForce false;
home-manager.users.root.home.stateVersion = "23.05"; home-manager.users.root.home.stateVersion = "23.05";
system.stateVersion = "23.05"; system.stateVersion = "23.05";
}; };

View file

@ -1,25 +1,17 @@
{pkgs, ...}: { {...}: {
services.secrets = { services.secrets = {
enable = true; enable = true;
packages = with pkgs; [rclone];
vaultLogin = { vaultLogin = {
enable = true; enable = true;
loginUsername = "raspberry"; loginUsername = "raspberry-container-piped-uk";
}; };
autoSecrets = { autoSecrets = {
enable = true; enable = true;
affectedSystemdServices = ["wg-quick-wg0" "cockroachdb"]; affectedSystemdServices = ["cockroachdb"];
}; };
extraFunctions = ''
simple_get_obscure() {
rclone obscure "$(simple_get "$@")"
}
'';
requiredVaultPaths = [ requiredVaultPaths = [
"private-public-keys/data/piped-cockroachdb-ca/nodes/raspberry" "private-public-keys/data/piped-cockroachdb-ca/nodes/raspberry"
]; ];
@ -29,7 +21,7 @@
manual = true; manual = true;
}; };
piped_cockroachdb_ca_certificate = { cockroachdb_ca_certificate = {
user = "cockroachdb"; user = "cockroachdb";
group = "cockroachdb"; group = "cockroachdb";
permissions = "600"; permissions = "600";
@ -42,7 +34,7 @@
| base64 -d > "$secretFile" | base64 -d > "$secretFile"
''; '';
}; };
piped_cockroachdb_node_certificate = { cockroachdb_node_certificate = {
user = "cockroachdb"; user = "cockroachdb";
group = "cockroachdb"; group = "cockroachdb";
permissions = "600"; permissions = "600";
@ -55,7 +47,7 @@
| base64 -d > "$secretFile" | base64 -d > "$secretFile"
''; '';
}; };
piped_cockroachdb_node_key = { cockroachdb_node_key = {
user = "cockroachdb"; user = "cockroachdb";
group = "cockroachdb"; group = "cockroachdb";
permissions = "600"; permissions = "600";

View file

@ -15,6 +15,7 @@
}; };
requiredVaultPaths = [ requiredVaultPaths = [
"/private-public-keys/data/ssh/root@vault"
"/private-public-keys/data/ssh/root@vault-decrypt" "/private-public-keys/data/ssh/root@vault-decrypt"
"private-public-keys/data/restic/Vault" "private-public-keys/data/restic/Vault"
@ -27,11 +28,28 @@
manual = true; manual = true;
}; };
ssh_host_ed25519_key = {
path = "/etc/ssh/ssh_host_ed25519_key";
permissions = "600";
fetchScript = ''
[ ! -d "$SYSROOT/etc/ssh" ] && mkdir -p "$SYSROOT/etc/ssh/"
simple_get "/private-public-keys/ssh/root@vault" .private | base64 -d > "$secretFile"
'';
};
ssh_host_ed25519_key_pub = {
path = "/etc/ssh/ssh_host_ed25519_key.pub";
permissions = "600";
fetchScript = ''
[ ! -d "$SYSROOT/etc/ssh" ] && mkdir -p "$SYSROOT/etc/ssh/"
simple_get "/private-public-keys/ssh/root@vault" .private | base64 -d > "$secretFile"
'';
};
# this doesn't need to be a secret and can be generated at install time # this doesn't need to be a secret and can be generated at install time
# but it makes it easier to install. # but it makes it easier to install.
# it's stored in /nix store anyway # it's stored in /nix store anyway
ssh_host_ed25519_key = { initrd_ssh_host_ed25519_key = {
path = "/ssh_host_ed25519_key"; path = "/initrd_ssh_host_ed25519_key";
permissions = "600"; permissions = "600";
fetchScript = '' fetchScript = ''
simple_get "/private-public-keys/ssh/root@vault-decrypt" .private | base64 -d > "$secretFile" simple_get "/private-public-keys/ssh/root@vault-decrypt" .private | base64 -d > "$secretFile"

View file

@ -14,6 +14,7 @@
] ]
++ (with hosts.vault.profiles; [ ++ (with hosts.vault.profiles; [
vault vault
vaultUI
restic restic
]); ]);

View file

@ -8,7 +8,7 @@
inherit (lib.options) mkOption mkEnableOption; inherit (lib.options) mkOption mkEnableOption;
inherit (lib.lists) filter; inherit (lib.lists) filter;
inherit (lib) types; inherit (lib) types;
inherit (builtins) isString listToAttrs; inherit (builtins) isString listToAttrs attrNames;
cfg = config.services.secrets; cfg = config.services.secrets;
@ -115,25 +115,79 @@ in {
extraFunctions = mkOption { extraFunctions = mkOption {
type = types.lines; type = types.lines;
default = ""; default = "";
description = "extra bash functions to add to top of script"; description = "extra bash functions to add to top of script for init";
};
extraCheckFunctions = mkOption {
type = types.lines;
default = "";
description = "extra bash functions to add to top of script for check";
}; };
uidMap = mkOption { uidMap = mkOption {
type = types.attrsOf types.int; type = types.attrsOf types.int;
default = {}; default = listToAttrs (map (
description = "optional mapping of users to user IDs; required for SYSROOT when user isn't available on host"; secretName: let
secretUserName = cfg.secrets.${secretName}.user;
in {
name = "${secretUserName}";
value = config.users.users.${secretUserName}.uid;
}
) (filter
(secretName: let
secret = cfg.secrets.${secretName};
in
isString secret.user
&& (
if config.users.users ? "${secret.user}"
then true
else builtins.trace "warning: secrets module could not find a uid mapping for user ${secret.user}" false
))
(attrNames cfg.secrets)));
description = ''
optional mapping of users to user IDs
required for SYSROOT when user isn't available on host
defaults to getting values from users.users.<name>.uid for all secrets with user set as string
'';
}; };
gidMap = mkOption { gidMap = mkOption {
type = types.attrsOf types.int; type = types.attrsOf types.int;
default = {}; default = listToAttrs (map (
description = "optional mapping of groups to group IDs; required for SYSROOT when group isn't available on host"; secretName: let
secretGroupName = cfg.secrets.${secretName}.group;
in {
name = "${secretGroupName}";
value = config.users.groups.${secretGroupName}.gid;
}
) (filter
(secretName: let
secret = cfg.secrets.${secretName};
in
isString secret.group
&& (
if config.users.groups ? "${secret.group}"
then true
else builtins.trace "warning: secrets module could not find a gid mapping for group ${secret.group}" false
))
(attrNames cfg.secrets)));
description = ''
optional mapping of groups to group IDs
required for SYSROOT when group isn't available on host
defaults to getting values from users.groups.<group>.gid for all secrets with group set as string
'';
}; };
packages = mkOption { packages = mkOption {
type = types.listOf types.package; type = types.listOf types.package;
default = []; default = [];
description = "packages for script"; description = "packages for init script";
};
checkPackages = mkOption {
type = types.listOf types.package;
default = [];
description = "packages for checkscript";
}; };
secrets = mkOption { secrets = mkOption {
@ -241,7 +295,7 @@ in {
// { // {
auto-secrets.partOf = auto-secrets.partOf =
map (unitConfig: unitConfig.name + ".service") map (unitConfig: unitConfig.name + ".service")
(lib.filter (filter
(unitConfig: unitConfig.withPartOf) (unitConfig: unitConfig.withPartOf)
affectedSystemdServices); affectedSystemdServices);
}; };

View file

@ -195,6 +195,11 @@
stat --format "%a" "$1" 2>/dev/null stat --format "%a" "$1" 2>/dev/null
} }
emojiTick=""
emojiCross=""
${cfg.extraCheckFunctions}
GLOBAL_FAIL=false GLOBAL_FAIL=false
'' ''
+ (concatStringsSep "\n" (mapAttrsToList (_name: secret: let + (concatStringsSep "\n" (mapAttrsToList (_name: secret: let
@ -226,40 +231,40 @@
secretFile="$SYSROOT${secretPath}" secretFile="$SYSROOT${secretPath}"
if [[ -f "$SYSROOT${secretPath}" ]]; then if [[ -f "$SYSROOT${secretPath}" ]]; then
echo " File Exists" echo "$emojiTick File Exists"
else else
echo " File Does Not Exist" echo "$emojiCross File Does Not Exist"
LOCAL_FAIL=true LOCAL_FAIL=true
fi fi
if getUserID "$SYSROOT${secretPath}" >/dev/null && ${userCheck}; then if getUserID "$SYSROOT${secretPath}" >/dev/null && ${userCheck}; then
echo " File Is Owned By Correct User" echo "$emojiTick File Is Owned By Correct User"
else else
echo " File Is Not Owned By Correct User (${toString secretUser})" echo "$emojiCross File Is Not Owned By Correct User (${toString secretUser})"
LOCAL_FAIL=true LOCAL_FAIL=true
fi fi
if getGroupID "$SYSROOT${secretPath}" >/dev/null && ${groupCheck}; then if getGroupID "$SYSROOT${secretPath}" >/dev/null && ${groupCheck}; then
echo " File Is Owned By Correct Group" echo "$emojiTick File Is Owned By Correct Group"
else else
echo " File Is Not Owned By Correct Group (${toString secretGroup})" echo "$emojiCross File Is Not Owned By Correct Group (${toString secretGroup})"
LOCAL_FAIL=true LOCAL_FAIL=true
fi fi
if getPermissions "$SYSROOT${secretPath}" >/dev/null && [[ "$(getPermissions "$SYSROOT${secretPath}")" -eq "${secretPermissions}" ]]; then if getPermissions "$SYSROOT${secretPath}" >/dev/null && [[ "$(getPermissions "$SYSROOT${secretPath}")" -eq "${secretPermissions}" ]]; then
echo " File Has Correct Permissions" echo "$emojiTick File Has Correct Permissions"
else else
echo " File Does Not Have Correct Permissions (${secretPermissions})" echo "$emojiCross File Does Not Have Correct Permissions (${secretPermissions})"
LOCAL_FAIL=true LOCAL_FAIL=true
fi fi
${optionalString (secret.checkScript != null) secret.checkScript} ${optionalString (secret.checkScript != null) secret.checkScript}
if [[ "$LOCAL_FAIL" == "true" ]]; then if [[ "$LOCAL_FAIL" == "true" ]]; then
echo " File Did Not Pass The Vibe Check" echo "$emojiCross File Did Not Pass The Vibe Check"
GLOBAL_FAIL=true GLOBAL_FAIL=true
else else
echo " File Passed The Vibe Check" echo "$emojiTick File Passed The Vibe Check"
fi fi
echo echo
@ -267,10 +272,10 @@
cfg.secrets)) cfg.secrets))
+ '' + ''
if [[ "$GLOBAL_FAIL" == "true" ]]; then if [[ "$GLOBAL_FAIL" == "true" ]]; then
echo " One Or More Secrets Did Not Pass The Vibe Check" echo "$emojiCross One Or More Secrets Did Not Pass The Vibe Check"
exit 1 exit 1
else else
echo " All Secrets Passed The Vibe Check" echo "$emojiTick All Secrets Passed The Vibe Check"
fi fi
''; '';
}; };
@ -319,7 +324,7 @@ in rec {
scripts = genScripts cfg; scripts = genScripts cfg;
in (writeShellApplication { in (writeShellApplication {
name = scriptName; name = scriptName;
runtimeInputs = defaultPackages ++ cfg.packages; runtimeInputs = defaultPackages ++ cfg.checkPackages;
text = scripts.checkScript; text = scripts.checkScript;
}) })
); );

View file

@ -18,6 +18,22 @@ in
overlays = [ overlays = [
(import ./overlay) (import ./overlay)
inputs.piped-flake.overlays.default inputs.piped-flake.overlays.default
(_prev: final: {
piped-backend-deps =
final.piped-backend-deps.overrideAttrs
{
# Won't build due to this; added a native-arm64 to all builders on arm64
# https://github.com/NixOS/nixpkgs/issues/255780
requiredSystemFeatures = ["native-arm64"];
};
piped-backend =
final.piped-backend.overrideAttrs
{
# Won't build due to this; added a native-arm64 to all builders on arm64
# https://github.com/NixOS/nixpkgs/issues/255780
requiredSystemFeatures = ["native-arm64"];
};
})
]; ];
}; };
in in
@ -124,18 +140,15 @@ in
# All machines/containers with secrets.nix # All machines/containers with secrets.nix
machines = rec { machines = rec {
"hetzner-vm" = {
containers = ["storage" "piped-fi"];
sshAddress = "hetzner-vm.servers.genderfucked.monster";
};
"hetzner-arm" = { "hetzner-arm" = {
containers = ["storage" "piped-fi"]; containers = ["storage" "music" "quassel" "social" "mail" "piped-fi"];
sshAddress = "hetzner-vm.servers.genderfucked.monster"; sshAddress = "hetzner-arm.servers.genderfucked.monster";
}; };
"vault" = { "vault" = {
sshAddress = "vault.servers.genderfucked.monster"; sshAddress = "vault.servers.genderfucked.monster";
}; };
"raspberry" = { "raspberry" = {
containers = ["piped-uk"];
sshAddress = "raspberry.servers.genderfucked.monster"; sshAddress = "raspberry.servers.genderfucked.monster";
}; };
"lappy-t495" = {}; "lappy-t495" = {};

View file

@ -7,7 +7,7 @@
... ...
}: let }: let
inherit (lib.modules) mkForce; inherit (lib.modules) mkForce;
inherit (lib.lists) optional; inherit (lib.lists) optionals;
system = pkgs.system; system = pkgs.system;
@ -33,10 +33,10 @@ in {
"dm_mod" "dm_mod"
"cryptd" "cryptd"
] ]
++ (lib.optionals (system == "x86_64_linux") ["aesni_intel"]); ++ (optionals (system == "x86_64_linux") ["aesni_intel"]);
secrets = { secrets = {
"/ssh_host_ed25519_key" = "/ssh_host_ed25519_key"; "/ssh_host_ed25519_key" = mkForce "/initrd_ssh_host_ed25519_key";
}; };
luks = { luks = {

View file

@ -1,10 +1,12 @@
{ {
inputs, inputs,
config, config,
pkgs,
lib, lib,
... ...
}: let }: let
inherit (lib.strings) optionalString versionAtLeast; inherit (lib.strings) optionalString versionAtLeast;
inherit (lib.optional);
in { in {
nix = { nix = {
nixPath = ["nixpkgs=${inputs.nixpkgs}"]; nixPath = ["nixpkgs=${inputs.nixpkgs}"];
@ -13,6 +15,7 @@ in {
(versionAtLeast config.nix.package.version "2.4") '' (versionAtLeast config.nix.package.version "2.4") ''
experimental-features = nix-command flakes experimental-features = nix-command flakes
''; '';
settings.system-features = lib.optional (pkgs.system == "aarch64-linux") "native-arm64";
settings.trusted-users = ["root" "@wheel"]; settings.trusted-users = ["root" "@wheel"];
}; };
nixpkgs = { nixpkgs = {
@ -30,6 +33,23 @@ in {
inputs.gitlab_artifacts_sync.overlays.default inputs.gitlab_artifacts_sync.overlays.default
inputs.gitlab_archiver.overlays.default inputs.gitlab_archiver.overlays.default
inputs.piped-flake.overlays.default inputs.piped-flake.overlays.default
(_prev: final: {
piped-backend-deps =
final.piped-backend-deps.overrideAttrs
{
# Won't build due to this; added a native-arm64 to all builders on arm64
# https://github.com/NixOS/nixpkgs/issues/255780
requiredSystemFeatures = ["native-arm64"];
};
piped-backend =
final.piped-backend.overrideAttrs
{
# Won't build due to this; added a native-arm64 to all builders on arm64
# https://github.com/NixOS/nixpkgs/issues/255780
requiredSystemFeatures = ["native-arm64"];
};
})
]; ];
}; };
environment.etc."nixpkgs-commit".text = inputs.nixpkgs-unstable.rev; environment.etc."nixpkgs-commit".text = inputs.nixpkgs-unstable.rev;

View file

@ -12,14 +12,11 @@
currentHostName = config.networking.hostName; currentHostName = config.networking.hostName;
joinString = lib.concatStringsSep "," ([ joinString = lib.concatStringsSep "," (
"localhost:${toString ports.cockroachDB}" map
] (hostName: hosts.${hostName}.joinString)
++ ( (filter (hostName: hostName != currentHostName) (attrNames hosts))
map );
(hostName: hosts.${hostName}.joinString)
(filter (hostName: hostName != currentHostName) (attrNames hosts))
));
in { in {
systemd.services.haproxy.wantedBy = ["piped-backend.service"]; systemd.services.haproxy.wantedBy = ["piped-backend.service"];

View file

@ -1,13 +1,19 @@
{ {
self,
pkgs, pkgs,
config, config,
... ...
}: let }: let
secrets = config.services.secrets.secrets; secrets = config.services.secrets.secrets;
clusterConfig = import "${self}/data/piped/pipedClusterConfig.nix";
currentHostConfig = clusterConfig.hosts.${config.networking.hostName};
inherit (currentHostConfig) resticName resticBucket;
in { in {
environment.systemPackages = with pkgs; [ environment.systemPackages = with pkgs; [
restic restic
(pkgs.writeShellScriptBin "restic-piped-finland" '' (pkgs.writeShellScriptBin "restic-${resticName}" ''
env \ env \
RESTIC_PASSWORD_FILE=${secrets.restic_password.path} \ RESTIC_PASSWORD_FILE=${secrets.restic_password.path} \
$(cat ${secrets.restic_env.path}) \ $(cat ${secrets.restic_env.path}) \
@ -15,14 +21,14 @@ in {
'') '')
]; ];
services.restic.backups.piped-finland = { services.restic.backups.${resticName} = {
user = "root"; user = "root";
paths = [ paths = [
"/var/lib/cockroachdb" "/var/lib/cockroachdb"
"/var/lib/cockroachdb-certs" "/var/lib/cockroachdb-certs"
]; ];
repository = "rest:https://storage-restic.owo.monster/Piped-Finland"; repository = "rest:https://storage-restic.owo.monster/${resticBucket}";
passwordFile = "${secrets.restic_password.path}"; passwordFile = "${secrets.restic_password.path}";
environmentFile = "${secrets.restic_env.path}"; environmentFile = "${secrets.restic_env.path}";

View file

@ -3,7 +3,7 @@
config, config,
... ...
}: let }: let
inherit (lib.modules) mkIf; inherit (lib.modules) mkIf mkMerge;
currentHostname = config.networking.hostName; currentHostname = config.networking.hostName;
@ -26,22 +26,28 @@
}; };
in { in {
nix.buildMachines = [ nix.buildMachines = [
(mkIf (currentHostname != "hetzner-vm") (builderDefaults (mkIf (currentHostname != "hetzner-arm") (mkMerge [
// { builderDefaults
hostName = "hetzner-vm.servers.genderfucked.monster"; {
systems = ["x86_64-linux" "aarch64-linux"]; hostName = "hetzner-arm.servers.genderfucked.monster";
publicHostKey = "c3NoLWVkMjU1MTkgQUFBQUMzTnphQzFsWkRJMU5URTVBQUFBSU1JdDJBQnF3SGhNano5cjZhdHY0WHVYNTh4RVdlU3RrbVhVd3ZNVkd2NHcgcm9vdEBuaXhvcwo="; systems = ["aarch64-linux"];
maxJobs = 3; supportedFeatures = ["native-arm64"];
speedFactor = 2; publicHostKey = "c3NoLWVkMjU1MTkgQUFBQUMzTnphQzFsWkRJMU5URTVBQUFBSUk5cGM0REU1UlV4UUp2T1pwenFOQWVac0JlRW1kcmp4OFlnV3orVXBMckcgcm9vdEBoZXR6bmVyLWFybQo=";
})) maxJobs = 4;
(mkIf (currentHostname != "vault") (builderDefaults speedFactor = 3;
// { }
]))
(mkIf (currentHostname != "vault") (mkMerge [
builderDefaults
{
hostName = "vault.servers.genderfucked.monster"; hostName = "vault.servers.genderfucked.monster";
systems = ["x86_64-linux"]; systems = ["aarch64-linux"];
publicHostKey = "c3NoLWVkMjU1MTkgQUFBQUMzTnphQzFsWkRJMU5URTVBQUFBSU16L1dyaG81MTFGdzhXN3FsU0NUY1V4cWh4TGlBQkJXbFNNNFRNNzJ5RWQgcm9vdEBuaXhvcwo="; supportedFeatures = ["native-arm64"];
maxJobs = 2; publicHostKey = "c3NoLWVkMjU1MTkgQUFBQUMzTnphQzFsWkRJMU5URTVBQUFBSURGTlFjUTdkbUlRS1lqMUVVTFBlcTI4d2hzMTg2YVZ0WitWU05rd3I2aEkgcm9vdEB2YXVsdAo=";
maxJobs = 1;
speedFactor = 1; speedFactor = 1;
})) }
]))
]; ];
nix.distributedBuilds = true; nix.distributedBuilds = true;
nix.extraOptions = "builders-use-substitutes = true"; nix.extraOptions = "builders-use-substitutes = true";

1
result-man Symbolic link
View file

@ -0,0 +1 @@
/nix/store/026j6nzg6hyllkkvzjnqnarxwrc32nsa-bash-5.2-p15-man

9
scripts/deploy/hetzner-arm.sh Executable file
View file

@ -0,0 +1,9 @@
#!/usr/bin/env bash
SCRIPT_DIR=$( cd -- "$( dirname -- "${BASH_SOURCE[0]}" )" &> /dev/null && pwd )
cd $SCRIPT_DIR
cd $(git rev-parse --show-toplevel)
DEFAULT_HOST="root@hetzner-arm.servers.genderfucked.monster"
TARGET_HOST=${HOST:-${DEFAULT_HOST}}
nixos-rebuild switch --flake .#hetzner-arm --target-host "$TARGET_HOST" --use-substitutes -s "$@"

View file

@ -1,7 +0,0 @@
#!/usr/bin/env bash
SCRIPT_DIR=$( cd -- "$( dirname -- "${BASH_SOURCE[0]}" )" &> /dev/null && pwd )
cd $SCRIPT_DIR
cd $(git rev-parse --show-toplevel)
nixos-rebuild switch --flake .#hetzner-vm --target-host hetzner-vm -s "$@"

View file

@ -4,5 +4,6 @@ SCRIPT_DIR=$( cd -- "$( dirname -- "${BASH_SOURCE[0]}" )" &> /dev/null && pwd )
cd $SCRIPT_DIR cd $SCRIPT_DIR
cd $(git rev-parse --show-toplevel) cd $(git rev-parse --show-toplevel)
[ -n "$NO_BUILD_PIPED_BACKEND" ] && ./scripts/buildPipedBackendAArch64.nix DEFAULT_HOST="root@raspberry.servers.genderfucked.monster"
nixos-rebuild switch --flake .#raspberry --target-host raspberry -s "$@" TARGET_HOST=${HOST:-${DEFAULT_HOST}}
nixos-rebuild switch --flake .#raspberry --target-host "$TARGET_HOST" --use-substitutes -s "$@"

View file

@ -4,4 +4,6 @@ SCRIPT_DIR=$( cd -- "$( dirname -- "${BASH_SOURCE[0]}" )" &> /dev/null && pwd )
cd $SCRIPT_DIR cd $SCRIPT_DIR
cd $(git rev-parse --show-toplevel) cd $(git rev-parse --show-toplevel)
nixos-rebuild switch --flake .#vault --target-host vault -s "$@" DEFAULT_HOST="root@vault.servers.genderfucked.monster"
TARGET_HOST=${HOST:-${DEFAULT_HOST}}
nixos-rebuild switch --flake .#vault --target-host "$TARGET_HOST" --use-substitutes -s "$@"

View file

@ -9,6 +9,6 @@ cd $(git rev-parse --show-toplevel)
HOSTNAME=$(hostname) HOSTNAME=$(hostname)
[ "${NO_REBUILD}" == "" ] && ./scripts/rebuild.sh "$@" [ "${NO_REBUILD}" == "" ] && ./scripts/rebuild.sh "$@"
[ "${HOSTNAME}" != "hetzner-vm" ] && ./scripts/deploy/hetzner-vm.sh "$@" [ "${HOSTNAME}" != "hetzner-arm" ] && ./scripts/deploy/hetzner-arm.sh "$@"
[ "${HOSTNAME}" != "vault" ] && ./scripts/deploy/vault.sh "$@" [ "${HOSTNAME}" != "vault" ] && ./scripts/deploy/vault.sh "$@"
[ "${HOSTNAME}" != "raspberry" ] && ./scripts/deploy/raspberry.sh "$@" [ "${HOSTNAME}" != "raspberry" ] && ./scripts/deploy/raspberry.sh "$@"