ssl: make self-signed certs idempotent
This commit is contained in:
parent
9d7e93b70d
commit
9bfd954c1f
2 changed files with 109 additions and 32 deletions
|
|
@ -399,21 +399,25 @@ in
|
||||||
crl_signing_key
|
crl_signing_key
|
||||||
EOF
|
EOF
|
||||||
|
|
||||||
mkdir -p "$(dirname -- "${caCfg.paths.key}")"
|
keyfile="${caCfg.paths.key}"
|
||||||
${pkgs.gnutls}/bin/certtool \
|
keydir="$(dirname -- "$keyfile")"
|
||||||
--generate-privkey \
|
mkdir -p "$keydir"
|
||||||
--key-type rsa \
|
[ -f "$keyfile" ] || ${pkgs.gnutls}/bin/certtool \
|
||||||
--sec-param High \
|
--generate-privkey \
|
||||||
--outfile ${caCfg.paths.key}
|
--key-type rsa \
|
||||||
chmod 666 ${caCfg.paths.key}
|
--sec-param High \
|
||||||
|
--outfile "$keyfile"
|
||||||
|
chmod 666 "$keyfile"
|
||||||
|
|
||||||
mkdir -p "$(dirname -- "${caCfg.paths.cert}")"
|
certfile="${caCfg.paths.cert}"
|
||||||
${pkgs.gnutls}/bin/certtool \
|
certdir="$(dirname -- "$certfile")"
|
||||||
--generate-self-signed \
|
mkdir -p "$certdir"
|
||||||
--load-privkey ${caCfg.paths.key} \
|
[ -f "$certfile" ] || ${pkgs.gnutls}/bin/certtool \
|
||||||
--template ca.template \
|
--generate-self-signed \
|
||||||
--outfile ${caCfg.paths.cert}
|
--load-privkey "$keyfile" \
|
||||||
chmod 666 ${caCfg.paths.cert}
|
--template ca.template \
|
||||||
|
--outfile "$certfile"
|
||||||
|
chmod 666 "$certfile"
|
||||||
'';
|
'';
|
||||||
}
|
}
|
||||||
) cfg.cas.selfsigned;
|
) cfg.cas.selfsigned;
|
||||||
|
|
@ -427,6 +431,8 @@ in
|
||||||
script = ''
|
script = ''
|
||||||
mkdir -p /etc/ssl/certs
|
mkdir -p /etc/ssl/certs
|
||||||
|
|
||||||
|
# This file is automatically idempotent since the source files used are idempotent.
|
||||||
|
|
||||||
rm -f /etc/ssl/certs/ca-bundle.crt
|
rm -f /etc/ssl/certs/ca-bundle.crt
|
||||||
rm -f /etc/ssl/certs/ca-certificates.crt
|
rm -f /etc/ssl/certs/ca-certificates.crt
|
||||||
|
|
||||||
|
|
@ -456,8 +462,8 @@ in
|
||||||
let
|
let
|
||||||
extraDnsNames = lib.strings.concatStringsSep "\n" (map (n: "dns_name = ${n}") certCfg.extraDomains);
|
extraDnsNames = lib.strings.concatStringsSep "\n" (map (n: "dns_name = ${n}") certCfg.extraDomains);
|
||||||
chmod = cert: ''
|
chmod = cert: ''
|
||||||
chown root:${certCfg.group} ${cert}
|
chown root:${certCfg.group} "${cert}"
|
||||||
chmod 640 ${cert}
|
chmod 640 "${cert}"
|
||||||
'';
|
'';
|
||||||
in
|
in
|
||||||
''
|
''
|
||||||
|
|
@ -474,23 +480,27 @@ in
|
||||||
signing_key
|
signing_key
|
||||||
EOF
|
EOF
|
||||||
|
|
||||||
mkdir -p "$(dirname -- "${certCfg.paths.key}")"
|
keyfile="${certCfg.paths.key}"
|
||||||
${pkgs.gnutls}/bin/certtool \
|
keydir="$(dirname -- "$keyfile")"
|
||||||
--generate-privkey \
|
mkdir -p "$keydir"
|
||||||
--key-type rsa \
|
[ -f "$keyfile" ] || ${pkgs.gnutls}/bin/certtool \
|
||||||
--sec-param High \
|
--generate-privkey \
|
||||||
--outfile ${certCfg.paths.key}
|
--key-type rsa \
|
||||||
${chmod certCfg.paths.key}
|
--sec-param High \
|
||||||
|
--outfile "$keyfile"
|
||||||
|
${chmod "$keyfile"}
|
||||||
|
|
||||||
mkdir -p "$(dirname -- "${certCfg.paths.cert}")"
|
certfile="${certCfg.paths.cert}"
|
||||||
${pkgs.gnutls}/bin/certtool \
|
certdir="$(dirname -- "$certfile")"
|
||||||
--generate-certificate \
|
mkdir -p "$certdir"
|
||||||
--load-privkey ${certCfg.paths.key} \
|
[ -f "$certfile" ] || ${pkgs.gnutls}/bin/certtool \
|
||||||
--load-ca-privkey ${certCfg.ca.paths.key} \
|
--generate-certificate \
|
||||||
--load-ca-certificate ${certCfg.ca.paths.cert} \
|
--load-privkey "$keyfile" \
|
||||||
--template server.template \
|
--load-ca-privkey "${certCfg.ca.paths.key}" \
|
||||||
--outfile ${certCfg.paths.cert}
|
--load-ca-certificate "${certCfg.ca.paths.cert}" \
|
||||||
${chmod certCfg.paths.cert}
|
--template server.template \
|
||||||
|
--outfile "$certfile"
|
||||||
|
${chmod "$certfile"}
|
||||||
'';
|
'';
|
||||||
|
|
||||||
postStart = lib.optionalString (certCfg.reloadServices != [ ]) ''
|
postStart = lib.optionalString (certCfg.reloadServices != [ ]) ''
|
||||||
|
|
|
||||||
|
|
@ -172,6 +172,32 @@ in
|
||||||
if perm != want_perm:
|
if perm != want_perm:
|
||||||
raise Exception('Unexpected perm for {}: wanted "{}", got: "{}"'.format(path, want_perm, perm))
|
raise Exception('Unexpected perm for {}: wanted "{}", got: "{}"'.format(path, want_perm, perm))
|
||||||
|
|
||||||
|
with subtest("Certificates content seem correct"):
|
||||||
|
myca_key = server.succeed("cat {}".format("${myca.paths.key}")).strip();
|
||||||
|
myca_cert = server.succeed("cat {}".format("${myca.paths.cert}")).strip();
|
||||||
|
cert1_key = server.succeed("cat {}".format("${cert1.paths.key}")).strip();
|
||||||
|
cert1_cert = server.succeed("cat {}".format("${cert1.paths.cert}")).strip();
|
||||||
|
cert2_key = server.succeed("cat {}".format("${cert2.paths.key}")).strip();
|
||||||
|
cert2_cert = server.succeed("cat {}".format("${cert2.paths.cert}")).strip();
|
||||||
|
ca_bundle = server.succeed("cat /etc/ssl/certs/ca-bundle.crt").strip();
|
||||||
|
|
||||||
|
if myca_cert == "":
|
||||||
|
raise Exception("CA cert was empty")
|
||||||
|
if cert1_key == "":
|
||||||
|
raise Exception("Cert1 key was empty")
|
||||||
|
if cert1_cert == "":
|
||||||
|
raise Exception("Cert1 cert was empty")
|
||||||
|
if cert2_key == "":
|
||||||
|
raise Exception("Cert2 key was empty")
|
||||||
|
if cert2_cert == "":
|
||||||
|
raise Exception("Cert2 cert was empty")
|
||||||
|
if cert1_key == cert2_key:
|
||||||
|
raise Exception("Cert1 key and cert2 key are the same")
|
||||||
|
if cert1_cert == cert2_cert:
|
||||||
|
raise Exception("Cert1 cert and cert2 cert are the same")
|
||||||
|
if ca_bundle == "":
|
||||||
|
raise Exception("CA bundle was empty")
|
||||||
|
|
||||||
with subtest("Certificate is trusted in curl"):
|
with subtest("Certificate is trusted in curl"):
|
||||||
resp = server.succeed("curl --fail-with-body -v https://example.com")
|
resp = server.succeed("curl --fail-with-body -v https://example.com")
|
||||||
if resp != "Top domain":
|
if resp != "Top domain":
|
||||||
|
|
@ -204,11 +230,52 @@ in
|
||||||
assert_perm("${cert2.paths.key}", "640")
|
assert_perm("${cert2.paths.key}", "640")
|
||||||
assert_perm("${cert2.paths.cert}", "640")
|
assert_perm("${cert2.paths.cert}", "640")
|
||||||
|
|
||||||
|
with subtest("Certificates content seem correct"):
|
||||||
|
if cert1_key == "":
|
||||||
|
raise Exception("Cert1 key was empty")
|
||||||
|
if cert1_cert == "":
|
||||||
|
raise Exception("Cert1 cert was empty")
|
||||||
|
if cert2_key == "":
|
||||||
|
raise Exception("Cert2 key was empty")
|
||||||
|
if cert2_cert == "":
|
||||||
|
raise Exception("Cert2 cert was empty")
|
||||||
|
if cert1_key == cert2_key:
|
||||||
|
raise Exception("Cert1 key and cert2 key are the same")
|
||||||
|
if cert1_cert == cert2_cert:
|
||||||
|
raise Exception("Cert1 cert and cert2 cert are the same")
|
||||||
|
|
||||||
with subtest("Fail if certificate is not in CA bundle"):
|
with subtest("Fail if certificate is not in CA bundle"):
|
||||||
server.fail("curl --cacert /etc/static/ssl/certs/ca-bundle.crt --fail-with-body -v https://example.com")
|
server.fail("curl --cacert /etc/static/ssl/certs/ca-bundle.crt --fail-with-body -v https://example.com")
|
||||||
server.fail("curl --cacert /etc/static/ssl/certs/ca-bundle.crt --fail-with-body -v https://subdomain.example.com")
|
server.fail("curl --cacert /etc/static/ssl/certs/ca-bundle.crt --fail-with-body -v https://subdomain.example.com")
|
||||||
server.fail("curl --cacert /etc/static/ssl/certs/ca-certificates.crt --fail-with-body -v https://example.com")
|
server.fail("curl --cacert /etc/static/ssl/certs/ca-certificates.crt --fail-with-body -v https://example.com")
|
||||||
server.fail("curl --cacert /etc/static/ssl/certs/ca-certificates.crt --fail-with-body -v https://subdomain.example.com")
|
server.fail("curl --cacert /etc/static/ssl/certs/ca-certificates.crt --fail-with-body -v https://subdomain.example.com")
|
||||||
|
|
||||||
|
with subtest("Idempotency"):
|
||||||
|
server.succeed("systemctl restart shb-certs-ca-myca")
|
||||||
|
server.succeed("systemctl restart shb-certs-cert-selfsigned-cert1")
|
||||||
|
server.succeed("systemctl restart shb-certs-cert-selfsigned-cert2")
|
||||||
|
|
||||||
|
new_myca_key = server.succeed("cat {}".format("${myca.paths.key}")).strip();
|
||||||
|
new_myca_cert = server.succeed("cat {}".format("${myca.paths.cert}")).strip();
|
||||||
|
new_cert1_key = server.succeed("cat {}".format("${cert1.paths.key}")).strip();
|
||||||
|
new_cert1_cert = server.succeed("cat {}".format("${cert1.paths.cert}")).strip();
|
||||||
|
new_cert2_key = server.succeed("cat {}".format("${cert2.paths.key}")).strip();
|
||||||
|
new_cert2_cert = server.succeed("cat {}".format("${cert2.paths.cert}")).strip();
|
||||||
|
new_ca_bundle = server.succeed("cat /etc/ssl/certs/ca-bundle.crt").strip();
|
||||||
|
if new_myca_key != myca_key:
|
||||||
|
raise Exception("New CA key is different from old one.")
|
||||||
|
if new_myca_cert != myca_cert:
|
||||||
|
raise Exception("New CA cert is different from old one.")
|
||||||
|
if new_cert1_key != cert1_key:
|
||||||
|
raise Exception("New Cert1 key is different from old one.")
|
||||||
|
if new_cert1_cert != cert1_cert:
|
||||||
|
raise Exception("New Cert1 cert is different from old one.")
|
||||||
|
if new_cert2_key != cert2_key:
|
||||||
|
raise Exception("New Cert2 key is different from old one.")
|
||||||
|
if new_cert2_cert != cert2_cert:
|
||||||
|
raise Exception("New Cert2 cert is different from old one.")
|
||||||
|
if new_ca_bundle != ca_bundle:
|
||||||
|
raise Exception("New CA bundle is different from old one.")
|
||||||
'';
|
'';
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue