Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

acme: Add csr option #376334

Open
wants to merge 1 commit into
base: master
Choose a base branch
from
Open
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
29 changes: 24 additions & 5 deletions nixos/modules/security/acme/default.nix
Original file line number Diff line number Diff line change
Expand Up @@ -227,12 +227,11 @@ let
commonOpts = [
"--accept-tos" # Checking the option is covered by the assertions
"--path" "."
"-d" data.domain
"--email" data.email
"--key-type" data.keyType
] ++ protocolOpts
++ lib.optionals (acmeServer != null) [ "--server" acmeServer ]
++ lib.concatMap (name: [ "-d" name ]) extraDomains
++ lib.optionals (data.csr != null) [ "--csr" data.csr ]
++ lib.optionals (data.csr == null) [ "--key-type" data.keyType "-d" data.domain ] ++ lib.concatMap (name: [ "-d" name ]) extraDomains
++ data.extraLegoFlags;

# Although --must-staple is common to both modes, it is not declared as a
Expand All @@ -258,6 +257,8 @@ let
(builtins.map
(certAttrs: certAttrs.webroot)
(lib.attrValues config.security.acme.certs)));

certificateKey = if data.csrKey != null then "${data.csrKey}" else "certificates/${keyName}.key";
in {
inherit accountHash cert selfsignedDeps;

Expand Down Expand Up @@ -440,7 +441,7 @@ let
# Check if we can renew.
# We can only renew if the list of domains has not changed.
# We also need an account key. Avoids #190493
if cmp -s domainhash.txt certificates/domainhash.txt && [ -e 'certificates/${keyName}.key' ] && [ -e 'certificates/${keyName}.crt' ] && [ -n "$(find accounts -name '${data.email}.key')" ]; then
if cmp -s domainhash.txt certificates/domainhash.txt && [ -e ${certificateKey} ] && [ -e 'certificates/${keyName}.crt' ] && [ -n "$(find accounts -name '${data.email}.key')" ]; then

# Even if a cert is not expired, it may be revoked by the CA.
# Try to renew, and silently fail if the cert is not expired.
Expand Down Expand Up @@ -475,7 +476,7 @@ let
touch out/renewed
echo Installing new certificate
cp -vp 'certificates/${keyName}.crt' out/fullchain.pem
cp -vp 'certificates/${keyName}.key' out/key.pem
cp -vp ${certificateKey} out/key.pem
cp -vp 'certificates/${keyName}.issuer.crt' out/chain.pem
ln -sf fullchain.pem out/cert.pem
cat out/key.pem out/fullchain.pem > out/full.pem
Expand Down Expand Up @@ -732,6 +733,18 @@ let
description = "Domain to fetch certificate for (defaults to the entry name).";
};

csr = lib.mkOption {
type = lib.types.nullOr lib.types.str;
default = null;
description = "Path to a Certificate Signing Request to use for fetching the certificate.";
};

csrKey = lib.mkOption {
type = lib.types.nullOr lib.types.str;
default = null;
description = "Path to a the Key of the matching Certificate Signing Request.";
};

extraDomainNames = lib.mkOption {
type = lib.types.listOf lib.types.str;
default = [];
Expand Down Expand Up @@ -963,6 +976,12 @@ in {
used for variables suffixed by "_FILE".
'';
}
{
assertion = lib.all (certOpts: (certOpts.csr == null && certOpts.csrKey == null) || (certOpts.csr != null && certOpts.csrKey != null) ) certs;
message = ''
Either both `security.acme.certs.${cert}.csr` and `security.acme.certs.${cert}.csrKey` need to be specified, or none.
'';
}
]) cfg.certs));

users.users.acme = {
Expand Down