def main(): logging_setup.DefineCommandLineArgs(parser) args = parser.parse_args() logging_setup.Init(args=args) if not args.name or not args.tarball: raise Exception('--name and --tarball are required arguments.') retry_factory = retry.Factory() retry_factory = retry_factory.WithSourceTransportCallable(httplib2.Http) transport = transport_pool.Http(retry_factory.Build, size=_THREADS) # This library can support push-by-digest, but the likelihood of a user # correctly providing us with the digest without using this library # directly is essentially nil. name = Tag(args.name, args.stamp_info_file) # Resolve the appropriate credential to use based on the standard Docker # client logic. creds = docker_creds.DefaultKeychain.Resolve(name) with docker_session.Push(name, creds, transport, threads=_THREADS) as session: logging.info('Reading v2.2 image from tarball %r', args.tarball) with v2_2_image.FromTarball(args.tarball) as v2_2_img: logging.info('Starting upload ...') if args.oci: with oci_compat.OCIFromV22(v2_2_img) as oci_img: session.upload(oci_img) digest = oci_img.digest() else: session.upload(v2_2_img) digest = v2_2_img.digest() print('{name} was published with digest: {digest}'.format( name=name, digest=digest))
def main(): logging_setup.DefineCommandLineArgs(parser) args = parser.parse_args() logging_setup.Init(args=args) transport = transport_pool.Http(httplib2.Http, size=_THREADS) # This library can support push-by-digest, but the likelihood of a user # correctly providing us with the digest without using this library # directly is essentially nil. src = docker_name.Tag(args.src_image) dst = docker_name.Tag(args.dst_image) # Resolve the appropriate credential to use based on the standard Docker # client logic. creds = docker_creds.DefaultKeychain.Resolve(src) logging.info('Pulling v2.2 image from %r ...', src) with v2_2_image.FromRegistry(src, creds, transport) as src_image: with open(args.tarball, 'rb') as f: new_img = append.Layer(src_image, f.read()) creds = docker_creds.DefaultKeychain.Resolve(dst) with docker_session.Push(dst, creds, transport, threads=_THREADS, mount=[src.as_repository()]) as session: logging.info('Starting upload ...') session.upload(new_img) digest = new_img.digest() print(('{name} was published with digest: {digest}'.format( name=dst, digest=digest)))
def main(): logging_setup.DefineCommandLineArgs(parser) args = parser.parse_args() logging_setup.Init(args=args) # If config is specified, use that. Otherwise, fall back on reading # the config from the tarball. if args.config: logging.info('Reading config from %r', args.config) with open(args.config, 'r') as reader: config = reader.read() elif args.tarball: logging.info('Reading config from tarball %r', args.tarball) with v2_2_image.FromTarball(args.tarball) as base: config = base.config_file() else: config = args.config layers = list(zip(args.digest or [], args.layer or [])) uncompressed_layers = list( zip(args.diff_id or [], args.uncompressed_layer or [])) logging.info('Loading v2.2 image From Disk ...') with v2_2_image.FromDisk(config_file=config, layers=layers, uncompressed_layers=uncompressed_layers, legacy_base=args.tarball) as v2_2_img: with tarfile.open(args.filesystem, 'w') as tar: v2_2_image.extract(v2_2_img, tar) with open(args.metadata, 'w') as f: f.write(v2_2_img.config_file())
def main(): logging_setup.DefineCommandLineArgs(parser) args = parser.parse_args() logging_setup.Init(args=args) if not args.name: raise Exception('--name is a required arguments.') # This library can support push-by-digest, but the likelihood of a user # correctly providing us with the digest without using this library # directly is essentially nil. name = Tag(args.name, args.stamp_info_file) if not args.config and (args.layer or args.digest): raise Exception( 'Using --layer or --digest requires --config to be specified.') if not args.config and not args.tarball: raise Exception('Either --config or --tarball must be specified.') # If config is specified, use that. Otherwise, fallback on reading # the config from the tarball. config = args.config if args.config: logging.info('Reading config from %r', args.config) with open(args.config, 'r') as reader: config = reader.read() elif args.tarball: logging.info('Reading config from tarball %r', args.tarball) with v2_2_image.FromTarball(args.tarball) as base: config = base.config_file() if len(args.digest or []) != len(args.layer or []): raise Exception('--digest and --layer must have matching lengths.') transport = transport_pool.Http(httplib2.Http, size=_THREADS) # Resolve the appropriate credential to use based on the standard Docker # client logic. creds = docker_creds.DefaultKeychain.Resolve(name) with docker_session.Push(name, creds, transport, threads=_THREADS) as session: logging.info('Loading v2.2 image from disk ...') with v2_2_image.FromDisk(config, zip(args.digest or [], args.layer or []), legacy_base=args.tarball) as v2_2_img: logging.info('Starting upload ...') if args.oci: with oci_compat.OCIFromV22(v2_2_img) as oci_img: session.upload(oci_img) digest = oci_img.digest() else: session.upload(v2_2_img) digest = v2_2_img.digest() print('{name} was published with digest: {digest}'.format( name=name, digest=digest))
def main(): logging_setup.DefineCommandLineArgs(parser) args = parser.parse_args() logging_setup.Init(args=args) if not args.tarball or not args.directory: raise Exception('--tarball and --directory are required arguments.') logging.info('Reading v2.2 image from tarball %r', args.tarball) with v2_2_image.FromTarball(args.tarball) as v2_2_img: save.uncompressed(v2_2_img, args.directory, threads=_THREADS)
def main(): logging_setup.DefineCommandLineArgs(parser) args = parser.parse_args() logging_setup.Init(args=args) if not args.config and (args.layer or args.digest): logging.fatal( 'Using --layer or --digest requires --config to be specified.') sys.exit(1) if not args.config and not args.tarball: logging.fatal('Either --config or --tarball must be specified.') sys.exit(1) # If config is specified, use that. Otherwise, fallback on reading # the config from the tarball. config = args.config manifest = args.manifest if args.config: logging.info('Reading config from %r', args.config) with open(args.config, 'r') as reader: config = reader.read() elif args.tarball: logging.info('Reading config from tarball %r', args.tarball) with v2_2_image.FromTarball(args.tarball) as base: config = base.config_file() if args.manifest: with open(args.manifest, 'r') as reader: manifest = reader.read() if len(args.digest or []) != len(args.layer or []): logging.fatal('--digest and --layer must have matching lengths.') sys.exit(1) logging.info('Loading v2.2 image from disk ...') with v2_2_image.FromDisk(config, list(zip(args.digest or [], args.layer or [])), legacy_base=args.tarball, foreign_layers_manifest=manifest) as v2_2_img: try: if args.oci: with oci_compat.OCIFromV22(v2_2_img) as oci_img: digest = oci_img.digest() else: digest = v2_2_img.digest() with open(args.output_digest, 'w+') as digest_file: digest_file.write(digest) # pylint: disable=broad-except except Exception as e: logging.fatal('Error getting digest: %s', e) sys.exit(1)
def main(): logging_setup.DefineCommandLineArgs(parser) args = parser.parse_args() logging_setup.Init(args=args) if not args.name or not args.tarball: logging.fatal('--name and --tarball are required arguments.') sys.exit(1) retry_factory = retry.Factory() retry_factory = retry_factory.WithSourceTransportCallable(httplib2.Http) transport = transport_pool.Http(retry_factory.Build, size=8) if '@' in args.name: name = docker_name.Digest(args.name) else: name = docker_name.Tag(args.name) # OCI Image Manifest is compatible with Docker Image Manifest Version 2, # Schema 2. We indicate support for both formats by passing both media types # as 'Accept' headers. # # For reference: # OCI: https://github.com/opencontainers/image-spec # Docker: https://docs.docker.com/registry/spec/manifest-v2-2/ accept = docker_http.SUPPORTED_MANIFEST_MIMES # Resolve the appropriate credential to use based on the standard Docker # client logic. try: creds = docker_creds.DefaultKeychain.Resolve(name) # pylint: disable=broad-except except Exception as e: logging.fatal('Error resolving credentials for %s: %s', name, e) sys.exit(1) try: with tarfile.open(name=args.tarball, mode='w') as tar: logging.info('Pulling v2.2 image from %r ...', name) with v2_2_image.FromRegistry(name, creds, transport, accept) as v2_2_img: if v2_2_img.exists(): save.tarball(_make_tag_if_digest(name), v2_2_img, tar) return logging.info('Pulling v2 image from %r ...', name) with v2_image.FromRegistry(name, creds, transport) as v2_img: with v2_compat.V22FromV2(v2_img) as v2_2_img: save.tarball(_make_tag_if_digest(name), v2_2_img, tar) return # pylint: disable=broad-except except Exception as e: logging.fatal('Error pulling and saving image %s: %s', name, e) sys.exit(1)
def main(): logging_setup.DefineCommandLineArgs(parser) args = parser.parse_args() logging_setup.Init(args=args) method = save.uncompressed if args.format == 'tar.gz': method = save.fast logging.info('Reading v2.2 image from tarball %r', args.tarball) with v2_2_image.FromTarball(args.tarball) as v2_2_img: method(v2_2_img, args.directory, threads=_THREADS)
def main(): logging_setup.DefineCommandLineArgs(parser) args = parser.parse_args() logging_setup.Init(args=args) if not args.name or not args.directory: raise Exception('--name and --directory are required arguments.') retry_factory = retry.Factory() retry_factory = retry_factory.WithSourceTransportCallable(httplib2.Http) transport = transport_pool.Http(retry_factory.Build, size=_THREADS) if '@' in args.name: name = docker_name.Digest(args.name) else: name = docker_name.Tag(args.name) # OCI Image Manifest is compatible with Docker Image Manifest Version 2, # Schema 2. We indicate support for both formats by passing both media types # as 'Accept' headers. # # For reference: # OCI: https://github.com/opencontainers/image-spec # Docker: https://docs.docker.com/registry/spec/manifest-v2-2/ accept = docker_http.SUPPORTED_MANIFEST_MIMES # Resolve the appropriate credential to use based on the standard Docker # client logic. creds = docker_creds.DefaultKeychain.Resolve(name) logging.info('Pulling v2.2 image from %r ...', name) with v2_2_image.FromRegistry(name, creds, transport, accept) as v2_2_img: if v2_2_img.exists(): save.fast(v2_2_img, args.directory, threads=_THREADS) return logging.info('Pulling v2 image from %r ...', name) with v2_image.FromRegistry(name, creds, transport) as v2_img: with v2_compat.V22FromV2(v2_img) as v2_2_img: save.fast(v2_2_img, args.directory, threads=_THREADS) return
def main(): logging_setup.DefineCommandLineArgs(parser) args = parser.parse_args() logging_setup.Init(args=args) if not args.config and (args.layer or args.digest): raise Exception( 'Using --layer or --digest requires --config to be specified.') if not args.filesystem or not args.metadata: raise Exception( '--filesystem and --metadata are required flags.') if not args.config and not args.tarball: raise Exception('Either --config or --tarball must be specified.') # If config is specified, use that. Otherwise, fall back on reading # the config from the tarball. if args.config: logging.info('Reading config from %r', args.config) with open(args.config, 'r') as reader: config = reader.read() elif args.tarball: logging.info('Reading config from tarball %r', args.tarball) with v2_2_image.FromTarball(args.tarball) as base: config = base.config_file() else: config = args.config if len(args.digest or []) != len(args.layer or []): raise Exception('--digest and --layer must have matching lengths.') logging.info('Loading v2.2 image from disk ...') with v2_2_image.FromDisk(config, zip(args.digest or [], args.layer or []), legacy_base=args.tarball) as v2_2_img: with tarfile.open(args.filesystem, 'w') as tar: v2_2_image.extract(v2_2_img, tar) with open(args.metadata, 'w') as f: f.write(v2_2_img.config_file())
def main(): logging_setup.DefineCommandLineArgs(parser) args = parser.parse_args() logging_setup.Init(args=args) if not args.name or not args.directory: logging.fatal('--name and --directory are required arguments.') retry_factory = retry.Factory() retry_factory = retry_factory.WithSourceTransportCallable(httplib2.Http) transport = transport_pool.Http(retry_factory.Build, size=_THREADS) if '@' in args.name: name = docker_name.Digest(args.name) else: name = docker_name.Tag(args.name) # OCI Image Manifest is compatible with Docker Image Manifest Version 2, # Schema 2. We indicate support for both formats by passing both media types # as 'Accept' headers. # # For reference: # OCI: https://github.com/opencontainers/image-spec # Docker: https://docs.docker.com/registry/spec/manifest-v2-2/ accept = docker_http.SUPPORTED_MANIFEST_MIMES # Resolve the appropriate credential to use based on the standard Docker # client logic. try: creds = docker_creds.DefaultKeychain.Resolve(name) # pylint: disable=broad-except except Exception as e: logging.fatal('Error resolving credentials for %s: %s', name, e) sys.exit(1) try: logging.info('Pulling manifest list from %r ...', name) with image_list.FromRegistry(name, creds, transport) as img_list: if img_list.exists(): platform = image_list.Platform({ 'architecture': _PROCESSOR_ARCHITECTURE, 'os': _OPERATING_SYSTEM, }) # pytype: disable=wrong-arg-types with img_list.resolve(platform) as default_child: save.fast(default_child, args.directory, threads=_THREADS) return # pytype: enable=wrong-arg-types logging.info('Pulling v2.2 image from %r ...', name) with v2_2_image.FromRegistry(name, creds, transport, accept) as v2_2_img: if v2_2_img.exists(): save.fast(v2_2_img, args.directory, threads=_THREADS) return logging.info('Pulling v2 image from %r ...', name) with v2_image.FromRegistry(name, creds, transport) as v2_img: with v2_compat.V22FromV2(v2_img) as v2_2_img: save.fast(v2_2_img, args.directory, threads=_THREADS) return # pylint: disable=broad-except except Exception as e: logging.fatal('Error pulling and saving image %s: %s', name, e) sys.exit(1)
def main(): logging_setup.DefineCommandLineArgs(parser) args = parser.parse_args() logging_setup.Init(args=args) # retry if error acc to retry plan retry_factory = retry.Factory() retry_factory = retry_factory.WithSourceTransportCallable(httplib2.Http) transport = transport_pool.Http(retry_factory.Build, size=_THREADS) if '@' in args.name: name = docker_name.Digest(args.name) else: name = docker_name.Tag(args.name) # If the user provided a client config directory, instruct the keychain # resolver to use it to look for the docker client config if args.client_config_dir is not None: docker_creds.DefaultKeychain.setCustomConfigDir(args.client_config_dir) # OCI Image Manifest is compatible with Docker Image Manifest Version 2, # Schema 2. We indicate support for both formats by passing both media types # as 'Accept' headers. # # For reference: # OCI: https://github.com/opencontainers/image-spec # Docker: https://docs.docker.com/registry/spec/manifest-v2-2/ accept = docker_http.SUPPORTED_MANIFEST_MIMES # Resolve the appropriate credential to use based on the standard Docker # client logic. try: # check username/paswd match up creds = docker_creds.DefaultKeychain.Resolve(name) # pylint: disable=broad-except except Exception as e: logging.fatal('Error resolving credentials for %s: %s', name, e) sys.exit(1) try: logging.info('Pulling manifest list from %r ...', name) # (image, [(.sha, tar)]) with image_list.FromRegistry(name, creds, transport) as img_list: if img_list.exists(): # populate docker_image_list.Platform object (runtime requirements for an object) # from the provided args # see: docker image manifest list platform = platform_args.FromArgs(args) # pytype: disable=wrong-arg-types with img_list.resolve(platform) as default_child: # save.fast( # create new filesystem (directory) with config files and sha/tars (_save.py) default_child, args.directory, threads=_THREADS, cache_directory=args.cache) return # pytype: enable=wrong-arg-types logging.info('Pulling v2.2 image from %r ...', name) with v2_2_image.FromRegistry(name, creds, transport, accept) as v2_2_img: if v2_2_img.exists(): save.fast(v2_2_img, args.directory, threads=_THREADS, cache_directory=args.cache) return logging.info('Pulling v2 image from %r ...', name) with v2_image.FromRegistry(name, creds, transport) as v2_img: with v2_compat.V22FromV2(v2_img) as v2_2_img: save.fast(v2_2_img, args.directory, threads=_THREADS, cache_directory=args.cache) return # pylint: disable=broad-except except Exception as e: logging.fatal('Error pulling and saving image %s: %s', name, e) sys.exit(1)
def main(): logging_setup.DefineCommandLineArgs(parser) args = parser.parse_args() logging_setup.Init(args=args) if not args.name: logging.fatal('--name is a required arguments.') sys.exit(1) # This library can support push-by-digest, but the likelihood of a user # correctly providing us with the digest without using this library # directly is essentially nil. name = Tag(args.name, args.stamp_info_file) if not args.config and (args.layer or args.digest): logging.fatal( 'Using --layer or --digest requires --config to be specified.') sys.exit(1) if not args.config and not args.tarball: logging.fatal('Either --config or --tarball must be specified.') sys.exit(1) if not args.protocol: logging.fatal('--protocol is a required argument') sys.exit(1) # If config is specified, use that. Otherwise, fallback on reading # the config from the tarball. config = args.config manifest = args.manifest protocol = args.protocol if protocol != 'http' and protocol != 'https': logging.fatal('Protocol should be http or https') if args.config: logging.info('Reading config from %r', args.config) with open(args.config, 'r') as reader: config = reader.read() elif args.tarball: logging.info('Reading config from tarball %r', args.tarball) with v2_2_image.FromTarball(args.tarball) as base: config = base.config_file() if args.manifest: with open(args.manifest, 'r') as reader: manifest = reader.read() if len(args.digest or []) != len(args.layer or []): logging.fatal('--digest and --layer must have matching lengths.') sys.exit(1) retry_factory = retry.Factory() retry_factory = retry_factory.WithSourceTransportCallable(httplib2.Http) transport = transport_pool.Http(retry_factory.Build, size=_THREADS) logging.info('Loading v2.2 image from disk ...') with v2_2_image.FromDisk(config, list(zip(args.digest or [], args.layer or [])), legacy_base=args.tarball, foreign_layers_manifest=manifest) as v2_2_img: # Resolve the appropriate credential to use based on the standard Docker # client logic. try: creds = docker_creds.DefaultKeychain.Resolve(name) # pylint: disable=broad-except except Exception as e: logging.fatal('Error resolving credentials for %s: %s', name, e) sys.exit(1) try: with docker_session.Push(protocol, name, creds, transport, threads=_THREADS) as session: logging.info('Starting upload ...') if args.oci: with oci_compat.OCIFromV22(v2_2_img) as oci_img: session.upload(oci_img) digest = oci_img.digest() else: session.upload(v2_2_img) digest = v2_2_img.digest() print(('{name} was published with digest: {digest}'.format( name=name, digest=digest))) # pylint: disable=broad-except except Exception as e: logging.fatal('Error publishing %s: %s', name, e) sys.exit(1)