def setUp(self): self.tmpdir = tempfile.mkdtemp() self.client_cert = os.path.join(self.tmpdir, "client.pem") self.server_cert = os.path.join(self.tmpdir, "server.pem") some_serial_no = int(time.time()) utils.GenerateSelfSignedSslCert(self.server_cert, some_serial_no)
def testLegacy(self): cert1_filename = os.path.join(self.tmpdir, "cert1.pem") utils.GenerateSelfSignedSslCert(cert1_filename, 1, validity=1) cert1 = utils.ReadFile(cert1_filename) self.assert_(self._checkRsaPrivateKey(cert1)) self.assert_(self._checkCertificate(cert1))
def testSignedSslCertificate(self): server_cert_filename = os.path.join(self.tmpdir, "server.pem") utils.GenerateSelfSignedSslCert(server_cert_filename, 123456) client_hostname = "myhost.example.com" client_cert_filename = os.path.join(self.tmpdir, "client.pem") utils.GenerateSignedSslCert(client_cert_filename, 666, server_cert_filename, common_name=client_hostname) client_cert_pem = utils.ReadFile(client_cert_filename) self._checkRsaPrivateKey(client_cert_pem) self._checkCertificate(client_cert_pem) priv_key = OpenSSL.crypto.load_privatekey(OpenSSL.crypto.FILETYPE_PEM, client_cert_pem) client_cert = OpenSSL.crypto.load_certificate( OpenSSL.crypto.FILETYPE_PEM, client_cert_pem) self.assertTrue(self._checkKeyMatchesCert(priv_key, client_cert)) self.assertEqual(client_cert.get_issuer().CN, "ganeti.example.com") self.assertEqual(client_cert.get_subject().CN, client_hostname)
def GenerateClusterCrypto(new_cluster_cert, new_rapi_cert, new_spice_cert, new_confd_hmac_key, new_cds, new_client_cert, master_name, rapi_cert_pem=None, spice_cert_pem=None, spice_cacert_pem=None, cds=None, nodecert_file=pathutils.NODED_CERT_FILE, clientcert_file=pathutils.NODED_CLIENT_CERT_FILE, rapicert_file=pathutils.RAPI_CERT_FILE, spicecert_file=pathutils.SPICE_CERT_FILE, spicecacert_file=pathutils.SPICE_CACERT_FILE, hmackey_file=pathutils.CONFD_HMAC_KEY, cds_file=pathutils.CLUSTER_DOMAIN_SECRET_FILE): """Updates the cluster certificates, keys and secrets. @type new_cluster_cert: bool @param new_cluster_cert: Whether to generate a new cluster certificate @type new_rapi_cert: bool @param new_rapi_cert: Whether to generate a new RAPI certificate @type new_spice_cert: bool @param new_spice_cert: Whether to generate a new SPICE certificate @type new_confd_hmac_key: bool @param new_confd_hmac_key: Whether to generate a new HMAC key @type new_cds: bool @param new_cds: Whether to generate a new cluster domain secret @type new_client_cert: bool @param new_client_cert: Whether to generate a new client certificate @type master_name: string @param master_name: FQDN of the master node @type rapi_cert_pem: string @param rapi_cert_pem: New RAPI certificate in PEM format @type spice_cert_pem: string @param spice_cert_pem: New SPICE certificate in PEM format @type spice_cacert_pem: string @param spice_cacert_pem: Certificate of the CA that signed the SPICE certificate, in PEM format @type cds: string @param cds: New cluster domain secret @type nodecert_file: string @param nodecert_file: optional override of the node cert file path @type rapicert_file: string @param rapicert_file: optional override of the rapi cert file path @type spicecert_file: string @param spicecert_file: optional override of the spice cert file path @type spicecacert_file: string @param spicecacert_file: optional override of the spice CA cert file path @type hmackey_file: string @param hmackey_file: optional override of the hmac key file path """ # pylint: disable=R0913 # noded SSL certificate utils.GenerateNewSslCert( new_cluster_cert, nodecert_file, 1, "Generating new cluster certificate at %s" % nodecert_file) # If the cluster certificate was renewed, the client cert has to be # renewed and resigned. if new_cluster_cert or new_client_cert: utils.GenerateNewClientSslCert(clientcert_file, nodecert_file, master_name) # confd HMAC key if new_confd_hmac_key or not os.path.exists(hmackey_file): logging.debug("Writing new confd HMAC key to %s", hmackey_file) GenerateHmacKey(hmackey_file) if rapi_cert_pem: # Assume rapi_pem contains a valid PEM-formatted certificate and key logging.debug("Writing RAPI certificate at %s", rapicert_file) utils.WriteFile(rapicert_file, data=rapi_cert_pem, backup=True) else: utils.GenerateNewSslCert( new_rapi_cert, rapicert_file, 1, "Generating new RAPI certificate at %s" % rapicert_file) # SPICE spice_cert_exists = os.path.exists(spicecert_file) spice_cacert_exists = os.path.exists(spicecacert_file) if spice_cert_pem: # spice_cert_pem implies also spice_cacert_pem logging.debug("Writing SPICE certificate at %s", spicecert_file) utils.WriteFile(spicecert_file, data=spice_cert_pem, backup=True) logging.debug("Writing SPICE CA certificate at %s", spicecacert_file) utils.WriteFile(spicecacert_file, data=spice_cacert_pem, backup=True) elif new_spice_cert or not spice_cert_exists: if spice_cert_exists: utils.CreateBackup(spicecert_file) if spice_cacert_exists: utils.CreateBackup(spicecacert_file) logging.debug("Generating new self-signed SPICE certificate at %s", spicecert_file) (_, cert_pem) = utils.GenerateSelfSignedSslCert(spicecert_file, 1) # Self-signed certificate -> the public certificate is also the CA public # certificate logging.debug("Writing the public certificate to %s", spicecert_file) utils.io.WriteFile(spicecacert_file, mode=0400, data=cert_pem) # Cluster domain secret if cds: logging.debug("Writing cluster domain secret to %s", cds_file) utils.WriteFile(cds_file, data=cds, backup=True) elif new_cds or not os.path.exists(cds_file): logging.debug("Generating new cluster domain secret at %s", cds_file) GenerateHmacKey(cds_file)
def TestClusterRenewCrypto(): """gnt-cluster renew-crypto""" master = qa_config.GetMasterNode() # Conflicting options cmd = [ "gnt-cluster", "renew-crypto", "--force", "--new-cluster-certificate", "--new-confd-hmac-key" ] conflicting = [ ["--new-rapi-certificate", "--rapi-certificate=/dev/null"], ["--new-cluster-domain-secret", "--cluster-domain-secret=/dev/null"], ] for i in conflicting: AssertCommand(cmd + i, fail=True) # Invalid RAPI certificate cmd = [ "gnt-cluster", "renew-crypto", "--force", "--rapi-certificate=/dev/null" ] AssertCommand(cmd, fail=True) rapi_cert_backup = qa_utils.BackupFile(master.primary, pathutils.RAPI_CERT_FILE) try: # Custom RAPI certificate fh = tempfile.NamedTemporaryFile() # Ensure certificate doesn't cause "gnt-cluster verify" to complain validity = constants.SSL_CERT_EXPIRATION_WARN * 3 utils.GenerateSelfSignedSslCert(fh.name, validity=validity) tmpcert = qa_utils.UploadFile(master.primary, fh.name) try: AssertCommand([ "gnt-cluster", "renew-crypto", "--force", "--rapi-certificate=%s" % tmpcert ]) finally: AssertCommand(["rm", "-f", tmpcert]) # Custom cluster domain secret cds_fh = tempfile.NamedTemporaryFile() cds_fh.write(utils.GenerateSecret()) cds_fh.write("\n") cds_fh.flush() tmpcds = qa_utils.UploadFile(master.primary, cds_fh.name) try: AssertCommand([ "gnt-cluster", "renew-crypto", "--force", "--cluster-domain-secret=%s" % tmpcds ]) finally: AssertCommand(["rm", "-f", tmpcds]) # Normal case AssertCommand([ "gnt-cluster", "renew-crypto", "--force", "--new-cluster-certificate", "--new-confd-hmac-key", "--new-rapi-certificate", "--new-cluster-domain-secret" ]) # Restore RAPI certificate AssertCommand([ "gnt-cluster", "renew-crypto", "--force", "--rapi-certificate=%s" % rapi_cert_backup ]) finally: AssertCommand(["rm", "-f", rapi_cert_backup])