Skip to content

Commit df1d8fe

Browse files
authored
use registry.AuthConfig everywhere possible and deprecated config.AuthConfig (#107)
Signed-off-by: Nicolas De Loof <nicolas.deloof@gmail.com>
1 parent 009435f commit df1d8fe

10 files changed

Lines changed: 112 additions & 133 deletions

File tree

config/auth.go

Lines changed: 6 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,6 @@
11
package config
22

33
import (
4-
"encoding/base64"
5-
"encoding/json"
64
"fmt"
75

86
"github.com/docker/docker/api/types/registry"
@@ -16,7 +14,7 @@ const tokenUsername = "<token>"
1614
// AuthConfigs returns the auth configs for the given images.
1715
// The images slice must contain images that are used in a Dockerfile.
1816
// The returned map is keyed by the registry registry hostname for each image.
19-
func AuthConfigs(images ...string) (map[string]AuthConfig, error) {
17+
func AuthConfigs(images ...string) (map[string]registry.AuthConfig, error) {
2018
cfg, err := Load()
2119
if err != nil {
2220
return nil, fmt.Errorf("load config: %w", err)
@@ -29,31 +27,16 @@ func AuthConfigs(images ...string) (map[string]AuthConfig, error) {
2927
//
3028
// This will use [Load] to read registry auth details from the config.
3129
// If the config doesn't exist, it will attempt to load registry credentials using the default credential helper for the platform.
32-
func AuthConfigForHostname(hostname string) (AuthConfig, error) {
30+
func AuthConfigForHostname(hostname string) (registry.AuthConfig, error) {
3331
cfg, err := Load()
3432
if err != nil {
35-
return AuthConfig{}, fmt.Errorf("load config: %w", err)
33+
return registry.AuthConfig{}, fmt.Errorf("load config: %w", err)
3634
}
3735

3836
return cfg.AuthConfigForHostname(hostname)
3937
}
4038

41-
func (authConfig AuthConfig) EncodeBase64() (string, error) {
42-
jsonAuth, err := json.Marshal(authConfig)
43-
if err != nil {
44-
return "", err
45-
}
46-
return base64.URLEncoding.EncodeToString(jsonAuth), nil
47-
}
48-
49-
func (authConfig AuthConfig) ToRegistryAuthConfig() registry.AuthConfig {
50-
return registry.AuthConfig{
51-
Username: authConfig.Username,
52-
Password: authConfig.Password,
53-
Auth: authConfig.Auth,
54-
Email: "",
55-
ServerAddress: authConfig.ServerAddress,
56-
IdentityToken: authConfig.IdentityToken,
57-
RegistryToken: authConfig.RegistryToken,
58-
}
39+
// EncodeBase64 encodes an AuthConfig into base64.
40+
func EncodeBase64(authConfig registry.AuthConfig) (string, error) {
41+
return registry.EncodeAuthConfig(authConfig)
5942
}

config/auth_test.go

Lines changed: 11 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -10,13 +10,15 @@ import (
1010
"testing"
1111

1212
"github.com/stretchr/testify/require"
13+
14+
"github.com/docker/docker/api/types/registry"
1315
)
1416

1517
func TestDecodeBase64Auth(t *testing.T) {
1618
for _, tc := range base64TestCases() {
17-
t.Run(tc.name, testBase64Case(tc, func() (AuthConfig, error) {
19+
t.Run(tc.name, testBase64Case(tc, func() (registry.AuthConfig, error) {
1820
user, pass, err := decodeBase64Auth(tc.config)
19-
return AuthConfig{
21+
return registry.AuthConfig{
2022
Username: user,
2123
Password: pass,
2224
}, err
@@ -29,11 +31,11 @@ func TestConfig_RegistryCredentialsForHostname(t *testing.T) {
2931
for _, tc := range base64TestCases() {
3032
t.Run(tc.name, func(t *testing.T) {
3133
config := Config{
32-
AuthConfigs: map[string]AuthConfig{
34+
AuthConfigs: map[string]registry.AuthConfig{
3335
"some.domain": tc.config,
3436
},
3537
}
36-
testBase64Case(tc, func() (AuthConfig, error) {
38+
testBase64Case(tc, func() (registry.AuthConfig, error) {
3739
return config.AuthConfigForHostname("some.domain")
3840
})(t)
3941
})
@@ -43,7 +45,7 @@ func TestConfig_RegistryCredentialsForHostname(t *testing.T) {
4345

4446
type base64TestCase struct {
4547
name string
46-
config AuthConfig
48+
config registry.AuthConfig
4749
expUser string
4850
expPass string
4951
expErr bool
@@ -52,19 +54,19 @@ type base64TestCase struct {
5254
func base64TestCases() []base64TestCase {
5355
cases := []base64TestCase{
5456
{name: "empty"},
55-
{name: "not base64", expErr: true, config: AuthConfig{Auth: "not base64"}},
56-
{name: "invalid format", expErr: true, config: AuthConfig{
57+
{name: "not base64", expErr: true, config: registry.AuthConfig{Auth: "not base64"}},
58+
{name: "invalid format", expErr: true, config: registry.AuthConfig{
5759
Auth: base64.StdEncoding.EncodeToString([]byte("invalid format")),
5860
}},
59-
{name: "happy case", expUser: "user", expPass: "pass", config: AuthConfig{
61+
{name: "happy case", expUser: "user", expPass: "pass", config: registry.AuthConfig{
6062
Auth: base64.StdEncoding.EncodeToString([]byte("user:pass")),
6163
}},
6264
}
6365

6466
return cases
6567
}
6668

67-
type testAuthFn func() (AuthConfig, error)
69+
type testAuthFn func() (registry.AuthConfig, error)
6870

6971
func testBase64Case(tc base64TestCase, authFn testAuthFn) func(t *testing.T) {
7072
return func(t *testing.T) {

config/config.go

Lines changed: 18 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -12,14 +12,15 @@ import (
1212
"sync"
1313
"time"
1414

15+
"github.com/docker/docker/api/types/registry"
1516
"github.com/docker/go-sdk/config/auth"
1617
)
1718

1819
var cacheInitMutex sync.Mutex
1920

2021
// authConfigCache holds the caching state for a Config instance
2122
type authConfigCache struct {
22-
entries map[string]AuthConfig
23+
entries map[string]registry.AuthConfig
2324
mutex sync.RWMutex
2425
key string
2526
}
@@ -30,7 +31,7 @@ func (c *Config) clearAuthCache() {
3031
cache.mutex.Lock()
3132
defer cache.mutex.Unlock()
3233

33-
cache.entries = make(map[string]AuthConfig)
34+
cache.entries = make(map[string]registry.AuthConfig)
3435
}
3536

3637
// cacheStats returns statistics about the auth config cache
@@ -72,7 +73,7 @@ func (c *Config) initCache() {
7273
}
7374

7475
newCache := &authConfigCache{
75-
entries: make(map[string]AuthConfig),
76+
entries: make(map[string]registry.AuthConfig),
7677
key: c.generateCacheKey(),
7778
}
7879

@@ -89,7 +90,7 @@ func (c *Config) generateCacheKey() string {
8990
}
9091

9192
// AuthConfigForHostname returns the auth config for the given hostname with caching
92-
func (c *Config) AuthConfigForHostname(hostname string) (AuthConfig, error) {
93+
func (c *Config) AuthConfigForHostname(hostname string) (registry.AuthConfig, error) {
9394
cache := c.getCache()
9495

9596
// Try cache first
@@ -103,7 +104,7 @@ func (c *Config) AuthConfigForHostname(hostname string) (AuthConfig, error) {
103104
// Cache miss - resolve auth config
104105
authConfig, err := c.resolveAuthConfigForHostname(hostname)
105106
if err != nil {
106-
return AuthConfig{}, err
107+
return registry.AuthConfig{}, err
107108
}
108109

109110
// Cache the result
@@ -115,8 +116,8 @@ func (c *Config) AuthConfigForHostname(hostname string) (AuthConfig, error) {
115116
}
116117

117118
// AuthConfigsForImages returns auth configs for multiple images with caching
118-
func (c *Config) AuthConfigsForImages(images []string) (map[string]AuthConfig, error) {
119-
result := make(map[string]AuthConfig)
119+
func (c *Config) AuthConfigsForImages(images []string) (map[string]registry.AuthConfig, error) {
120+
result := make(map[string]registry.AuthConfig)
120121
var errs []error
121122

122123
// Process each image
@@ -143,15 +144,15 @@ func (c *Config) AuthConfigsForImages(images []string) (map[string]AuthConfig, e
143144
}
144145

145146
// AuthConfigForImage returns the auth config for a single image
146-
func (c *Config) AuthConfigForImage(image string) (string, AuthConfig, error) {
147+
func (c *Config) AuthConfigForImage(image string) (string, registry.AuthConfig, error) {
147148
ref, err := auth.ParseImageRef(image)
148149
if err != nil {
149-
return "", AuthConfig{}, fmt.Errorf("parse image ref: %w", err)
150+
return "", registry.AuthConfig{}, fmt.Errorf("parse image ref: %w", err)
150151
}
151152

152153
authConfig, err := c.AuthConfigForHostname(ref.Registry)
153154
if err != nil {
154-
return ref.Registry, AuthConfig{}, err
155+
return ref.Registry, registry.AuthConfig{}, err
155156
}
156157

157158
authConfig.ServerAddress = ref.Registry
@@ -206,7 +207,7 @@ func (c *Config) Save() error {
206207
}
207208

208209
// resolveAuthConfigForHostname performs the actual auth config resolution
209-
func (c *Config) resolveAuthConfigForHostname(hostname string) (AuthConfig, error) {
210+
func (c *Config) resolveAuthConfigForHostname(hostname string) (registry.AuthConfig, error) {
210211
// Normalize Docker registry hostnames
211212
hostname = auth.ResolveRegistryHost(hostname)
212213

@@ -234,19 +235,19 @@ func (c *Config) resolveAuthConfigForHostname(hostname string) (AuthConfig, erro
234235
}
235236

236237
// resolveFromCredentialHelper resolves credentials from a credential helper
237-
func (c *Config) resolveFromCredentialHelper(helper, hostname string) (AuthConfig, error) {
238+
func (c *Config) resolveFromCredentialHelper(helper, hostname string) (registry.AuthConfig, error) {
238239
// Use existing credentialsFromHelper function but adapt to return AuthConfig
239240
credentials, err := credentialsFromHelper(helper, hostname)
240241
if err != nil {
241-
return AuthConfig{}, err
242+
return registry.AuthConfig{}, err
242243
}
243244

244245
return credentials, nil
245246
}
246247

247248
// processStoredAuthConfig processes auth config from stored configuration
248-
func (c *Config) processStoredAuthConfig(stored AuthConfig, hostname string) (AuthConfig, error) {
249-
authConfig := AuthConfig{
249+
func (c *Config) processStoredAuthConfig(stored registry.AuthConfig, hostname string) (registry.AuthConfig, error) {
250+
authConfig := registry.AuthConfig{
250251
Auth: stored.Auth,
251252
IdentityToken: stored.IdentityToken,
252253
Password: stored.Password,
@@ -269,7 +270,7 @@ func (c *Config) processStoredAuthConfig(stored AuthConfig, hostname string) (Au
269270
// Base64 auth case
270271
user, pass, err := decodeBase64Auth(authConfig)
271272
if err != nil {
272-
return AuthConfig{}, fmt.Errorf("decode base64 auth: %w", err)
273+
return registry.AuthConfig{}, fmt.Errorf("decode base64 auth: %w", err)
273274
}
274275
authConfig.Username = user
275276
authConfig.Password = pass
@@ -286,7 +287,7 @@ func (c *Config) processStoredAuthConfig(stored AuthConfig, hostname string) (Au
286287
// It takes the "Auth" filed from AuthConfig and decodes that into a username and password.
287288
//
288289
// If "Auth" is empty, an empty user/pass will be returned, but not an error.
289-
func decodeBase64Auth(auth AuthConfig) (string, string, error) {
290+
func decodeBase64Auth(auth registry.AuthConfig) (string, string, error) {
290291
if auth.Auth == "" {
291292
return "", "", nil
292293
}

config/config_benchmarks_test.go

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,11 +4,13 @@ import (
44
"testing"
55

66
"github.com/stretchr/testify/require"
7+
8+
"github.com/docker/docker/api/types/registry"
79
)
810

911
func BenchmarkAuthConfigCaching(b *testing.B) {
1012
cfg := Config{
11-
AuthConfigs: map[string]AuthConfig{
13+
AuthConfigs: map[string]registry.AuthConfig{
1214
"test.io": {Username: "user", Password: "pass"},
1315
},
1416
}

config/config_test.go

Lines changed: 8 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -7,11 +7,13 @@ import (
77
"testing"
88

99
"github.com/stretchr/testify/require"
10+
11+
"github.com/docker/docker/api/types/registry"
1012
)
1113

1214
func TestConfig_AuthConfigsForImages(t *testing.T) {
1315
config := Config{
14-
AuthConfigs: map[string]AuthConfig{
16+
AuthConfigs: map[string]registry.AuthConfig{
1517
"registry1.io": {Username: "user1", Password: "pass1"},
1618
"registry2.io": {Username: "user2", Password: "pass2"},
1719
},
@@ -35,7 +37,7 @@ func TestConfig_AuthConfigsForImages(t *testing.T) {
3537

3638
func TestConfig_CacheManagement(t *testing.T) {
3739
config := Config{
38-
AuthConfigs: map[string]AuthConfig{
40+
AuthConfigs: map[string]registry.AuthConfig{
3941
"test.io": {Username: "user", Password: "pass"},
4042
},
4143
}
@@ -63,7 +65,7 @@ func TestConfig_CacheManagement(t *testing.T) {
6365

6466
func TestConfig_ConcurrentAccess(t *testing.T) {
6567
config := Config{
66-
AuthConfigs: map[string]AuthConfig{
68+
AuthConfigs: map[string]registry.AuthConfig{
6769
"test.io": {Username: "user", Password: "pass"},
6870
},
6971
}
@@ -87,13 +89,13 @@ func TestConfig_ConcurrentAccess(t *testing.T) {
8789

8890
func TestConfig_CacheKeyGeneration(t *testing.T) {
8991
config1 := Config{
90-
AuthConfigs: map[string]AuthConfig{
92+
AuthConfigs: map[string]registry.AuthConfig{
9193
"test.io": {Username: "user1", Password: "pass1"},
9294
},
9395
}
9496

9597
config2 := Config{
96-
AuthConfigs: map[string]AuthConfig{
98+
AuthConfigs: map[string]registry.AuthConfig{
9799
"test.io": {Username: "user2", Password: "pass2"},
98100
},
99101
}
@@ -119,7 +121,7 @@ func TestConfigSave(t *testing.T) {
119121
c := Config{
120122
filepath: filepath.Join(dockerDir, FileName),
121123
CurrentContext: "test",
122-
AuthConfigs: map[string]AuthConfig{},
124+
AuthConfigs: map[string]registry.AuthConfig{},
123125
}
124126

125127
require.NoError(t, c.Save())

config/credentials_helpers.go

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,8 @@ import (
88
"os/exec"
99
"runtime"
1010
"strings"
11+
12+
"github.com/docker/docker/api/types/registry"
1113
)
1214

1315
// Errors from credential helpers.
@@ -34,8 +36,8 @@ var (
3436
// Hostnames should already be resolved using [ResolveRegistryHost]
3537
//
3638
// If the username string is empty, the password string is an identity token.
37-
func credentialsFromHelper(helper, hostname string) (AuthConfig, error) {
38-
var creds AuthConfig
39+
func credentialsFromHelper(helper, hostname string) (registry.AuthConfig, error) {
40+
var creds registry.AuthConfig
3941
credHelperName := helper
4042
if helper == "" {
4143
helper, helperErr := getCredentialHelper()

0 commit comments

Comments
 (0)