-
Notifications
You must be signed in to change notification settings - Fork 41.1k
Add support for Docker's credential stores and helpers #45269
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
Conversation
7e7684d
to
0990c9a
Compare
This commit includes Docker CLI default authentication, leveraging credential helpers, the credential store, and static credentials. Previously, empty credentials were used by default. With this commit, a DefaultDockerRegistryAuthentication is introduced. It reads the Docker configuration file and, based on its contents, determines the appropriate authentication details for the requested ImageReference Signed-off-by: Dmytro Nosan <dimanosan@gmail.com>
@philwebb |
Thanks, I've started and I'm hoping to finish something before RC1 but it's going to be tight :) |
Update `DockerConfigurationMetadata` with support for `credsStore`, `credHelpers` and `auth` sections. These values will be required to support credential helper based authentication. See gh-45269 Signed-off-by: Dmytro Nosan <dimanosan@gmail.com>
Add `DockerRegistryAuthentication` implementation that uses standard Docker config to authenticate requests. Prior to this commit, we only supported username/password and token based authentication. This commit allows authentication based on the contents of the Docker configuration file, including support for executing credential helpers. See gh-45269 Signed-off-by: Dmytro Nosan <dimanosan@gmail.com> Co-authored-by: Phillip Webb <phil.webb@broadcom.com>
Update the Maven and Gradle plugins to make use of the new Docker configuration authentication support. See gh-45269 Signed-off-by: Dmytro Nosan <dimanosan@gmail.com> Co-authored-by: Phillip Webb <phil.webb@broadcom.com>
Thanks very very very much @nosan! This one was very timely and I'm super glad to get it into RC1. I've did a little work on refactoring some of the platform code then I've rebased and split up your PR into more granular commits. Some of the PR was harder to apply due to my refactoring so I've combined a bit of your original PR with some updates that I made and made a single commit with us both as authors. I hope that's OK. For the TODOs:
I've tested things manually on both Mac and Windows and things all seem to work very well. Thanks again for the PR! |
Thank you so much for taking the time to include this in 3.5.0! That is awesome!
I'm not entirely sure it should align with Testcontainers. I tested the Docker CLI with an empty helper, and it appears that an empty helper takes precedence over the credential store. The algorithm should be as follows:
I believe Spring Boot should follow the same behavior as the Docker CLI to avoid inconsistencies between the two. Users are more likely to compare Spring Boot's approach to the Docker CLI rather than Testcontainers. For this reason, I used the Docker CLI as the reference implementation. |
That would be this logic I guess in the updated code? Is the error in using the |
Nothing, Docker CLI treats it as a helper.
This should be: String name = this.dockerConfig.getCredHelpers().getOrDefault(serverUrl, this.dockerConfig.getCredsStore()); to align with Go code from Docker CLI: func getConfiguredCredentialStore(c *ConfigFile, registryHostname string) string {
if c.CredentialHelpers != nil && registryHostname != "" {
if helper, exists := c.CredentialHelpers[registryHostname]; exists {
return helper
}
}
return c.CredentialsStore
} |
Thanks, hopefully fixed in 79f7529 |
Thanks, @philwebb //Builder.ImageFetcher
String authHeader = authHeader(this.registryAuthentication, reference);
Assert.state(authHeader == null || reference.getDomain().equals(this.domain),
() -> String.format("%s '%s' must be pulled from the '%s' authenticated registry",
StringUtils.capitalize(type.getDescription()), reference, this.domain));
If someone tries to use a BUILDER image from a public registry and a RUNNER image from a private registry both with the default authentication, an exception is thrown because the domains are different. My understanding is that this check was originally added to ensure the credentials provided by the user are consistent for both the builder and runner images. With the new configuration strategy, this is no longer valid as the credentials can now differ. |
Yes, I just hit that one as well as a bunch of test failures. I really messed up the merge of this one 😭! I'm trying to fix it up now. |
Attempt to fix a few issues that were accidentally introduced by missing some code from the original pull-request. See gh-45269
I don't think so! You have done an incredible piece of work in such a short time! That is amazing. I should have provided more information about that PR to make it much easier to review, |
I left TODO in
DefaultDockerRegistryAuthentication
for consideration.I didn't have time to update the documentation.See #44633