Files
nixfiles/lib/constants.nix
T
jackos1998 5171a10079
CI / Check, build and cache nixfiles (push) Failing after 59m32s
Update docs / update (push) Failing after 1m12s
nixpkgs: Refresh channels and inputs
Rebase the fork branches and refresh nixpkgs, home-manager, and the
approved ancillary inputs. Update kernel and release metadata, adapt
removed package and Home Assistant options, and keep Determinate Nix
on its tested nixpkgs revision to avoid duplicate Boost patches.

Retire Sharry and its public endpoint because copyparty replaces it.
Document the GitHub mirror gate and require real devshell and system
builds in the upgrade validation workflow.
2026-08-24 00:10:18 +01:00

499 lines
12 KiB
Nix

{ lib }:
let
inherit (lib) concatStringsSep;
in
rec {
# See https://github.com/NixOS/nixpkgs/blob/master/nixos/modules/misc/ids.nix
ids = {
uids = {
matrix-syncv3 = 400;
gitea-runner = 401;
jellyseerr = 402;
atticd = 403;
kea = 404;
keepalived_script = 405;
photoprism = 406;
copyparty = 408;
};
gids = {
matrix-syncv3 = 400;
gitea-runner = 401;
jellyseerr = 402;
atticd = 403;
kea = 404;
keepalived_script = 405;
photoprism = 406;
adbusers = 407;
copyparty = 408;
};
};
kernel = {
lts = pkgs: pkgs.linuxKernel.packages.linux_6_18;
latest = pkgs: pkgs.linuxKernel.packages.linux_7_2;
};
nginx = rec {
proxyHeaders = ''
# Setting any proxy_header in a child (e.g. location) will nuke the parents...
proxy_set_header X-Origin-URI $request_uri;
proxy_set_header Host $host;
proxy_set_header X-Host $http_host;
proxy_set_header X-Forwarded-Host $http_host;
proxy_set_header X-Forwarded-Server $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_set_header X-Forwarded-Protocol $scheme;
proxy_set_header X-Scheme $scheme;
'';
baseHttpConfig = ''
# NixOS provides a logrotate config that auto-compresses :)
log_format main
'$remote_addr - $remote_user [$time_local] $scheme "$host" "$request" $status $body_bytes_sent "$http_referer" "$http_user_agent"';
access_log /var/log/nginx/access.log main;
# optimisation
sendfile on;
tcp_nopush on;
tcp_nodelay on;
keepalive_timeout 65;
# gzip
gzip on;
gzip_proxied any;
gzip_comp_level 5;
gzip_types
application/atom+xml
application/javascript
application/json
application/xml
application/xml+rss
image/svg+xml
text/css
text/javascript
text/plain
text/xml;
gzip_vary on;
# proxying
proxy_buffering off;
proxy_redirect off;
proxy_connect_timeout 60s;
proxy_read_timeout 60s;
proxy_send_timeout 60s;
proxy_http_version 1.1;
${proxyHeaders}
'';
};
networkd = {
noL3 = {
LinkLocalAddressing = "no";
DHCP = "no";
LLDP = false;
EmitLLDP = false;
IPv6AcceptRA = false;
};
};
nix = {
cache = rec {
substituters = [
"https://nix-cache.${pubDomain}"
];
keys = [
"nix-cache.nul.ie-1:BzH5yMfF4HbzY1C977XzOxoPhEc9Zbu39ftPkUbH+m4="
];
conf = ''
extra-substituters = ${concatStringsSep " " substituters}
extra-trusted-public-keys = ${concatStringsSep " " keys}
'';
};
# Determinate-specific settings enabling its performance features. Only understood by the
# Determinate Nix binary, so they must not be emitted for a base-Nix package.
determinateSettings = {
lazy-trees = true;
eval-cores = 0;
};
};
pubDomain = "nul.ie";
colony = rec {
domain = "ams1.int.${pubDomain}";
pubV4 = "94.142.240.44";
prefixes = with lib.my.net.cidr; rec {
all = {
v4 = "10.100.0.0/16";
v6 = "2a0e:97c0:4d2:10::/60";
};
base = {
v4 = subnet 8 0 all.v4;
v6 = subnet 4 0 all.v6;
};
vms = {
v4 = subnet 8 1 all.v4;
v6 = subnet 4 1 all.v6;
};
ctrs = {
v4 = subnet 8 2 all.v4;
v6 = subnet 4 2 all.v6;
};
oci = {
v4 = subnet 8 3 all.v4;
v6 = subnet 4 3 all.v6;
};
qclk = {
v4 = subnet 8 4 all.v4;
};
p2pTunnels = {
v4 = subnet 8 5 all.v4;
};
hillcrest = {
v4 = subnet 6 0 p2pTunnels.v4;
};
john-valorant = {
v4 = subnet 6 1 p2pTunnels.v4;
};
cust = {
v4 = subnet 8 100 all.v4; # single ip for routing only
v6 = "2a0e:97c0:4d2:2000::/56";
};
mail = {
v4 = "94.142.241.227/32";
v6 = subnet 8 0 cust.v6;
};
darts = {
v4 = "94.142.242.255/32";
v6 = subnet 8 1 cust.v6;
};
jam = {
v4 = subnet 8 4 cust.v4;
v6 = subnet 8 2 cust.v6;
};
vip1 = "94.142.241.224/30";
vip2 = "94.142.242.254/31";
vip3 = "94.142.241.117/32";
as211024 = {
v4 = subnet 8 50 all.v4;
v6 = "2a0e:97c0:4df::/64";
};
home.v6 = "2a0e:97c0:4d0::/48";
};
custRouting = with lib.my.net.cidr; {
mail-vm = host 1 prefixes.cust.v4;
darts-vm = host 2 prefixes.cust.v4;
jam-ctr = host 3 prefixes.cust.v4;
};
qclk = {
wgPort = 51821;
};
firewallForwards = aa: [
{
port = "http";
dst = aa.middleman.internal.ipv4.address;
}
{
port = "https";
dst = aa.middleman.internal.ipv4.address;
}
{
port = 8448;
dst = aa.middleman.internal.ipv4.address;
}
{
port = 25565;
dst = aa.simpcraft-oci.internal.ipv4.address;
}
{
port = 25566;
dst = aa.simpcraft-staging-oci.internal.ipv4.address;
}
{
port = 25567;
dst = aa.kevcraft-oci.internal.ipv4.address;
}
{
port = 25568;
dst = aa.kinkcraft-oci.internal.ipv4.address;
}
{
port = 25569;
dst = aa.graeme-oci.internal.ipv4.address;
}
# RCON... unsafe?
# {
# port = 25575;
# dst = aa.simpcraft-oci.internal.ipv4.address;
# }
{
port = 7777;
dst = aa.gam.internal.ipv4.address;
}
{
port = 2456;
dst = aa.valheim-oci.internal.ipv4.address;
proto = "udp";
}
{
port = 2457;
dst = aa.valheim-oci.internal.ipv4.address;
proto = "udp";
}
{
port = 41641;
dst = aa.waffletail.internal.ipv4.address;
proto = "udp";
}
{
port = 25565;
dst = aa.simpcraft-oci.internal.ipv4.address;
proto = "udp";
}
{
port = 25567;
dst = aa.kevcraft-oci.internal.ipv4.address;
proto = "udp";
}
{
port = 25568;
dst = aa.kinkcraft-oci.internal.ipv4.address;
proto = "udp";
}
{
port = 25569;
dst = aa.graeme-oci.internal.ipv4.address;
proto = "udp";
}
{
port = 15636;
dst = aa.enshrouded-oci.internal.ipv4.address;
proto = "udp";
}
{
port = 15637;
dst = aa.enshrouded-oci.internal.ipv4.address;
proto = "udp";
}
{
port = qclk.wgPort;
dst = aa.qclk.internal.ipv4.address;
proto = "udp";
}
{
port = 7777;
dst = aa.gam.internal.ipv4.address;
proto = "udp";
}
];
fstrimConfig = {
enable = true;
# backup happens at 05:00
interval = "04:45";
};
};
home = rec {
domain = "h.${pubDomain}";
# Search domains advertised to clients (radvd DNSSL / kea domain-search)
searchDomains = [ domain "dyn.${domain}" colony.domain britway.domain ];
vlans = {
hi = 100;
lo = 110;
untrusted = 120;
wan = 130;
# Digiweb delivers the ISP VLAN (pon-isp, 10) single-tagged at the ONT alongside the ONT's
# own untagged management traffic. With a single ONT we trunk pon-isp (10) straight through
# the switches to river (PPPoE runs directly on it), and the switch at the ONT edge PVIDs the
# untagged management port onto wan-pon-ont (140). wan-pon-isp (141) is reserved for the
# future multi-ONT case, where per-port VLAN translation on a dedicated switch swaps each
# ONT's VLAN 10 to a distinct fabric VLAN (see docs/sites/home/switches.md).
pon-isp = 10;
wan-pon-ont = 140;
wan-pon-isp = 141;
};
hiMTU = 9000;
routers = [
"river"
"stream"
];
routersPubV4 = [
"84.203.124.128" # river: Digiweb static
"109.255.108.121"
];
prefixes = with lib.my.net.cidr; rec {
modem = {
v4 = "192.168.0.0/24";
};
ont = {
v4 = "192.168.100.0/24";
};
all = {
v4 = "192.168.64.0/18";
v6 = "2a0e:97c0:4d0::/60";
};
core = {
v4 = subnet 6 0 all.v4;
};
hi = {
v4 = subnet 4 1 all.v4;
v6 = subnet 4 1 all.v6;
mtu = hiMTU;
};
lo = {
v4 = subnet 3 1 all.v4;
v6 = subnet 4 2 all.v6;
mtu = 1500;
};
untrusted = {
v4 = subnet 6 16 all.v4;
v6 = subnet 4 3 all.v6;
mtu = 1500;
};
inherit (colony.prefixes) as211024;
};
vips = with lib.my.net.cidr; {
hi = {
v4 = host (4*256-2) prefixes.hi.v4;
v6 = host 65535 prefixes.hi.v6;
};
lo = {
v4 = host (8*256-2) prefixes.lo.v4;
v6 = host 65535 prefixes.lo.v6;
};
untrusted = {
v4 = host 254 prefixes.untrusted.v4;
v6 = host 65535 prefixes.untrusted.v6;
};
as211024 = {
v4 = host 4 prefixes.as211024.v4;
v6 = host ((1*65536*65536*65536) + 65535) prefixes.as211024.v6;
};
};
# networkConfig fragment anchoring a VLAN client's DNS on the router pair's
# VRRP VIPs rather than the RA RDNSS. v6 addresses here are RA/token-derived,
# so when RA is absent (e.g. v6 disabled) there is no v6 and no RDNSS at all;
# the always-present static v4 VIP keeps name resolution working, with the v6
# VIP as a bonus when v6 is up. Merge into the VLAN network's networkConfig.
vlanDns = vlan: {
DNS = [ vips.${vlan}.v4 vips.${vlan}.v6 ];
Domains = searchDomains;
};
roceBootModules = [ "ib_core" "ib_uverbs" "mlx5_core" "mlx5_ib" ];
};
britway = {
domain = "lon1.int.${pubDomain}";
pubV4 = "45.76.141.188";
prefixes = {
vultr = {
v6 = "2001:19f0:7402:128b::/64";
};
inherit (colony.prefixes) as211024;
};
# Need to use this IP as the source address for BGP
assignedV6 = "2001:19f0:7402:128b:5400:04ff:feac:6e06";
};
britnet = {
domain = "bhx1.int.${pubDomain}";
pubV4 = "77.74.199.67";
vpn = {
port = 51820;
};
prefixes = with lib.my.net.cidr; rec {
vpn = {
v4 = "10.200.0.0/24";
v6 = "fdfb:5ebf:6e84::/64";
};
};
};
tailscale = {
prefix = {
v4 = "100.64.0.0/10";
v6 = "fd7a:115c:a1e0::/48";
};
};
as211024 = rec {
trusted = {
v4 = [
colony.prefixes.as211024.v4
colony.prefixes.all.v4
home.prefixes.all.v4
tailscale.prefix.v4
];
v6 = [
colony.prefixes.as211024.v6
colony.prefixes.all.v6
home.prefixes.all.v6
tailscale.prefix.v6
];
};
nftTrust = ''
iifname as211024 ip saddr { ${concatStringsSep ", " trusted.v4} } accept
iifname as211024 ip6 saddr { ${concatStringsSep ", " trusted.v6} } accept
'';
};
kelder = {
groups = {
storage = 2000;
media = 2010;
};
domain = "hentai.engineer";
ipv4MTU = 1460;
vpn = {
port = 51820;
};
prefixes = with lib.my.net.cidr; rec {
all.v4 = "172.16.64.0/20";
ctrs.v4 = subnet 4 0 all.v4;
};
};
hillcrest = {
vpn.port = 51822;
};
john-valorant = {
vpn.port = 51823;
};
sshKeyFiles = {
me = ../.keys/me.pub;
deploy = ../.keys/deploy.pub;
rsyncNet = ../.keys/zh2855.rsync.net.pub;
mailcowAcme = ../.keys/mailcow-acme.pub;
harmonia = ../.keys/harmonia.pub;
};
sshHostKeys = {
mail-vm = ../.keys/mail-vm-host.pub;
};
}