libimage: Fix getDockerAuthConfig() for authentication
- We need to set DockerAuthConfig even if we use of non-IdentityToken credentials. - This function should be failed when there are multiple credential sources, not only `Username` + `Credentials`. Signed-off-by: Toshiki Sonoda <sonoda.toshiki@fujitsu.com>
This commit is contained in:
		
							parent
							
								
									bdaecd9e8d
								
							
						
					
					
						commit
						0bffdb0df5
					
				| 
						 | 
				
			
			@ -167,39 +167,37 @@ var storageAllowedPolicyScopes = signature.PolicyTransportScopes{
 | 
			
		|||
	},
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// getDockerAuthConfig extracts a docker auth config from the CopyOptions.  Returns
 | 
			
		||||
// nil if no credentials are set.
 | 
			
		||||
func (options *CopyOptions) getDockerAuthConfig() (*types.DockerAuthConfig, error) {
 | 
			
		||||
	authConf := &types.DockerAuthConfig{IdentityToken: options.IdentityToken}
 | 
			
		||||
// getDockerAuthConfig extracts a docker auth config. Returns nil if
 | 
			
		||||
// no credentials are set.
 | 
			
		||||
func getDockerAuthConfig(name, passwd, creds, idToken string) (*types.DockerAuthConfig, error) {
 | 
			
		||||
	numCredsSources := 0
 | 
			
		||||
 | 
			
		||||
	if options.Username != "" {
 | 
			
		||||
		if options.Credentials != "" {
 | 
			
		||||
			return nil, errors.New("username/password cannot be used with credentials")
 | 
			
		||||
		}
 | 
			
		||||
		authConf.Username = options.Username
 | 
			
		||||
		authConf.Password = options.Password
 | 
			
		||||
		return authConf, nil
 | 
			
		||||
	if name != "" {
 | 
			
		||||
		numCredsSources++
 | 
			
		||||
	}
 | 
			
		||||
	if creds != "" {
 | 
			
		||||
		name, passwd, _ = strings.Cut(creds, ":")
 | 
			
		||||
		numCredsSources++
 | 
			
		||||
	}
 | 
			
		||||
	if idToken != "" {
 | 
			
		||||
		numCredsSources++
 | 
			
		||||
	}
 | 
			
		||||
	authConf := &types.DockerAuthConfig{
 | 
			
		||||
		Username:      name,
 | 
			
		||||
		Password:      passwd,
 | 
			
		||||
		IdentityToken: idToken,
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	if options.Credentials != "" {
 | 
			
		||||
		split := strings.SplitN(options.Credentials, ":", 2)
 | 
			
		||||
		switch len(split) {
 | 
			
		||||
		case 1:
 | 
			
		||||
			authConf.Username = split[0]
 | 
			
		||||
		default:
 | 
			
		||||
			authConf.Username = split[0]
 | 
			
		||||
			authConf.Password = split[1]
 | 
			
		||||
		}
 | 
			
		||||
	switch numCredsSources {
 | 
			
		||||
	case 0:
 | 
			
		||||
		// Return nil if there is no credential source.
 | 
			
		||||
		return nil, nil
 | 
			
		||||
	case 1:
 | 
			
		||||
		return authConf, nil
 | 
			
		||||
	default:
 | 
			
		||||
		// Cannot use the multiple credential sources.
 | 
			
		||||
		return nil, errors.New("cannot use the multiple credential sources")
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	// We should return nil unless a token was set.  That's especially
 | 
			
		||||
	// useful for Podman's remote API.
 | 
			
		||||
	if options.IdentityToken != "" {
 | 
			
		||||
		return authConf, nil
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	return nil, nil
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// newCopier creates a copier.  Note that fields in options *may* overwrite the
 | 
			
		||||
| 
						 | 
				
			
			@ -237,7 +235,7 @@ func (r *Runtime) newCopier(options *CopyOptions) (*copier, error) {
 | 
			
		|||
		c.systemContext.SignaturePolicyPath = options.SignaturePolicyPath
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	dockerAuthConfig, err := options.getDockerAuthConfig()
 | 
			
		||||
	dockerAuthConfig, err := getDockerAuthConfig(options.Username, options.Password, options.Credentials, options.IdentityToken)
 | 
			
		||||
	if err != nil {
 | 
			
		||||
		return nil, err
 | 
			
		||||
	}
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -2,7 +2,6 @@ package libimage
 | 
			
		|||
 | 
			
		||||
import (
 | 
			
		||||
	"context"
 | 
			
		||||
	"errors"
 | 
			
		||||
	"fmt"
 | 
			
		||||
	"strconv"
 | 
			
		||||
	"strings"
 | 
			
		||||
| 
						 | 
				
			
			@ -219,29 +218,12 @@ func (r *Runtime) searchImageInRegistry(ctx context.Context, term, registry stri
 | 
			
		|||
		sys.DockerCertPath = options.CertDirPath
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	authConf := &types.DockerAuthConfig{IdentityToken: options.IdentityToken}
 | 
			
		||||
	if options.Username != "" {
 | 
			
		||||
		if options.Credentials != "" {
 | 
			
		||||
			return nil, errors.New("username/password cannot be used with credentials")
 | 
			
		||||
		}
 | 
			
		||||
		authConf.Username = options.Username
 | 
			
		||||
		authConf.Password = options.Password
 | 
			
		||||
	dockerAuthConfig, err := getDockerAuthConfig(options.Username, options.Password, options.Credentials, options.IdentityToken)
 | 
			
		||||
	if err != nil {
 | 
			
		||||
		return nil, err
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	if options.Credentials != "" {
 | 
			
		||||
		split := strings.SplitN(options.Credentials, ":", 2)
 | 
			
		||||
		switch len(split) {
 | 
			
		||||
		case 1:
 | 
			
		||||
			authConf.Username = split[0]
 | 
			
		||||
		default:
 | 
			
		||||
			authConf.Username = split[0]
 | 
			
		||||
			authConf.Password = split[1]
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
	// We should set the authConf unless a token was set.  That's especially
 | 
			
		||||
	// useful for Podman's remote API.
 | 
			
		||||
	if options.IdentityToken != "" {
 | 
			
		||||
		sys.DockerAuthConfig = authConf
 | 
			
		||||
	if dockerAuthConfig != nil {
 | 
			
		||||
		sys.DockerAuthConfig = dockerAuthConfig
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	if options.ListTags {
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
		Loading…
	
		Reference in New Issue