Esempio n. 1
0
def generate(image, outputdir, platform, searchpath, creds, ipk, appmetadata,
             yes, nodepwalking, libmatchingmode):
    """Generate an OCI Bundle for a specified platform
    """

    logger.info(f'Generating new OCI bundle* from {image} for {platform}')

    outputdir = os.path.abspath(outputdir)

    # Check if the output dir already exists
    if os.path.exists(outputdir):
        if not yes:
            click.confirm(
                f"The directory {outputdir} already exists. Are you sure you want to continue? The contents of this directory will be deleted",
                abort=True)

        # Delete existing directory
        shutil.rmtree(outputdir)

    # Load the config for the platform
    selected_platform = STBPlatform(platform, searchpath)

    if not selected_platform.found_config():
        logger.error(f"Could not find config for platform {platform}")
        return

    # Download the image to a temp directory
    img_downloader = ImageDownloader()
    img_path = img_downloader.download_image(image, creds,
                                             selected_platform.get_config())

    if not img_path:
        return

    # Unpack the image with umoci
    tag = ImageDownloader().get_image_tag(image)
    img_unpacker = ImageUnpackager()
    unpack_success = img_unpacker.unpack_image(img_path, tag, outputdir)

    if not unpack_success:
        return

    # Delete the downloaded image now we've unpacked it
    logger.info(f"Deleting {img_path}")
    shutil.rmtree(img_path)

    # Load app metadata
    app_metadata_file = ""
    app_metadata_image_path = os.path.join(outputdir, "rootfs",
                                           "appmetadata.json")

    image_metadata_exists = os.path.exists(app_metadata_image_path)

    if not image_metadata_exists and not appmetadata:
        # No metadata at all
        logger.error(
            f"Cannot find app metadata file in OCI image and none provided to BundleGen"
        )
        return
    elif not image_metadata_exists and appmetadata:
        # No metadata in image, but custom file provided
        if not os.path.exists(appmetadata):
            logger.error(f'App metadata file {appmetadata} does not exist')
            return
        app_metadata_file = appmetadata
    elif image_metadata_exists and appmetadata:
        # Got two options for metadata, which one do we want?
        if click.confirm(
                "Metadata found in image, but custom metadata provided. Use custom metadata?"
        ):
            app_metadata_file = appmetadata
        else:
            app_metadata_file = app_metadata_image_path
    else:
        app_metadata_file = app_metadata_image_path

    logger.debug(f"Loading metadata from {app_metadata_file}")

    # Load the metadata
    app_metadata_dict = {}
    with open(app_metadata_file) as metadata:
        app_metadata_dict = json.load(metadata)

    # remove app metadata from image rootfs
    if image_metadata_exists:
        os.remove(app_metadata_image_path)

    # Begin processing. Work in the output dir where the img was unpacked to
    processor = BundleProcessor(selected_platform.get_config(), outputdir,
                                app_metadata_dict, nodepwalking,
                                libmatchingmode)
    if not processor.check_compatibility():
        # Not compatible - delete any work done so far
        shutil.rmtree(outputdir)
        return

    success = processor.begin_processing()

    if not success:
        logger.warning("Failed to produce bundle")
        return

    # Processing finished, now create a tarball/ipk of the output directory
    if ipk:
        # create control file
        Utils.create_control_file(selected_platform.get_config(),
                                  app_metadata_dict)
        Utils.create_ipk(outputdir, outputdir)
        logger.success(f"Successfully generated bundle at {outputdir}.ipk")
    else:
        Utils.create_tgz(outputdir, outputdir)
        logger.success(f"Successfully generated bundle at {outputdir}.tar.gz")
Esempio n. 2
0
def generate(image, outputdir, platform, searchpath, creds, ipk, appmetadata, yes, nodepwalking, libmatchingmode, createmountpoints, appid):
    """Generate an OCI Bundle for a specified platform
    """

    logger.info(f'Generating new OCI bundle* from {image} for {platform}')

    outputdir = os.path.abspath(outputdir)

    # Check if the output dir already exists
    if os.path.exists(outputdir):
        if not yes:
            click.confirm(
                f"The directory {outputdir} already exists. Are you sure you want to continue? The contents of this directory will be deleted", abort=True)

        # Delete existing directory
        shutil.rmtree(outputdir)

    # Load the config for the platform
    selected_platform = STBPlatform(platform, searchpath)

    if not selected_platform.found_config():
        logger.error(f"Could not find config for platform {platform}")
        sys.exit(1)

    # Download the image to a temp directory
    img_downloader = ImageDownloader()
    img_path = img_downloader.download_image(
        image, creds, selected_platform.get_config())

    if not img_path:
        sys.exit(1)

    # Unpack the image with umoci
    tag = ImageDownloader().get_image_tag(image)
    img_unpacker = ImageUnpackager(src=img_path, dst=outputdir)
    unpack_success = img_unpacker.unpack_image(tag, delete=True)

    if not unpack_success:
        sys.exit(1)

    # Load app metadata
    metadata_from_image = img_unpacker.get_app_metadata_from_img()
    appmetadata = os.path.abspath(appmetadata) if appmetadata else None

    app_metadata_dict = {}
    if not metadata_from_image and not appmetadata:
        # No metadata at all
        logger.error(
            f"Cannot find app metadata file in OCI image and none provided to BundleGen")
        sys.exit(1)

    if not metadata_from_image and appmetadata:
        # No metadata in image, but custom file provided
        if not os.path.exists(appmetadata):
            logger.error(f'App metadata file {appmetadata} does not exist')
            sys.exit(1)
        with open(appmetadata) as metadata:
            logger.debug(f"Loading metadata from {appmetadata}")
            app_metadata_dict = json.load(metadata)
    elif metadata_from_image and appmetadata:
        # Got two options for metadata, which one do we want?
        if click.confirm("Metadata found in image, but custom metadata provided. Use custom metadata?"):
            with open(appmetadata) as metadata:
                logger.debug(f"Loading metadata from {appmetadata}")
                app_metadata_dict = json.load(metadata)
        else:
            app_metadata_dict = metadata_from_image

        img_unpacker.delete_img_app_metadata()
    else:
        # Take metadata from image
        app_metadata_dict = metadata_from_image
        img_unpacker.delete_img_app_metadata()

    if appid:
         app_metadata_dict['id'] = appid

    # Begin processing. Work in the output dir where the img was unpacked to
    processor = BundleProcessor(
        selected_platform.get_config(), outputdir, app_metadata_dict, nodepwalking, libmatchingmode, createmountpoints)
    if not processor.check_compatibility():
        # Not compatible - delete any work done so far
        shutil.rmtree(outputdir)
        sys.exit(2)

    success = processor.begin_processing()

    if not success:
        logger.warning("Failed to produce bundle")
        sys.exit(3)

    # Processing finished, now create a tarball/ipk of the output directory
    if ipk:
        # create control file
        Utils.create_control_file(
            selected_platform.get_config(), app_metadata_dict)
        Utils.create_ipk(outputdir, outputdir)
        logger.success(f"Successfully generated bundle at {outputdir}.ipk")
    else:
        tarball_settings = processor.platform_cfg.get('tarball')
        file_ownership_user = tarball_settings.get('fileOwnershipSameAsUser') if tarball_settings else None
        file_mask = tarball_settings.get('fileMask') if tarball_settings else None

        container_uid_gid = processor.get_real_uid_gid()

        uid = container_uid_gid[0] if container_uid_gid[0] and file_ownership_user else None
        gid = container_uid_gid[1] if container_uid_gid[1] and file_ownership_user else None

        Utils.create_tgz(outputdir, outputdir, uid, gid, file_mask)
        logger.success(f"Successfully generated bundle at {outputdir}.tar.gz")