From a3cbc701474dc7b48d80f78a1f93604c85b7672d Mon Sep 17 00:00:00 2001 From: Daniel Nephin Date: Wed, 21 Jun 2017 17:20:49 -0400 Subject: [PATCH] Move credential getting functions to the ConfigFile. Signed-off-by: Daniel Nephin --- cli/command/cli.go | 52 -------------------------------- cli/command/image/build.go | 9 +++--- cli/command/image/cmd.go | 3 +- cli/command/image/pull_test.go | 9 ++++-- cli/command/image/push_test.go | 11 +++++-- cli/command/registry.go | 4 +-- cli/command/registry/login.go | 2 +- cli/command/registry/logout.go | 2 +- cli/config/config.go | 8 ++--- cli/config/configfile/file.go | 54 ++++++++++++++++++++++++++++++++++ cli/internal/test/cli.go | 8 ----- 11 files changed, 83 insertions(+), 79 deletions(-) diff --git a/cli/command/cli.go b/cli/command/cli.go index 110d242655..885859abc9 100644 --- a/cli/command/cli.go +++ b/cli/command/cli.go @@ -9,11 +9,9 @@ import ( "github.com/docker/cli/cli" cliconfig "github.com/docker/cli/cli/config" "github.com/docker/cli/cli/config/configfile" - "github.com/docker/cli/cli/config/credentials" cliflags "github.com/docker/cli/cli/flags" dopts "github.com/docker/cli/opts" "github.com/docker/docker/api" - "github.com/docker/docker/api/types" "github.com/docker/docker/client" "github.com/docker/go-connections/sockets" "github.com/docker/go-connections/tlsconfig" @@ -38,7 +36,6 @@ type Cli interface { In() *InStream SetIn(in *InStream) ConfigFile() *configfile.ConfigFile - CredentialsStore(serverAddress string) credentials.Store } // DockerCli is an instance the docker command line client. @@ -103,55 +100,6 @@ func (cli *DockerCli) ServerInfo() ServerInfo { return cli.server } -// GetAllCredentials returns all of the credentials stored in all of the -// configured credential stores. -func (cli *DockerCli) GetAllCredentials() (map[string]types.AuthConfig, error) { - auths := make(map[string]types.AuthConfig) - for registry := range cli.configFile.CredentialHelpers { - helper := cli.CredentialsStore(registry) - newAuths, err := helper.GetAll() - if err != nil { - return nil, err - } - addAll(auths, newAuths) - } - defaultStore := cli.CredentialsStore("") - newAuths, err := defaultStore.GetAll() - if err != nil { - return nil, err - } - addAll(auths, newAuths) - return auths, nil -} - -func addAll(to, from map[string]types.AuthConfig) { - for reg, ac := range from { - to[reg] = ac - } -} - -// CredentialsStore returns a new credentials store based -// on the settings provided in the configuration file. Empty string returns -// the default credential store. -func (cli *DockerCli) CredentialsStore(serverAddress string) credentials.Store { - if helper := getConfiguredCredentialStore(cli.configFile, serverAddress); helper != "" { - return credentials.NewNativeStore(cli.configFile, helper) - } - return credentials.NewFileStore(cli.configFile) -} - -// getConfiguredCredentialStore returns the credential helper configured for the -// given registry, the default credsStore, or the empty string if neither are -// configured. -func getConfiguredCredentialStore(c *configfile.ConfigFile, serverAddress string) string { - if c.CredentialHelpers != nil && serverAddress != "" { - if helper, exists := c.CredentialHelpers[serverAddress]; exists { - return helper - } - } - return c.CredentialsStore -} - // Initialize the dockerCli runs initialization that must happen after command // line flags are parsed. func (cli *DockerCli) Initialize(opts *cliflags.ClientOptions) error { diff --git a/cli/command/image/build.go b/cli/command/image/build.go index a05970b8b0..3d595e0393 100644 --- a/cli/command/image/build.go +++ b/cli/command/image/build.go @@ -78,7 +78,7 @@ func (o buildOptions) contextFromStdin() bool { } // NewBuildCommand creates a new `docker build` command -func NewBuildCommand(dockerCli *command.DockerCli) *cobra.Command { +func NewBuildCommand(dockerCli command.Cli) *cobra.Command { ulimits := make(map[string]*units.Ulimit) options := buildOptions{ tags: opts.NewListOpts(validateTag), @@ -159,7 +159,7 @@ func (out *lastProgressOutput) WriteProgress(prog progress.Progress) error { } // nolint: gocyclo -func runBuild(dockerCli *command.DockerCli, options buildOptions) error { +func runBuild(dockerCli command.Cli, options buildOptions) error { var ( buildCtx io.ReadCloser dockerfileCtx io.ReadCloser @@ -336,7 +336,8 @@ func runBuild(dockerCli *command.DockerCli, options buildOptions) error { body = buildCtx } - authConfigs, _ := dockerCli.GetAllCredentials() + configFile := dockerCli.ConfigFile() + authConfigs, _ := configFile.GetAllCredentials() buildOptions := types.ImageBuildOptions{ Memory: options.memory.Value(), MemorySwap: options.memorySwap.Value(), @@ -356,7 +357,7 @@ func runBuild(dockerCli *command.DockerCli, options buildOptions) error { Dockerfile: relDockerfile, ShmSize: options.shmSize.Value(), Ulimits: options.ulimits.GetList(), - BuildArgs: dockerCli.ConfigFile().ParseProxyConfig(dockerCli.Client().DaemonHost(), options.buildArgs.GetAll()), + BuildArgs: configFile.ParseProxyConfig(dockerCli.Client().DaemonHost(), options.buildArgs.GetAll()), AuthConfigs: authConfigs, Labels: opts.ConvertKVStringsToMap(options.labels.GetAll()), CacheFrom: options.cacheFrom, diff --git a/cli/command/image/cmd.go b/cli/command/image/cmd.go index 10357fcfd8..a12bf3395b 100644 --- a/cli/command/image/cmd.go +++ b/cli/command/image/cmd.go @@ -8,8 +8,7 @@ import ( ) // NewImageCommand returns a cobra command for `image` subcommands -// nolint: interfacer -func NewImageCommand(dockerCli *command.DockerCli) *cobra.Command { +func NewImageCommand(dockerCli command.Cli) *cobra.Command { cmd := &cobra.Command{ Use: "image", Short: "Manage images", diff --git a/cli/command/image/pull_test.go b/cli/command/image/pull_test.go index d72531b768..731c774a1c 100644 --- a/cli/command/image/pull_test.go +++ b/cli/command/image/pull_test.go @@ -6,6 +6,7 @@ import ( "io/ioutil" "testing" + "github.com/docker/cli/cli/config/configfile" "github.com/docker/cli/cli/internal/test" "github.com/docker/docker/pkg/testutil" "github.com/docker/docker/pkg/testutil/golden" @@ -41,7 +42,9 @@ func TestNewPullCommandErrors(t *testing.T) { } for _, tc := range testCases { buf := new(bytes.Buffer) - cmd := NewPullCommand(test.NewFakeCli(&fakeClient{}, buf)) + cli := test.NewFakeCli(&fakeClient{}, buf) + cli.SetConfigfile(configfile.NewConfigFile("filename")) + cmd := NewPullCommand(cli) cmd.SetOutput(ioutil.Discard) cmd.SetArgs(tc.args) testutil.ErrorContains(t, cmd.Execute(), tc.expectedError) @@ -64,7 +67,9 @@ func TestNewPullCommandSuccess(t *testing.T) { } for _, tc := range testCases { buf := new(bytes.Buffer) - cmd := NewPullCommand(test.NewFakeCli(&fakeClient{}, buf)) + cli := test.NewFakeCli(&fakeClient{}, buf) + cli.SetConfigfile(configfile.NewConfigFile("filename")) + cmd := NewPullCommand(cli) cmd.SetOutput(ioutil.Discard) cmd.SetArgs(tc.args) err := cmd.Execute() diff --git a/cli/command/image/push_test.go b/cli/command/image/push_test.go index 559b1b89c3..f02e0407d6 100644 --- a/cli/command/image/push_test.go +++ b/cli/command/image/push_test.go @@ -7,6 +7,7 @@ import ( "strings" "testing" + "github.com/docker/cli/cli/config/configfile" "github.com/docker/cli/cli/internal/test" "github.com/docker/docker/api/types" "github.com/docker/docker/pkg/testutil" @@ -47,7 +48,9 @@ func TestNewPushCommandErrors(t *testing.T) { } for _, tc := range testCases { buf := new(bytes.Buffer) - cmd := NewPushCommand(test.NewFakeCli(&fakeClient{imagePushFunc: tc.imagePushFunc}, buf)) + cli := test.NewFakeCli(&fakeClient{imagePushFunc: tc.imagePushFunc}, buf) + cli.SetConfigfile(configfile.NewConfigFile("filename")) + cmd := NewPushCommand(cli) cmd.SetOutput(ioutil.Discard) cmd.SetArgs(tc.args) testutil.ErrorContains(t, cmd.Execute(), tc.expectedError) @@ -66,11 +69,13 @@ func TestNewPushCommandSuccess(t *testing.T) { } for _, tc := range testCases { buf := new(bytes.Buffer) - cmd := NewPushCommand(test.NewFakeCli(&fakeClient{ + cli := test.NewFakeCli(&fakeClient{ imagePushFunc: func(ref string, options types.ImagePushOptions) (io.ReadCloser, error) { return ioutil.NopCloser(strings.NewReader("")), nil }, - }, buf)) + }, buf) + cli.SetConfigfile(configfile.NewConfigFile("filename")) + cmd := NewPushCommand(cli) cmd.SetOutput(ioutil.Discard) cmd.SetArgs(tc.args) assert.NoError(t, cmd.Execute()) diff --git a/cli/command/registry.go b/cli/command/registry.go index 802b3a4b83..f3958d8a46 100644 --- a/cli/command/registry.go +++ b/cli/command/registry.go @@ -70,7 +70,7 @@ func ResolveAuthConfig(ctx context.Context, cli Cli, index *registrytypes.IndexI configKey = ElectAuthServer(ctx, cli) } - a, _ := cli.CredentialsStore(configKey).Get(configKey) + a, _ := cli.ConfigFile().GetAuthConfig(configKey) return a } @@ -85,7 +85,7 @@ func ConfigureAuth(cli Cli, flUser, flPassword, serverAddress string, isDefaultR serverAddress = registry.ConvertToHostname(serverAddress) } - authconfig, err := cli.CredentialsStore(serverAddress).Get(serverAddress) + authconfig, err := cli.ConfigFile().GetAuthConfig(serverAddress) if err != nil { return authconfig, err } diff --git a/cli/command/registry/login.go b/cli/command/registry/login.go index ba1b133054..4ffca2bed2 100644 --- a/cli/command/registry/login.go +++ b/cli/command/registry/login.go @@ -71,7 +71,7 @@ func runLogin(dockerCli command.Cli, opts loginOptions) error { authConfig.Password = "" authConfig.IdentityToken = response.IdentityToken } - if err := dockerCli.CredentialsStore(serverAddress).Store(authConfig); err != nil { + if err := dockerCli.ConfigFile().GetCredentialsStore(serverAddress).Store(authConfig); err != nil { return errors.Errorf("Error saving credentials: %v", err) } diff --git a/cli/command/registry/logout.go b/cli/command/registry/logout.go index d241df4cf0..cce626e58a 100644 --- a/cli/command/registry/logout.go +++ b/cli/command/registry/logout.go @@ -68,7 +68,7 @@ func runLogout(dockerCli command.Cli, serverAddress string) error { fmt.Fprintf(dockerCli.Out(), "Removing login credentials for %s\n", hostnameAddress) for _, r := range regsToLogout { - if err := dockerCli.CredentialsStore(r).Erase(r); err != nil { + if err := dockerCli.ConfigFile().GetCredentialsStore(r).Erase(r); err != nil { fmt.Fprintf(dockerCli.Err(), "WARNING: could not erase credentials: %v\n", err) } } diff --git a/cli/config/config.go b/cli/config/config.go index ce296a6b13..b054dc49fa 100644 --- a/cli/config/config.go +++ b/cli/config/config.go @@ -114,10 +114,10 @@ func Load(configDir string) (*configfile.ConfigFile, error) { // LoadDefaultConfigFile attempts to load the default config file and returns // an initialized ConfigFile struct if none is found. -func LoadDefaultConfigFile(err io.Writer) *configfile.ConfigFile { - configFile, e := Load(Dir()) - if e != nil { - fmt.Fprintf(err, "WARNING: Error loading config file:%v\n", e) +func LoadDefaultConfigFile(stderr io.Writer) *configfile.ConfigFile { + configFile, err := Load(Dir()) + if err != nil { + fmt.Fprintf(stderr, "WARNING: Error loading config file: %v\n", err) } if !configFile.ContainsAuth() { configFile.CredentialsStore = credentials.DetectDefaultStore(configFile.CredentialsStore) diff --git a/cli/config/configfile/file.go b/cli/config/configfile/file.go index 0be6e70b63..d599cc5aa9 100644 --- a/cli/config/configfile/file.go +++ b/cli/config/configfile/file.go @@ -9,6 +9,7 @@ import ( "path/filepath" "strings" + "github.com/docker/cli/cli/config/credentials" "github.com/docker/cli/opts" "github.com/docker/docker/api/types" "github.com/pkg/errors" @@ -245,3 +246,56 @@ func decodeAuth(authStr string) (string, string, error) { password := strings.Trim(arr[1], "\x00") return arr[0], password, nil } + +// GetCredentialsStore returns a new credentials store from the settings in the +// configuration file +func (configFile *ConfigFile) GetCredentialsStore(serverAddress string) credentials.Store { + if helper := getConfiguredCredentialStore(configFile, serverAddress); helper != "" { + return credentials.NewNativeStore(configFile, helper) + } + return credentials.NewFileStore(configFile) +} + +// GetAuthConfig for a repository from the credential store +func (configFile *ConfigFile) GetAuthConfig(serverAddress string) (types.AuthConfig, error) { + return configFile.GetCredentialsStore(serverAddress).Get(serverAddress) +} + +// getConfiguredCredentialStore returns the credential helper configured for the +// given registry, the default credsStore, or the empty string if neither are +// configured. +func getConfiguredCredentialStore(c *ConfigFile, serverAddress string) string { + if c.CredentialHelpers != nil && serverAddress != "" { + if helper, exists := c.CredentialHelpers[serverAddress]; exists { + return helper + } + } + return c.CredentialsStore +} + +// GetAllCredentials returns all of the credentials stored in all of the +// configured credential stores. +func (configFile *ConfigFile) GetAllCredentials() (map[string]types.AuthConfig, error) { + auths := make(map[string]types.AuthConfig) + addAll := func(from map[string]types.AuthConfig) { + for reg, ac := range from { + auths[reg] = ac + } + } + + for registry := range configFile.CredentialHelpers { + helper := configFile.GetCredentialsStore(registry) + newAuths, err := helper.GetAll() + if err != nil { + return nil, err + } + addAll(newAuths) + } + defaultStore := configFile.GetCredentialsStore("") + newAuths, err := defaultStore.GetAll() + if err != nil { + return nil, err + } + addAll(newAuths) + return auths, nil +} diff --git a/cli/internal/test/cli.go b/cli/internal/test/cli.go index f0f75f7bd5..fa77a86a31 100644 --- a/cli/internal/test/cli.go +++ b/cli/internal/test/cli.go @@ -71,11 +71,3 @@ func (c *FakeCli) In() *command.InStream { func (c *FakeCli) ConfigFile() *configfile.ConfigFile { return c.configfile } - -// CredentialsStore returns the fake store the cli will use -func (c *FakeCli) CredentialsStore(serverAddress string) credentials.Store { - if c.store == nil { - c.store = NewFakeStore() - } - return c.store -}