mirror of https://github.com/containers/podman.git
				
				
				
			pull: special case all-tags semantics
Supporting the all-tags semantics added some non-trivial code to the pull command which does not make use of `registries.conf` and introduced some regressions such as not adhering to the configured search registries. Speacial case the all-tags flags to let existing users of all-tags continue working while others can work again. This implies that the all-tags pull does not adhere to configured search registries while the default (non-all-tags) pull does. Note that this is a purely symptomaic fix. A final solution should include Buildah and the c/image library to avoid redundant and error-prone code across the projects. Bugzilla: https://bugzilla.redhat.com/show_bug.cgi?id=1701922 Signed-off-by: Valentin Rothberg <rothberg@redhat.com>
This commit is contained in:
		
							parent
							
								
									b4cba6090d
								
							
						
					
					
						commit
						b90a5107e9
					
				|  | @ -46,7 +46,7 @@ func init() { | |||
| 	pullCommand.SetHelpTemplate(HelpTemplate()) | ||||
| 	pullCommand.SetUsageTemplate(UsageTemplate()) | ||||
| 	flags := pullCommand.Flags() | ||||
| 	flags.BoolVar(&pullCommand.AllTags, "all-tags", false, "All tagged images inthe repository will be pulled") | ||||
| 	flags.BoolVar(&pullCommand.AllTags, "all-tags", false, "All tagged images in the repository will be pulled") | ||||
| 	flags.StringVar(&pullCommand.CertDir, "cert-dir", "", "`Pathname` of a directory containing TLS certificates and keys") | ||||
| 	flags.StringVar(&pullCommand.Creds, "creds", "", "`Credentials` (USERNAME:PASSWORD) to use for authenticating to a registry") | ||||
| 	flags.BoolVarP(&pullCommand.Quiet, "quiet", "q", false, "Suppress output information when pulling images") | ||||
|  | @ -94,8 +94,9 @@ func pullCmd(c *cliconfig.PullValues) (retError error) { | |||
| 			return errors.Errorf("tag can't be used with --all-tags") | ||||
| 		} | ||||
| 	} | ||||
| 
 | ||||
| 	ctx := getContext() | ||||
| 	img := args[0] | ||||
| 	imgArg := args[0] | ||||
| 
 | ||||
| 	var registryCreds *types.DockerAuthConfig | ||||
| 
 | ||||
|  | @ -122,68 +123,86 @@ func pullCmd(c *cliconfig.PullValues) (retError error) { | |||
| 		dockerRegistryOptions.DockerInsecureSkipTLSVerify = types.NewOptionalBool(!c.TlsVerify) | ||||
| 	} | ||||
| 
 | ||||
| 	// Possible for docker-archive to have multiple tags, so use LoadFromArchiveReference instead
 | ||||
| 	if strings.HasPrefix(img, dockerarchive.Transport.Name()+":") { | ||||
| 		srcRef, err := alltransports.ParseImageName(img) | ||||
| 	// Special-case for docker-archive which allows multiple tags.
 | ||||
| 	if strings.HasPrefix(imgArg, dockerarchive.Transport.Name()+":") { | ||||
| 		srcRef, err := alltransports.ParseImageName(imgArg) | ||||
| 		if err != nil { | ||||
| 			return errors.Wrapf(err, "error parsing %q", img) | ||||
| 			return errors.Wrapf(err, "error parsing %q", imgArg) | ||||
| 		} | ||||
| 		newImage, err := runtime.LoadFromArchiveReference(getContext(), srcRef, c.SignaturePolicy, writer) | ||||
| 		if err != nil { | ||||
| 			return errors.Wrapf(err, "error pulling image from %q", img) | ||||
| 			return errors.Wrapf(err, "error pulling image from %q", imgArg) | ||||
| 		} | ||||
| 		fmt.Println(newImage[0].ID()) | ||||
| 	} else { | ||||
| 		authfile := getAuthFile(c.String("authfile")) | ||||
| 		spec := img | ||||
| 		systemContext := image.GetSystemContext("", authfile, false) | ||||
| 		srcRef, err := alltransports.ParseImageName(spec) | ||||
| 
 | ||||
| 		return nil | ||||
| 	} | ||||
| 
 | ||||
| 	authfile := getAuthFile(c.String("authfile")) | ||||
| 
 | ||||
| 	// FIXME: the default pull consults the registries.conf's search registries
 | ||||
| 	// while the all-tags pull does not. This behavior must be fixed in the
 | ||||
| 	// future and span across c/buildah, c/image and c/libpod to avoid redundant
 | ||||
| 	// and error prone code.
 | ||||
| 	//
 | ||||
| 	// See https://bugzilla.redhat.com/show_bug.cgi?id=1701922 for background
 | ||||
| 	// information.
 | ||||
| 	if !c.Bool("all-tags") { | ||||
| 		newImage, err := runtime.New(getContext(), imgArg, c.SignaturePolicy, authfile, writer, &dockerRegistryOptions, image.SigningOptions{}, true, nil) | ||||
| 		if err != nil { | ||||
| 			dockerTransport := "docker://" | ||||
| 			logrus.Debugf("error parsing image name %q, trying with transport %q: %v", spec, dockerTransport, err) | ||||
| 			spec = dockerTransport + spec | ||||
| 			srcRef2, err2 := alltransports.ParseImageName(spec) | ||||
| 			if err2 != nil { | ||||
| 				return errors.Wrapf(err2, "error parsing image name %q", img) | ||||
| 			} | ||||
| 			srcRef = srcRef2 | ||||
| 			return errors.Wrapf(err, "error pulling image %q", imgArg) | ||||
| 		} | ||||
| 		var names []string | ||||
| 		if c.Bool("all-tags") { | ||||
| 			if srcRef.DockerReference() == nil { | ||||
| 				return errors.New("Non-docker transport is currently not supported") | ||||
| 			} | ||||
| 			tags, err := docker.GetRepositoryTags(ctx, systemContext, srcRef) | ||||
| 			if err != nil { | ||||
| 				return errors.Wrapf(err, "error getting repository tags") | ||||
| 			} | ||||
| 			for _, tag := range tags { | ||||
| 				name := spec + ":" + tag | ||||
| 				names = append(names, name) | ||||
| 			} | ||||
| 		} else { | ||||
| 			names = append(names, spec) | ||||
| 		fmt.Println(newImage.ID()) | ||||
| 		return nil | ||||
| 	} | ||||
| 
 | ||||
| 	// FIXME: all-tags should use the libpod backend instead of baking its own bread.
 | ||||
| 	spec := imgArg | ||||
| 	systemContext := image.GetSystemContext("", authfile, false) | ||||
| 	srcRef, err := alltransports.ParseImageName(spec) | ||||
| 	if err != nil { | ||||
| 		dockerTransport := "docker://" | ||||
| 		logrus.Debugf("error parsing image name %q, trying with transport %q: %v", spec, dockerTransport, err) | ||||
| 		spec = dockerTransport + spec | ||||
| 		srcRef2, err2 := alltransports.ParseImageName(spec) | ||||
| 		if err2 != nil { | ||||
| 			return errors.Wrapf(err2, "error parsing image name %q", imgArg) | ||||
| 		} | ||||
| 		var foundIDs []string | ||||
| 		foundImage := true | ||||
| 		for _, name := range names { | ||||
| 			newImage, err := runtime.New(getContext(), name, c.String("signature-policy"), authfile, writer, &dockerRegistryOptions, image.SigningOptions{}, true, nil) | ||||
| 			if err != nil { | ||||
| 				logrus.Errorf("error pulling image %q", name) | ||||
| 				foundImage = false | ||||
| 				continue | ||||
| 			} | ||||
| 			foundIDs = append(foundIDs, newImage.ID()) | ||||
| 		srcRef = srcRef2 | ||||
| 	} | ||||
| 	var names []string | ||||
| 	if srcRef.DockerReference() == nil { | ||||
| 		return errors.New("Non-docker transport is currently not supported") | ||||
| 	} | ||||
| 	tags, err := docker.GetRepositoryTags(ctx, systemContext, srcRef) | ||||
| 	if err != nil { | ||||
| 		return errors.Wrapf(err, "error getting repository tags") | ||||
| 	} | ||||
| 	for _, tag := range tags { | ||||
| 		name := spec + ":" + tag | ||||
| 		names = append(names, name) | ||||
| 	} | ||||
| 
 | ||||
| 	var foundIDs []string | ||||
| 	foundImage := true | ||||
| 	for _, name := range names { | ||||
| 		newImage, err := runtime.New(getContext(), name, c.String("signature-policy"), authfile, writer, &dockerRegistryOptions, image.SigningOptions{}, true, nil) | ||||
| 		if err != nil { | ||||
| 			logrus.Errorf("error pulling image %q", name) | ||||
| 			foundImage = false | ||||
| 			continue | ||||
| 		} | ||||
| 		if len(names) == 1 && !foundImage { | ||||
| 			return errors.Wrapf(err, "error pulling image %q", img) | ||||
| 		} | ||||
| 		if len(names) > 1 { | ||||
| 			fmt.Println("Pulled Images:") | ||||
| 		} | ||||
| 		for _, id := range foundIDs { | ||||
| 			fmt.Println(id) | ||||
| 		} | ||||
| 	} // end else if strings.HasPrefix(img, dockerarchive.Transport.Name()+":")
 | ||||
| 		foundIDs = append(foundIDs, newImage.ID()) | ||||
| 	} | ||||
| 	if len(names) == 1 && !foundImage { | ||||
| 		return errors.Wrapf(err, "error pulling image %q", imgArg) | ||||
| 	} | ||||
| 	if len(names) > 1 { | ||||
| 		fmt.Println("Pulled Images:") | ||||
| 	} | ||||
| 	for _, id := range foundIDs { | ||||
| 		fmt.Println(id) | ||||
| 	} | ||||
| 
 | ||||
| 	return nil | ||||
| } | ||||
|  |  | |||
|  | @ -49,6 +49,8 @@ Image stored in local container/storage | |||
| 
 | ||||
| All tagged images in the repository will be pulled. | ||||
| 
 | ||||
| Note: When using the all-tags flag, Podman will not iterate over the search registries in the containers-registries.conf(5) but will always use docker.io for unqualified image names. | ||||
| 
 | ||||
| **--authfile** | ||||
| 
 | ||||
| Path of the authentication file. Default is ${XDG_RUNTIME\_DIR}/containers/auth.json, which is set using `podman login`. | ||||
|  |  | |||
		Loading…
	
		Reference in New Issue