summary refs log tree commit diff
diff options
context:
space:
mode:
authorLucas Savva <lucas@m1cr0man.com>2021-12-04 19:01:18 +0000
committerLucas Savva <lucas@m1cr0man.com>2021-12-26 16:49:57 +0000
commit41fb8d71ab5d92118eec5f056d3ce7e8f370a652 (patch)
treec8299c00c480167274f527e5a224b8270069b3bf
parent8d01b0862d3d52d72539cff65a405c09d864f82f (diff)
downloadnixpkgs-41fb8d71ab5d92118eec5f056d3ce7e8f370a652.tar
nixpkgs-41fb8d71ab5d92118eec5f056d3ce7e8f370a652.tar.gz
nixpkgs-41fb8d71ab5d92118eec5f056d3ce7e8f370a652.tar.bz2
nixpkgs-41fb8d71ab5d92118eec5f056d3ce7e8f370a652.tar.lz
nixpkgs-41fb8d71ab5d92118eec5f056d3ce7e8f370a652.tar.xz
nixpkgs-41fb8d71ab5d92118eec5f056d3ce7e8f370a652.tar.zst
nixpkgs-41fb8d71ab5d92118eec5f056d3ce7e8f370a652.zip
nixos/acme: Add useRoot option
-rw-r--r--nixos/modules/security/acme.nix23
-rw-r--r--nixos/tests/acme.nix13
2 files changed, 31 insertions, 5 deletions
diff --git a/nixos/modules/security/acme.nix b/nixos/modules/security/acme.nix
index 1b116482cae..57e83a4a27b 100644
--- a/nixos/modules/security/acme.nix
+++ b/nixos/modules/security/acme.nix
@@ -3,6 +3,7 @@ with lib;
 let
   cfg = config.security.acme;
   opt = options.security.acme;
+  user = if cfg.useRoot then "root" else "acme";
 
   # Used to calculate timer accuracy for coalescing
   numCerts = length (builtins.attrNames cfg.certs);
@@ -23,7 +24,7 @@ let
   # security.acme.certs.<cert>.group on some of the services.
   commonServiceConfig = {
     Type = "oneshot";
-    User = "acme";
+    User = user;
     Group = mkDefault "acme";
     UMask = 0022;
     StateDirectoryMode = 750;
@@ -101,12 +102,12 @@ let
   # is configurable on a per-cert basis.
   userMigrationService = let
     script = with builtins; ''
-      chown -R acme .lego/accounts
+      chown -R ${user} .lego/accounts
     '' + (concatStringsSep "\n" (mapAttrsToList (cert: data: ''
       for fixpath in ${escapeShellArg cert} .lego/${escapeShellArg cert}; do
         if [ -d "$fixpath" ]; then
           chmod -R u=rwX,g=rX,o= "$fixpath"
-          chown -R acme:${data.group} "$fixpath"
+          chown -R ${user}:${data.group} "$fixpath"
         fi
       done
     '') certConfigs));
@@ -268,7 +269,7 @@ let
         cat key.pem fullchain.pem > full.pem
 
         # Group might change between runs, re-apply it
-        chown 'acme:${data.group}' *
+        chown '${user}:${data.group}' *
 
         # Default permissions make the files unreadable by group + anon
         # Need to be readable by group
@@ -403,7 +404,7 @@ let
         mv domainhash.txt certificates/
 
         # Group might change between runs, re-apply it
-        chown 'acme:${data.group}' certificates/*
+        chown '${user}:${data.group}' certificates/*
 
         # Copy all certs to the "real" certs directory
         if ! cmp -s 'certificates/${keyName}.crt' out/fullchain.pem; then
@@ -723,6 +724,18 @@ in {
         '';
       };
 
+      useRoot = mkOption {
+        type = types.bool;
+        default = false;
+        description = ''
+          Whether to use the root user when generating certs. This is not recommended
+          for security + compatiblity reasons. If a service requires root owned certificates
+          consider following the guide on "Using ACME with services demanding root
+          owned certificates" in the NixOS manual, and only using this as a fallback
+          or for testing.
+        '';
+      };
+
       defaults = mkOption {
         type = types.submodule { options = inheritableOpts {}; };
         description = ''
diff --git a/nixos/tests/acme.nix b/nixos/tests/acme.nix
index 549fa9e64ee..a4ed8fa67bf 100644
--- a/nixos/tests/acme.nix
+++ b/nixos/tests/acme.nix
@@ -232,6 +232,13 @@ in {
           }
         ];
 
+        use-root.configuration = { ... }: lib.mkMerge [
+          webserverBasicConfig
+          {
+            security.acme.useRoot = true;
+          }
+        ];
+
       # Test compatibility with Nginx
       } // (mkServerConfigs {
           server = "nginx";
@@ -450,6 +457,12 @@ in {
           webserver.wait_for_unit("nginx.service")
           check_connection(client, "slow.example.com")
 
+      with subtest("Can set useRoot to true and still use certs normally"):
+          switch_to(webserver, "use-root")
+          webserver.wait_for_unit("nginx.service")
+          webserver.succeed("test \"$(stat -c '%U' /var/lib/acme/* | uniq)\" = \"root\"")
+          check_connection(client, "a.example.com")
+
       domains = ["http", "dns", "wildcard"]
       for server, logsrc in [
           ("nginx", "journalctl -n 30 -u nginx.service"),