From 4a2a0b86d64b3f8caa056d7f170f01d981d42412 Mon Sep 17 00:00:00 2001 From: Christopher Bacher Date: Sat, 3 Dec 2022 23:07:47 +0100 Subject: [PATCH] modules(pihole-container): simplify exposing PiHole ports Initially the PiHole module was supposed to provide an option to expose rootless PiHole on privileged ports s.t. the user does not have to find out/decide how to do it herself. However, it seems to be out-of-scope for flake which should provide a rootless PiHole container. Further, any decision taken on how to achieve this could limit the users choices for other system configuration options. Inestead options for making PiHole available on priviledged ports should be described in the Readme and maybe in example configurations. --- lib/options.nix | 40 ------------------ modules/pihole-container.factory.nix | 63 ++++++++++++++++++++++------ 2 files changed, 50 insertions(+), 53 deletions(-) delete mode 100644 lib/options.nix diff --git a/lib/options.nix b/lib/options.nix deleted file mode 100644 index f52be68..0000000 --- a/lib/options.nix +++ /dev/null @@ -1,40 +0,0 @@ -nixpkgsLib: with nixpkgsLib; { - mkContainerEnvOption = { envVar, ... }@optionAttrs: - (mkOption (removeAttrs optionAttrs [ "envVar" ])) - // { inherit envVar; }; - - mkHostPortsOption = { service, publicDefaultPort }: { - hostInternalPort = mkOption { - type = types.port; - description = '' - The internal port on the host on which the ${service} port of the pihole container should be exposed. - Only needs to be specified if he container port should be exposed - or if the port-forwarding for this service is enabled. - - As the pihole container is running rootless this cannot be a privileged port (<1024). - ''; - }; - - hostPublicPort = mkOption { - type = types.port; - description = '' - The public port on the host on which the ${service} port of the pihole container should be forwared to. - - This option can be used to together with the according `forwardPublicToInternal` to expose a pihole subservice on a privileged port, - e.g., if you want to expose the DNS service on port 53. - ''; - default = publicDefaultPort; - }; - - forwardPublicToInternal = mkOption { - type = types.bool; - description = '' - Enable port-forwarding between the public & the internal port of the host. - This effectively makes pihole's ${service} port available on the network to which the host is connected to. - - Use this option together with the according `hostPublicPort` to expose a pihole subservice on a privileged port. - ''; - default = false; - }; - }; -} diff --git a/modules/pihole-container.factory.nix b/modules/pihole-container.factory.nix index 91ec40a..6c54b9b 100644 --- a/modules/pihole-container.factory.nix +++ b/modules/pihole-container.factory.nix @@ -1,6 +1,9 @@ { piholeFlake, lingerFlake }: { config, pkgs, lib, ... }: with lib; with builtins; let inherit (import ../lib/util.nix) extractContainerEnvVars extractContainerFTLEnvVars; - inherit (import ../lib/options.nix lib) mkContainerEnvOption mkHostPortsOption; + + mkContainerEnvOption = { envVar, ... }@optionAttrs: + (mkOption (removeAttrs optionAttrs [ "envVar" ])) + // { inherit envVar; }; cfg = config.services.pihole; hostUserCfg = config.users.users.${cfg.hostConfig.user}; @@ -59,19 +62,40 @@ in rec { example = "/home/pihole-user/pihole-volumes"; }; - dns = mkHostPortsOption { - service = "DNS"; - publicDefaultPort = 53; + dnsPort = mkOption { + type = with types; nullOr (either port str); + description = '' + THe port on which PiHole's DNS service shoud be exposed. + Either pass a port number as integer or a string in the format `ip:port` (see [Docker docs](https://docs.docker.com/engine/reference/run/#expose-incoming-ports) for details). + + If this option is not specified the DNS service will not be exposed on the host. + Remember that if the container is running rootless exposing on a privileged port is not possible. + ''; + default = null; }; - dhcp = mkHostPortsOption { - service = "DHCP"; - publicDefaultPort = 67; + dhcpPort = mkOption { + type = with types; nullOr (either port str); + description = '' + THe port on which PiHole's DHCP service shoud be exposed. + Either pass a port number as integer or a string in the format `ip:port` (see [Docker docs](https://docs.docker.com/engine/reference/run/#expose-incoming-ports) for details). + + If this option is not specified the DHCP service will not be exposed on the host. + Remember that if the container is running rootless exposing on a privileged port is not possible. + ''; + default = null; }; - web = mkHostPortsOption { - service = "Web"; - publicDefaultPort = 80; + webPort = mkOption { + type = with types; nullOr (either port str); + description = '' + THe port on which PiHole's web interface shoud be exposed. + Either pass a port number as integer or a string in the format `ip:port` (see [Docker docs](https://docs.docker.com/engine/reference/run/#expose-incoming-ports) for details). + + If this option is not specified the web interface will not be exposed on the host. + Remember that if the container is running rootless exposing on a privileged port is not possible. + ''; + default = null; }; suppressTmpDirWarning = mkOption { @@ -359,9 +383,22 @@ in rec { -v ${cfg.hostConfig.volumesPath}/etc-dnsmasq.d:/etc/dnsmasq.d \ '' else "" } \ - -p ${toString cfg.hostConfig.dns.hostInternalPort}:53/tcp \ - -p ${toString cfg.hostConfig.dns.hostInternalPort}:53/udp \ - -p ${toString cfg.hostConfig.web.hostInternalPort}:80/tcp \ + ${ + if !(isNull cfg.hostConfig.dnsPort) then '' + -p ${toString cfg.hostConfig.dnsPort}:53/tcp \ + -p ${toString cfg.hostConfig.dnsPort}:53/udp \ + '' else "" + } \ + ${ + if !(isNull cfg.hostConfig.dhcpPort) then '' + -p ${toString cfg.hostConfig.dhcpPort}:67/udp \ + '' else "" + } \ + ${ + if !(isNull cfg.hostConfig.webPort) then '' + -p ${toString cfg.hostConfig.webPort}:80/tcp \ + '' else "" + } \ ${ concatStringsSep " \\\n" (map (envVar: " -e '${envVar.name}=${toString envVar.value}'") (containerEnvVars ++ containerFTLEnvVars))