@@ -25,7 +25,6 @@ import (
2525 "github.com/containers/image/v5/transports/alltransports"
2626 "github.com/containers/image/v5/types"
2727 "github.com/containers/storage"
28- digest "github.com/opencontainers/go-digest"
2928 ociSpec "github.com/opencontainers/image-spec/specs-go/v1"
3029 "github.com/sirupsen/logrus"
3130)
@@ -457,52 +456,38 @@ func (r *Runtime) copyFromRegistry(ctx context.Context, ref types.ImageReference
457456 return pulledIDs , nil
458457}
459458
460- // imageIDForManifest() parses the manifest of the copied image and then looks
461- // up the ID of the matching image. There's a small slice of time, between
462- // when we copy the image into local storage and when we go to look for it
463- // using the name that we gave it when we copied it, when the name we wanted to
464- // assign to the image could have been moved, but the image's ID will remain
465- // the same until it is deleted.
466- func (r * Runtime ) imageIDForManifest (manifestBytes []byte , sys * types.SystemContext ) (string , error ) {
467- var imageDigest digest.Digest
468- manifestType := manifest .GuessMIMEType (manifestBytes )
469- if manifest .MIMETypeIsMultiImage (manifestType ) {
470- list , err := manifest .ListFromBlob (manifestBytes , manifestType )
471- if err != nil {
472- return "" , fmt .Errorf ("parsing manifest list: %w" , err )
473- }
474- d , err := list .ChooseInstance (sys )
475- if err != nil {
476- return "" , fmt .Errorf ("choosing instance from manifest list: %w" , err )
477- }
478- imageDigest = d
479- } else {
480- d , err := manifest .Digest (manifestBytes )
481- if err != nil {
482- return "" , errors .New ("digesting manifest" )
483- }
484- imageDigest = d
459+ // imageIDForPulledImage makes a best-effort guess at an image ID for
460+ // a just-pulled image written to destName, where the pull returned manifestBytes
461+ func (r * Runtime ) imageIDForPulledImage (destName reference.Named , manifestBytes []byte ) (string , error ) {
462+ // The caller, copySingleImageFromRegistry, never triggers a multi-platform copy, so manifestBytes
463+ // is always a single-platform manifest instance.
464+ manifestDigest , err := manifest .Digest (manifestBytes )
465+ if err != nil {
466+ return "" , err
485467 }
486- images , err := r . store . ImagesByDigest ( imageDigest )
468+ destDigestedName , err := reference . WithDigest ( reference . TrimNamed ( destName ), manifestDigest )
487469 if err != nil {
488- return "" , fmt . Errorf ( "listing images by manifest digest: %w" , err )
470+ return "" , err
489471 }
490-
491- // If you have additionStores defined and the same image stored in
492- // both storage and additional store, it can be output twice.
493- //
494- // Worse, with zstd:chunked partial pulls, the same image can have several
472+ storeRef , err := storageTransport . Transport . NewStoreReference ( r . store , destDigestedName , "" )
473+ if err != nil {
474+ return "" , err
475+ }
476+ // With zstd:chunked partial pulls, the same image can have several
495477 // different IDs, depending on which layers of the image were pulled using the
496478 // partial pull (are identified by TOC, not by uncompressed digest).
497479 //
498480 // At this point, from just the manifest digest, we can’t tell which image
499481 // is the one that was actually pulled. (They should all have the same contents
500482 // unless the image author is malicious.)
501- // So just return the first matching image ID.
502- if len (images ) == 0 {
503- return "" , fmt .Errorf ("identifying new image by manifest digest: %w" , storage .ErrImageUnknown )
483+ //
484+ // FIXME: To return an accurate value, c/image would need to return the image ID,
485+ // not just manifestBytes.
486+ _ , image , err := storageTransport .ResolveReference (storeRef )
487+ if err != nil {
488+ return "" , fmt .Errorf ("looking up a just-pulled image: %w" , err )
504489 }
505- return images [ 0 ] .ID , nil
490+ return image .ID , nil
506491}
507492
508493// copySingleImageFromRegistry pulls the specified, possibly unqualified, name
@@ -702,7 +687,7 @@ func (r *Runtime) copySingleImageFromRegistry(ctx context.Context, imageName str
702687 }
703688
704689 logrus .Debugf ("Pulled candidate %s successfully" , candidateString )
705- ids , err := r .imageIDForManifest ( manifestBytes , sys )
690+ ids , err := r .imageIDForPulledImage ( candidate . Value , manifestBytes )
706691 if err != nil {
707692 return "" , err
708693 }
0 commit comments