Ejemplo n.º 1
0
    def extract_nulecule_data(self, image, source, dest, update=False):
        """
        Extract the Nulecule contents from a container into a destination
        directory.

        Args:
            image (str): Docker image name
            source (str): Source directory in Docker image to copy from
            dest (str): Path to destination directory on host
            update (bool): Update destination directory if it exists when
                           True

        Returns:
            None
        """
        logger.info(
            'Extracting Nulecule data from image %s to %s' % (image, dest))
        if self.dryrun:
            return

        # Create a temporary directory for extraction
        tmpdir = '/tmp/nulecule-{}'.format(uuid.uuid1())

        self.extract_files(image, source=source, dest=tmpdir)

        # If the application already exists locally then need to
        # make sure the local app id is the same as the one requested
        # on the command line.
        mainfile = os.path.join(dest, MAIN_FILE)
        tmpmainfile = os.path.join(tmpdir, MAIN_FILE)
        if os.path.exists(mainfile):
            existing_id = Utils.getAppId(mainfile)
            new_id = Utils.getAppId(tmpmainfile)
            cockpit_logger.info("Loading app_id %s" % new_id)
            if existing_id != new_id:
                raise NuleculeException(
                    "Existing app (%s) and requested app (%s) differ" %
                    (existing_id, new_id))
            # If app exists and no update requested then move on
            if update:
                logger.info("App exists locally. Performing update...")
            else:
                logger.info("App exists locally and no update requested")
                return

        # Copy files from tmpdir into place
        logger.debug('Copying nulecule data from %s to %s' % (tmpdir, dest))
        Utils.copy_dir(tmpdir, dest, update)

        # Clean up tmpdir
        logger.debug('Removing tmp dir: %s' % tmpdir)
        Utils.rm_dir(tmpdir)

        # Set the proper permissions on the extracted folder
        Utils.setFileOwnerGroup(dest)
Ejemplo n.º 2
0
    def extract_nulecule_data(self, image, source, dest, update=False):
        """
        Extract the Nulecule contents from a container into a destination
        directory.

        Args:
            image (str): Docker image name
            source (str): Source directory in Docker image to copy from
            dest (str): Path to destination directory on host
            update (bool): Update destination directory if it exists when
                           True

        Returns:
            None
        """
        logger.info("Extracting Nulecule data from image %s to %s" % (image, dest))
        if self.dryrun:
            return

        # Create a temporary directory for extraction
        tmpdir = "/tmp/nulecule-{}".format(uuid.uuid1())

        self.extract_files(image, source=source, dest=tmpdir)

        # If the application already exists locally then need to
        # make sure the local app id is the same as the one requested
        # on the command line.
        mainfile = os.path.join(dest, MAIN_FILE)
        tmpmainfile = os.path.join(tmpdir, MAIN_FILE)
        if os.path.exists(mainfile):
            existing_id = Utils.getAppId(mainfile)
            new_id = Utils.getAppId(tmpmainfile)
            cockpit_logger.info("Loading app_id %s" % new_id)
            if existing_id != new_id:
                raise NuleculeException("Existing app (%s) and requested app (%s) differ" % (existing_id, new_id))
            # If app exists and no update requested then move on
            if update:
                logger.info("App exists locally. Performing update...")
            else:
                logger.info("App exists locally and no update requested")
                return

        # Copy files from tmpdir into place
        logger.debug("Copying nulecule data from %s to %s" % (tmpdir, dest))
        Utils.copy_dir(tmpdir, dest, update)

        # Clean up tmpdir
        logger.debug("Removing tmp dir: %s" % tmpdir)
        Utils.rm_dir(tmpdir)

        # Set the proper permissions on the extracted folder
        Utils.setFileOwnerGroup(dest)
Ejemplo n.º 3
0
    def extract_files(self, image, source, dest):
        """
        Extracts a directory/file in a Docker image to a specified
        destination.

        Args:
            image (str): Docker image name
            source (str): Source directory in Docker image to copy from
            dest (str): Path to destination directory on host

        Returns:
            None
        """
        logger.info(
            'Copying files from image %s:%s to %s' % (image, source, dest))
        if self.dryrun:
            return

        # Create a dummy container in order to retrieve the file(s)
        run_cmd = [
            self.docker_cli, 'create', '--entrypoint', '/bin/true', image]
        logger.debug('Creating docker container: %s' % ' '.join(run_cmd))
        container_id = subprocess.check_output(run_cmd).strip()

        # Copy files out of dummy container to the destination directory
        cp_cmd = [self.docker_cli, 'cp',
                  '%s:/%s' % (container_id, source), dest]
        logger.debug(
            'Copying data from docker container: %s' % ' '.join(cp_cmd))
        try:
            subprocess.check_output(cp_cmd, stderr=subprocess.STDOUT)
        except subprocess.CalledProcessError as e:
            raise DockerException('Copying data from docker container failed: %s. \n%s' % (cp_cmd, e.output))

        # Clean up dummy container
        rm_cmd = [self.docker_cli, 'rm', '-f', container_id]
        logger.debug('Removing docker container: %s' % ' '.join(rm_cmd))
        try:
            subprocess.check_output(rm_cmd)
        except subprocess.CalledProcessError as e:
            raise DockerException('Removing docker container failed: %s. \n%s' % (rm_cmd, e.output))

        # Set the proper permissions on the extracted folder
        Utils.setFileOwnerGroup(dest)
Ejemplo n.º 4
0
    def _write_answers(self, path, answers, answers_format):
        """
        Write answers data to file.

        Args:
            path (str): path to answers file to write to
            answers (dict): Answers data
            answers_format (str): Format to use to dump answers data to file,
                                  e.g., json
        Returns:
            None
        """
        logger.debug("Writing answers to file.")
        logger.debug("FILE: %s", path)
        logger.debug("ANSWERS: %s", answers)
        anymarkup.serialize_file(answers, path, format=answers_format)

        # Make sure that the permission of the file is set to the current user
        Utils.setFileOwnerGroup(path)
Ejemplo n.º 5
0
    def _write_answers(self, path, answers, answers_format):
        """
        Write answers data to file.

        Args:
            path (str): path to answers file to write to
            answers (dict): Answers data
            answers_format (str): Format to use to dump answers data to file,
                                  e.g., json
        Returns:
            None
        """
        logger.debug("Writing answers to file.")
        logger.debug("FILE: %s", path)
        logger.debug("ANSWERS: %s", answers)
        logger.debug("ANSWERS FORMAT: %s", answers_format)
        anymarkup.serialize_file(answers, path, format=answers_format)

        # Make sure that the permission of the file is set to the current user
        Utils.setFileOwnerGroup(path)
Ejemplo n.º 6
0
    def extract_files(self, image, source, dest):
        """
        Extracts a directory/file in a Docker image to a specified
        destination.

        Args:
            image (str): Docker image name
            source (str): Source directory in Docker image to copy from
            dest (str): Path to destination directory on host

        Returns:
            None
        """
        logger.info("Copying files from image %s:%s to %s" % (image, source, dest))
        if self.dryrun:
            return

        # Create a dummy container in order to retrieve the file(s)
        run_cmd = [self.docker_cli, "create", "--entrypoint", "/bin/true", image]
        logger.debug("Creating docker container: %s" % " ".join(run_cmd))
        container_id = subprocess.check_output(run_cmd).strip()

        # Copy files out of dummy container to the destination directory
        cp_cmd = [self.docker_cli, "cp", "%s:/%s" % (container_id, source), dest]
        logger.debug("Copying data from docker container: %s" % " ".join(cp_cmd))
        try:
            subprocess.check_output(cp_cmd, stderr=subprocess.STDOUT)
        except subprocess.CalledProcessError as e:
            raise DockerException("Copying data from docker container failed: %s. \n%s" % (cp_cmd, e.output))

        # Clean up dummy container
        rm_cmd = [self.docker_cli, "rm", "-f", container_id]
        logger.debug("Removing docker container: %s" % " ".join(rm_cmd))
        try:
            subprocess.check_output(rm_cmd)
        except subprocess.CalledProcessError as e:
            raise DockerException("Removing docker container failed: %s. \n%s" % (rm_cmd, e.output))

        # Set the proper permissions on the extracted folder
        Utils.setFileOwnerGroup(dest)
Ejemplo n.º 7
0
    def load_external_application(self, dryrun=False, update=False):
        """
        Loads an external application for the NuleculeComponent.

        Args:
            dryrun (bool): When True, skips pulling an external application.
            update (bool): When True, it ignores an already pulled external
                           application, and tries to pull the external
                           application and update the existing one.

        Returns:
            A Nulecule instance or None
        """
        nulecule = None
        external_app_path = os.path.join(
            self.basepath, EXTERNAL_APP_DIR, self.name)
        if os.path.isdir(external_app_path) and not update:
            logger.info(
                'Found existing external application: %s '
                'Loading: ' % self.name)
            nulecule = Nulecule.load_from_path(
                external_app_path, dryrun=dryrun, update=update,
                namespace=self.namespace)
        elif not dryrun:
            logger.info('Pulling external application: %s' % self.name)
            nulecule = Nulecule.unpack(
                self.source,
                external_app_path,
                config=self.config,
                namespace=self.namespace,
                dryrun=dryrun,
                update=update
            )

            # When pulling an external application, make sure that the
            # "external" folder is owned by the respective user extracting it
            # by providing the basepath of the extraction
            Utils.setFileOwnerGroup(self.basepath)
        self._app = nulecule
        cockpit_logger.info("Copied app successfully.")