Beispiel #1
0
 def create_encryption_at_rest_file(self, extra_vars, ssh_options):
     node_ip = ssh_options["ssh_host"]
     encryption_key_path = extra_vars["encryption_key_file"]  # Source file path
     key_node_dir = extra_vars["encryption_key_dir"]  # Target file path
     with open(encryption_key_path, "r") as f:
         encryption_key = f.read()
     key_file = os.path.basename(encryption_key_path)
     common_path = os.path.join(self.CERTS_TEMP_DIR, node_ip)
     try:
         os.makedirs(common_path)
     except OSError as exc:  # Guard against race condition
         if exc.errno != errno.EEXIST:
             raise YBOpsRuntimeError(common_path + " could not be  be created")
     # Write encryption-at-rest key to file
     with open(os.path.join(common_path, key_file), 'wb') as key_out:
         key_out.write(encryption_key)
     # Copy files over to node
     remote_shell = RemoteShell(ssh_options)
     remote_shell.run_command('mkdir -p ' + key_node_dir)
     remote_shell.put_file(os.path.join(common_path, key_file),
                           os.path.join(key_node_dir, key_file))
     try:
         shutil.rmtree(common_path)
     except OSError as e:
         raise YBOpsRuntimeError("Error: %s - %s." % (e.filename, e.strerror))
Beispiel #2
0
 def create_encryption_at_rest_file(self, extra_vars, ssh_options):
     encryption_key_path = extra_vars["encryption_key_file"]  # Source file path
     key_node_dir = extra_vars["encryption_key_dir"]  # Target file path
     with open(encryption_key_path, "r") as f:
         encryption_key = f.read()
     key_file = os.path.basename(encryption_key_path)
     with tempfile.TemporaryDirectory() as common_path:
         # Write encryption-at-rest key to file
         with open(os.path.join(common_path, key_file), 'wb') as key_out:
             key_out.write(encryption_key)
         # Copy files over to node
         remote_shell = RemoteShell(ssh_options)
         remote_shell.run_command('mkdir -p ' + key_node_dir)
         remote_shell.put_file(os.path.join(common_path, key_file),
                               os.path.join(key_node_dir, key_file))
Beispiel #3
0
    def append_new_root_cert(self, ssh_options, root_cert_path,
                             certs_location, certs_dir):
        remote_shell = RemoteShell(ssh_options)
        yb_root_cert_path = os.path.join(certs_dir, self.ROOT_CERT_NAME)
        yb_root_cert_new_path = os.path.join(certs_dir, self.ROOT_CERT_NEW_NAME)

        # Give write permissions to cert directory
        remote_shell.run_command('chmod -f 666 {}/* || true'.format(certs_dir))
        # Copy the new root cert to ca_new.crt
        if certs_location == self.CERT_LOCATION_NODE:
            remote_shell.run_command("cp '{}' '{}'".format(root_cert_path,
                                                           yb_root_cert_new_path))
        if certs_location == self.CERT_LOCATION_PLATFORM:
            remote_shell.put_file(root_cert_path, yb_root_cert_new_path)
        # Append new cert content to ca.crt
        remote_shell.run_command(
            "cat '{}' >> '{}'".format(yb_root_cert_new_path, yb_root_cert_path))
        # Reset the write permissions
        remote_shell.run_command('chmod 400 {}/*'.format(certs_dir))
Beispiel #4
0
    def copy_client_certs(self, ssh_options, root_cert_path, client_cert_path,
                          client_key_path, certs_location):
        remote_shell = RemoteShell(ssh_options)
        yb_root_cert_path = os.path.join(self.YSQLSH_CERT_DIR,
                                         self.CLIENT_ROOT_NAME)
        yb_client_cert_path = os.path.join(self.YSQLSH_CERT_DIR,
                                           self.CLIENT_CERT_NAME)
        yb_client_key_path = os.path.join(self.YSQLSH_CERT_DIR,
                                          self.CLIENT_KEY_NAME)

        logging.info("Moving client certs located at {}, {}, {}.".format(
            root_cert_path, client_cert_path, client_key_path))

        remote_shell.run_command('mkdir -p ' + self.YSQLSH_CERT_DIR)
        # Give write permissions. If the command fails, ignore.
        remote_shell.run_command('chmod -f 666 {}/* || true'.format(
            self.YSQLSH_CERT_DIR))

        if certs_location == self.CERT_LOCATION_NODE:
            remote_shell.run_command("cp '{}' '{}'".format(
                root_cert_path, yb_root_cert_path))
            remote_shell.run_command("cp '{}' '{}'".format(
                client_cert_path, yb_client_cert_path))
            remote_shell.run_command("cp '{}' '{}'".format(
                client_key_path, yb_client_key_path))
        if certs_location == self.CERT_LOCATION_PLATFORM:
            remote_shell.put_file(root_cert_path, yb_root_cert_path)
            remote_shell.put_file(client_cert_path, yb_client_cert_path)
            remote_shell.put_file(client_key_path, yb_client_key_path)

        # Reset the write permission as a sanity check.
        remote_shell.run_command('chmod 400 {}/*'.format(self.YSQLSH_CERT_DIR))
Beispiel #5
0
    def copy_server_certs(self, ssh_options, root_cert_path, server_cert_path,
                          server_key_path, certs_location, certs_dir):
        remote_shell = RemoteShell(ssh_options)
        node_ip = ssh_options["ssh_host"]
        logging.info("Moving server certs located at {}, {}, {}.".format(
            root_cert_path, server_cert_path, server_key_path))
        cert_file = 'node.{}.crt'.format(node_ip)
        key_file = 'node.{}.key'.format(node_ip)

        remote_shell.run_command('mkdir -p ' + certs_dir)
        # Give write permission in case file exists. If the command fails, ignore.
        remote_shell.run_command('chmod -f 666 {}/* || true'.format(certs_dir))

        if certs_location == self.CERT_LOCATION_NODE:
            self.verify_certs(root_cert_path,
                              server_cert_path,
                              ssh_options,
                              verify_hostname=True)
            remote_shell.run_command('cp {} {}'.format(
                root_cert_path, os.path.join(certs_dir, self.ROOT_CERT_NAME)))
            remote_shell.run_command('cp {} {}'.format(
                server_cert_path, os.path.join(certs_dir, cert_file)))
            remote_shell.run_command('cp {} {}'.format(
                server_key_path, os.path.join(certs_dir, key_file)))
        if certs_location == self.CERT_LOCATION_PLATFORM:
            remote_shell.put_file(root_cert_path,
                                  os.path.join(certs_dir, self.ROOT_CERT_NAME))
            remote_shell.put_file(server_cert_path,
                                  os.path.join(certs_dir, cert_file))
            remote_shell.put_file(server_key_path,
                                  os.path.join(certs_dir, key_file))

        # Reset the write permission as a sanity check.
        remote_shell.run_command('chmod 400 {}/*'.format(certs_dir))
Beispiel #6
0
    def copy_xcluster_root_cert(self, ssh_options, root_cert_path,
                                replication_config_name, producer_certs_dir):
        if producer_certs_dir is None:
            producer_certs_dir = self.PRODUCER_CERTS_DIR_NAME
        remote_shell = RemoteShell(ssh_options)
        node_ip = ssh_options["ssh_host"]
        src_root_cert_dir_path = os.path.join(producer_certs_dir,
                                              replication_config_name)
        src_root_cert_path = os.path.join(src_root_cert_dir_path,
                                          self.ROOT_CERT_NAME)
        logging.info("Moving server cert located at {} to {}:{}.".format(
            root_cert_path, node_ip, src_root_cert_dir_path))

        remote_shell.run_command('mkdir -p ' + src_root_cert_dir_path)
        # Give write permissions. If the command fails, ignore.
        remote_shell.run_command(
            'chmod -f 666 {}/* || true'.format(src_root_cert_dir_path))
        remote_shell.put_file(root_cert_path, src_root_cert_path)

        # Reset the write permission as a sanity check.
        remote_shell.run_command(
            'chmod 400 {}/*'.format(src_root_cert_dir_path))
    def generate_client_cert(self, extra_vars, ssh_options):
        remote_shell = RemoteShell(ssh_options)
        if "rootCA_cert" in extra_vars:
            root_cert_path = extra_vars["rootCA_cert"]
            root_key_path = extra_vars["rootCA_key"]
            certs_node_dir = extra_vars["certs_node_dir"]
            self.__generate_client_cert(extra_vars, ssh_options,
                                        root_cert_path, root_key_path,
                                        certs_node_dir, remote_shell)

        if "clientRootCA_cert" in extra_vars:
            root_cert_path = extra_vars["clientRootCA_cert"]
            root_key_path = extra_vars["clientRootCA_key"]
            certs_client_dir = extra_vars["certs_client_dir"]
            self.__generate_client_cert(extra_vars, ssh_options,
                                        root_cert_path, root_key_path,
                                        certs_client_dir, remote_shell)

        if "client_cert" in extra_vars:
            if "rootCA_cert" in extra_vars:
                root_cert_path = extra_vars["rootCA_cert"]
            else:
                root_cert_path = extra_vars["clientRootCA_cert"]
            client_cert_path = extra_vars["client_cert"]
            client_key_path = extra_vars["client_key"]
            remote_shell.run_command('mkdir -p ' + self.YSQLSH_CERT_DIR)
            # Give write permission in case file exists. If the command fails, ignore.
            remote_shell.run_command('chmod -f 666 {}/* || true'.format(
                self.YSQLSH_CERT_DIR))
            remote_shell.put_file(
                root_cert_path,
                os.path.join(self.YSQLSH_CERT_DIR, self.CLIENT_ROOT_NAME))
            remote_shell.put_file(
                client_cert_path,
                os.path.join(self.YSQLSH_CERT_DIR, self.CLIENT_CERT_NAME))
            remote_shell.put_file(
                client_key_path,
                os.path.join(self.YSQLSH_CERT_DIR, self.CLIENT_KEY_NAME))
            remote_shell.run_command('chmod 400 {}/*'.format(
                self.YSQLSH_CERT_DIR))
    def copy_server_certs(self, extra_vars, ssh_options):
        remote_shell = RemoteShell(ssh_options)
        root_cert_path = extra_vars["server_root_cert"]
        node_cert_path = extra_vars["server_node_cert"]
        node_key_path = extra_vars["server_node_key"]
        certs_dir = extra_vars["certs_client_dir"]
        node_ip = ssh_options["ssh_host"]

        logging.info("Copying server certs located at {}, {}, {}.".format(
            root_cert_path, node_cert_path, node_key_path))
        key_file = 'node.{}.key'.format(node_ip)
        cert_file = 'node.{}.crt'.format(node_ip)

        remote_shell.run_command('mkdir -p ' + certs_dir)
        # Give write permission in case file exists. If the command fails, ignore.
        remote_shell.run_command('chmod -f 666 {}/* || true'.format(certs_dir))
        remote_shell.put_file(root_cert_path,
                              os.path.join(certs_dir, self.ROOT_CERT_NAME))
        remote_shell.put_file(node_cert_path,
                              os.path.join(certs_dir, cert_file))
        remote_shell.put_file(node_key_path, os.path.join(certs_dir, key_file))
        remote_shell.run_command('chmod 400 {}/*'.format(certs_dir))
Beispiel #9
0
    def copy_client_certs(self, ssh_options, root_cert_path, client_cert_path,
                          client_key_path, certs_location):
        remote_shell = RemoteShell(ssh_options)
        node_ip = ssh_options["ssh_host"]
        logging.info("Moving client certs located at {}, {}, {}.".format(
            root_cert_path, client_cert_path, client_key_path))
        cert_file = 'node.{}.crt'.format(node_ip)
        key_file = 'node.{}.key'.format(node_ip)

        remote_shell.run_command('mkdir -p ' + self.YSQLSH_CERT_DIR)
        # Give write permission in case file exists. If the command fails, ignore.
        remote_shell.run_command('chmod -f 666 {}/* || true'.format(
            self.YSQLSH_CERT_DIR))

        if certs_location == self.CERT_LOCATION_NODE:
            remote_shell.run_command('cp {} {}'.format(
                root_cert_path,
                os.path.join(self.YSQLSH_CERT_DIR, self.ROOT_CERT_NAME)))
            remote_shell.run_command('cp {} {}'.format(
                client_cert_path,
                os.path.join(self.YSQLSH_CERT_DIR, self.CLIENT_CERT_NAME)))
            remote_shell.run_command('cp {} {}'.format(
                client_key_path,
                os.path.join(self.YSQLSH_CERT_DIR, self.CLIENT_KEY_NAME)))
        if certs_location == self.CERT_LOCATION_PLATFORM:
            remote_shell.put_file(
                root_cert_path,
                os.path.join(self.YSQLSH_CERT_DIR, self.CLIENT_ROOT_NAME))
            remote_shell.put_file(
                client_cert_path,
                os.path.join(self.YSQLSH_CERT_DIR, self.CLIENT_CERT_NAME))
            remote_shell.put_file(
                client_key_path,
                os.path.join(self.YSQLSH_CERT_DIR, self.CLIENT_KEY_NAME))

        remote_shell.run_command('chmod 400 {}/*'.format(self.YSQLSH_CERT_DIR))
Beispiel #10
0
    def generate_client_cert(self, extra_vars, ssh_options):
        node_ip = ssh_options["ssh_host"]
        root_cert_path = extra_vars["rootCA_cert"]
        root_key_path = extra_vars["rootCA_key"]
        certs_node_dir = extra_vars["certs_node_dir"]
        with open(root_cert_path, 'r') as cert_in:
            certlines = cert_in.read()
        root_cert = x509.load_pem_x509_certificate(certlines, default_backend())
        with open(root_key_path, 'r') as key_in:
            keylines = key_in.read()
        root_key = load_pem_private_key(keylines, None, default_backend())
        private_key = rsa.generate_private_key(
            public_exponent=self.PUBLIC_EXPONENT,
            key_size=self.KEY_SIZE,
            backend=default_backend()
        )
        public_key = private_key.public_key()
        builder = x509.CertificateBuilder()
        builder = builder.subject_name(x509.Name([
            x509.NameAttribute(NameOID.COMMON_NAME, six.text_type(node_ip)),
            x509.NameAttribute(NameOID.ORGANIZATION_NAME, six.text_type(extra_vars["org_name"]))
        ]))
        builder = builder.issuer_name(root_cert.subject)
        builder = builder.not_valid_before(datetime.datetime.utcnow())
        builder = builder.not_valid_after(datetime.datetime.utcnow() + datetime.timedelta(
            extra_vars["cert_valid_duration"]))
        builder = builder.serial_number(x509.random_serial_number())
        builder = builder.public_key(public_key)
        builder = builder.add_extension(x509.BasicConstraints(ca=False, path_length=None),
                                        critical=True)
        certificate = builder.sign(private_key=root_key, algorithm=hashes.SHA256(),
                                   backend=default_backend())
        # Write private key to file
        pem = private_key.private_bytes(
            encoding=Encoding.PEM,
            format=PrivateFormat.TraditionalOpenSSL,
            encryption_algorithm=NoEncryption()
        )
        key_file = 'node.{}.key'.format(node_ip)
        cert_file = 'node.{}.crt'.format(node_ip)
        common_path = '{}/{}'.format(self.CERTS_TEMP_DIR, node_ip)
        try:
            os.makedirs(common_path)
        except OSError as exc:  # Guard against race condition
            if exc.errno != errno.EEXIST:
                raise YBOpsRuntimeError(common_path + " could not be  be created")
        with open(os.path.join(common_path, key_file), 'wb') as pem_out:
            pem_out.write(pem)
        # Write certificate to file
        pem = certificate.public_bytes(encoding=Encoding.PEM)
        with open(os.path.join(common_path, cert_file), 'wb') as pem_out:
            pem_out.write(pem)
        # Copy files over to node
        remote_shell = RemoteShell(ssh_options)
        remote_shell.run_command('mkdir -p ' + certs_node_dir)
        # Give write permission in case file exists. If the command fails, ignore.
        remote_shell.run_command('chmod -f 666 {}/* || true'.format(certs_node_dir))
        remote_shell.put_file(os.path.join(common_path, key_file),
                              os.path.join(certs_node_dir, key_file))
        remote_shell.put_file(os.path.join(common_path, cert_file),
                              os.path.join(certs_node_dir, cert_file))
        remote_shell.put_file(root_cert_path, os.path.join(certs_node_dir, self.ROOT_CERT_NAME))
        remote_shell.run_command('chmod 400 {}/*'.format(certs_node_dir))

        if "client_cert" in extra_vars:
            client_cert_path = extra_vars["client_cert"]
            client_key_path = extra_vars["client_key"]
            remote_shell.run_command('mkdir -p ' + self.YSQLSH_CERT_DIR)
            # Give write permission in case file exists. If the command fails, ignore.
            remote_shell.run_command('chmod -f 666 {}/* || true'.format(self.YSQLSH_CERT_DIR))
            remote_shell.put_file(root_cert_path, os.path.join(self.YSQLSH_CERT_DIR,
                                                               self.CLIENT_ROOT_NAME))
            remote_shell.put_file(client_cert_path, os.path.join(self.YSQLSH_CERT_DIR,
                                                                 self.CLIENT_CERT_NAME))
            remote_shell.put_file(client_key_path, os.path.join(self.YSQLSH_CERT_DIR,
                                                                self.CLIENT_KEY_NAME))
            remote_shell.run_command('chmod 400 {}/*'.format(self.YSQLSH_CERT_DIR))

        try:
            shutil.rmtree(common_path)
        except OSError as e:
            raise YBOpsRuntimeError("Error: %s - %s." % (e.filename, e.strerror))
Beispiel #11
0
    def copy_server_certs(self, ssh_options, root_cert_path, server_cert_path,
                          server_key_path, certs_location, certs_dir,
                          rotate_certs, skip_cert_validation):
        remote_shell = RemoteShell(ssh_options)
        node_ip = ssh_options["ssh_host"]
        cert_file = 'node.{}.crt'.format(node_ip)
        key_file = 'node.{}.key'.format(node_ip)
        yb_root_cert_path = os.path.join(certs_dir, self.ROOT_CERT_NAME)
        yb_server_cert_path = os.path.join(certs_dir, cert_file)
        yb_server_key_path = os.path.join(certs_dir, key_file)

        copy_root = True
        if rotate_certs:
            root_cert_command = remote_shell.run_command_raw(
                "cat '{}'".format(yb_root_cert_path))
            # In case of tls toggle root cert might not be present
            if not root_cert_command.exited:
                root_cert = root_cert_command.stdout
                root_cert_new = None
                if certs_location == self.CERT_LOCATION_NODE:
                    root_cert_new = remote_shell.run_command(
                        "cat '{}'".format(root_cert_path)).stdout
                if certs_location == self.CERT_LOCATION_PLATFORM:
                    with open(root_cert_path) as file:
                        root_cert_new = file.read()
                if root_cert is not None and root_cert_new is not None:
                    compare_result = self.compare_certs(
                        root_cert_new, root_cert)
                    if compare_result == 0 or compare_result == 1:
                        # Don't copy root certs if the new root cert is
                        # same or subset of the existing root cert
                        copy_root = False
                else:
                    raise YBOpsRuntimeError(
                        "Unable to fetch the certificate {}".format(
                            root_cert_path))

        logging.info("Moving server certs located at {}, {}, {}.".format(
            root_cert_path, server_cert_path, server_key_path))

        remote_shell.run_command('mkdir -p ' + certs_dir)
        # Give write permissions. If the command fails, ignore.
        remote_shell.run_command('chmod -f 666 {}/* || true'.format(certs_dir))

        if certs_location == self.CERT_LOCATION_NODE:
            if skip_cert_validation == 'ALL':
                logging.info(
                    "Skipping all validations for certs for node {}".format(
                        node_ip))
            else:
                verify_hostname = True
                if skip_cert_validation == 'HOSTNAME':
                    logging.info(
                        "Skipping host name validation for certs for node {}".
                        format(node_ip))
                    verify_hostname = False
                self.verify_certs(root_cert_path, server_cert_path,
                                  ssh_options, verify_hostname)
            if copy_root:
                remote_shell.run_command("cp '{}' '{}'".format(
                    root_cert_path, yb_root_cert_path))
            remote_shell.run_command("cp '{}' '{}'".format(
                server_cert_path, yb_server_cert_path))
            remote_shell.run_command("cp '{}' '{}'".format(
                server_key_path, yb_server_key_path))
        if certs_location == self.CERT_LOCATION_PLATFORM:
            if copy_root:
                remote_shell.put_file(root_cert_path, yb_root_cert_path)
            remote_shell.put_file(server_cert_path, yb_server_cert_path)
            remote_shell.put_file(server_key_path, yb_server_key_path)

        # Reset the write permission as a sanity check.
        remote_shell.run_command('chmod 400 {}/*'.format(certs_dir))