commit b8402a9049c941bd32da3efafbe7878f61120a85 Author: Ellie <6687206+wizzeh@users.noreply.github.com> Date: Sun Feb 15 14:57:00 2026 -0800 Initial commit Co-Authored-By: Claude Opus 4.6 diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..77f12ae --- /dev/null +++ b/.gitignore @@ -0,0 +1 @@ +docs/ diff --git a/.sops.yaml b/.sops.yaml new file mode 100644 index 0000000..46b26f7 --- /dev/null +++ b/.sops.yaml @@ -0,0 +1,5 @@ +creation_rules: + - path_regex: .*_vps\.yaml$ + age: age1856wmagg3dz4j07alwqnn6d75655t6wcs8glklyjyezhu5p875fq9sez4p + - path_regex: .*\.yaml$ + age: age126v48dgev6pu3uhe7dtpdhax2yes2ff9u42ke2k2h97e90z8d4psedau7u diff --git a/common.nix b/common.nix new file mode 100644 index 0000000..98b8800 --- /dev/null +++ b/common.nix @@ -0,0 +1,81 @@ +{ lib, ... }: + +{ + nix.gc = { + automatic = true; + dates = "weekly"; + options = "--delete-older-than 7d"; + }; + + time.timeZone = "America/Vancouver"; + + i18n.defaultLocale = "en_US.UTF-8"; + + nix.settings.experimental-features = "nix-command flakes"; + nix.settings.trusted-public-keys = lib.mkAfter [ + "local.yesod.ellie:3cAK/At9uVQq5kNrZco1cuthpgoPy7JfEvd+sBs80fk=" + ]; + + networking.useDHCP = true; + + services.openssh = { + enable = true; + settings = { + PasswordAuthentication = false; + KbdInteractiveAuthentication = false; + PermitRootLogin = "no"; + AllowUsers = [ "ellie" ]; + }; + }; + + services.fail2ban = { + enable = true; + maxretry = 5; + bantime = "1h"; + bantime-increment.enable = true; + jails = { + sshd.settings = { + enabled = true; + maxretry = 3; + }; + nginx-botsearch.settings = { + enabled = true; + filter = "nginx-botsearch"; + backend = "systemd"; + maxretry = 2; + }; + nginx-http-auth.settings = { + enabled = true; + filter = "nginx-http-auth"; + backend = "systemd"; + }; + nginx-bad-request.settings = { + enabled = true; + filter = "nginx-bad-request"; + backend = "systemd"; + }; + }; + }; + + users.mutableUsers = true; + security.sudo.wheelNeedsPassword = true; + + users.users.ellie = { + openssh.authorizedKeys.keys = [ + "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIOv7i4ChPUm+DmELG6uRx0co4quhQ+h7QB4fgcxcC3qx contact@elliehigh.com" + ]; + + isNormalUser = true; + description = "Ellie"; + extraGroups = [ "wheel" ]; + initialPassword = "install"; + }; + + system.autoUpgrade = { + enable = true; + allowReboot = true; + dates = "04:00"; + }; + + system.stateVersion = "25.05"; +} diff --git a/data/service-directory/images/3d-software.png b/data/service-directory/images/3d-software.png new file mode 100644 index 0000000..de5eff8 Binary files /dev/null and b/data/service-directory/images/3d-software.png differ diff --git a/data/service-directory/images/_icons.png b/data/service-directory/images/_icons.png new file mode 100644 index 0000000..9ea1aaa Binary files /dev/null and b/data/service-directory/images/_icons.png differ diff --git a/data/service-directory/images/angel01.gif b/data/service-directory/images/angel01.gif new file mode 100644 index 0000000..3ba7911 Binary files /dev/null and b/data/service-directory/images/angel01.gif differ diff --git a/data/service-directory/images/angel02.gif b/data/service-directory/images/angel02.gif new file mode 100644 index 0000000..578aff6 Binary files /dev/null and b/data/service-directory/images/angel02.gif differ diff --git a/data/service-directory/images/book-01.png b/data/service-directory/images/book-01.png new file mode 100644 index 0000000..d55a56c Binary files /dev/null and b/data/service-directory/images/book-01.png differ diff --git a/data/service-directory/images/book-02.png b/data/service-directory/images/book-02.png new file mode 100644 index 0000000..f925819 Binary files /dev/null and b/data/service-directory/images/book-02.png differ diff --git a/data/service-directory/images/book-03.png b/data/service-directory/images/book-03.png new file mode 100644 index 0000000..a2f2294 Binary files /dev/null and b/data/service-directory/images/book-03.png differ diff --git a/data/service-directory/images/capcut.png b/data/service-directory/images/capcut.png new file mode 100644 index 0000000..7cf2638 Binary files /dev/null and b/data/service-directory/images/capcut.png differ diff --git a/data/service-directory/images/chat.png b/data/service-directory/images/chat.png new file mode 100644 index 0000000..991c92f Binary files /dev/null and b/data/service-directory/images/chat.png differ diff --git a/data/service-directory/images/cursor-01.png b/data/service-directory/images/cursor-01.png new file mode 100644 index 0000000..9b45c00 Binary files /dev/null and b/data/service-directory/images/cursor-01.png differ diff --git a/data/service-directory/images/cursor-02.png b/data/service-directory/images/cursor-02.png new file mode 100644 index 0000000..5eeb333 Binary files /dev/null and b/data/service-directory/images/cursor-02.png differ diff --git a/data/service-directory/images/cursor-03.png b/data/service-directory/images/cursor-03.png new file mode 100644 index 0000000..f15de40 Binary files /dev/null and b/data/service-directory/images/cursor-03.png differ diff --git a/data/service-directory/images/cursor-04-cuttledreams.png b/data/service-directory/images/cursor-04-cuttledreams.png new file mode 100644 index 0000000..f258d7a Binary files /dev/null and b/data/service-directory/images/cursor-04-cuttledreams.png differ diff --git a/data/service-directory/images/cursor-05.png b/data/service-directory/images/cursor-05.png new file mode 100644 index 0000000..fc13b37 Binary files /dev/null and b/data/service-directory/images/cursor-05.png differ diff --git a/data/service-directory/images/cursor-06.png b/data/service-directory/images/cursor-06.png new file mode 100644 index 0000000..88f72a3 Binary files /dev/null and b/data/service-directory/images/cursor-06.png differ diff --git a/data/service-directory/images/cursor-07.png b/data/service-directory/images/cursor-07.png new file mode 100644 index 0000000..8513a77 Binary files /dev/null and b/data/service-directory/images/cursor-07.png differ diff --git a/data/service-directory/images/cursor-08.png b/data/service-directory/images/cursor-08.png new file mode 100644 index 0000000..2f954d8 Binary files /dev/null and b/data/service-directory/images/cursor-08.png differ diff --git a/data/service-directory/images/discord.png b/data/service-directory/images/discord.png new file mode 100644 index 0000000..aa78192 Binary files /dev/null and b/data/service-directory/images/discord.png differ diff --git a/data/service-directory/images/disk drive.png b/data/service-directory/images/disk drive.png new file mode 100644 index 0000000..abefb00 Binary files /dev/null and b/data/service-directory/images/disk drive.png differ diff --git a/data/service-directory/images/downloads.png b/data/service-directory/images/downloads.png new file mode 100644 index 0000000..d03bc09 Binary files /dev/null and b/data/service-directory/images/downloads.png differ diff --git a/data/service-directory/images/drive-01.png b/data/service-directory/images/drive-01.png new file mode 100644 index 0000000..5519280 Binary files /dev/null and b/data/service-directory/images/drive-01.png differ diff --git a/data/service-directory/images/drive-02.png b/data/service-directory/images/drive-02.png new file mode 100644 index 0000000..89a9bf7 Binary files /dev/null and b/data/service-directory/images/drive-02.png differ diff --git a/data/service-directory/images/eyedrop.png b/data/service-directory/images/eyedrop.png new file mode 100644 index 0000000..0564d04 Binary files /dev/null and b/data/service-directory/images/eyedrop.png differ diff --git a/data/service-directory/images/flower.png b/data/service-directory/images/flower.png new file mode 100644 index 0000000..c7fe405 Binary files /dev/null and b/data/service-directory/images/flower.png differ diff --git a/data/service-directory/images/folder-01.png b/data/service-directory/images/folder-01.png new file mode 100644 index 0000000..f2a9de3 Binary files /dev/null and b/data/service-directory/images/folder-01.png differ diff --git a/data/service-directory/images/folder-02.png b/data/service-directory/images/folder-02.png new file mode 100644 index 0000000..858f7fb Binary files /dev/null and b/data/service-directory/images/folder-02.png differ diff --git a/data/service-directory/images/folder-03.png b/data/service-directory/images/folder-03.png new file mode 100644 index 0000000..3188a77 Binary files /dev/null and b/data/service-directory/images/folder-03.png differ diff --git a/data/service-directory/images/folder-04.png b/data/service-directory/images/folder-04.png new file mode 100644 index 0000000..cc39dc9 Binary files /dev/null and b/data/service-directory/images/folder-04.png differ diff --git a/data/service-directory/images/folder-05.png b/data/service-directory/images/folder-05.png new file mode 100644 index 0000000..9dac478 Binary files /dev/null and b/data/service-directory/images/folder-05.png differ diff --git a/data/service-directory/images/folder-06.png b/data/service-directory/images/folder-06.png new file mode 100644 index 0000000..6e949f9 Binary files /dev/null and b/data/service-directory/images/folder-06.png differ diff --git a/data/service-directory/images/folder-07.png b/data/service-directory/images/folder-07.png new file mode 100644 index 0000000..7b0eba0 Binary files /dev/null and b/data/service-directory/images/folder-07.png differ diff --git a/data/service-directory/images/folder-08.png b/data/service-directory/images/folder-08.png new file mode 100644 index 0000000..c3d66f1 Binary files /dev/null and b/data/service-directory/images/folder-08.png differ diff --git a/data/service-directory/images/folder-too many.png b/data/service-directory/images/folder-too many.png new file mode 100644 index 0000000..0cb0eb1 Binary files /dev/null and b/data/service-directory/images/folder-too many.png differ diff --git a/data/service-directory/images/games-01.png b/data/service-directory/images/games-01.png new file mode 100644 index 0000000..0a7465a Binary files /dev/null and b/data/service-directory/images/games-01.png differ diff --git a/data/service-directory/images/games-02.png b/data/service-directory/images/games-02.png new file mode 100644 index 0000000..47e6bfb Binary files /dev/null and b/data/service-directory/images/games-02.png differ diff --git a/data/service-directory/images/games-03.png b/data/service-directory/images/games-03.png new file mode 100644 index 0000000..ca176a8 Binary files /dev/null and b/data/service-directory/images/games-03.png differ diff --git a/data/service-directory/images/illustrator.png b/data/service-directory/images/illustrator.png new file mode 100644 index 0000000..e4f0a89 Binary files /dev/null and b/data/service-directory/images/illustrator.png differ diff --git a/data/service-directory/images/indesign.png b/data/service-directory/images/indesign.png new file mode 100644 index 0000000..504a215 Binary files /dev/null and b/data/service-directory/images/indesign.png differ diff --git a/data/service-directory/images/internet.png b/data/service-directory/images/internet.png new file mode 100644 index 0000000..7a0bafd Binary files /dev/null and b/data/service-directory/images/internet.png differ diff --git a/data/service-directory/images/juice.png b/data/service-directory/images/juice.png new file mode 100644 index 0000000..95b8842 Binary files /dev/null and b/data/service-directory/images/juice.png differ diff --git a/data/service-directory/images/music-01.png b/data/service-directory/images/music-01.png new file mode 100644 index 0000000..ba73718 Binary files /dev/null and b/data/service-directory/images/music-01.png differ diff --git a/data/service-directory/images/music-02.png b/data/service-directory/images/music-02.png new file mode 100644 index 0000000..594a966 Binary files /dev/null and b/data/service-directory/images/music-02.png differ diff --git a/data/service-directory/images/my puter.png b/data/service-directory/images/my puter.png new file mode 100644 index 0000000..6501fc4 Binary files /dev/null and b/data/service-directory/images/my puter.png differ diff --git a/data/service-directory/images/notepad-01.png b/data/service-directory/images/notepad-01.png new file mode 100644 index 0000000..084c379 Binary files /dev/null and b/data/service-directory/images/notepad-01.png differ diff --git a/data/service-directory/images/notepad-02.png b/data/service-directory/images/notepad-02.png new file mode 100644 index 0000000..2f01104 Binary files /dev/null and b/data/service-directory/images/notepad-02.png differ diff --git a/data/service-directory/images/onedrive.png b/data/service-directory/images/onedrive.png new file mode 100644 index 0000000..3dcb8e7 Binary files /dev/null and b/data/service-directory/images/onedrive.png differ diff --git a/data/service-directory/images/photo-software.png b/data/service-directory/images/photo-software.png new file mode 100644 index 0000000..267a5b8 Binary files /dev/null and b/data/service-directory/images/photo-software.png differ diff --git a/data/service-directory/images/photoshop.png b/data/service-directory/images/photoshop.png new file mode 100644 index 0000000..eeec324 Binary files /dev/null and b/data/service-directory/images/photoshop.png differ diff --git a/data/service-directory/images/reference-software.png b/data/service-directory/images/reference-software.png new file mode 100644 index 0000000..8cbed6b Binary files /dev/null and b/data/service-directory/images/reference-software.png differ diff --git a/data/service-directory/images/roesbudtrelbg.gif b/data/service-directory/images/roesbudtrelbg.gif new file mode 100644 index 0000000..73c0344 Binary files /dev/null and b/data/service-directory/images/roesbudtrelbg.gif differ diff --git a/data/service-directory/images/speaker.png b/data/service-directory/images/speaker.png new file mode 100644 index 0000000..80537f5 Binary files /dev/null and b/data/service-directory/images/speaker.png differ diff --git a/data/service-directory/images/telegram.png b/data/service-directory/images/telegram.png new file mode 100644 index 0000000..a78a5ce Binary files /dev/null and b/data/service-directory/images/telegram.png differ diff --git a/data/service-directory/images/torrent.png b/data/service-directory/images/torrent.png new file mode 100644 index 0000000..d446cd7 Binary files /dev/null and b/data/service-directory/images/torrent.png differ diff --git a/data/service-directory/images/trash bin-full.png b/data/service-directory/images/trash bin-full.png new file mode 100644 index 0000000..4e6144d Binary files /dev/null and b/data/service-directory/images/trash bin-full.png differ diff --git a/data/service-directory/images/trash bin.png b/data/service-directory/images/trash bin.png new file mode 100644 index 0000000..a8437c4 Binary files /dev/null and b/data/service-directory/images/trash bin.png differ diff --git a/data/service-directory/images/vpn-software.png b/data/service-directory/images/vpn-software.png new file mode 100644 index 0000000..b847e2c Binary files /dev/null and b/data/service-directory/images/vpn-software.png differ diff --git a/data/service-directory/images/whatsapp.png b/data/service-directory/images/whatsapp.png new file mode 100644 index 0000000..19464ab Binary files /dev/null and b/data/service-directory/images/whatsapp.png differ diff --git a/data/service-directory/index.html b/data/service-directory/index.html new file mode 100644 index 0000000..69c9824 --- /dev/null +++ b/data/service-directory/index.html @@ -0,0 +1,48 @@ + + + + + Service Directory + + + + +
+

service directory

+
+
+ +
+ + diff --git a/data/service-directory/style.css b/data/service-directory/style.css new file mode 100644 index 0000000..7caae9f --- /dev/null +++ b/data/service-directory/style.css @@ -0,0 +1,60 @@ +body { + background: url("images/roesbudtrelbg.gif") repeat; +} + +header { + display: flex; + justify-content: center; + align-items: center; + margin: 0 auto 0 auto; +} + +header h1::before { + content: url("images/angel01.gif"); + display: inline-block; + vertical-align: middle; + margin-right: .05em; +} + +header h1::after { + content: url("images/angel02.gif"); + display: inline-block; + vertical-align: middle; + margin-left: .05em; +} + +service { + display: flex; + flex-direction: column; + align-items: center; + align-content: center; + margin: 1em; + & a { + display: contents; + } + & img { + width: 64px; + height: 64px; + image-rendering: pixelated; + transform-origin: top left; + } +} + +#services { + display: flex; + flex-direction: row; + flex-wrap: wrap; + justify-content: center; + align-items: center; +} + +article { + background-color: white; + border: 1px dashed #fed1c9; + max-width: 30rem; +} +main { + display: flex; + flex-direction: column; + align-items: center; +} diff --git a/flake.lock b/flake.lock new file mode 100644 index 0000000..1a2da29 --- /dev/null +++ b/flake.lock @@ -0,0 +1,251 @@ +{ + "nodes": { + "advisory-db": { + "flake": false, + "locked": { + "lastModified": 1766324728, + "narHash": "sha256-9C+WyE5U3y5w4WQXxmb0ylRyMMsPyzxielWXSHrcDpE=", + "owner": "rustsec", + "repo": "advisory-db", + "rev": "c88b88c62bda077be8aa621d4e89d8701e39cb5d", + "type": "github" + }, + "original": { + "owner": "rustsec", + "repo": "advisory-db", + "type": "github" + } + }, + "continuwuity": { + "inputs": { + "advisory-db": "advisory-db", + "crane": "crane", + "fenix": "fenix", + "flake-compat": "flake-compat", + "flake-parts": "flake-parts", + "nixpkgs": "nixpkgs", + "treefmt-nix": "treefmt-nix" + }, + "locked": { + "lastModified": 1771194746, + "narHash": "sha256-U/BvGW5p405bbsxd8IdMHbSUNVXsLpgPy0ieQwEh3mE=", + "ref": "refs/heads/main", + "rev": "4e1dac32a5c0bf71021027bee35eca53892b069f", + "revCount": 6085, + "type": "git", + "url": "https://forgejo.ellis.link/continuwuation/continuwuity" + }, + "original": { + "type": "git", + "url": "https://forgejo.ellis.link/continuwuation/continuwuity" + } + }, + "crane": { + "locked": { + "lastModified": 1766194365, + "narHash": "sha256-4AFsUZ0kl6MXSm4BaQgItD0VGlEKR3iq7gIaL7TjBvc=", + "owner": "ipetkov", + "repo": "crane", + "rev": "7d8ec2c71771937ab99790b45e6d9b93d15d9379", + "type": "github" + }, + "original": { + "owner": "ipetkov", + "repo": "crane", + "type": "github" + } + }, + "disko": { + "inputs": { + "nixpkgs": [ + "nixpkgs" + ] + }, + "locked": { + "lastModified": 1769524058, + "narHash": "sha256-zygdD6X1PcVNR2PsyK4ptzrVEiAdbMqLos7utrMDEWE=", + "owner": "nix-community", + "repo": "disko", + "rev": "71a3fc97d80881e91710fe721f1158d3b96ae14d", + "type": "github" + }, + "original": { + "owner": "nix-community", + "repo": "disko", + "type": "github" + } + }, + "fenix": { + "inputs": { + "nixpkgs": [ + "continuwuity", + "nixpkgs" + ], + "rust-analyzer-src": "rust-analyzer-src" + }, + "locked": { + "lastModified": 1766299592, + "narHash": "sha256-7u+q5hexu2eAxL2VjhskHvaUKg+GexmelIR2ve9Nbb4=", + "owner": "nix-community", + "repo": "fenix", + "rev": "381579dee168d5ced412e2990e9637ecc7cf1c5d", + "type": "github" + }, + "original": { + "owner": "nix-community", + "repo": "fenix", + "type": "github" + } + }, + "flake-compat": { + "flake": false, + "locked": { + "lastModified": 1765121682, + "narHash": "sha256-4VBOP18BFeiPkyhy9o4ssBNQEvfvv1kXkasAYd0+rrA=", + "owner": "edolstra", + "repo": "flake-compat", + "rev": "65f23138d8d09a92e30f1e5c87611b23ef451bf3", + "type": "github" + }, + "original": { + "owner": "edolstra", + "ref": "master", + "repo": "flake-compat", + "type": "github" + } + }, + "flake-parts": { + "inputs": { + "nixpkgs-lib": "nixpkgs-lib" + }, + "locked": { + "lastModified": 1765835352, + "narHash": "sha256-XswHlK/Qtjasvhd1nOa1e8MgZ8GS//jBoTqWtrS1Giw=", + "owner": "hercules-ci", + "repo": "flake-parts", + "rev": "a34fae9c08a15ad73f295041fec82323541400a9", + "type": "github" + }, + "original": { + "owner": "hercules-ci", + "repo": "flake-parts", + "type": "github" + } + }, + "nixpkgs": { + "locked": { + "lastModified": 1766070988, + "narHash": "sha256-G/WVghka6c4bAzMhTwT2vjLccg/awmHkdKSd2JrycLc=", + "owner": "NixOS", + "repo": "nixpkgs", + "rev": "c6245e83d836d0433170a16eb185cefe0572f8b8", + "type": "github" + }, + "original": { + "owner": "NixOS", + "ref": "nixos-unstable", + "repo": "nixpkgs", + "type": "github" + } + }, + "nixpkgs-lib": { + "locked": { + "lastModified": 1765674936, + "narHash": "sha256-k00uTP4JNfmejrCLJOwdObYC9jHRrr/5M/a/8L2EIdo=", + "owner": "nix-community", + "repo": "nixpkgs.lib", + "rev": "2075416fcb47225d9b68ac469a5c4801a9c4dd85", + "type": "github" + }, + "original": { + "owner": "nix-community", + "repo": "nixpkgs.lib", + "type": "github" + } + }, + "nixpkgs_2": { + "locked": { + "lastModified": 1771008912, + "narHash": "sha256-gf2AmWVTs8lEq7z/3ZAsgnZDhWIckkb+ZnAo5RzSxJg=", + "owner": "nixos", + "repo": "nixpkgs", + "rev": "a82ccc39b39b621151d6732718e3e250109076fa", + "type": "github" + }, + "original": { + "owner": "nixos", + "ref": "nixos-unstable", + "repo": "nixpkgs", + "type": "github" + } + }, + "root": { + "inputs": { + "continuwuity": "continuwuity", + "disko": "disko", + "nixpkgs": "nixpkgs_2", + "sops-nix": "sops-nix" + } + }, + "rust-analyzer-src": { + "flake": false, + "locked": { + "lastModified": 1766253897, + "narHash": "sha256-ChK07B1aOlJ4QzWXpJo+y8IGAxp1V9yQ2YloJ+RgHRw=", + "owner": "rust-lang", + "repo": "rust-analyzer", + "rev": "765b7bdb432b3740f2d564afccfae831d5a972e4", + "type": "github" + }, + "original": { + "owner": "rust-lang", + "ref": "nightly", + "repo": "rust-analyzer", + "type": "github" + } + }, + "sops-nix": { + "inputs": { + "nixpkgs": [ + "nixpkgs" + ] + }, + "locked": { + "lastModified": 1771166946, + "narHash": "sha256-UFc4lfGBr+wJmwgDGJDn1cVD6DTr0/8TdronNUiyXlU=", + "owner": "Mic92", + "repo": "sops-nix", + "rev": "2d0cf89b4404529778bc82de7e42b5754e0fe4fa", + "type": "github" + }, + "original": { + "owner": "Mic92", + "repo": "sops-nix", + "type": "github" + } + }, + "treefmt-nix": { + "inputs": { + "nixpkgs": [ + "continuwuity", + "nixpkgs" + ] + }, + "locked": { + "lastModified": 1766000401, + "narHash": "sha256-+cqN4PJz9y0JQXfAK5J1drd0U05D5fcAGhzhfVrDlsI=", + "owner": "numtide", + "repo": "treefmt-nix", + "rev": "42d96e75aa56a3f70cab7e7dc4a32868db28e8fd", + "type": "github" + }, + "original": { + "owner": "numtide", + "repo": "treefmt-nix", + "type": "github" + } + } + }, + "root": "root", + "version": 7 +} diff --git a/flake.nix b/flake.nix new file mode 100644 index 0000000..5318df1 --- /dev/null +++ b/flake.nix @@ -0,0 +1,90 @@ +{ + inputs = { + nixpkgs.url = "github:nixos/nixpkgs/nixos-unstable"; + + disko = { + url = "github:nix-community/disko"; + inputs.nixpkgs.follows = "nixpkgs"; + }; + + sops-nix = { + url = "github:Mic92/sops-nix"; + inputs.nixpkgs.follows = "nixpkgs"; + }; + + continuwuity = { + url = "git+https://forgejo.ellis.link/continuwuation/continuwuity"; + }; + }; + + outputs = + { + nixpkgs, + disko, + sops-nix, + continuwuity, + ... + }: + let + system = "x86_64-linux"; + pkgs = import nixpkgs { + inherit system; + config.allowUnfree = true; + }; + in + { + nixosConfigurations.home-server = nixpkgs.lib.nixosSystem { + inherit system; + specialArgs = { inherit continuwuity; }; + + modules = [ + disko.nixosModules.disko + sops-nix.nixosModules.sops + ( + { ... }: + { + nixpkgs = { + config.allowUnfree = true; + system = "x86_64-linux"; + }; + } + ) + ./hosts/homeserver/hardware-configuration.nix + ./common.nix + ./hosts/homeserver/configuration.nix + ./hosts/homeserver/setup.nix + ./services/website.nix + ./services/wireguard-inner.nix + ./services/matrix.nix + ./services/ergo.nix + ./services/akkoma.nix + ]; + }; + + nixosConfigurations.vps = nixpkgs.lib.nixosSystem { + inherit system; + + modules = [ + disko.nixosModules.disko + sops-nix.nixosModules.sops + ( + { ... }: + { + nixpkgs = { + config.allowUnfree = true; + system = "x86_64-linux"; + }; + } + ) + ./hosts/vps/hardware-configuration.nix + ./common.nix + ./hosts/vps/configuration.nix + ./hosts/vps/disko-config.nix + ./services/coturn.nix + ./services/wireguard-outer.nix + ]; + }; + + formatter.${system} = pkgs.nixfmt-tree; + }; +} diff --git a/hosts/homeserver/configuration.nix b/hosts/homeserver/configuration.nix new file mode 100644 index 0000000..434785a --- /dev/null +++ b/hosts/homeserver/configuration.nix @@ -0,0 +1,70 @@ +{ + modulesPath, + lib, + pkgs, + config, + ... +}: + +{ + boot.loader.systemd-boot = { + enable = true; + configurationLimit = 10; + }; + boot.loader.efi.canTouchEfiVariables = true; + + networking.hostName = "ellie-server"; + networking.useNetworkd = true; + + systemd.network.enable = true; + + hardware.graphics = { + enable = true; + }; + hardware.nvidia = { + package = config.boot.kernelPackages.nvidiaPackages.stable; + modesetting.enable = true; + open = false; + }; + + services.resolved.enable = true; + + services.openssh = { + openFirewall = false; + }; + + networking.nftables.enable = true; + networking.firewall = { + enable = true; + allowPing = true; + + checkReversePath = true; + rejectPackets = true; + allowedTCPPorts = [ ]; + interfaces."enp34s0".allowedTCPPorts = [ ]; + extraInputRules = '' + ip saddr 192.168.1.0/24 tcp dport {22, 8096, 8920, 3000, 8282, 9696, 8989, 7878, 80} accept + tcp dport {22, 8096, 8920, 3000, 8282, 9696, 8989, 7878, 80} drop + + ip saddr 192.168.1.0/24 udp dport 5353 accept + udp dport 5353 drop + ''; + }; + + users.groups.media = { }; + #users.users.radarr.extraGroups = [ "media" ]; + #users.users.sonarr.extraGroups = [ "media" ]; + #users.users.jellyfin.extraGroups = [ "media" ]; + + sops.age.keyFile = "/home/ellie/.config/sops/age/keys.txt"; + + environment.systemPackages = with pkgs; [ + git + vim + dropbear + age + sops + ]; + + system.stateVersion = "25.05"; +} diff --git a/hosts/homeserver/hardware-configuration.nix b/hosts/homeserver/hardware-configuration.nix new file mode 100644 index 0000000..a1db409 --- /dev/null +++ b/hosts/homeserver/hardware-configuration.nix @@ -0,0 +1,25 @@ +{ + config, + lib, + pkgs, + modulesPath, + ... +}: + +{ + imports = [ + (modulesPath + "/installer/scan/not-detected.nix") + ]; + + boot.initrd.availableKernelModules = [ + "xhci-pci" + "ahci" + "usbhid" + ]; + boot.initrd.kernelModules = [ ]; + boot.kernelModules = [ ]; + boot.extraModulePackages = [ ]; + + nixpkgs.hostPlatform = lib.mkDefault "x86_64-linux"; + hardware.cpu.amd.updateMicrocode = lib.mkDefault config.hardware.enableRedistributableFirmware; +} diff --git a/hosts/homeserver/setup.nix b/hosts/homeserver/setup.nix new file mode 100644 index 0000000..2b45fd3 --- /dev/null +++ b/hosts/homeserver/setup.nix @@ -0,0 +1,91 @@ +{ ... }: + +{ + boot.initrd.network = { + enable = true; + ssh = { + enable = true; + authorizedKeys = [ + "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIOv7i4ChPUm+DmELG6uRx0co4quhQ+h7QB4fgcxcC3qx contact@elliehigh.com" + ]; + shell = "/bin/cryptsetup-askpass"; + hostKeys = [ "/etc/initrd-ssh/ssh_host_ed25519_dropbear" ]; + }; + }; + + boot.initrd.preLVMCommands = '' + iptables -A INPUT -s 192.168.1.0/24 -p tcp --dport 22 -j ACCEPT + iptables -A INPUT -p tcp --dport 22 -j DROP + ''; + + fileSystems."/media" = { + device = "/dev/mapper/crypted"; + fsType = "btrfs"; + options = [ + "subvol=/media" + "compress=zstd" + "noatime" + ]; + }; + + disko.devices.disk.main = { + type = "disk"; + device = "/dev/sda"; + content = { + "type" = "gpt"; + partitions = { + ESP = { + size = "512M"; + type = "EF00"; + content = { + type = "filesystem"; + format = "vfat"; + mountpoint = "/boot"; + mountOptions = [ "umask=0077" ]; + }; + }; + luks = { + size = "100%"; + content = { + type = "luks"; + name = "crypted"; + settings = { + allowDiscards = true; + }; + content = { + type = "btrfs"; + # extraArgs = [ "-f" ]; + subvolumes = { + "/root" = { + mountpoint = "/"; + mountOptions = [ + "compress=zstd" + "noatime" + ]; + }; + "/home" = { + mountpoint = "/home"; + mountOptions = [ + "compress=zstd" + "noatime" + ]; + }; + "/jellyfin" = { + mountpoint = "/jellyfin"; + mountOptions = [ + "compress=zstd" + "noatime" + ]; + }; + "/swap" = { + mountpoint = "/.swapvol"; + swap.swapfile.size = "36G"; + }; + }; + }; + }; + }; + }; + }; + }; +} diff --git a/hosts/vps/configuration.nix b/hosts/vps/configuration.nix new file mode 100644 index 0000000..034d422 --- /dev/null +++ b/hosts/vps/configuration.nix @@ -0,0 +1,7 @@ +{ ... }: + +{ + boot.loader.grub.enable = true; + + sops.age.keyFile = "/var/lib/sops-nix/key.txt"; +} diff --git a/hosts/vps/disko-config.nix b/hosts/vps/disko-config.nix new file mode 100644 index 0000000..4bc9b3d --- /dev/null +++ b/hosts/vps/disko-config.nix @@ -0,0 +1,39 @@ +{ ... }: + +{ + disko.devices = { + disk = { + main = { + type = "disk"; + device = "/dev/sda"; + content = { + type = "gpt"; + partitions = { + boot = { + size = "1M"; + type = "EF02"; + priority = 1; + }; + ESP = { + size = "512M"; + type = "EF00"; + content = { + type = "filesystem"; + format = "vfat"; + mountpoint = "/boot"; + }; + }; + root = { + size = "100%"; + content = { + type = "filesystem"; + format = "ext4"; + mountpoint = "/"; + }; + }; + }; + }; + }; + }; + }; +} diff --git a/hosts/vps/hardware-configuration.nix b/hosts/vps/hardware-configuration.nix new file mode 100644 index 0000000..b3a836b --- /dev/null +++ b/hosts/vps/hardware-configuration.nix @@ -0,0 +1,8 @@ +{ modulesPath, lib, ... }: + +{ + imports = [ (modulesPath + "/profiles/qemu-guest.nix") ]; + + networking.useDHCP = lib.mkDefault true; + nixpkgs.hostPlatform = lib.mkDefault "x86_64-linux"; +} diff --git a/services/akkoma.nix b/services/akkoma.nix new file mode 100644 index 0000000..7f8fe4d --- /dev/null +++ b/services/akkoma.nix @@ -0,0 +1,103 @@ +{ pkgs, ... }: + +let + inherit ((pkgs.formats.elixirConf { }).lib) mkRaw; + + mangane = pkgs.stdenv.mkDerivation rec { + pname = "mangane"; + version = "1.19.4"; + + src = pkgs.fetchzip { + url = "https://github.com/BDX-town/Mangane/releases/download/${version}/static.zip"; + hash = "sha256-Z+3rhqAlPX1sO0Lswky0rMe9pZmdFGWrckHDJnaCyQU="; + stripRoot = false; + }; + + installPhase = '' + runHook preInstall + + mkdir -p $out + cp -r dist/* $out/ + + runHook postInstall + ''; + }; +in +{ + networking.firewall.interfaces.wg0.allowedTCPPorts = [ 4000 ]; + + services.postgresql = { + enable = true; + }; + + services.akkoma = { + enable = true; + + frontends = { + primary = { + package = mangane; + name = "mangane"; + ref = "stable"; + }; + admin = { + package = pkgs.akkoma-admin-fe; + name = "admin-fe"; + ref = "stable"; + }; + }; + + config = { + ":pleroma" = { + "Pleroma.Web.Endpoint" = { + http = { + ip = "10.10.0.2"; + port = 4000; + }; + url = { + host = "akkoma.ellie.town"; + scheme = "https"; + port = 443; + }; + }; + "Pleroma.Upload" = { + base_url = "https://media.ellie.town"; + filters = map mkRaw [ + "Pleroma.Upload.Filter.Exiftool.StripMetadata" + ]; + }; + ":instance" = { + name = "ellie town"; + email = "wizzeh@protonmail.com"; + notify_email = "akkoma@ellie.town"; + description = "ellie's akkoma instance"; + registrations_open = false; + invites_enabled = false; + account_approval_required = false; + federating = true; + allow_relay = true; + languages = ["en"]; + public = false; + safe_dm_mentions = true; + healthcheck = true; + limit = 5000; + }; + ":configurable_from_database" = true; + ":http_security" = { + sts = true; + referrer_policy = "same-origin"; + }; + ":mrf" = { + policies = map mkRaw [ + "Pleroma.Web.ActivityPub.MRF.SimplePolicy" + "Pleroma.Web.ActivityPub.MRF.HellthreadPolicy" + "Pleroma.Web.ActivityPub.MRF.AntiLinkSpamPolicy" + ]; + }; + ":mrf_hellthread" = { + delist_threshold = 10; + reject_threshold = 20; + }; + }; + }; + }; +} diff --git a/services/coturn.nix b/services/coturn.nix new file mode 100644 index 0000000..18cd4e0 --- /dev/null +++ b/services/coturn.nix @@ -0,0 +1,72 @@ +{ config, pkgs, ... }: + +{ + sops.secrets."coturn/auth_secret_vps" = { + sopsFile = ./secrets/coturn_vps.yaml; + mode = "0400"; + owner = "turnserver"; + group = "turnserver"; + }; + + security.acme = { + acceptTerms = true; + defaults.email = "wizzeh@protonmail.com"; + certs."turn.ellie.town" = { + webroot = "/var/lib/acme/acme-challenges"; + }; + certs."ellie.town" = { }; + }; + + networking.firewall = { + allowedUDPPorts = [ + 3478 + 5349 + ]; + allowedTCPPorts = [ + 3478 + 5349 + 80 + 443 + ]; + allowedUDPPortRanges = [ + { + from = 49152; + to = 65535; + } + ]; + }; + + services.coturn = { + enable = true; + + realm = "turn.ellie.town"; + + use-auth-secret = true; + static-auth-secret-file = config.sops.secrets."coturn/auth_secret_vps".path; + + cert = "/var/lib/acme/turn.ellie.town/fullchain.pem"; + pkey = "/var/lib/acme/turn.ellie.town/key.pem"; + + listening-ips = [ + "0.0.0.0" + "::" + ]; + listening-port = 3478; + tls-listening-port = 5349; + + lt-cred-mech = true; + no-tcp-relay = true; + + min-port = 49152; + max-port = 65535; + }; + + services.nginx = { + enable = true; + virtualHosts."turn.ellie.town" = { + locations."/.well-known/acme-challenge/" = { + root = "/var/lib/acme/acme-challenges"; + }; + }; + }; +} diff --git a/services/ergo.nix b/services/ergo.nix new file mode 100644 index 0000000..8257cfc --- /dev/null +++ b/services/ergo.nix @@ -0,0 +1,113 @@ +{ lib, pkgs, config, ... }: + +let + settingsFormat = pkgs.formats.yaml { }; + ergoConfigFile = settingsFormat.generate "ircd.yaml" config.services.ergochat.settings; +in +{ + sops.secrets."ergo/oper_password_hash" = { + sopsFile = ./secrets/ergo.yaml; + mode = "0400"; + }; + + networking.firewall.interfaces.wg0.allowedTCPPorts = [ 6667 8097 ]; + + services.mysql = { + enable = true; + package = pkgs.mariadb; + ensureDatabases = [ "ergochat" ]; + ensureUsers = [ + { + name = "ergochat"; + ensurePermissions = { + "ergochat.*" = "ALL PRIVILEGES"; + }; + } + ]; + }; + + systemd.services.ergochat = { + after = [ "mysql.service" ]; + requires = [ "mysql.service" ]; + serviceConfig = { + SupplementaryGroups = [ "mysql" ]; + RuntimeDirectory = "ergochat"; + ExecStartPre = [ + # Run as root (+) to read our SOPS secret, then write the patched config + "+${pkgs.writeShellScript "ergochat-inject-secrets" '' + OPER_HASH=$(cat ${config.sops.secrets."ergo/oper_password_hash".path}) + sed "s|__OPER_PASSWORD_PLACEHOLDER__|$OPER_HASH|" ${ergoConfigFile} > /run/ergochat/ircd.yaml + chown ergochat:ergochat /run/ergochat/ircd.yaml + chmod 0400 /run/ergochat/ircd.yaml + ''}" + ]; + ExecStart = lib.mkForce "${pkgs.ergochat}/bin/ergo run --conf /run/ergochat/ircd.yaml"; + }; + }; + + services.ergochat = { + enable = true; + settings = { + network.name = "ellie.town"; + + server = { + name = "irc.ellie.town"; + enforce-utf8 = true; + listeners = lib.mkForce { + "10.10.0.2:6667" = { }; + "10.10.0.2:8097" = { websocket = true; }; + }; + }; + + accounts.registration.enabled = false; + accounts.nick-reservation.force-nick-equals-account = true; + accounts.nick-reservation.method = "strict"; + + datastore.mysql = { + enabled = true; + socket-path = "/run/mysqld/mysqld.sock"; + user = "ergochat"; + password = ""; + history-database = "ergochat"; + }; + + history.persistent = { + enabled = true; + unregistered-channels = false; + registered-channels = "opt-out"; + direct-messages = "opt-out"; + }; + + history.restrictions.expire-time = "0"; + + oper-classes = { + server-admin = { + title = "Server Admin"; + capabilities = [ + "rehash" + "accreg" + "chanreg" + "kill" + "ban" + "nofakelag" + "relaymsg" + "sajoin" + "samode" + "snomasks" + "history" + "defcon" + "massmessage" + ]; + }; + }; + + opers = { + ellie = { + class = "server-admin"; + whois-line = "is a server administrator"; + password = "__OPER_PASSWORD_PLACEHOLDER__"; + }; + }; + }; + }; +} diff --git a/services/matrix.nix b/services/matrix.nix new file mode 100644 index 0000000..9520c19 --- /dev/null +++ b/services/matrix.nix @@ -0,0 +1,33 @@ +{ config, continuwuity, ... }: + +{ + sops.secrets."coturn/auth_secret_home" = { + sopsFile = ./secrets/coturn_home.yaml; + mode = "0400"; + owner = "continuwuity"; + group = "continuwuity"; + }; + + networking.firewall.interfaces.wg0.allowedTCPPorts = [ 8008 ]; + + services.matrix-continuwuity = { + enable = true; + package = continuwuity.packages.x86_64-linux.default; + settings.global = { + server_name = "ellie.town"; + new_user_displayname_suffix = ""; + allow_registration = true; + + address = [ "10.10.0.2" ]; + port = [ 8008 ]; + + turn_uris = [ "turns:turn.ellie.town" ]; + turn_secret_file = config.sops.secrets."coturn/auth_secret_home".path; + + well_known = { + client = "https://matrix.ellie.town"; + server = "matrix.ellie.town:443"; + }; + }; + }; +} diff --git a/services/secrets/coturn_home.yaml b/services/secrets/coturn_home.yaml new file mode 100644 index 0000000..c1b0718 --- /dev/null +++ b/services/secrets/coturn_home.yaml @@ -0,0 +1,17 @@ +coturn: + auth_secret_home: ENC[AES256_GCM,data:ezWNA0NfHYBNq+pfwMBAl5I+g79Bx277NfLEi9irp+ey3EoZKwbRnfJ6gwExskUV8hiUWiCqj/Anbbd7XerF5w==,iv:neGLTFE8vdW6eALsOgrm5/nxqtx/+V1PY7xPG94BQN8=,tag:MXRiLPChtNvMKId/HX1fMA==,type:str] +sops: + age: + - recipient: age126v48dgev6pu3uhe7dtpdhax2yes2ff9u42ke2k2h97e90z8d4psedau7u + enc: | + -----BEGIN AGE ENCRYPTED FILE----- + YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSArQnREeGtpTmx4WGtETThz + Nkk1bG9DUkJIWndhVzRkdGxFSUV0NmY2cW5nClg4L0g0T3NpT3U3YStOa3pPajVo + ZTNtTlk4WlpOc1Fra3I1RzRHWmRhbDgKLS0tIElBR1RyMjJxdjAyRm9rZFRDYzVq + V2RqU3VCTnY5UXIvMWRnTnV4MnpCeVUKQSqKoD0CpBYNklgUN400zXwzKCHKExMU + p83UFI1k/89VZCEJm/GJ+QrMl1fRj9zgNxakK4tFghEfNu4tkAub5A== + -----END AGE ENCRYPTED FILE----- + lastmodified: "2025-09-01T00:22:01Z" + mac: ENC[AES256_GCM,data:3jh/mzPw2Q3Bsc1WYG9T/6VjxwpbP+meUkTZSqMbcIVgob22mAc0VWtRlAjK2183huqro5Od7O9+bOYUQ4s/TnaC8f79vi4aPAjgrFuAn0lCZLlF76d+1jMdBNzlXxdXfL5bkbBEYFnSzzkC+oRcRRW9iU83Nx1nJ4iZ6i1BZKU=,iv:mAmdvfBSXWmL+aZU+nn6IGEEKj1qByLZgeO7KGMcdWk=,tag:Ex3vSlAJdkh85xX1RP3fgg==,type:str] + unencrypted_suffix: _unencrypted + version: 3.10.2 diff --git a/services/secrets/coturn_vps.yaml b/services/secrets/coturn_vps.yaml new file mode 100644 index 0000000..ce7980f --- /dev/null +++ b/services/secrets/coturn_vps.yaml @@ -0,0 +1,17 @@ +coturn: + auth_secret_vps: ENC[AES256_GCM,data:/kDgDOJ0FwmhcqDRVi8xGNrOK+4n38cPYr3KuKHXZkd7HdCUZSMY3f62BUZdAnIXaASFSQkmWEIjqT2LSCBz6Q==,iv:bRWwG6Yn319W/lxi9k1zSSJRBRNcRFxnpMs0EGXeKIc=,tag:+mPHNJTcYm07RWgSHdwEjA==,type:str] +sops: + age: + - recipient: age1856wmagg3dz4j07alwqnn6d75655t6wcs8glklyjyezhu5p875fq9sez4p + enc: | + -----BEGIN AGE ENCRYPTED FILE----- + YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSAxc05wa21aWmN1dGZWdWZO + VWg4WDJRMjZJYVZMZUxQSCtMdXRYdjloWmlBCmowdk1VY0pXbTluMHdQYlpwbG82 + bmZQZjRvZ1FKVklrc2xRcjBhSHNaeFkKLS0tIFA0VWdCdmxiTzU2R08reTA2WXNm + dUFXU0dLNFlvYXc5cWtKSGhveTErZ1EKGUZDVHYTiufhp3P2IKcBv0QUM9KremOr + vfG+83HK3LkydiOBUtYEuh/2Xv86dJ9Xs/be+HMbUwETNlzAHcyhNA== + -----END AGE ENCRYPTED FILE----- + lastmodified: "2025-09-01T00:22:26Z" + mac: ENC[AES256_GCM,data:QA7OTsClu+3GXbqxmfN53cUN778ZPfjX9ve+XYF1tjpyVcfSnLB9m0Dnb2xAI9AnZSRCPwqZq0sIAiUWzbVZ6TdgEMU+hEQq8immUg+ZchbKUkfQORgflcJtaRQI2ms6h7oHGPJLuSV3deUBqeRNx1Q31DpnsUcy94Qd/6JIHUg=,iv:33Kf+wt0gwf9wmyPQT2JyrmWPJ+u3jbexEJQ5j0paxk=,tag:g5ycy+E3I97XWecbnXMTEw==,type:str] + unencrypted_suffix: _unencrypted + version: 3.10.2 diff --git a/services/secrets/ergo.yaml b/services/secrets/ergo.yaml new file mode 100644 index 0000000..1b65c6f --- /dev/null +++ b/services/secrets/ergo.yaml @@ -0,0 +1,17 @@ +ergo: + oper_password_hash: ENC[AES256_GCM,data:9INtvkk0bbaaNw+uHqy7/ms9bEQ/AwQoP1WYKdJSS7HJDs5Ki0MhzgFFq2fCf6ovJdDs/cbwDSIjIJXZ,iv:NKUmdz6o5zbKWbNOpiqtM3OaU/tmMpYmgEQlqtNDIsY=,tag:n822gtnHaH/ffL3BvBIX6w==,type:str] +sops: + age: + - recipient: age126v48dgev6pu3uhe7dtpdhax2yes2ff9u42ke2k2h97e90z8d4psedau7u + enc: | + -----BEGIN AGE ENCRYPTED FILE----- + YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBwT0RyeVlwYjRtbnRmOHZO + WE8wRXpYS2pQNlhUSUJoS0ZOb0NHajlDZ2tNCkNobnNWTDVCd2xWblNENUNiOWRM + c2svWEdkbUtKSkVOV0MvK2l1MjB1Y0EKLS0tIDhNaFBLZ3JnY2JBY0pjc0RSd1M5 + KzYxaXVacEh2MmdNbnhPMEtkSUJ0UHcKfLGMEsdGDcmAnXWK7aGSMr6ZjsQQiT8l + PjTGUyVAWBVGaQEaV33VT7y4rrns+8PmEzfMKl2y12iP6R7Jm9AntA== + -----END AGE ENCRYPTED FILE----- + lastmodified: "2026-02-10T23:31:43Z" + mac: ENC[AES256_GCM,data:l2C3HPIn5NiidEgS38vsxxkJRtij6mTiqoSQGYaaLc7tKAbJnppLwO7/Ps/3ZwcLVe+Se7/5sEel2u0aXO9nbhs4e0T83x0+wOOW4464tdN66gn3mGcNslWS7LzMl4JbL57Qx6WC9OW1xg3lw67FcPte/j7KWO3xGqG6K5Bqrjo=,iv:nE8ez8udhu0IVg7CGM2/pPxPn4gehWwxbXXwPc8TI0E=,tag:bScTdwfH6edsQOTEgyl6fg==,type:str] + unencrypted_suffix: _unencrypted + version: 3.11.0 diff --git a/services/secrets/wireguard_home.yaml b/services/secrets/wireguard_home.yaml new file mode 100644 index 0000000..3b6d066 --- /dev/null +++ b/services/secrets/wireguard_home.yaml @@ -0,0 +1,17 @@ +wireguard: + private_key: ENC[AES256_GCM,data:2UFwy9hqFIZ61pminFni+w0uJJlKL9vJz4Kh81Z+NtH8K3sgOy5ZVsfH6+0=,iv:CPq9xVzSxo9A7LfzEpyTAthqRQ26aeOOEEOt1izIA9E=,tag:X5HdQD7TnTdmGc227HrJfQ==,type:str] +sops: + age: + - recipient: age126v48dgev6pu3uhe7dtpdhax2yes2ff9u42ke2k2h97e90z8d4psedau7u + enc: | + -----BEGIN AGE ENCRYPTED FILE----- + YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBhOW1HbmUrYmdwQ21GQ3FP + UWM0cEFqcDlnQ2U3WldWRDhIOVpMM2tQSlJZCmp0dldJd3pxd0luRitmWk1hVk5w + SWZNZVdrRnV0MEtYSWtYb2xramlOczAKLS0tIDBCTVJ5clozUzZ4dDBXU3dxVG5n + bm9EeXFQNFZQT0tvT05PeXB3bGNxLzQKDXcd3unCZ0SgBrYFehz38ppHFF8T5QqH + TcZMPWHthvGt0OrY6uis/aTBZOBSv/k4sAocTN/e+vR0v9kHMcSw3A== + -----END AGE ENCRYPTED FILE----- + lastmodified: "2026-02-10T23:31:35Z" + mac: ENC[AES256_GCM,data:XkhjxTIQJBZgSVyeQcx9J3BLux/4+JPnDjZyaL4utZWWP+mkzNmD4UNU/6YpWahouix/ftq9bT2ISV/m5b9+ps9eMHjTLGGjnPB0O4gJx0sEYqY1lOgW51NnqXcogvQ6JEMkO03C/0zyXpn+GEf2Yq0sEnh2XGLTsoojGgS+CTY=,iv:rZPBJnJgOG9l1yWZ2rdzweBda6vwa06P1kkGOlDBVPY=,tag:1QjaoljyCF92YMQB4ysYpQ==,type:str] + unencrypted_suffix: _unencrypted + version: 3.11.0 diff --git a/services/secrets/wireguard_vps.yaml b/services/secrets/wireguard_vps.yaml new file mode 100644 index 0000000..f6e6059 --- /dev/null +++ b/services/secrets/wireguard_vps.yaml @@ -0,0 +1,17 @@ +wireguard: + private_key: ENC[AES256_GCM,data:SY/y0Lo2c3luFgTGMzkmFUuDk/JXD0exrZpIglfvdRto0lci0B7k/iVQv8Y=,iv:2lUzaKj0eEZVbRORd9BuPLK5thX8kxEszfsknBNSP2E=,tag:yABpH9Opuwu5MmtygmMpwA==,type:str] +sops: + age: + - recipient: age1856wmagg3dz4j07alwqnn6d75655t6wcs8glklyjyezhu5p875fq9sez4p + enc: | + -----BEGIN AGE ENCRYPTED FILE----- + YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBZYW1LR09adjllcy9OMzVm + T2lGdjlRWU53KyttaElPeGtQY1ZZRWRpOGlRCkp6ckdkSnAwazQwM3NQV1JVOHJp + OTZRWGYyWnovanljbG5FRGI3ZllQckEKLS0tIFR2ZW14QmxDcElWSXAzSzNXS1BS + eW9jQVdEUFpsR1hDRXR0dDhrVFo4VjAKiOPabz4+pb5lwxh0gAhr35cavG9aS/qa + xUndQM6xGfZQwgoOt5LX1Xlo5HBJifTpdUPvMxgPKwHbUyTQY5lKNQ== + -----END AGE ENCRYPTED FILE----- + lastmodified: "2026-02-10T23:31:40Z" + mac: ENC[AES256_GCM,data:Z/qrV4V4ZaIhzrIC/SDnCdRFnQEbaYn/zZ/PVhcVkA8qd5WHLHLZMRjOTLPstMo8ll88ua00e6KShlZJLsi1/bSG4WKxTz2Yv/TkGRTD4KE25LmqFLe/70YM1f7SC/QvmlYecVCCWpwXB6rRprt38X2Fzez5AeReZdkdo/IuH1w=,iv:38GOJdQw/9vJQPKHkK/U1HBixqQfo8m0l4HwYOKkm4s=,tag:9Ci8yglwFLQz1RXoXCCN6A==,type:str] + unencrypted_suffix: _unencrypted + version: 3.11.0 diff --git a/services/website.nix b/services/website.nix new file mode 100644 index 0000000..5d730f4 --- /dev/null +++ b/services/website.nix @@ -0,0 +1,31 @@ +{ pkgs, ... }: + +let + site = pkgs.copyPathToStore ../data/service-directory; +in +{ + services.avahi = { + enable = true; + nssmdns4 = true; + nssmdns6 = true; + + publish = { + enable = true; + addresses = true; + domain = true; + workstation = true; + }; + }; + + services.nginx = { + enable = true; + + virtualHosts."service-directory" = { + root = site; + + locations."/" = { + index = "index.html"; + }; + }; + }; +} diff --git a/services/wireguard-inner.nix b/services/wireguard-inner.nix new file mode 100644 index 0000000..bad611f --- /dev/null +++ b/services/wireguard-inner.nix @@ -0,0 +1,24 @@ +{ config, ... }: + +{ + sops.secrets."wireguard/private_key" = { + sopsFile = ./secrets/wireguard_home.yaml; + mode = "0400"; + }; + + networking.firewall.allowedUDPPorts = [ 51820 ]; + + networking.wireguard.interfaces."wg0" = { + ips = [ "10.10.0.2/24" ]; + privateKeyFile = config.sops.secrets."wireguard/private_key".path; + listenPort = 51820; + peers = [ + { + publicKey = "9itF3RfEP/DhK1C1288njiCQg0AMjjvRsWDYGyNj0ns="; + endpoint = "23.88.105.213:51820"; + allowedIPs = [ "10.10.0.1/32" ]; + persistentKeepalive = 25; + } + ]; + }; +} diff --git a/services/wireguard-outer.nix b/services/wireguard-outer.nix new file mode 100644 index 0000000..4d88630 --- /dev/null +++ b/services/wireguard-outer.nix @@ -0,0 +1,108 @@ +{ lib, pkgs, config, ... }: + +{ + sops.secrets."wireguard/private_key" = { + sopsFile = ./secrets/wireguard_vps.yaml; + mode = "0400"; + }; + + networking.firewall.allowedTCPPorts = [ + 80 + 443 + 6697 + ]; + networking.firewall.allowedUDPPorts = [ 51820 ]; + + networking.wireguard.interfaces."wg0" = { + ips = [ "10.10.0.1/24" ]; + listenPort = 51820; + privateKeyFile = config.sops.secrets."wireguard/private_key".path; + + peers = [ + { + publicKey = "s2plHABMTF83iqrCHlQ+o5ieJSAfudx3upm3v77y1DI="; + allowedIPs = [ "10.10.0.2/32" ]; + } + ]; + }; + + services.nginx = { + enable = true; + + recommendedGzipSettings = true; + recommendedProxySettings = true; + recommendedTlsSettings = true; + + defaultListen = [ + { addr = "0.0.0.0"; } + { addr = "[::]"; } + ]; + + virtualHosts."matrix.ellie.town" = { + enableACME = true; + forceSSL = true; + locations."/" = { + proxyPass = "http://10.10.0.2:8008"; + }; + }; + + # virtualHosts."akkoma.ellie.town" = { + # enableACME = true; + # forceSSL = true; + # locations."/" = { + # proxyPass = "http://10.10.0.2:4000"; + # proxyWebsockets = true; + # extraConfig = '' + # client_max_body_size 16m; + # ''; + # }; + # }; + + # virtualHosts."media.ellie.town" = { + # enableACME = true; + # forceSSL = true; + # locations."/" = { + # proxyPass = "http://10.10.0.2:4000"; + # extraConfig = '' + # client_max_body_size 16m; + # ''; + # }; + # }; + + virtualHosts."irc.ellie.town" = { + enableACME = true; + forceSSL = true; + }; + + streamConfig = '' + upstream ergo { + server 10.10.0.2:6667; + } + server { + listen 6697 ssl; + ssl_certificate /var/lib/acme/irc.ellie.town/fullchain.pem; + ssl_certificate_key /var/lib/acme/irc.ellie.town/key.pem; + proxy_pass ergo; + } + ''; + + virtualHosts."ellie.town" = { + enableACME = true; + forceSSL = true; + locations."= /.well-known/matrix/server".extraConfig = '' + default_type application/json; + add_header Access-Control-Allow-Origin *; + return 200 '{"m.server":"matrix.ellie.town:443"}';''; + + locations."= /.well-known/matrix/client".extraConfig = '' + default_type application/json; + add_header Access-Control-Allow-Origin *; + return 200 '{"m.homeserver":{"base_url":"https://matrix.ellie.town"}}';''; + }; + }; + + security.acme = { + acceptTerms = true; + defaults.email = "wizzeh@protonmail.com"; + }; +}