Search in sources :

Example 1 with TimerEventDispatcher

use of com.google.cloud.tools.jib.builder.TimerEventDispatcher in project jib by GoogleContainerTools.

the class PullBaseImageStep method tryMirrors.

@VisibleForTesting
Optional<ImagesAndRegistryClient> tryMirrors(BuildContext buildContext, ProgressEventDispatcher.Factory progressDispatcherFactory) throws LayerCountMismatchException, BadContainerConfigurationFormatException {
    EventHandlers eventHandlers = buildContext.getEventHandlers();
    Collection<Map.Entry<String, String>> mirrorEntries = buildContext.getRegistryMirrors().entries();
    try (ProgressEventDispatcher progressDispatcher1 = progressDispatcherFactory.create("trying mirrors", mirrorEntries.size());
        TimerEventDispatcher ignored1 = new TimerEventDispatcher(eventHandlers, "trying mirrors")) {
        for (Map.Entry<String, String> entry : mirrorEntries) {
            String registry = entry.getKey();
            String mirror = entry.getValue();
            eventHandlers.dispatch(LogEvent.debug("mirror config: " + registry + " --> " + mirror));
            if (!buildContext.getBaseImageConfiguration().getImageRegistry().equals(registry)) {
                progressDispatcher1.dispatchProgress(1);
                continue;
            }
            eventHandlers.dispatch(LogEvent.info("trying mirror " + mirror + " for the base image"));
            try (ProgressEventDispatcher progressDispatcher2 = progressDispatcher1.newChildProducer().create("trying mirror " + mirror, 2)) {
                RegistryClient registryClient = buildContext.newBaseImageRegistryClientFactory(mirror).newRegistryClient();
                List<Image> images = pullPublicImages(registryClient, progressDispatcher2);
                eventHandlers.dispatch(LogEvent.info("pulled manifest from mirror " + mirror));
                return Optional.of(new ImagesAndRegistryClient(images, registryClient));
            } catch (IOException | RegistryException ex) {
                // Ignore errors from this mirror and continue.
                eventHandlers.dispatch(LogEvent.debug("failed to get manifest from mirror " + mirror + ": " + ex.getMessage()));
            }
        }
        return Optional.empty();
    }
}
Also used : ProgressEventDispatcher(com.google.cloud.tools.jib.builder.ProgressEventDispatcher) IOException(java.io.IOException) Image(com.google.cloud.tools.jib.image.Image) RegistryException(com.google.cloud.tools.jib.api.RegistryException) ImagesAndRegistryClient(com.google.cloud.tools.jib.builder.steps.PullBaseImageStep.ImagesAndRegistryClient) TimerEventDispatcher(com.google.cloud.tools.jib.builder.TimerEventDispatcher) ImagesAndRegistryClient(com.google.cloud.tools.jib.builder.steps.PullBaseImageStep.ImagesAndRegistryClient) RegistryClient(com.google.cloud.tools.jib.registry.RegistryClient) EventHandlers(com.google.cloud.tools.jib.event.EventHandlers) Map(java.util.Map) VisibleForTesting(com.google.common.annotations.VisibleForTesting)

Example 2 with TimerEventDispatcher

use of com.google.cloud.tools.jib.builder.TimerEventDispatcher in project jib by GoogleContainerTools.

the class PullBaseImageStep method call.

@Override
public ImagesAndRegistryClient call() throws IOException, RegistryException, LayerPropertyNotFoundException, LayerCountMismatchException, BadContainerConfigurationFormatException, CacheCorruptedException, CredentialRetrievalException {
    EventHandlers eventHandlers = buildContext.getEventHandlers();
    try (ProgressEventDispatcher progressDispatcher = progressDispatcherFactory.create("pulling base image manifest", 4);
        TimerEventDispatcher ignored1 = new TimerEventDispatcher(eventHandlers, DESCRIPTION)) {
        // Skip this step if this is a scratch image
        ImageReference imageReference = buildContext.getBaseImageConfiguration().getImage();
        if (imageReference.isScratch()) {
            Set<Platform> platforms = buildContext.getContainerConfiguration().getPlatforms();
            Verify.verify(!platforms.isEmpty());
            eventHandlers.dispatch(LogEvent.progress("Getting scratch base image..."));
            ImmutableList.Builder<Image> images = ImmutableList.builder();
            for (Platform platform : platforms) {
                Image.Builder imageBuilder = Image.builder(buildContext.getTargetFormat());
                imageBuilder.setArchitecture(platform.getArchitecture()).setOs(platform.getOs());
                images.add(imageBuilder.build());
            }
            return new ImagesAndRegistryClient(images.build(), null);
        }
        eventHandlers.dispatch(LogEvent.progress("Getting manifest for base image " + imageReference + "..."));
        if (buildContext.isOffline()) {
            List<Image> images = getCachedBaseImages();
            if (!images.isEmpty()) {
                return new ImagesAndRegistryClient(images, null);
            }
            throw new IOException("Cannot run Jib in offline mode; " + imageReference + " not found in local Jib cache");
        } else if (imageReference.getDigest().isPresent()) {
            List<Image> images = getCachedBaseImages();
            if (!images.isEmpty()) {
                RegistryClient noAuthRegistryClient = buildContext.newBaseImageRegistryClientFactory().newRegistryClient();
                // https://github.com/GoogleContainerTools/jib/issues/2220
                return new ImagesAndRegistryClient(images, noAuthRegistryClient);
            }
        }
        Optional<ImagesAndRegistryClient> mirrorPull = tryMirrors(buildContext, progressDispatcher.newChildProducer());
        if (mirrorPull.isPresent()) {
            return mirrorPull.get();
        }
        try {
            // First, try with no credentials. This works with public GCR images (but not Docker Hub).
            // TODO: investigate if we should just pass credentials up front. However, this involves
            // some risk. https://github.com/GoogleContainerTools/jib/pull/2200#discussion_r359069026
            // contains some related discussions.
            RegistryClient noAuthRegistryClient = buildContext.newBaseImageRegistryClientFactory().newRegistryClient();
            return new ImagesAndRegistryClient(pullBaseImages(noAuthRegistryClient, progressDispatcher.newChildProducer()), noAuthRegistryClient);
        } catch (RegistryUnauthorizedException ex) {
            eventHandlers.dispatch(LogEvent.lifecycle("The base image requires auth. Trying again for " + imageReference + "..."));
            Credential credential = RegistryCredentialRetriever.getBaseImageCredential(buildContext).orElse(null);
            RegistryClient registryClient = buildContext.newBaseImageRegistryClientFactory().setCredential(credential).newRegistryClient();
            String wwwAuthenticate = ex.getHttpResponseException().getHeaders().getAuthenticate();
            if (wwwAuthenticate != null) {
                eventHandlers.dispatch(LogEvent.debug("WWW-Authenticate for " + imageReference + ": " + wwwAuthenticate));
                registryClient.authPullByWwwAuthenticate(wwwAuthenticate);
                return new ImagesAndRegistryClient(pullBaseImages(registryClient, progressDispatcher.newChildProducer()), registryClient);
            } else {
                // TODO: consider removing this fallback branch.
                if (credential != null && !credential.isOAuth2RefreshToken()) {
                    eventHandlers.dispatch(LogEvent.debug("Trying basic auth as fallback for " + imageReference + "..."));
                    registryClient.configureBasicAuth();
                    try {
                        return new ImagesAndRegistryClient(pullBaseImages(registryClient, progressDispatcher.newChildProducer()), registryClient);
                    } catch (RegistryUnauthorizedException ignored) {
                    // Fall back to try bearer auth.
                    }
                }
                eventHandlers.dispatch(LogEvent.debug("Trying bearer auth as fallback for " + imageReference + "..."));
                registryClient.doPullBearerAuth();
                return new ImagesAndRegistryClient(pullBaseImages(registryClient, progressDispatcher.newChildProducer()), registryClient);
            }
        }
    }
}
Also used : Credential(com.google.cloud.tools.jib.api.Credential) Platform(com.google.cloud.tools.jib.api.buildplan.Platform) ProgressEventDispatcher(com.google.cloud.tools.jib.builder.ProgressEventDispatcher) ImmutableList(com.google.common.collect.ImmutableList) IOException(java.io.IOException) Image(com.google.cloud.tools.jib.image.Image) ImageReference(com.google.cloud.tools.jib.api.ImageReference) ImagesAndRegistryClient(com.google.cloud.tools.jib.builder.steps.PullBaseImageStep.ImagesAndRegistryClient) RegistryUnauthorizedException(com.google.cloud.tools.jib.api.RegistryUnauthorizedException) TimerEventDispatcher(com.google.cloud.tools.jib.builder.TimerEventDispatcher) ArrayList(java.util.ArrayList) ImmutableList(com.google.common.collect.ImmutableList) List(java.util.List) ImagesAndRegistryClient(com.google.cloud.tools.jib.builder.steps.PullBaseImageStep.ImagesAndRegistryClient) RegistryClient(com.google.cloud.tools.jib.registry.RegistryClient) EventHandlers(com.google.cloud.tools.jib.event.EventHandlers)

Example 3 with TimerEventDispatcher

use of com.google.cloud.tools.jib.builder.TimerEventDispatcher in project jib by GoogleContainerTools.

the class PushBlobStep method call.

@Override
public BlobDescriptor call() throws IOException, RegistryException {
    EventHandlers eventHandlers = buildContext.getEventHandlers();
    DescriptorDigest blobDigest = blobDescriptor.getDigest();
    try (ProgressEventDispatcher progressEventDispatcher = progressEventDispatcherFactory.create("pushing blob " + blobDigest, blobDescriptor.getSize());
        TimerEventDispatcher ignored = new TimerEventDispatcher(eventHandlers, DESCRIPTION + blobDescriptor);
        ThrottledAccumulatingConsumer throttledProgressReporter = new ThrottledAccumulatingConsumer(progressEventDispatcher::dispatchProgress)) {
        // check if the BLOB is available
        if (!forcePush && registryClient.checkBlob(blobDigest).isPresent()) {
            eventHandlers.dispatch(LogEvent.info("Skipping push; BLOB already exists on target registry : " + blobDescriptor));
            return blobDescriptor;
        }
        // If base and target images are in the same registry, then use mount/from to try mounting the
        // BLOB from the base image repository to the target image repository and possibly avoid
        // having to push the BLOB. See
        // https://docs.docker.com/registry/spec/api/#cross-repository-blob-mount for details.
        String baseRegistry = buildContext.getBaseImageConfiguration().getImageRegistry();
        String baseRepository = buildContext.getBaseImageConfiguration().getImageRepository();
        String targetRegistry = buildContext.getTargetImageConfiguration().getImageRegistry();
        String sourceRepository = targetRegistry.equals(baseRegistry) ? baseRepository : null;
        registryClient.pushBlob(blobDigest, blob, sourceRepository, throttledProgressReporter);
        return blobDescriptor;
    }
}
Also used : ProgressEventDispatcher(com.google.cloud.tools.jib.builder.ProgressEventDispatcher) DescriptorDigest(com.google.cloud.tools.jib.api.DescriptorDigest) TimerEventDispatcher(com.google.cloud.tools.jib.builder.TimerEventDispatcher) ThrottledAccumulatingConsumer(com.google.cloud.tools.jib.event.progress.ThrottledAccumulatingConsumer) EventHandlers(com.google.cloud.tools.jib.event.EventHandlers)

Example 4 with TimerEventDispatcher

use of com.google.cloud.tools.jib.builder.TimerEventDispatcher in project jib by GoogleContainerTools.

the class PushImageStep method makeListForManifestList.

static ImmutableList<PushImageStep> makeListForManifestList(BuildContext buildContext, ProgressEventDispatcher.Factory progressEventDispatcherFactory, RegistryClient registryClient, ManifestTemplate manifestList, boolean manifestListAlreadyExists) throws IOException {
    Set<String> tags = buildContext.getAllTargetImageTags();
    EventHandlers eventHandlers = buildContext.getEventHandlers();
    try (TimerEventDispatcher ignored = new TimerEventDispatcher(eventHandlers, "Preparing manifest list pushers");
        ProgressEventDispatcher progressEventDispatcher = progressEventDispatcherFactory.create("launching manifest list pushers", tags.size())) {
        boolean singlePlatform = buildContext.getContainerConfiguration().getPlatforms().size() == 1;
        if (singlePlatform) {
            // single image; no need to push a manifest list
            return ImmutableList.of();
        }
        if (JibSystemProperties.skipExistingImages() && manifestListAlreadyExists) {
            eventHandlers.dispatch(LogEvent.info("Skipping pushing manifest list; already exists."));
            return ImmutableList.of();
        }
        DescriptorDigest manifestListDigest = Digests.computeJsonDigest(manifestList);
        return tags.stream().map(tag -> new PushImageStep(buildContext, progressEventDispatcher.newChildProducer(), registryClient, manifestList, tag, manifestListDigest, // return value and type.
        manifestListDigest)).collect(ImmutableList.toImmutableList());
    }
}
Also used : TimerEventDispatcher(com.google.cloud.tools.jib.builder.TimerEventDispatcher) BuildableManifestTemplate(com.google.cloud.tools.jib.image.json.BuildableManifestTemplate) ImageToJsonTranslator(com.google.cloud.tools.jib.image.json.ImageToJsonTranslator) Set(java.util.Set) IOException(java.io.IOException) Callable(java.util.concurrent.Callable) RegistryException(com.google.cloud.tools.jib.api.RegistryException) BuildContext(com.google.cloud.tools.jib.configuration.BuildContext) Collectors(java.util.stream.Collectors) BlobDescriptor(com.google.cloud.tools.jib.blob.BlobDescriptor) DescriptorDigest(com.google.cloud.tools.jib.api.DescriptorDigest) Digests(com.google.cloud.tools.jib.hash.Digests) RegistryClient(com.google.cloud.tools.jib.registry.RegistryClient) LogEvent(com.google.cloud.tools.jib.api.LogEvent) ImmutableList(com.google.common.collect.ImmutableList) JibSystemProperties(com.google.cloud.tools.jib.global.JibSystemProperties) ManifestTemplate(com.google.cloud.tools.jib.image.json.ManifestTemplate) ProgressEventDispatcher(com.google.cloud.tools.jib.builder.ProgressEventDispatcher) EventHandlers(com.google.cloud.tools.jib.event.EventHandlers) Collections(java.util.Collections) Image(com.google.cloud.tools.jib.image.Image) ProgressEventDispatcher(com.google.cloud.tools.jib.builder.ProgressEventDispatcher) DescriptorDigest(com.google.cloud.tools.jib.api.DescriptorDigest) TimerEventDispatcher(com.google.cloud.tools.jib.builder.TimerEventDispatcher) EventHandlers(com.google.cloud.tools.jib.event.EventHandlers)

Example 5 with TimerEventDispatcher

use of com.google.cloud.tools.jib.builder.TimerEventDispatcher in project jib by GoogleContainerTools.

the class PushImageStep method makeList.

static ImmutableList<PushImageStep> makeList(BuildContext buildContext, ProgressEventDispatcher.Factory progressEventDispatcherFactory, RegistryClient registryClient, BlobDescriptor containerConfigurationDigestAndSize, Image builtImage, boolean manifestAlreadyExists) throws IOException {
    // Gets the image manifest to push.
    BuildableManifestTemplate manifestTemplate = new ImageToJsonTranslator(builtImage).getManifestTemplate(buildContext.getTargetFormat(), containerConfigurationDigestAndSize);
    DescriptorDigest manifestDigest = Digests.computeJsonDigest(manifestTemplate);
    Set<String> imageQualifiers = getImageQualifiers(buildContext, builtImage, manifestDigest);
    EventHandlers eventHandlers = buildContext.getEventHandlers();
    try (TimerEventDispatcher ignored = new TimerEventDispatcher(eventHandlers, "Preparing manifest pushers");
        ProgressEventDispatcher progressDispatcher = progressEventDispatcherFactory.create("launching manifest pushers", imageQualifiers.size())) {
        if (JibSystemProperties.skipExistingImages() && manifestAlreadyExists) {
            eventHandlers.dispatch(LogEvent.info("Skipping pushing manifest; already exists."));
            return ImmutableList.of();
        }
        return imageQualifiers.stream().map(qualifier -> new PushImageStep(buildContext, progressDispatcher.newChildProducer(), registryClient, manifestTemplate, qualifier, manifestDigest, containerConfigurationDigestAndSize.getDigest())).collect(ImmutableList.toImmutableList());
    }
}
Also used : TimerEventDispatcher(com.google.cloud.tools.jib.builder.TimerEventDispatcher) BuildableManifestTemplate(com.google.cloud.tools.jib.image.json.BuildableManifestTemplate) ImageToJsonTranslator(com.google.cloud.tools.jib.image.json.ImageToJsonTranslator) Set(java.util.Set) IOException(java.io.IOException) Callable(java.util.concurrent.Callable) RegistryException(com.google.cloud.tools.jib.api.RegistryException) BuildContext(com.google.cloud.tools.jib.configuration.BuildContext) Collectors(java.util.stream.Collectors) BlobDescriptor(com.google.cloud.tools.jib.blob.BlobDescriptor) DescriptorDigest(com.google.cloud.tools.jib.api.DescriptorDigest) Digests(com.google.cloud.tools.jib.hash.Digests) RegistryClient(com.google.cloud.tools.jib.registry.RegistryClient) LogEvent(com.google.cloud.tools.jib.api.LogEvent) ImmutableList(com.google.common.collect.ImmutableList) JibSystemProperties(com.google.cloud.tools.jib.global.JibSystemProperties) ManifestTemplate(com.google.cloud.tools.jib.image.json.ManifestTemplate) ProgressEventDispatcher(com.google.cloud.tools.jib.builder.ProgressEventDispatcher) EventHandlers(com.google.cloud.tools.jib.event.EventHandlers) Collections(java.util.Collections) Image(com.google.cloud.tools.jib.image.Image) ProgressEventDispatcher(com.google.cloud.tools.jib.builder.ProgressEventDispatcher) ImageToJsonTranslator(com.google.cloud.tools.jib.image.json.ImageToJsonTranslator) DescriptorDigest(com.google.cloud.tools.jib.api.DescriptorDigest) TimerEventDispatcher(com.google.cloud.tools.jib.builder.TimerEventDispatcher) EventHandlers(com.google.cloud.tools.jib.event.EventHandlers) BuildableManifestTemplate(com.google.cloud.tools.jib.image.json.BuildableManifestTemplate)

Aggregations

TimerEventDispatcher (com.google.cloud.tools.jib.builder.TimerEventDispatcher)32 ProgressEventDispatcher (com.google.cloud.tools.jib.builder.ProgressEventDispatcher)28 EventHandlers (com.google.cloud.tools.jib.event.EventHandlers)22 DescriptorDigest (com.google.cloud.tools.jib.api.DescriptorDigest)12 Image (com.google.cloud.tools.jib.image.Image)10 RegistryClient (com.google.cloud.tools.jib.registry.RegistryClient)10 IOException (java.io.IOException)10 BlobDescriptor (com.google.cloud.tools.jib.blob.BlobDescriptor)8 RegistryException (com.google.cloud.tools.jib.api.RegistryException)6 BuildContext (com.google.cloud.tools.jib.configuration.BuildContext)6 ImageToJsonTranslator (com.google.cloud.tools.jib.image.json.ImageToJsonTranslator)6 ImmutableList (com.google.common.collect.ImmutableList)6 Credential (com.google.cloud.tools.jib.api.Credential)4 LogEvent (com.google.cloud.tools.jib.api.LogEvent)4 ImagesAndRegistryClient (com.google.cloud.tools.jib.builder.steps.PullBaseImageStep.ImagesAndRegistryClient)4 Cache (com.google.cloud.tools.jib.cache.Cache)4 CachedLayer (com.google.cloud.tools.jib.cache.CachedLayer)4 JibSystemProperties (com.google.cloud.tools.jib.global.JibSystemProperties)4 Digests (com.google.cloud.tools.jib.hash.Digests)4 BuildableManifestTemplate (com.google.cloud.tools.jib.image.json.BuildableManifestTemplate)4