Merge pull request 'feat: format with nixpkgs-fmt' (#103) from feat/nixpkgs-fmt into main

Reviewed-on: pub-solar/infra#103
Reviewed-by: Akshay Mankar <axeman@noreply.git.pub.solar>
This commit is contained in:
teutat3s 2024-01-28 23:19:13 +00:00
commit 9e80c52965
Signed by: pub.solar gitea
GPG key ID: F0332B04B7054873
44 changed files with 564 additions and 553 deletions

2
.git-blame-ignore-revs Normal file
View file

@ -0,0 +1,2 @@
# Apply treewide formatting with nixpkgs-fmt
815033c764660e1468b1564a02570bad0f84f77a

View file

@ -80,7 +80,8 @@
flake = flake =
let let
username = "barkeeper"; username = "barkeeper";
in { in
{
inherit username; inherit username;
checks = builtins.mapAttrs (system: deployLib: deployLib.deployChecks self.deploy) inputs.deploy-rs.lib; checks = builtins.mapAttrs (system: deployLib: deployLib.deployChecks self.deploy) inputs.deploy-rs.lib;

View file

@ -1,28 +1,28 @@
{ self, ... }: { self, ... }:
{ {
flake = { flake = {
nixosConfigurations = { nixosConfigurations = {
nachtigall = self.nixos-flake.lib.mkLinuxSystem { nachtigall = self.nixos-flake.lib.mkLinuxSystem {
imports = [ imports = [
self.inputs.agenix.nixosModules.default self.inputs.agenix.nixosModules.default
self.nixosModules.home-manager self.nixosModules.home-manager
./nachtigall ./nachtigall
self.nixosModules.overlays self.nixosModules.overlays
self.nixosModules.unlock-zfs-on-boot self.nixosModules.unlock-zfs-on-boot
self.nixosModules.core self.nixosModules.core
self.nixosModules.docker self.nixosModules.docker
]; ];
}; };
flora-6 = self.nixos-flake.lib.mkLinuxSystem { flora-6 = self.nixos-flake.lib.mkLinuxSystem {
imports = [ imports = [
self.inputs.agenix.nixosModules.default self.inputs.agenix.nixosModules.default
self.nixosModules.home-manager self.nixosModules.home-manager
./flora-6 ./flora-6
self.nixosModules.overlays self.nixosModules.overlays
self.nixosModules.core self.nixosModules.core
]; ];
};
}; };
}; };
} };
}

View file

@ -1,9 +1,8 @@
{ { config
config, , lib
lib, , pkgs
pkgs, , flake
flake, , ...
...
}: }:
{ {
systemd.tmpfiles.rules = [ systemd.tmpfiles.rules = [
@ -32,10 +31,10 @@
output discard output discard
''; '';
extraConfig = '' extraConfig = ''
basicauth * { basicauth * {
hakkonaut $2a$14$mmIAy/Ezm6YGohUtXa2mWeW6Bcw1MQXPhrRbz14jAD2iUu3oob/t. hakkonaut $2a$14$mmIAy/Ezm6YGohUtXa2mWeW6Bcw1MQXPhrRbz14jAD2iUu3oob/t.
} }
reverse_proxy :${toString config.services.loki.configuration.server.http_listen_port} reverse_proxy :${toString config.services.loki.configuration.server.http_listen_port}
''; '';
}; };
"grafana.pub.solar" = { "grafana.pub.solar" = {
@ -56,5 +55,5 @@
}; };
}; };
}; };
networking.firewall.allowedTCPPorts = [80 443]; networking.firewall.allowedTCPPorts = [ 80 443 ];
} }

View file

@ -1,9 +1,8 @@
{ { config
config, , lib
lib, , pkgs
pkgs, , flake
flake, , ...
...
}: { }: {
age.secrets.drone-secrets = { age.secrets.drone-secrets = {
file = "${flake.self}/secrets/drone-secrets.age"; file = "${flake.self}/secrets/drone-secrets.age";
@ -25,22 +24,24 @@
isSystemUser = true; isSystemUser = true;
}; };
users.groups.drone = {}; users.groups.drone = { };
systemd.tmpfiles.rules = [ systemd.tmpfiles.rules = [
"d '/var/lib/drone-db' 0750 drone drone - -" "d '/var/lib/drone-db' 0750 drone drone - -"
]; ];
systemd.services."docker-network-drone" = let systemd.services."docker-network-drone" =
docker = config.virtualisation.oci-containers.backend; let
dockerBin = "${pkgs.${docker}}/bin/${docker}"; docker = config.virtualisation.oci-containers.backend;
in { dockerBin = "${pkgs.${docker}}/bin/${docker}";
serviceConfig.Type = "oneshot"; in
before = ["docker-drone-server.service"]; {
script = '' serviceConfig.Type = "oneshot";
${dockerBin} network inspect drone-net >/dev/null 2>&1 || ${dockerBin} network create drone-net --subnet 172.20.0.0/24 before = [ "docker-drone-server.service" ];
''; script = ''
}; ${dockerBin} network inspect drone-net >/dev/null 2>&1 || ${dockerBin} network create drone-net --subnet 172.20.0.0/24
'';
};
virtualisation = { virtualisation = {
docker = { docker = {
@ -73,7 +74,7 @@
ports = [ ports = [
"4000:80" "4000:80"
]; ];
dependsOn = ["drone-db"]; dependsOn = [ "drone-db" ];
extraOptions = [ extraOptions = [
"--network=drone-net" "--network=drone-net"
"--pull=always" "--pull=always"
@ -96,7 +97,7 @@
volumes = [ volumes = [
"/var/run/docker.sock:/var/run/docker.sock" "/var/run/docker.sock:/var/run/docker.sock"
]; ];
dependsOn = ["drone-db"]; dependsOn = [ "drone-db" ];
extraOptions = [ extraOptions = [
"--network=drone-net" "--network=drone-net"
"--pull=always" "--pull=always"

View file

@ -1,9 +1,8 @@
{ { config
config, , lib
lib, , pkgs
pkgs, , flake
flake, , ...
...
}: { }: {
age.secrets.forgejo-actions-runner-token = { age.secrets.forgejo-actions-runner-token = {
file = "${flake.self}/secrets/forgejo-actions-runner-token.age"; file = "${flake.self}/secrets/forgejo-actions-runner-token.age";

View file

@ -1,9 +1,8 @@
{ { config
config, , lib
lib, , pkgs
pkgs, , flake
flake, , ...
...
}: { }: {
age.secrets.grafana-admin-password = { age.secrets.grafana-admin-password = {
file = "${flake.self}/secrets/grafana-admin-password.age"; file = "${flake.self}/secrets/grafana-admin-password.age";

View file

@ -1,9 +1,8 @@
{ { config
config, , lib
lib, , pkgs
pkgs, , flake
flake, , ...
...
}: { }: {
# source: https://gist.github.com/rickhull/895b0cb38fdd537c1078a858cf15d63e # source: https://gist.github.com/rickhull/895b0cb38fdd537c1078a858cf15d63e
# https://grafana.com/docs/loki/latest/configure/examples/#1-local-configuration-exampleyaml # https://grafana.com/docs/loki/latest/configure/examples/#1-local-configuration-exampleyaml

View file

@ -1,9 +1,8 @@
{ { config
config, , lib
lib, , pkgs
pkgs, , flake
flake, , ...
...
}: { }: {
age.secrets.nachtigall-metrics-prometheus-basic-auth-password = { age.secrets.nachtigall-metrics-prometheus-basic-auth-password = {
file = "${flake.self}/secrets/nachtigall-metrics-prometheus-basic-auth-password.age"; file = "${flake.self}/secrets/nachtigall-metrics-prometheus-basic-auth-password.age";

View file

@ -1,12 +1,13 @@
{ { config
config, , lib
lib, , pkgs
pkgs, , flake
flake, , ...
... }:
}: let let
psCfg = config.pub-solar; psCfg = config.pub-solar;
in { in
{
config = { config = {
# Override nix.conf for more agressive garbage collection # Override nix.conf for more agressive garbage collection
nix.extraOptions = lib.mkForce '' nix.extraOptions = lib.mkForce ''
@ -33,7 +34,7 @@ in {
# systemd-networkd-wait-online timeouts # systemd-networkd-wait-online timeouts
#systemd.services."systemd-networkd".environment.SYSTEMD_LOG_LEVEL = "debug"; #systemd.services."systemd-networkd".environment.SYSTEMD_LOG_LEVEL = "debug";
systemd.network.wait-online.ignoredInterfaces = [ systemd.network.wait-online.ignoredInterfaces = [
"docker0" "docker0"
]; ];
# List services that you want to enable: # List services that you want to enable:

View file

@ -2,7 +2,8 @@
{ {
imports = imports =
[ # Include the results of the hardware scan. [
# Include the results of the hardware scan.
./hardware-configuration.nix ./hardware-configuration.nix
./configuration.nix ./configuration.nix
./triton-vmtools.nix ./triton-vmtools.nix

View file

@ -1,19 +1,18 @@
# Do not modify this file! It was generated by nixos-generate-config # Do not modify this file! It was generated by nixos-generate-config
# and may be overwritten by future invocations. Please make changes # and may be overwritten by future invocations. Please make changes
# to /etc/nixos/configuration.nix instead. # to /etc/nixos/configuration.nix instead.
{ { config
config, , lib
lib, , pkgs
pkgs, , modulesPath
modulesPath, , ...
...
}: { }: {
imports = []; imports = [ ];
boot.initrd.availableKernelModules = ["ahci" "virtio_pci" "xhci_pci" "sr_mod" "virtio_blk"]; boot.initrd.availableKernelModules = [ "ahci" "virtio_pci" "xhci_pci" "sr_mod" "virtio_blk" ];
boot.initrd.kernelModules = []; boot.initrd.kernelModules = [ ];
boot.kernelModules = []; boot.kernelModules = [ ];
boot.extraModulePackages = []; boot.extraModulePackages = [ ];
fileSystems."/" = { fileSystems."/" = {
device = "/dev/disk/by-label/nixos"; device = "/dev/disk/by-label/nixos";
@ -35,7 +34,7 @@
]; ];
}; };
swapDevices = []; swapDevices = [ ];
networking.useDHCP = lib.mkDefault false; networking.useDHCP = lib.mkDefault false;
networking.networkmanager.enable = lib.mkForce false; networking.networkmanager.enable = lib.mkForce false;

View file

@ -1,7 +1,6 @@
{ { pkgs
pkgs, , flake
flake, , ...
...
}: { }: {
environment.systemPackages = with pkgs; [ environment.systemPackages = with pkgs; [
flake.inputs.triton-vmtools.packages.${pkgs.system}.default flake.inputs.triton-vmtools.packages.${pkgs.system}.default

View file

@ -1,9 +1,8 @@
{ { config
config, , lib
lib, , pkgs
pkgs, , self
self, , ...
...
}: { }: {
services.nginx.virtualHosts."collabora.pub.solar" = { services.nginx.virtualHosts."collabora.pub.solar" = {
enableACME = true; enableACME = true;
@ -15,7 +14,7 @@
proxy_pass http://127.0.0.1:9980; proxy_pass http://127.0.0.1:9980;
proxy_set_header Host $host; proxy_set_header Host $host;
''; '';
}; };
}; };
virtualisation = { virtualisation = {

View file

@ -1,4 +1,4 @@
{flake, config, lib, ...}: { flake, config, lib, ... }:
{ {
age.secrets."coturn-static-auth-secret" = { age.secrets."coturn-static-auth-secret" = {
file = "${flake.self}/secrets/coturn-static-auth-secret.age"; file = "${flake.self}/secrets/coturn-static-auth-secret.age";
@ -19,57 +19,59 @@
pkey = "${config.security.acme.certs.${realm}.directory}/key.pem"; pkey = "${config.security.acme.certs.${realm}.directory}/key.pem";
extraConfig = extraConfig =
let let
externalIPv4s = lib.strings.concatMapStringsSep "\n" ({address, ...}: "external-ip=${address}") config.networking.interfaces.enp35s0.ipv4.addresses; externalIPv4s = lib.strings.concatMapStringsSep "\n" ({ address, ... }: "external-ip=${address}") config.networking.interfaces.enp35s0.ipv4.addresses;
externalIPv6s = lib.strings.concatMapStringsSep "\n" ({address, ...}: "external-ip=${address}") config.networking.interfaces.enp35s0.ipv6.addresses; externalIPv6s = lib.strings.concatMapStringsSep "\n" ({ address, ... }: "external-ip=${address}") config.networking.interfaces.enp35s0.ipv6.addresses;
in '' in
${externalIPv4s} ''
${externalIPv6s} ${externalIPv4s}
${externalIPv6s}
no-tlsv1 no-tlsv1
no-tlsv1_1 no-tlsv1_1
no-rfc5780 no-rfc5780
response-origin-only-with-rfc5780 response-origin-only-with-rfc5780
prod prod
no-stun-backward-compatibility no-stun-backward-compatibility
# ban private IP ranges # ban private IP ranges
no-multicast-peers no-multicast-peers
denied-peer-ip=0.0.0.0-0.255.255.255 denied-peer-ip=0.0.0.0-0.255.255.255
denied-peer-ip=10.0.0.0-10.255.255.255 denied-peer-ip=10.0.0.0-10.255.255.255
denied-peer-ip=100.64.0.0-100.127.255.255 denied-peer-ip=100.64.0.0-100.127.255.255
denied-peer-ip=127.0.0.0-127.255.255.255 denied-peer-ip=127.0.0.0-127.255.255.255
denied-peer-ip=169.254.0.0-169.254.255.255 denied-peer-ip=169.254.0.0-169.254.255.255
denied-peer-ip=172.16.0.0-172.31.255.255 denied-peer-ip=172.16.0.0-172.31.255.255
denied-peer-ip=192.0.0.0-192.0.0.255 denied-peer-ip=192.0.0.0-192.0.0.255
denied-peer-ip=192.0.2.0-192.0.2.255 denied-peer-ip=192.0.2.0-192.0.2.255
denied-peer-ip=192.88.99.0-192.88.99.255 denied-peer-ip=192.88.99.0-192.88.99.255
denied-peer-ip=192.168.0.0-192.168.255.255 denied-peer-ip=192.168.0.0-192.168.255.255
denied-peer-ip=198.18.0.0-198.19.255.255 denied-peer-ip=198.18.0.0-198.19.255.255
denied-peer-ip=198.51.100.0-198.51.100.255 denied-peer-ip=198.51.100.0-198.51.100.255
denied-peer-ip=203.0.113.0-203.0.113.255 denied-peer-ip=203.0.113.0-203.0.113.255
denied-peer-ip=240.0.0.0-255.255.255.255 denied-peer-ip=240.0.0.0-255.255.255.255
denied-peer-ip=::1 denied-peer-ip=::1
denied-peer-ip=64:ff9b::-64:ff9b::ffff:ffff denied-peer-ip=64:ff9b::-64:ff9b::ffff:ffff
denied-peer-ip=::ffff:0.0.0.0-::ffff:255.255.255.255 denied-peer-ip=::ffff:0.0.0.0-::ffff:255.255.255.255
denied-peer-ip=100::-100::ffff:ffff:ffff:ffff denied-peer-ip=100::-100::ffff:ffff:ffff:ffff
denied-peer-ip=2001::-2001:1ff:ffff:ffff:ffff:ffff:ffff:ffff denied-peer-ip=2001::-2001:1ff:ffff:ffff:ffff:ffff:ffff:ffff
denied-peer-ip=2002::-2002:ffff:ffff:ffff:ffff:ffff:ffff:ffff denied-peer-ip=2002::-2002:ffff:ffff:ffff:ffff:ffff:ffff:ffff
denied-peer-ip=fc00::-fdff:ffff:ffff:ffff:ffff:ffff:ffff:ffff denied-peer-ip=fc00::-fdff:ffff:ffff:ffff:ffff:ffff:ffff:ffff
denied-peer-ip=fe80::-febf:ffff:ffff:ffff:ffff:ffff:ffff:ffff denied-peer-ip=fe80::-febf:ffff:ffff:ffff:ffff:ffff:ffff:ffff
''; '';
}; };
networking.firewall = { networking.firewall = {
interfaces.enp35s0 = let interfaces.enp35s0 =
range = with config.services.coturn; [ { let
from = min-port; range = with config.services.coturn; [{
to = max-port; from = min-port;
} ]; to = max-port;
in }];
in
{ {
allowedUDPPortRanges = range; allowedUDPPortRanges = range;
allowedUDPPorts = [ 3478 5349 ]; allowedUDPPorts = [ 3478 5349 ];

View file

@ -1,9 +1,8 @@
{ { config
config, , lib
lib, , pkgs
pkgs, , flake
flake, , ...
...
}: { }: {
age.secrets.forgejo-database-password = { age.secrets.forgejo-database-password = {
file = "${flake.self}/secrets/forgejo-database-password.age"; file = "${flake.self}/secrets/forgejo-database-password.age";
@ -22,7 +21,7 @@
forceSSL = true; forceSSL = true;
locations."/user/login".extraConfig = '' locations."/user/login".extraConfig = ''
return 302 /user/oauth2/keycloak; return 302 /user/oauth2/keycloak;
''; '';
locations."/" = { locations."/" = {

View file

@ -1,9 +1,8 @@
{ { flake
flake, , config
config, , lib
lib, , pkgs
pkgs, , ...
...
}: { }: {
age.secrets.keycloak-database-password = { age.secrets.keycloak-database-password = {
file = "${flake.self}/secrets/keycloak-database-password.age"; file = "${flake.self}/secrets/keycloak-database-password.age";

View file

@ -1,12 +1,11 @@
{ { flake
flake, , config
config, , lib
lib, , pkgs
pkgs, , ...
...
}: }:
{ {
networking.firewall.allowedTCPPorts = [25]; networking.firewall.allowedTCPPorts = [ 25 ];
users.users.nginx.extraGroups = [ "mailman" ]; users.users.nginx.extraGroups = [ "mailman" ];
@ -23,13 +22,13 @@
services.postfix = { services.postfix = {
enable = true; enable = true;
relayDomains = ["hash:/var/lib/mailman/data/postfix_domains"]; relayDomains = [ "hash:/var/lib/mailman/data/postfix_domains" ];
# get TLS certs for list.pub.solar from acme # get TLS certs for list.pub.solar from acme
sslCert = "/var/lib/acme/list.pub.solar/fullchain.pem"; sslCert = "/var/lib/acme/list.pub.solar/fullchain.pem";
sslKey = "/var/lib/acme/list.pub.solar/key.pem"; sslKey = "/var/lib/acme/list.pub.solar/key.pem";
config = { config = {
transport_maps = ["hash:/var/lib/mailman/data/postfix_lmtp"]; transport_maps = [ "hash:/var/lib/mailman/data/postfix_lmtp" ];
local_recipient_maps = ["hash:/var/lib/mailman/data/postfix_lmtp"]; local_recipient_maps = [ "hash:/var/lib/mailman/data/postfix_lmtp" ];
}; };
rootAlias = "admins@pub.solar"; rootAlias = "admins@pub.solar";
postmasterAlias = "admins@pub.solar"; postmasterAlias = "admins@pub.solar";
@ -38,34 +37,34 @@
systemd.paths.watcher-acme-ssl-file = { systemd.paths.watcher-acme-ssl-file = {
description = "Watches for changes in acme's TLS cert file (after renewals) to reload postfix"; description = "Watches for changes in acme's TLS cert file (after renewals) to reload postfix";
documentation = ["systemd.path(5)"]; documentation = [ "systemd.path(5)" ];
partOf = ["postfix-reload.service"]; partOf = [ "postfix-reload.service" ];
pathConfig = { pathConfig = {
PathChanged = "/var/lib/acme/list.pub.solar/fullchain.pem"; PathChanged = "/var/lib/acme/list.pub.solar/fullchain.pem";
Unit = "postfix-reload.service"; Unit = "postfix-reload.service";
}; };
wantedBy = ["multi-user.target"]; wantedBy = [ "multi-user.target" ];
}; };
systemd.services."postfix-reload" = { systemd.services."postfix-reload" = {
description = "Reloads postfix config, e.g. after TLS certs change, notified by watcher-acme-ssl-file.path"; description = "Reloads postfix config, e.g. after TLS certs change, notified by watcher-acme-ssl-file.path";
documentation = ["systemd.path(5)"]; documentation = [ "systemd.path(5)" ];
requires = ["postfix.service"]; requires = [ "postfix.service" ];
after = ["postfix.service"]; after = [ "postfix.service" ];
startLimitIntervalSec = 10; startLimitIntervalSec = 10;
startLimitBurst = 5; startLimitBurst = 5;
serviceConfig.Type = "oneshot"; serviceConfig.Type = "oneshot";
script = '' script = ''
${pkgs.systemd}/bin/systemctl reload postfix ${pkgs.systemd}/bin/systemctl reload postfix
''; '';
wantedBy = ["multi-user.target"]; wantedBy = [ "multi-user.target" ];
}; };
services.mailman = { services.mailman = {
enable = true; enable = true;
serve.enable = true; serve.enable = true;
hyperkitty.enable = true; hyperkitty.enable = true;
webHosts = ["list.pub.solar"]; webHosts = [ "list.pub.solar" ];
siteOwner = "admins@pub.solar"; siteOwner = "admins@pub.solar";
}; };

View file

@ -1,45 +1,45 @@
{ pkgs, lib, ... }: { { pkgs, lib, ... }: {
default_server_config = { default_server_config = {
"m.homeserver" = { "m.homeserver" = {
base_url = "https://matrix.pub.solar"; base_url = "https://matrix.pub.solar";
server_name = "pub.solar"; server_name = "pub.solar";
}; };
"m.identity_server" = { "m.identity_server" = {
base_url = ""; base_url = "";
}; };
}; };
setting_defaults = { setting_defaults = {
custom_themes = (lib.modules.importJSON "${pkgs.element-themes}").config; custom_themes = (lib.modules.importJSON "${pkgs.element-themes}").config;
}; };
default_theme = "light"; default_theme = "light";
default_country_code = "DE"; default_country_code = "DE";
permalink_prefix = "https://matrix.to"; permalink_prefix = "https://matrix.to";
disable_custom_urls = true; disable_custom_urls = true;
disable_guests = true; disable_guests = true;
brand = "Element Solar"; brand = "Element Solar";
# TODO: Configure these # TODO: Configure these
integrations_ui_url = ""; integrations_ui_url = "";
integrations_rest_url = ""; integrations_rest_url = "";
integrations_widgets_urls = ""; integrations_widgets_urls = "";
integrations_jitsi_widget_url = ""; integrations_jitsi_widget_url = "";
bug_report_endpoint_url = "https://element.io/bugreports/submit"; bug_report_endpoint_url = "https://element.io/bugreports/submit";
show_labs_settings = true; show_labs_settings = true;
room_directory = { room_directory = {
servers = ["matrix.org"]; servers = [ "matrix.org" ];
}; };
# TODO: This looks wrong # TODO: This looks wrong
enable_presence_by_hs_url = "\n"; enable_presence_by_hs_url = "\n";
embedded_pages = { embedded_pages = {
homeUrl = ""; homeUrl = "";
}; };
branding = { branding = {
auth_footer_links = [{ auth_footer_links = [{
text = "Privacy"; text = "Privacy";
url = "https://pub.solar/privacy"; url = "https://pub.solar/privacy";
}]; }];
# FUTUREWORK: Replace with pub.solar logo # FUTUREWORK: Replace with pub.solar logo
auth_header_logo_url = "themes/element/img/logos/element-logo.svg"; auth_header_logo_url = "themes/element/img/logos/element-logo.svg";
}; };
} }

View file

@ -1,4 +1,4 @@
{config, lib, pkgs, ...}: { config, lib, pkgs, ... }:
{ {
systemd.services.matrix-appservice-irc.serviceConfig.SystemCallFilter = lib.mkForce [ systemd.services.matrix-appservice-irc.serviceConfig.SystemCallFilter = lib.mkForce [
"@system-service @pkey" "@system-service @pkey"
@ -90,7 +90,8 @@
sendConnectionMessages = true; sendConnectionMessages = true;
ssl = true; ssl = true;
}; };
in { in
{
"irc.libera.chat" = lib.attrsets.recursiveUpdate commonConfig { "irc.libera.chat" = lib.attrsets.recursiveUpdate commonConfig {
name = "libera"; name = "libera";
dynamicChannels.groupId = "+libera.chat:localhost"; dynamicChannels.groupId = "+libera.chat:localhost";

View file

@ -27,7 +27,7 @@
id = "telegram"; id = "telegram";
max_body_size = 1; max_body_size = 1;
port = 8009; port = 8009;
provisioning = { provisioning = {
enabled = false; enabled = false;
prefix = "/_matrix/provision/v1"; prefix = "/_matrix/provision/v1";
shared_secret = "generate"; shared_secret = "generate";
@ -59,7 +59,7 @@
bot_messages_as_notices = true; bot_messages_as_notices = true;
bridge_notices = { bridge_notices = {
default = false; default = false;
exceptions = []; exceptions = [ ];
}; };
command_prefix = "!tg"; command_prefix = "!tg";
delivery_error_reports = true; delivery_error_reports = true;
@ -84,13 +84,13 @@
}; };
federate_rooms = true; federate_rooms = true;
filter = { filter = {
list = []; list = [ ];
mode = "blacklist"; mode = "blacklist";
}; };
image_as_file_size = 10; image_as_file_size = 10;
initial_power_level_overrides = { initial_power_level_overrides = {
group = {}; group = { };
user = {}; user = { };
}; };
inline_images = false; inline_images = false;
max_document_size = 100; max_document_size = 100;
@ -112,15 +112,15 @@
public_portals = true; public_portals = true;
relaybot = { relaybot = {
authless_portals = true; authless_portals = true;
group_chat_invite = []; group_chat_invite = [ ];
ignore_own_incoming_events = true; ignore_own_incoming_events = true;
ignore_unbridged_group_chat = true; ignore_unbridged_group_chat = true;
private_chat = { private_chat = {
invite = []; invite = [ ];
message = "This is a Matrix bridge relaybot and does not support direct chats"; message = "This is a Matrix bridge relaybot and does not support direct chats";
state_changes = true; state_changes = true;
}; };
whitelist = []; whitelist = [ ];
whitelist_group_admins = true; whitelist_group_admins = true;
}; };
resend_bridge_info = false; resend_bridge_info = false;
@ -145,7 +145,7 @@
}; };
logging = { logging = {
formatters= { formatters = {
precise = { precise = {
format = "[%(asctime)s] [%(levelname)s@%(name)s] %(message)s"; format = "[%(asctime)s] [%(levelname)s@%(name)s] %(message)s";
}; };
@ -156,14 +156,14 @@
formatter = "precise"; formatter = "precise";
}; };
}; };
loggers={ loggers = {
aiohttp.level = "WARNING"; aiohttp.level = "WARNING";
mau.level = "WARNING"; mau.level = "WARNING";
telethon.level = "WARNING"; telethon.level = "WARNING";
}; };
root = { root = {
handlers = [ "console" ]; handlers = [ "console" ];
level = "WARNING"; level = "WARNING";
}; };
version = 1; version = 1;
}; };
@ -202,8 +202,8 @@
}; };
systemd.services.mautrix-telegram.path = with pkgs; [ systemd.services.mautrix-telegram.path = with pkgs; [
lottieconverter # for animated stickers conversion, unfree package lottieconverter # for animated stickers conversion, unfree package
ffmpeg # if converting animated stickers to webm (very slow!) ffmpeg # if converting animated stickers to webm (very slow!)
]; ];
systemd.services.mautrix-telegram.serviceConfig = { systemd.services.mautrix-telegram.serviceConfig = {
User = "matrix-synapse"; User = "matrix-synapse";

View file

@ -1,8 +1,9 @@
{ flake, config, pkgs, ... }: { flake, config, pkgs, ... }:
let let
publicDomain = "matrix.pub.solar"; publicDomain = "matrix.pub.solar";
serverDomain = "pub.solar"; serverDomain = "pub.solar";
in { in
{
age.secrets."matrix-synapse-signing-key" = { age.secrets."matrix-synapse-signing-key" = {
file = "${flake.self}/secrets/matrix-synapse-signing-key.age"; file = "${flake.self}/secrets/matrix-synapse-signing-key.age";
mode = "400"; mode = "400";
@ -41,8 +42,8 @@ in {
account_threepid_delegates.msisdn = ""; account_threepid_delegates.msisdn = "";
alias_creation_rules = [{ alias_creation_rules = [{
action = "allow"; action = "allow";
alias= "*"; alias = "*";
room_id = "*" ; room_id = "*";
user_id = "*"; user_id = "*";
}]; }];
allow_guest_access = false; allow_guest_access = false;
@ -69,14 +70,14 @@ in {
federation_rr_transactions_per_room_per_second = 50; federation_rr_transactions_per_room_per_second = 50;
forget_rooms_on_leave = true; forget_rooms_on_leave = true;
include_profile_data_on_invite = true; include_profile_data_on_invite = true;
instance_map = {}; instance_map = { };
limit_profile_requests_to_users_who_share_rooms = false; limit_profile_requests_to_users_who_share_rooms = false;
log_config = ./matrix-log-config.yaml; log_config = ./matrix-log-config.yaml;
max_spider_size = "10M"; max_spider_size = "10M";
max_upload_size = "50M"; max_upload_size = "50M";
media_storage_providers = []; media_storage_providers = [ ];
password_config = { password_config = {
enabled = false; enabled = false;
@ -87,67 +88,67 @@ in {
presence.enabled = true; presence.enabled = true;
push.include_content = false; push.include_content = false;
rc_admin_redaction= { rc_admin_redaction = {
burst_count = 50; burst_count = 50;
per_second = 1; per_second = 1;
}; };
rc_federation= { rc_federation = {
concurrent = 3; concurrent = 3;
reject_limit = 50; reject_limit = 50;
sleep_delay = 500; sleep_delay = 500;
sleep_limit = 10; sleep_limit = 10;
window_size = 1000; window_size = 1000;
}; };
rc_invites= { rc_invites = {
per_issuer= { per_issuer = {
burst_count = 10; burst_count = 10;
per_second = 0.3; per_second = 0.3;
}; };
per_room= { per_room = {
burst_count = 10; burst_count = 10;
per_second = 0.3; per_second = 0.3;
}; };
per_user= { per_user = {
burst_count = 5; burst_count = 5;
per_second = 0.003; per_second = 0.003;
}; };
}; };
rc_joins= { rc_joins = {
local= { local = {
burst_count = 10; burst_count = 10;
per_second = 0.1; per_second = 0.1;
}; };
remote= { remote = {
burst_count = 10; burst_count = 10;
per_second = 0.01; per_second = 0.01;
}; };
}; };
rc_login= { rc_login = {
account= { account = {
burst_count = 3; burst_count = 3;
per_second = 0.17; per_second = 0.17;
}; };
address= { address = {
burst_count = 3; burst_count = 3;
per_second = 0.17; per_second = 0.17;
}; };
failed_attempts= { failed_attempts = {
burst_count = 3; burst_count = 3;
per_second = 0.17; per_second = 0.17;
}; };
}; };
rc_message= { rc_message = {
burst_count = 10; burst_count = 10;
per_second = 0.2; per_second = 0.2;
}; };
rc_registration= { rc_registration = {
burst_count = 3; burst_count = 3;
per_second = 0.17; per_second = 0.17;
}; };
redaction_retention_period = "7d"; redaction_retention_period = "7d";
redis.enabled = false; redis.enabled = false;
registration_requires_token = false; registration_requires_token = false;
registrations_require_3pid = ["email"]; registrations_require_3pid = [ "email" ];
report_stats = false; report_stats = false;
require_auth_for_profile_requests = false; require_auth_for_profile_requests = false;
room_list_publication_rules = [{ room_list_publication_rules = [{
@ -159,8 +160,8 @@ in {
signing_key_path = "/run/agenix/matrix-synapse-signing-key"; signing_key_path = "/run/agenix/matrix-synapse-signing-key";
stream_writers = {}; stream_writers = { };
trusted_key_servers = [{ server_name = "matrix.org";}]; trusted_key_servers = [{ server_name = "matrix.org"; }];
turn_allow_guests = false; turn_allow_guests = false;
turn_uris = [ turn_uris = [

View file

@ -1,160 +1,161 @@
{ { flake
flake, , config
config, , lib
lib, , pkgs
pkgs, , ...
... }:
}: let let
localSettingsPHP = pkgs.writeScript "LocalSettings.php" '' localSettingsPHP = pkgs.writeScript "LocalSettings.php" ''
<?php <?php
# Protect against web entry # Protect against web entry
if ( !defined( 'MEDIAWIKI' ) ) { if ( !defined( 'MEDIAWIKI' ) ) {
exit; exit;
} }
# error_reporting( -1 ); # error_reporting( -1 );
# ini_set( 'display_errors', 1 ); # ini_set( 'display_errors', 1 );
# $wgShowExceptionDetails = true; # $wgShowExceptionDetails = true;
# $wgDBerrorLog = '/dev/stderr'; # $wgDBerrorLog = '/dev/stderr';
# $wgDebugLogFile = "/dev/stderr"; # $wgDebugLogFile = "/dev/stderr";
$wgSitename = "pub.solar wiki"; $wgSitename = "pub.solar wiki";
$wgMetaNamespace = false; $wgMetaNamespace = false;
## The URL base path to the directory containing the wiki; ## The URL base path to the directory containing the wiki;
## defaults for all runtime URL paths are based off of this. ## defaults for all runtime URL paths are based off of this.
## For more information on customizing the URLs ## For more information on customizing the URLs
## (like /w/index.php/Page_title to /wiki/Page_title) please see: ## (like /w/index.php/Page_title to /wiki/Page_title) please see:
## https://www.mediawiki.org/wiki/Manual:Short_URL ## https://www.mediawiki.org/wiki/Manual:Short_URL
$wgScriptPath = "https://wiki.pub.solar"; $wgScriptPath = "https://wiki.pub.solar";
## https://www.mediawiki.org/wiki/Manual:Short_URL ## https://www.mediawiki.org/wiki/Manual:Short_URL
## https://www.mediawiki.org/wiki/Extension:OpenID_Connect#Known_issues ## https://www.mediawiki.org/wiki/Extension:OpenID_Connect#Known_issues
$wgArticlePath = "/index.php/$1"; $wgArticlePath = "/index.php/$1";
## The protocol and server name to use in fully-qualified URLs ## The protocol and server name to use in fully-qualified URLs
$wgServer = "https://wiki.pub.solar"; $wgServer = "https://wiki.pub.solar";
## The URL path to static resources (images, scripts, etc.) ## The URL path to static resources (images, scripts, etc.)
$wgResourceBasePath = $wgScriptPath; $wgResourceBasePath = $wgScriptPath;
## The URL path to the logo. Make sure you change this from the default, ## The URL path to the logo. Make sure you change this from the default,
## or else you'll overwrite your logo when you upgrade! ## or else you'll overwrite your logo when you upgrade!
$wgLogo = "https://pub.solar/assets/pubsolar.svg"; $wgLogo = "https://pub.solar/assets/pubsolar.svg";
## UPO means: this is also a user preference option ## UPO means: this is also a user preference option
$wgEnableEmail = true; $wgEnableEmail = true;
$wgEnableUserEmail = true; # UPO $wgEnableUserEmail = true; # UPO
$wgPasswordSender = "admins@pub.solar"; $wgPasswordSender = "admins@pub.solar";
$wgEnotifUserTalk = false; # UPO $wgEnotifUserTalk = false; # UPO
$wgEnotifWatchlist = false; # UPO $wgEnotifWatchlist = false; # UPO
$wgEmailAuthentication = true; $wgEmailAuthentication = true;
## Database settings ## Database settings
$wgDBtype = "postgres"; $wgDBtype = "postgres";
$wgDBserver = "host.docker.internal"; $wgDBserver = "host.docker.internal";
$wgDBport = "5432"; $wgDBport = "5432";
$wgDBname = "mediawiki"; $wgDBname = "mediawiki";
$wgDBuser = "mediawiki"; $wgDBuser = "mediawiki";
$wgDBpassword = trim(file_get_contents("/run/mediawiki/database-password")); $wgDBpassword = trim(file_get_contents("/run/mediawiki/database-password"));
## Shared memory settings ## Shared memory settings
$wgMainCacheType = CACHE_NONE; $wgMainCacheType = CACHE_NONE;
$wgMemCachedServers = []; $wgMemCachedServers = [];
$wgEnableUploads = true; $wgEnableUploads = true;
$wgUploadDirectory = "/var/www/html/uploads"; $wgUploadDirectory = "/var/www/html/uploads";
$wgUploadPath = $wgScriptPath . "/uploads"; $wgUploadPath = $wgScriptPath . "/uploads";
$wgUseImageMagick = true; $wgUseImageMagick = true;
$wgImageMagickConvertCommand = "/usr/bin/convert"; $wgImageMagickConvertCommand = "/usr/bin/convert";
# InstantCommons allows wiki to use images from https://commons.wikimedia.org # InstantCommons allows wiki to use images from https://commons.wikimedia.org
$wgUseInstantCommons = true; $wgUseInstantCommons = true;
# Periodically send a pingback to https://www.mediawiki.org/ with basic data # Periodically send a pingback to https://www.mediawiki.org/ with basic data
# about this MediaWiki instance. The Wikimedia Foundation shares this data # about this MediaWiki instance. The Wikimedia Foundation shares this data
# with MediaWiki developers to help guide future development efforts. # with MediaWiki developers to help guide future development efforts.
$wgPingback = true; $wgPingback = true;
## If you use ImageMagick (or any other shell command) on a ## If you use ImageMagick (or any other shell command) on a
## Linux server, this will need to be set to the name of an ## Linux server, this will need to be set to the name of an
## available UTF-8 locale ## available UTF-8 locale
$wgShellLocale = "C.UTF-8"; $wgShellLocale = "C.UTF-8";
# Site language code, should be one of the list in ./languages/data/Names.php # Site language code, should be one of the list in ./languages/data/Names.php
$wgLanguageCode = "en"; $wgLanguageCode = "en";
$wgSecretKey = trim(file_get_contents("/run/mediawiki/secret-key")); $wgSecretKey = trim(file_get_contents("/run/mediawiki/secret-key"));
# Changing this will log out all existing sessions. # Changing this will log out all existing sessions.
$wgAuthenticationTokenVersion = ""; $wgAuthenticationTokenVersion = "";
## For attaching licensing metadata to pages, and displaying an ## For attaching licensing metadata to pages, and displaying an
## appropriate copyright notice / icon. GNU Free Documentation ## appropriate copyright notice / icon. GNU Free Documentation
## License and Creative Commons licenses are supported so far. ## License and Creative Commons licenses are supported so far.
$wgRightsPage = ""; # Set to the title of a wiki page that describes your license/copyright $wgRightsPage = ""; # Set to the title of a wiki page that describes your license/copyright
$wgRightsUrl = ""; $wgRightsUrl = "";
$wgRightsText = ""; $wgRightsText = "";
$wgRightsIcon = ""; $wgRightsIcon = "";
# Path to the GNU diff3 utility. Used for conflict resolution. # Path to the GNU diff3 utility. Used for conflict resolution.
$wgDiff = "/usr/bin/diff"; $wgDiff = "/usr/bin/diff";
$wgDiff3 = "/usr/bin/diff3"; $wgDiff3 = "/usr/bin/diff3";
# Enabled skins. # Enabled skins.
wfLoadSkin('MonoBook'); wfLoadSkin('MonoBook');
wfLoadSkin('Timeless'); wfLoadSkin('Timeless');
wfLoadSkin('Vector'); wfLoadSkin('Vector');
# Enabled extensions. # Enabled extensions.
wfLoadExtension('OpenIDConnect'); wfLoadExtension('OpenIDConnect');
wfLoadExtension('PluggableAuth'); wfLoadExtension('PluggableAuth');
wfLoadExtension('VisualEditor'); wfLoadExtension('VisualEditor');
wfLoadExtension('TemplateStyles'); wfLoadExtension('TemplateStyles');
# End of automatically generated settings. # End of automatically generated settings.
# Add more configuration options below. # Add more configuration options below.
$wgLogos = [ $wgLogos = [
'svg' => "https://pub.solar/assets/pubsolar.svg", 'svg' => "https://pub.solar/assets/pubsolar.svg",
'icon' => "https://pub.solar/assets/pubsolar.svg", 'icon' => "https://pub.solar/assets/pubsolar.svg",
'wordmark' => [ 'wordmark' => [
'src'=> "https://pub.solar/assets/pubsolar.svg", 'src'=> "https://pub.solar/assets/pubsolar.svg",
'width'=> 0, 'width'=> 0,
'height'=> 0, 'height'=> 0,
], ],
]; ];
$wgFavicon = 'https://pub.solar/assets/pubsolar.svg'; $wgFavicon = 'https://pub.solar/assets/pubsolar.svg';
$wgDefaultSkin = 'vector-2022'; $wgDefaultSkin = 'vector-2022';
// https://www.mediawiki.org/wiki/Extension:PluggableAuth#Installation // https://www.mediawiki.org/wiki/Extension:PluggableAuth#Installation
$wgGroupPermissions['*']['autocreateaccount'] = true; $wgGroupPermissions['*']['autocreateaccount'] = true;
// https://www.mediawiki.org/wiki/Extension:PluggableAuth#Configuration // https://www.mediawiki.org/wiki/Extension:PluggableAuth#Configuration
$wgPluggableAuth_EnableAutoLogin = false; $wgPluggableAuth_EnableAutoLogin = false;
$wgPluggableAuth_ButtonLabel = 'Login with pub.solar ID'; $wgPluggableAuth_ButtonLabel = 'Login with pub.solar ID';
// https://www.mediawiki.org/wiki/Extension:OpenID_Connect#Keycloak // https://www.mediawiki.org/wiki/Extension:OpenID_Connect#Keycloak
$wgPluggableAuth_Config[] = [ $wgPluggableAuth_Config[] = [
'plugin' => 'OpenIDConnect', 'plugin' => 'OpenIDConnect',
'data' => [ 'data' => [
'providerURL' => 'https://auth.pub.solar/realms/pub.solar', 'providerURL' => 'https://auth.pub.solar/realms/pub.solar',
'clientID' => 'mediawiki', 'clientID' => 'mediawiki',
'clientsecret' => trim(file_get_contents('/run/mediawiki/oidc-client-secret')) 'clientsecret' => trim(file_get_contents('/run/mediawiki/oidc-client-secret'))
] ]
]; ];
$wgOpenIDConnect_SingleLogout = true; $wgOpenIDConnect_SingleLogout = true;
$wgOpenIDConnect_MigrateUsersByEmail = true; $wgOpenIDConnect_MigrateUsersByEmail = true;
''; '';
uid = 986; uid = 986;
gid = 984; gid = 984;
in { in
{
age.secrets.mediawiki-database-password = { age.secrets.mediawiki-database-password = {
file = "${flake.self}/secrets/mediawiki-database-password.age"; file = "${flake.self}/secrets/mediawiki-database-password.age";
path = "/run/mediawiki/database-password"; path = "/run/mediawiki/database-password";

View file

@ -1,8 +1,7 @@
{ { config
config, , pkgs
pkgs, , flake
flake, , ...
...
}: }:
{ {
age.secrets."nextcloud-secrets" = { age.secrets."nextcloud-secrets" = {

View file

@ -46,10 +46,12 @@ in
least_conn; least_conn;
''; '';
servers = builtins.listToAttrs servers = builtins.listToAttrs
(map (i: { (map
name = "unix:/run/mastodon-streaming/streaming-${toString i}.socket"; (i: {
value = { }; name = "unix:/run/mastodon-streaming/streaming-${toString i}.socket";
}) (lib.range 1 cfg.streamingProcesses)); value = { };
})
(lib.range 1 cfg.streamingProcesses));
}; };
}; };
} }

View file

@ -14,7 +14,7 @@ let
"io.element.e2ee" = { "io.element.e2ee" = {
default = true; default = true;
secure_backup_required = false; secure_backup_required = false;
secure_backup_setup_methods = []; secure_backup_setup_methods = [ ];
}; };
"m.integrations" = { "m.integrations" = {
managers = [ managers = [
@ -28,21 +28,21 @@ let
wellKnownServer = domain: { "m.server" = "matrix.${domain}:8448"; }; wellKnownServer = domain: { "m.server" = "matrix.${domain}:8448"; };
wellKnownSupport = { wellKnownSupport = {
contacts = [ contacts = [
{ {
email_address = "crew@pub.solar"; email_address = "crew@pub.solar";
matrix_id = "@b12f:pub.solar"; matrix_id = "@b12f:pub.solar";
role = "m.role.admin"; role = "m.role.admin";
} }
{ {
email_address = "crew@pub.solar"; email_address = "crew@pub.solar";
matrix_id = "@hensoko:pub.solar"; matrix_id = "@hensoko:pub.solar";
role = "m.role.admin"; role = "m.role.admin";
} }
{ {
email_address = "crew@pub.solar"; email_address = "crew@pub.solar";
matrix_id = "@teutat3s:pub.solar"; matrix_id = "@teutat3s:pub.solar";
role = "m.role.admin"; role = "m.role.admin";
} }
]; ];
support_page = "https://pub.solar/about"; support_page = "https://pub.solar/about";
}; };
@ -128,11 +128,12 @@ in
port = 8448; port = 8448;
addr = "0.0.0.0"; addr = "0.0.0.0";
ssl = true; ssl = true;
} { }
port = 8448; {
addr = "[::]"; port = 8448;
ssl = true; addr = "[::]";
}]; ssl = true;
}];
root = "/dev/null"; root = "/dev/null";
extraConfig = '' extraConfig = ''
server_tokens off; server_tokens off;
@ -154,6 +155,6 @@ in
}; };
}; };
}; };
networking.firewall.allowedTCPPorts = [8448]; networking.firewall.allowedTCPPorts = [ 8448 ];
} }

View file

@ -22,17 +22,17 @@
forceSSL = true; forceSSL = true;
locations = { locations = {
# serve base domain pub.solar for mastodon.pub.solar # serve base domain pub.solar for mastodon.pub.solar
# https://masto.host/mastodon-usernames-different-from-the-domain-used-for-installation/ # https://masto.host/mastodon-usernames-different-from-the-domain-used-for-installation/
"/.well-known/host-meta" = { "/.well-known/host-meta" = {
extraConfig = '' extraConfig = ''
return 301 https://mastodon.pub.solar$request_uri; return 301 https://mastodon.pub.solar$request_uri;
''; '';
}; };
# Tailscale OIDC webfinger requirement plus Mastodon webfinger redirect # Tailscale OIDC webfinger requirement plus Mastodon webfinger redirect
"/.well-known/webfinger" = { "/.well-known/webfinger" = {
# Redirect requests that match /.well-known/webfinger?resource=* to Mastodon # Redirect requests that match /.well-known/webfinger?resource=* to Mastodon
extraConfig = '' extraConfig = ''
if ($arg_resource) { if ($arg_resource) {
return 301 https://mastodon.pub.solar$request_uri; return 301 https://mastodon.pub.solar$request_uri;

View file

@ -1,13 +1,14 @@
{ { config
config, , lib
lib, , pkgs
pkgs, , self
self, , ...
... }:
}: let let
acmeEmailAddress = "admins@pub.solar"; acmeEmailAddress = "admins@pub.solar";
webserverGroup = "hakkonaut"; webserverGroup = "hakkonaut";
in { in
{
services.nginx = { services.nginx = {
enable = true; enable = true;
group = webserverGroup; group = webserverGroup;
@ -24,11 +25,11 @@ in {
proxy_headers_hash_bucket_size 128; proxy_headers_hash_bucket_size 128;
''; '';
}; };
security.acme = { security.acme = {
acceptTerms = true; acceptTerms = true;
defaults.email = acmeEmailAddress; defaults.email = acmeEmailAddress;
}; };
networking.firewall.allowedTCPPorts = [80 443]; networking.firewall.allowedTCPPorts = [ 80 443 ];
} }

View file

@ -1,9 +1,8 @@
{ { flake
flake, , config
config, , lib
lib, , pkgs
pkgs, , ...
...
}: { }: {
services.nginx.virtualHosts."stream.pub.solar" = { services.nginx.virtualHosts."stream.pub.solar" = {
enableACME = true; enableACME = true;

View file

@ -1,6 +1,5 @@
{ { config
config, , ...
...
}: { }: {
services.prometheus = { services.prometheus = {
exporters = { exporters = {

View file

@ -1,9 +1,8 @@
{ { config
config, , lib
lib, , pkgs
pkgs, , flake
flake, , ...
...
}: { }: {
age.secrets.nachtigall-metrics-prometheus-basic-auth-password = { age.secrets.nachtigall-metrics-prometheus-basic-auth-password = {
file = "${flake.self}/secrets/nachtigall-metrics-prometheus-basic-auth-password.age"; file = "${flake.self}/secrets/nachtigall-metrics-prometheus-basic-auth-password.age";

View file

@ -1,9 +1,8 @@
{ { flake
flake, , config
config, , lib
lib, , pkgs
pkgs, , ...
...
}: }:
{ {
age.secrets.searx-environment = { age.secrets.searx-environment = {
@ -33,7 +32,7 @@
chmod-socket = "660"; chmod-socket = "660";
}; };
environmentFile = config.age.secrets.searx-environment.path; environmentFile = config.age.secrets.searx-environment.path;
settings = { settings = {
use_default_settings = true; use_default_settings = true;

View file

@ -1,8 +1,7 @@
{ { flake
flake, , config
config, , pkgs
pkgs, , ...
...
}: { }: {
# Use GRUB2 as the boot loader. # Use GRUB2 as the boot loader.
# We don't use systemd-boot because Hetzner uses BIOS legacy boot. # We don't use systemd-boot because Hetzner uses BIOS legacy boot.

View file

@ -2,7 +2,8 @@
{ {
imports = imports =
[ # Include the results of the hardware scan. [
# Include the results of the hardware scan.
./hardware-configuration.nix ./hardware-configuration.nix
./configuration.nix ./configuration.nix

View file

@ -5,7 +5,8 @@
{ {
imports = imports =
[ (modulesPath + "/installer/scan/not-detected.nix") [
(modulesPath + "/installer/scan/not-detected.nix")
]; ];
boot.initrd.availableKernelModules = [ "ahci" "nvme" ]; boot.initrd.availableKernelModules = [ "ahci" "nvme" ];
@ -14,32 +15,38 @@
boot.extraModulePackages = [ ]; boot.extraModulePackages = [ ];
fileSystems."/" = fileSystems."/" =
{ device = "root_pool/root"; {
device = "root_pool/root";
fsType = "zfs"; fsType = "zfs";
}; };
fileSystems."/var/lib" = fileSystems."/var/lib" =
{ device = "root_pool/data"; {
device = "root_pool/data";
fsType = "zfs"; fsType = "zfs";
}; };
fileSystems."/var/lib/postgresql" = fileSystems."/var/lib/postgresql" =
{ device = "root_pool/data/postgresql"; {
device = "root_pool/data/postgresql";
fsType = "zfs"; fsType = "zfs";
}; };
fileSystems."/var/lib/docker" = fileSystems."/var/lib/docker" =
{ device = "root_pool/data/docker"; {
device = "root_pool/data/docker";
fsType = "zfs"; fsType = "zfs";
}; };
fileSystems."/boot1" = fileSystems."/boot1" =
{ device = "/dev/disk/by-uuid/5493-EFF5"; {
device = "/dev/disk/by-uuid/5493-EFF5";
fsType = "vfat"; fsType = "vfat";
}; };
fileSystems."/boot2" = fileSystems."/boot2" =
{ device = "/dev/disk/by-uuid/5494-BA1E"; {
device = "/dev/disk/by-uuid/5494-BA1E";
fsType = "vfat"; fsType = "vfat";
}; };

View file

@ -5,17 +5,17 @@ let
}); });
flake = flake =
import import
( (
fetchTarball { fetchTarball {
url = "https://github.com/edolstra/flake-compat/archive/${lock.nodes.flake-compat.locked.rev}.tar.gz"; url = "https://github.com/edolstra/flake-compat/archive/${lock.nodes.flake-compat.locked.rev}.tar.gz";
sha256 = lock.nodes.flake-compat.locked.narHash; sha256 = lock.nodes.flake-compat.locked.narHash;
} }
) )
{ {
src = builtins.path { src = builtins.path {
path = ../../.; path = ../../.;
name = "projectRoot"; name = "projectRoot";
};
}; };
};
in in
flake flake

View file

@ -1,4 +1,5 @@
{...}: let { ... }:
let
inherit (default.inputs.nixos) lib; inherit (default.inputs.nixos) lib;
host = configs.${hostname} or configs.PubSolarOS; host = configs.${hostname} or configs.PubSolarOS;
@ -6,4 +7,4 @@
default = (import ../.).defaultNix; default = (import ../.).defaultNix;
hostname = lib.fileContents /etc/hostname; hostname = lib.fileContents /etc/hostname;
in in
host host

View file

@ -1,16 +1,18 @@
{ self, lib, inputs, ... }: { { self, lib, inputs, ... }: {
# Configuration common to all Linux systems # Configuration common to all Linux systems
flake = { flake = {
lib = let lib =
callLibs = file: import file {inherit lib;}; let
in rec { callLibs = file: import file { inherit lib; };
## Define your own library functions here! in
#id = x: x; rec {
## Or in files, containing functions that take {lib} ## Define your own library functions here!
#foo = callLibs ./foo.nix; #id = x: x;
## In configs, they can be used under "lib.our" ## Or in files, containing functions that take {lib}
#foo = callLibs ./foo.nix;
## In configs, they can be used under "lib.our"
deploy = import ./deploy.nix { inherit inputs lib; }; deploy = import ./deploy.nix { inherit inputs lib; };
}; };
}; };
} }

View file

@ -5,7 +5,8 @@
* Licensed under the MIT license * Licensed under the MIT license
*/ */
{ lib, inputs }: let { lib, inputs }:
let
# https://github.com/serokell/deploy-rs#overall-usage # https://github.com/serokell/deploy-rs#overall-usage
system = "x86_64-linux"; system = "x86_64-linux";
pkgs = import inputs.nixpkgs { inherit system; }; pkgs = import inputs.nixpkgs { inherit system; };
@ -16,57 +17,59 @@
(self: super: { deploy-rs = { inherit (pkgs) deploy-rs; lib = super.deploy-rs.lib; }; }) (self: super: { deploy-rs = { inherit (pkgs) deploy-rs; lib = super.deploy-rs.lib; }; })
]; ];
}; };
getFqdn = c: let getFqdn = c:
net = c.config.networking; let
fqdn = net = c.config.networking;
if (net ? domain) && (net.domain != null) fqdn =
then "${net.hostName}.${net.domain}" if (net ? domain) && (net.domain != null)
else net.hostName; then "${net.hostName}.${net.domain}"
in else net.hostName;
in
fqdn; fqdn;
in { in
{
mkDeployNodes = systemConfigurations: extraConfig: mkDeployNodes = systemConfigurations: extraConfig:
/* /*
* *
Synopsis: mkNodes _systemConfigurations_ _extraConfig_ Synopsis: mkNodes _systemConfigurations_ _extraConfig_
Generate the `nodes` attribute expected by deploy-rs Generate the `nodes` attribute expected by deploy-rs
where _systemConfigurations_ are `nodes`. where _systemConfigurations_ are `nodes`.
_systemConfigurations_ should take the form of a flake's _systemConfigurations_ should take the form of a flake's
_nixosConfigurations_. Note that deploy-rs does not currently support _nixosConfigurations_. Note that deploy-rs does not currently support
deploying to darwin hosts. deploying to darwin hosts.
_extraConfig_, if specified, will be merged into each of the _extraConfig_, if specified, will be merged into each of the
nodes' configurations. nodes' configurations.
Example _systemConfigurations_ input: Example _systemConfigurations_ input:
``` ```
{ {
hostname-1 = { hostname-1 = {
fastConnection = true; fastConnection = true;
sshOpts = [ "-p" "25" ]; sshOpts = [ "-p" "25" ];
}; };
hostname-2 = { hostname-2 = {
sshOpts = [ "-p" "19999" ]; sshOpts = [ "-p" "19999" ];
sshUser = "root"; sshUser = "root";
}; };
} }
``` ```
* *
*/ */
lib.recursiveUpdate lib.recursiveUpdate
(lib.mapAttrs (lib.mapAttrs
( (
_: c: { _: c: {
hostname = getFqdn c; hostname = getFqdn c;
profiles.system = { profiles.system = {
user = "root"; user = "root";
path = deployPkgs.deploy-rs.lib.activate.nixos c; path = deployPkgs.deploy-rs.lib.activate.nixos c;
}; };
} }
) )
systemConfigurations) systemConfigurations)
extraConfig; extraConfig;
} }

View file

@ -1,9 +1,8 @@
{ { config
config, , pkgs
pkgs, , lib
lib, , flake
flake, , ...
...
}: { }: {
nixpkgs.config.allowUnfreePredicate = pkg: builtins.elem (lib.getName pkg) [ nixpkgs.config.allowUnfreePredicate = pkg: builtins.elem (lib.getName pkg) [
]; ];
@ -26,9 +25,9 @@
# Prevents impurities in builds # Prevents impurities in builds
sandbox = true; sandbox = true;
# Give root and @wheel special privileges with nix # Give root and @wheel special privileges with nix
trusted-users = ["root" "@wheel"]; trusted-users = [ "root" "@wheel" ];
# Allow only group wheel to connect to the nix daemon # Allow only group wheel to connect to the nix daemon
allowed-users = ["@wheel"]; allowed-users = [ "@wheel" ];
}; };
# Generally useful nix option defaults # Generally useful nix option defaults

View file

@ -2,11 +2,11 @@
users.users.${flake.self.username} = { users.users.${flake.self.username} = {
name = flake.self.username; name = flake.self.username;
group = flake.self.username; group = flake.self.username;
extraGroups = ["wheel" "docker"]; extraGroups = [ "wheel" "docker" ];
isNormalUser = true; isNormalUser = true;
openssh.authorizedKeys.keys = flake.self.publicKeys.admins; openssh.authorizedKeys.keys = flake.self.publicKeys.admins;
}; };
users.groups.${flake.self.username} = {}; users.groups.${flake.self.username} = { };
# TODO: Remove when we stop locking ourselves out. # TODO: Remove when we stop locking ourselves out.
users.users.root.openssh.authorizedKeys.keys = flake.self.publicKeys.admins; users.users.root.openssh.authorizedKeys.keys = flake.self.publicKeys.admins;
@ -22,7 +22,7 @@
openssh.authorizedKeys.keys = flake.self.publicKeys.robots; openssh.authorizedKeys.keys = flake.self.publicKeys.robots;
}; };
users.groups.hakkonaut = {}; users.groups.hakkonaut = { };
users.users.root.initialHashedPassword = "$y$j9T$bIN6GjQkmPMllOcQsq52K0$q0Z5B5.KW/uxXK9fItB8H6HO79RYAcI/ZZdB0Djke32"; users.users.root.initialHashedPassword = "$y$j9T$bIN6GjQkmPMllOcQsq52K0$q0Z5B5.KW/uxXK9fItB8H6HO79RYAcI/ZZdB0Djke32";

View file

@ -1,21 +1,20 @@
{ { self
self, , inputs
inputs, , ...
...
}: { }: {
flake = { flake = {
nixosModules = rec { nixosModules = rec {
overlays = ({ ... }: { overlays = ({ ... }: {
nixpkgs.overlays = [ nixpkgs.overlays = [
(final: prev: (final: prev:
let let
unstable = import inputs.unstable { unstable = import inputs.unstable {
system = prev.system; system = prev.system;
}; };
in in
{ {
element-themes = prev.callPackage ./pkgs/element-themes { inherit (inputs) element-themes; }; element-themes = prev.callPackage ./pkgs/element-themes { inherit (inputs) element-themes; };
}) })
]; ];
}); });
}; };

View file

@ -1,8 +1,8 @@
{lib, ...}: { lib, ... }:
{ {
flake = { flake = {
publicKeys = { publicKeys = {
admins = lib.attrsets.attrValues (import ./admins.nix); admins = lib.attrsets.attrValues (import ./admins.nix);
robots = lib.attrsets.attrValues (import ./robots.nix); robots = lib.attrsets.attrValues (import ./robots.nix);
}; };
}; };

View file

@ -24,7 +24,8 @@ let
flora6Keys = [ flora6Keys = [
flora-6-host flora-6-host
]; ];
in { in
{
# ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIBB5XaH02a6+TchnyQED2VwaltPgeFCbildbE2h6nF5e root@nachtigall # ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIBB5XaH02a6+TchnyQED2VwaltPgeFCbildbE2h6nF5e root@nachtigall
"nachtigall-root-ssh-key.age".publicKeys = nachtigallKeys ++ baseKeys; "nachtigall-root-ssh-key.age".publicKeys = nachtigallKeys ++ baseKeys;