-
Notifications
You must be signed in to change notification settings - Fork 1.9k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Add support for device-code oauth login #5244
Changes from all commits
0bfb1e5
e7dd302
fe1a817
a7bf65b
4ed0c6c
bdf5e4a
0bac5a7
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -10,6 +10,7 @@ import ( | |
|
||
"github.com/docker/cli/cli/config/credentials" | ||
"github.com/docker/cli/cli/config/types" | ||
"github.com/docker/cli/cli/internal/oauth/manager" | ||
"github.com/pkg/errors" | ||
"github.com/sirupsen/logrus" | ||
) | ||
|
@@ -254,10 +255,13 @@ func decodeAuth(authStr string) (string, string, error) { | |
// GetCredentialsStore returns a new credentials store from the settings in the | ||
// configuration file | ||
func (configFile *ConfigFile) GetCredentialsStore(registryHostname string) credentials.Store { | ||
var credsStore credentials.Store | ||
if helper := getConfiguredCredentialStore(configFile, registryHostname); helper != "" { | ||
return newNativeStore(configFile, helper) | ||
credsStore = newNativeStore(configFile, helper) | ||
} else { | ||
credsStore = credentials.NewFileStore(configFile) | ||
} | ||
return credentials.NewFileStore(configFile) | ||
return credentials.NewOAuthStore(credsStore, manager.NewManager()) | ||
} | ||
Comment on lines
257
to
265
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. This is not something new, but I think your PR makes it more apparent, and ... maybe I'm rambling; I need to have a closer look; I'm somewhat starting to consider if constructing these stores should happen here, or if they should be constructed when initialising the configfile. Basically; I need to look where this code is used; it may be imported elsewhere, which can be in code that's "non-interactive" (say k8s); for those, getting credentials through the OAuth flow isn't an option. So I'm thinking if whether or not to use the interactive flow is something that must be set when constructing all of this 🤔 There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
True, but as you said, it's not different/new here. With the "old" flow, if there are no credentials, we also can't prompt the user to input them if running non-interactive. And if the user does have "oauth" credentials stored, even in a non-interactive environment, we want the oauth codepath to be executed so that the CLI can use the refresh token to fetch a fresh access token before returning them to whoever is calling it, right? Basically, what setting this when initializing let us do/decide that we can't already? |
||
|
||
// var for unit testing. | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thinking now; instead of
oauthStore
(oauthStore.Get()
etc) checking forif serverAddress != defaultRegistry {
, should that be handled here instead; i.e. along these lines;Alternatively, we could have a way to set some helper to do this; that way we can keep the implementation out of here, and have some way to set "how to construct a helper")
I wish we hadn't conflated the ConfigFile type (for serialising) with the ConfigFile functionality (saving, loading, manipulating) that much though. We need to look if we can get out of that at some point.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Hmm, I find it easier to reason about if we have a single point managing both. Otherwise, if someone does
GetCredentialsStore("some-other-registry").GetAll()
they're going to get theaccess-token
andrefresh-token
specific keys that we shouldn't leak out/callers shouldn't concern themselves with. There might be other things that the wrapper does that should be abstracted away by the wrapper.