refactor: make all host and ip lookups centralize in the main lib

This commit is contained in:
Ceferino Patino 2026-06-21 14:08:18 -05:00
commit ce339f71cb
Signed by: c4patino
SSH key fingerprint: SHA256:Wu+cU1t+7zVT9wzew/4meNmeulo66NzMqc22MdDBgXI
23 changed files with 94 additions and 121 deletions

View file

@ -140,6 +140,32 @@ with lib; rec {
then devices.${node}.gateway
else false;
## Resolve the hostname that hosts a specific database.
##
## @param databases A set mapping hostnames to lists of database names.
## @param dbName The name of the database to find.
## @return The hostname where the database is hosted.
## @throws If no host is found for the given database.
resolveDatabaseHost = databases: dbName: let
matchingHosts =
databases
|> filterAttrs (host: dbs: lib.elem dbName dbs)
|> attrNames;
in
if matchingHosts == []
then throw "No host found for database '${dbName}'."
else builtins.head matchingHosts;
## Resolve the IP address of the host that hosts a specific database.
##
## @param devices A set mapping hostnames to their configuration (must include `ip`).
## @param databases A set mapping hostnames to lists of database names.
## @param dbName The name of the database to find.
## @return The IP address of the host where the database is hosted.
## @throws If no host is found for the given database.
resolveDatabaseIP = devices: databases: dbName:
resolveHostIP devices (resolveDatabaseHost databases dbName);
## Check for configuration conflicts between mount and share declarations.
##
## @param shares A list of folder names that are shared.
@ -223,15 +249,6 @@ with lib; rec {
then throw "flattenHostServices: duplicate service names across hosts detected"
else flattenedAttrs;
## Check if a host has any services defined in the network-services config.
##
## @param networkServices The network-services attribute set (host-first shape).
## @param hostName The hostname to check.
## @return true if the host has any services defined, false otherwise.
hostHasServices = networkServices: hostName:
networkServices ? ${hostName}
&& networkServices.${hostName} != {};
## Check if a host has a specific service defined in the network-services config.
##
## @param networkServices The network-services attribute set (host-first shape).
@ -242,20 +259,20 @@ with lib; rec {
networkServices ? ${hostName}
&& networkServices.${hostName} ? ${serviceName};
## Get the port for a service from the flattened network-services map.
## Resolve the port for a service from the network-services map.
##
## @param networkServicesFlat The flattened network-services map (from flattenHostServices).
## @param serviceName The name of the service.
## @param defaultPort The default port to use if not specified in network-services.
## @return The port (either from config or default).
getServicePort = networkServicesFlat: serviceName: defaultPort:
networkServicesFlat.${serviceName}.port or defaultPort;
## @param networkServices The network-services attribute set (host-first shape).
## @param serviceName The name of the service.
## @param defaultPort The default port to use if not specified in network-services.
## @return The port (either from config or default).
resolveServicePort = networkServices: serviceName: defaultPort:
(flattenHostServices networkServices).${serviceName}.port or defaultPort;
## Get the host for a service from the flattened network-services map.
## Resolve the host for a service from the network-services map.
##
## @param networkServicesFlat The flattened network-services map (from flattenHostServices).
## @param serviceName The name of the service.
## @return The host name where the service is defined.
getServiceHost = networkServicesFlat: serviceName:
networkServicesFlat.${serviceName}.host;
## @param networkServices The network-services attribute set (host-first shape).
## @param serviceName The name of the service.
## @return The host name where the service is defined.
resolveServiceHost = networkServices: serviceName:
(flattenHostServices networkServices).${serviceName}.host;
}

View file

@ -6,22 +6,15 @@
pkgs,
...
}: let
inherit (lib) mkIf filterAttrs attrNames head mkForce;
inherit (lib.${namespace}) getAttrByNamespace resolveHostIP readJsonOrEmpty getIn hostHasService flattenHostServices getServicePort;
inherit (lib) mkIf mkForce;
inherit (lib.${namespace}) getAttrByNamespace resolveDatabaseHost resolveDatabaseIP readJsonOrEmpty getIn hostHasService resolveServicePort;
inherit (config.networking) hostName;
networkCfg = getAttrByNamespace config "${namespace}.services.networking";
networkServices = flattenHostServices networkCfg.network-services;
pgCfg = getAttrByNamespace config "${namespace}.services.storage.postgresql";
dbHost =
pgCfg.databases
|> filterAttrs (host: dbs: lib.elem "forgejo" dbs)
|> attrNames
|> head;
isEnabled = hostHasService networkCfg.network-services hostName "git";
port = getServicePort networkServices "git" 5300;
port = resolveServicePort networkCfg.network-services "git" 5300;
in {
config = mkIf isEnabled {
services.forgejo = {
@ -32,7 +25,7 @@ in {
lfs.enable = true;
database.type = mkIf (dbHost == hostName) "postgres";
database.type = "postgres";
settings = {
actions.ENABLED = true;
@ -55,7 +48,7 @@ in {
database = {
DB_TYPE = mkForce "postgres";
HOST = mkForce "${resolveHostIP networkCfg.devices dbHost}:5600";
HOST = mkForce "${resolveDatabaseIP networkCfg.devices pgCfg.databases "forgejo"}:5600";
NAME = "forgejo";
USER = "forgejo";
PASSWD =
@ -103,7 +96,7 @@ in {
systemd.services.forgejo = let
inherit (config.networking) hostName;
in
mkIf (dbHost == hostName) {
mkIf (resolveDatabaseHost pgCfg.databases "forgejo" == hostName) {
after = ["postgresql.service" "pgbouncer.service"];
requires = ["postgresql.service" "pgbouncer.service"];
serviceConfig = {

View file

@ -6,14 +6,13 @@
...
} @ args: let
inherit (lib) mkIf;
inherit (lib.${namespace}) getAttrByNamespace hostHasService flattenHostServices getServicePort;
inherit (lib.${namespace}) getAttrByNamespace hostHasService resolveServicePort;
inherit (config.networking) hostName;
networkCfg = getAttrByNamespace config "${namespace}.services.networking";
networkServices = flattenHostServices networkCfg.network-services;
isEnabled = hostHasService networkCfg.network-services hostName "dash";
port = getServicePort networkServices "dash" 5150;
port = resolveServicePort networkCfg.network-services "dash" 5150;
in {
imports = [
(import ./layout.nix args)

View file

@ -6,17 +6,16 @@
pkgs,
...
}: let
inherit (lib) mkIf attrNames filterAttrs elem head;
inherit (lib.${namespace}) getAttrByNamespace resolveHostIP readJsonOrEmpty getIn hostHasService flattenHostServices getServicePort;
inherit (lib) mkIf;
inherit (lib.${namespace}) getAttrByNamespace resolveDatabaseHost resolveDatabaseIP readJsonOrEmpty getIn hostHasService resolveServicePort;
inherit (config.networking) hostName;
pgCfg = getAttrByNamespace config "${namespace}.services.storage.postgresql";
networkCfg = getAttrByNamespace config "${namespace}.services.networking";
networkServices = flattenHostServices networkCfg.network-services;
isEnabled = hostHasService networkCfg.network-services hostName "grafana";
port = getServicePort networkServices "grafana" 5500;
port = resolveServicePort networkCfg.network-services "grafana" 5500;
in {
config = mkIf isEnabled {
services.grafana = {
@ -36,12 +35,7 @@ in {
database = {
type = "postgres";
host = let
ip =
pgCfg.databases
|> filterAttrs (host: dbs: elem "grafana" dbs)
|> attrNames
|> head
|> resolveHostIP networkCfg.devices;
ip = resolveDatabaseIP networkCfg.devices pgCfg.databases "grafana";
in "${ip}:5600";
name = "grafana";
user = "grafana";
@ -63,11 +57,7 @@ in {
};
systemd.services.grafana = let
dbHost =
pgCfg.databases
|> filterAttrs (host: dbs: elem "grafana" dbs)
|> attrNames
|> head;
dbHost = resolveDatabaseHost pgCfg.databases "grafana";
in
mkIf (dbHost == config.networking.hostName) {
after = ["postgresql.service" "pgbouncer.service"];

View file

@ -6,16 +6,15 @@
...
}: let
inherit (lib) mkIf mkOption types;
inherit (lib.${namespace}) getAttrByNamespace mkOptionsWithNamespace hostHasService flattenHostServices getServicePort;
inherit (lib.${namespace}) getAttrByNamespace mkOptionsWithNamespace hostHasService resolveServicePort;
inherit (config.networking) hostName;
base = "${namespace}.services.apps.miasma";
cfg = getAttrByNamespace config base;
networkCfg = getAttrByNamespace config "${namespace}.services.networking";
networkServices = flattenHostServices networkCfg.network-services;
isEnabled = hostHasService networkCfg.network-services hostName "miasma";
port = getServicePort networkServices "miasma" 9999;
port = resolveServicePort networkCfg.network-services "miasma" 9999;
in {
options = with types;
mkOptionsWithNamespace base {

View file

@ -7,14 +7,13 @@
with lib;
with lib.${namespace}; let
inherit (lib) mkIf;
inherit (lib.${namespace}) getAttrByNamespace hostHasService flattenHostServices getServicePort;
inherit (lib.${namespace}) getAttrByNamespace hostHasService resolveServicePort;
inherit (config.networking) hostName;
networkCfg = getAttrByNamespace config "${namespace}.services.networking";
networkServices = flattenHostServices networkCfg.network-services;
isEnabled = hostHasService networkCfg.network-services hostName "ntfy";
port = getServicePort networkServices "ntfy" 5201;
port = resolveServicePort networkCfg.network-services "ntfy" 5201;
in {
config = mkIf isEnabled {
services.ntfy-sh = {

View file

@ -5,14 +5,13 @@
...
}: let
inherit (lib) mkIf;
inherit (lib.${namespace}) getAttrByNamespace hostHasService flattenHostServices getServicePort;
inherit (lib.${namespace}) getAttrByNamespace hostHasService resolveServicePort;
inherit (config.networking) hostName;
networkCfg = getAttrByNamespace config "${namespace}.services.networking";
networkServices = flattenHostServices networkCfg.network-services;
isEnabled = hostHasService networkCfg.network-services hostName "prometheus";
port = getServicePort networkServices "prometheus" 9090;
port = resolveServicePort networkCfg.network-services "prometheus" 9090;
in {
config = mkIf isEnabled {
services.prometheus = {

View file

@ -7,17 +7,16 @@
...
}: let
inherit (lib) mkIf;
inherit (lib.${namespace}) getAttrByNamespace hostHasService getServicePort flattenHostServices;
inherit (lib.${namespace}) getAttrByNamespace hostHasService resolveServicePort;
inherit (config.networking) hostName;
networkCfg = getAttrByNamespace config "${namespace}.services.networking";
networkServices = flattenHostServices networkCfg.network-services;
uid = 980;
gid = 975;
isEnabled = hostHasService networkCfg.network-services hostName "qbittorrent";
port = getServicePort networkServices "qbittorrent" 9000;
port = resolveServicePort networkCfg.network-services "qbittorrent" 9000;
torrentingPort = 23345;
in {
config = mkIf isEnabled {

View file

@ -7,7 +7,7 @@
...
}: let
inherit (lib) mkIf mkEnableOption;
inherit (lib.${namespace}) getAttrByNamespace mkOptionsWithNamespace hostHasService flattenHostServices getServicePort;
inherit (lib.${namespace}) getAttrByNamespace mkOptionsWithNamespace hostHasService resolveServicePort;
inherit (config.users) users groups;
inherit (config.sops) secrets;
inherit (config.networking) hostName;
@ -16,10 +16,9 @@
cfg = getAttrByNamespace config base;
networkCfg = getAttrByNamespace config "${namespace}.services.networking";
networkServices = flattenHostServices networkCfg.network-services;
isEnabled = hostHasService networkCfg.network-services hostName "paste";
port = getServicePort networkServices "paste" 5100;
port = resolveServicePort networkCfg.network-services "paste" 5100;
in {
options = mkOptionsWithNamespace base {
client = {

View file

@ -6,14 +6,13 @@
...
}: let
inherit (lib) mkForce mkIf;
inherit (lib.${namespace}) getAttrByNamespace hostHasService getServicePort flattenHostServices;
inherit (lib.${namespace}) getAttrByNamespace hostHasService resolveServicePort;
inherit (config.networking) hostName;
networkCfg = getAttrByNamespace config "${namespace}.services.networking";
networkServices = flattenHostServices networkCfg.network-services;
isEnabled = hostHasService networkCfg.network-services hostName "autobrr";
port = getServicePort networkServices "autobrr" 7474;
port = resolveServicePort networkCfg.network-services "autobrr" 7474;
in {
config = mkIf isEnabled {
services.autobrr = {

View file

@ -5,14 +5,13 @@
...
}: let
inherit (lib) mkForce mkIf;
inherit (lib.${namespace}) getAttrByNamespace hostHasService flattenHostServices getServicePort;
inherit (lib.${namespace}) getAttrByNamespace hostHasService resolveServicePort;
inherit (config.networking) hostName;
networkCfg = getAttrByNamespace config "${namespace}.services.networking";
networkServices = flattenHostServices networkCfg.network-services;
isEnabled = hostHasService networkCfg.network-services hostName "bazarr";
port = getServicePort networkServices "bazarr" 6767;
port = resolveServicePort networkCfg.network-services "bazarr" 6767;
in {
config = mkIf isEnabled {
services.bazarr = {

View file

@ -5,14 +5,13 @@
...
}: let
inherit (lib) mkForce mkIf;
inherit (lib.${namespace}) getAttrByNamespace hostHasService flattenHostServices getServicePort;
inherit (lib.${namespace}) getAttrByNamespace hostHasService resolveServicePort;
inherit (config.networking) hostName;
networkCfg = getAttrByNamespace config "${namespace}.services.networking";
networkServices = flattenHostServices networkCfg.network-services;
isEnabled = hostHasService networkCfg.network-services hostName "lidarr";
port = getServicePort networkServices "lidarr" 8686;
port = resolveServicePort networkCfg.network-services "lidarr" 8686;
in {
config = mkIf isEnabled {
services.lidarr = {

View file

@ -5,14 +5,13 @@
...
}: let
inherit (lib) mkIf;
inherit (lib.${namespace}) getAttrByNamespace hostHasService flattenHostServices getServicePort;
inherit (lib.${namespace}) getAttrByNamespace hostHasService resolveServicePort;
inherit (config.networking) hostName;
networkCfg = getAttrByNamespace config "${namespace}.services.networking";
networkServices = flattenHostServices networkCfg.network-services;
isEnabled = hostHasService networkCfg.network-services hostName "ombi";
port = getServicePort networkServices "ombi" 5000;
port = resolveServicePort networkCfg.network-services "ombi" 5000;
in {
config = mkIf isEnabled {
services.ombi = {

View file

@ -5,14 +5,13 @@
...
}: let
inherit (lib) mkForce mkIf;
inherit (lib.${namespace}) getAttrByNamespace hostHasService flattenHostServices getServicePort;
inherit (lib.${namespace}) getAttrByNamespace hostHasService resolveServicePort;
inherit (config.networking) hostName;
networkCfg = getAttrByNamespace config "${namespace}.services.networking";
networkServices = flattenHostServices networkCfg.network-services;
isEnabled = hostHasService networkCfg.network-services hostName "prowlarr";
port = getServicePort networkServices "prowlarr" 9696;
port = resolveServicePort networkCfg.network-services "prowlarr" 9696;
in {
config = mkIf isEnabled {
services.prowlarr = {

View file

@ -5,14 +5,13 @@
...
}: let
inherit (lib) mkForce mkIf;
inherit (lib.${namespace}) getAttrByNamespace hostHasService flattenHostServices getServicePort;
inherit (lib.${namespace}) getAttrByNamespace hostHasService resolveServicePort;
inherit (config.networking) hostName;
networkCfg = getAttrByNamespace config "${namespace}.services.networking";
networkServices = flattenHostServices networkCfg.network-services;
isEnabled = hostHasService networkCfg.network-services hostName "radarr";
port = getServicePort networkServices "radarr" 7878;
port = resolveServicePort networkCfg.network-services "radarr" 7878;
in {
config = mkIf isEnabled {
services.radarr = {

View file

@ -5,14 +5,13 @@
...
}: let
inherit (lib) mkForce mkIf;
inherit (lib.${namespace}) getAttrByNamespace hostHasService flattenHostServices getServicePort;
inherit (lib.${namespace}) getAttrByNamespace hostHasService resolveServicePort;
inherit (config.networking) hostName;
networkCfg = getAttrByNamespace config "${namespace}.services.networking";
networkServices = flattenHostServices networkCfg.network-services;
isEnabled = hostHasService networkCfg.network-services hostName "seerr";
port = getServicePort networkServices "seerr" 5055;
port = resolveServicePort networkCfg.network-services "seerr" 5055;
in {
config = mkIf isEnabled {
services.seerr = {

View file

@ -5,14 +5,13 @@
...
}: let
inherit (lib) mkForce mkIf;
inherit (lib.${namespace}) getAttrByNamespace hostHasService flattenHostServices getServicePort;
inherit (lib.${namespace}) getAttrByNamespace hostHasService resolveServicePort;
inherit (config.networking) hostName;
networkCfg = getAttrByNamespace config "${namespace}.services.networking";
networkServices = flattenHostServices networkCfg.network-services;
isEnabled = hostHasService networkCfg.network-services hostName "sonarr";
port = getServicePort networkServices "sonarr" 8989;
port = resolveServicePort networkCfg.network-services "sonarr" 8989;
in {
config = mkIf isEnabled {
services.sonarr = {

View file

@ -5,15 +5,14 @@
...
}: let
inherit (lib) mkIf mkForce;
inherit (lib.${namespace}) getAttrByNamespace hostHasService flattenHostServices getServicePort;
inherit (lib.${namespace}) getAttrByNamespace hostHasService resolveServicePort;
inherit (config.users) users;
inherit (config.networking) hostName;
networkCfg = getAttrByNamespace config "${namespace}.services.networking";
networkServices = flattenHostServices networkCfg.network-services;
isEnabled = hostHasService networkCfg.network-services hostName "monitor";
port = getServicePort networkServices "monitor" 5200;
port = resolveServicePort networkCfg.network-services "monitor" 5200;
in {
config = mkIf isEnabled {
services.uptime-kuma = {

View file

@ -6,17 +6,16 @@
pkgs,
...
}: let
inherit (lib) mkIf filterAttrs attrNames head elem;
inherit (lib.${namespace}) getAttrByNamespace readJsonOrEmpty getIn resolveHostIP hostHasService flattenHostServices getServicePort;
inherit (lib) mkIf;
inherit (lib.${namespace}) getAttrByNamespace readJsonOrEmpty getIn resolveDatabaseHost resolveDatabaseIP hostHasService resolveServicePort;
inherit (config.networking) hostName;
pgCfg = getAttrByNamespace config "${namespace}.services.storage.postgresql";
networkCfg = getAttrByNamespace config "${namespace}.services.networking";
networkServices = flattenHostServices networkCfg.network-services;
isEnabled = hostHasService networkCfg.network-services hostName "vault";
port = getServicePort networkServices "vault" 5400;
port = resolveServicePort networkCfg.network-services "vault" 5400;
in {
config = mkIf isEnabled {
services.vaultwarden = {
@ -34,12 +33,7 @@ in {
DATABASE_URL = let
secrets = readJsonOrEmpty "${inputs.self}/secrets/crypt/secrets.json";
ip =
pgCfg.databases
|> filterAttrs (host: dbs: elem "vaultwarden" dbs)
|> attrNames
|> head
|> resolveHostIP networkCfg.devices;
ip = resolveDatabaseIP networkCfg.devices pgCfg.databases "vaultwarden";
in ''postgresql://vaultwarden:${getIn "postgresql.vaultwarden.password" secrets}@${ip}:5600/vaultwarden'';
LOG_LEVEL = "Info";
@ -55,11 +49,7 @@ in {
networking.firewall.allowedTCPPorts = [port];
systemd.services.vaultwarden = let
dbHost =
pgCfg.databases
|> filterAttrs (host: dbs: elem "vaultwarden" dbs)
|> attrNames
|> head;
dbHost = resolveDatabaseHost pgCfg.databases "vaultwarden";
in
mkIf (dbHost == config.networking.hostName) {
after = ["postgresql.service" "pgbouncer.service"];

View file

@ -6,7 +6,7 @@
...
}: let
inherit (lib) mkIf mkOption mkEnableOption types mapAttrs' mkMerge filterAttrs listToAttrs;
inherit (lib.${namespace}) getAttrByNamespace mkOptionsWithNamespace resolveHostIP hostHasService flattenHostServices getServicePort;
inherit (lib.${namespace}) getAttrByNamespace mkOptionsWithNamespace resolveHostIP hostHasService flattenHostServices resolveServicePort;
inherit (config.networking) hostName;
base = "${namespace}.services.ci.woodpecker";
@ -19,7 +19,7 @@
woodpeckerHost = networkServicesFlat.woodpecker.host;
isEnabled = hostHasService networkServices hostName "woodpecker";
port = getServicePort networkServicesFlat "woodpecker" 5301;
port = resolveServicePort networkServices "woodpecker" 5301;
gprcPort = port + 1;
in {
options = with types;

View file

@ -6,14 +6,14 @@
...
}: let
inherit (lib) mkIf mapAttrsToList listToAttrs filterAttrs flatten;
inherit (lib.${namespace}) getAttrByNamespace resolveHostIP flattenHostServices hostHasService getServicePort;
inherit (lib.${namespace}) getAttrByNamespace resolveHostIP flattenHostServices hostHasService resolveServicePort;
inherit (config.networking) hostName;
networkCfg = getAttrByNamespace config "${namespace}.services.networking";
networkServices = flattenHostServices networkCfg.network-services;
isEnabled = hostHasService networkCfg.network-services hostName "blocky";
port = getServicePort networkServices "blocky" 53;
port = resolveServicePort networkCfg.network-services "blocky" 53;
in {
config = mkIf isEnabled {
services.blocky = {

View file

@ -5,11 +5,10 @@
...
}: let
inherit (lib) types mkOption optional optionalString concatStringsSep;
inherit (lib.${namespace}) getAttrByNamespace mkOptionsWithNamespace resolveHostIP flattenHostServices getServiceHost;
inherit (lib.${namespace}) getAttrByNamespace mkOptionsWithNamespace resolveHostIP resolveServiceHost;
base = "${namespace}.services.networking";
cfg = getAttrByNamespace config base;
networkServices = flattenHostServices cfg.network-services;
in {
options = with types;
mkOptionsWithNamespace base {
@ -68,8 +67,8 @@ in {
enable = true;
extraConfig = let
unboundIP =
if networkServices ? unbound
then resolveHostIP cfg.devices (getServiceHost networkServices "unbound")
if cfg.network-services ? unbound
then resolveHostIP cfg.devices (resolveServiceHost cfg.network-services "unbound")
else null;
allDns = optional (unboundIP != null) unboundIP ++ ["1.1.1.1" "8.8.8.8" "100.100.100.100"];
in ''

View file

@ -5,14 +5,13 @@
...
}: let
inherit (lib) mkIf;
inherit (lib.${namespace}) getAttrByNamespace hostHasService flattenHostServices getServicePort;
inherit (lib.${namespace}) getAttrByNamespace hostHasService resolveServicePort;
inherit (config.networking) hostName;
networkCfg = getAttrByNamespace config "${namespace}.services.networking";
networkServices = flattenHostServices networkCfg.network-services;
isEnabled = hostHasService networkCfg.network-services hostName "unbound";
port = getServicePort networkServices "unbound" 54;
port = resolveServicePort networkCfg.network-services "unbound" 54;
in {
config = mkIf isEnabled {
services.unbound = {