From 7a3b7fba59a9ff9e8756976cf6f55117b1814a63 Mon Sep 17 00:00:00 2001 From: Kohei Tokunaga Date: Thu, 29 Feb 2024 15:26:59 +0900 Subject: [PATCH] Transfer: Registry: Enable to use registry configuration diretory Currently transfer service isn't aware of configurations of hosts directory and ctr's `--hosts-dir` doesn't work. This commit fixes this issue by using `config.ConfigureHosts` instead of `docker.ConfigureDefaultRegistries`. This commit also fixes ctr to use this feature for "--hosts-dir" flag. Signed-off-by: Kohei Tokunaga --- api/next.pb.txt | 7 +++ api/types/transfer/registry.pb.go | 74 +++++++++++++---------- api/types/transfer/registry.proto | 2 +- cmd/ctr/commands/images/pull.go | 5 +- cmd/ctr/commands/images/push.go | 5 +- core/transfer/registry/registry.go | 94 +++++++++++++++++++++--------- 6 files changed, 124 insertions(+), 63 deletions(-) diff --git a/api/next.pb.txt b/api/next.pb.txt index 4e5795c73..5056b4b85 100644 --- a/api/next.pb.txt +++ b/api/next.pb.txt @@ -7461,6 +7461,13 @@ file { type_name: ".containerd.types.transfer.RegistryResolver.HeadersEntry" json_name: "headers" } + field { + name: "host_dir" + number: 3 + label: LABEL_OPTIONAL + type: TYPE_STRING + json_name: "hostDir" + } nested_type { name: "HeadersEntry" field { diff --git a/api/types/transfer/registry.pb.go b/api/types/transfer/registry.pb.go index 891839a13..b2ead984e 100644 --- a/api/types/transfer/registry.pb.go +++ b/api/types/transfer/registry.pb.go @@ -160,6 +160,7 @@ type RegistryResolver struct { AuthStream string `protobuf:"bytes,1,opt,name=auth_stream,json=authStream,proto3" json:"auth_stream,omitempty"` // Headers Headers map[string]string `protobuf:"bytes,2,rep,name=headers,proto3" json:"headers,omitempty" protobuf_key:"bytes,1,opt,name=key,proto3" protobuf_val:"bytes,2,opt,name=value,proto3"` + HostDir string `protobuf:"bytes,3,opt,name=host_dir,json=hostDir,proto3" json:"host_dir,omitempty"` } func (x *RegistryResolver) Reset() { @@ -208,6 +209,13 @@ func (x *RegistryResolver) GetHeaders() map[string]string { return nil } +func (x *RegistryResolver) GetHostDir() string { + if x != nil { + return x.HostDir + } + return "" +} + // AuthRequest is sent as a callback on a stream type AuthRequest struct { state protoimpl.MessageState @@ -364,7 +372,7 @@ var file_github_com_containerd_containerd_api_types_transfer_registry_proto_rawD 0x2b, 0x2e, 0x63, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x64, 0x2e, 0x74, 0x79, 0x70, 0x65, 0x73, 0x2e, 0x74, 0x72, 0x61, 0x6e, 0x73, 0x66, 0x65, 0x72, 0x2e, 0x52, 0x65, 0x67, 0x69, 0x73, 0x74, 0x72, 0x79, 0x52, 0x65, 0x73, 0x6f, 0x6c, 0x76, 0x65, 0x72, 0x52, 0x08, 0x72, 0x65, - 0x73, 0x6f, 0x6c, 0x76, 0x65, 0x72, 0x22, 0xc3, 0x01, 0x0a, 0x10, 0x52, 0x65, 0x67, 0x69, 0x73, + 0x73, 0x6f, 0x6c, 0x76, 0x65, 0x72, 0x22, 0xde, 0x01, 0x0a, 0x10, 0x52, 0x65, 0x67, 0x69, 0x73, 0x74, 0x72, 0x79, 0x52, 0x65, 0x73, 0x6f, 0x6c, 0x76, 0x65, 0x72, 0x12, 0x1f, 0x0a, 0x0b, 0x61, 0x75, 0x74, 0x68, 0x5f, 0x73, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0a, 0x61, 0x75, 0x74, 0x68, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x12, 0x52, 0x0a, 0x07, @@ -373,37 +381,39 @@ var file_github_com_containerd_containerd_api_types_transfer_registry_proto_rawD 0x2e, 0x74, 0x72, 0x61, 0x6e, 0x73, 0x66, 0x65, 0x72, 0x2e, 0x52, 0x65, 0x67, 0x69, 0x73, 0x74, 0x72, 0x79, 0x52, 0x65, 0x73, 0x6f, 0x6c, 0x76, 0x65, 0x72, 0x2e, 0x48, 0x65, 0x61, 0x64, 0x65, 0x72, 0x73, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x52, 0x07, 0x68, 0x65, 0x61, 0x64, 0x65, 0x72, 0x73, - 0x1a, 0x3a, 0x0a, 0x0c, 0x48, 0x65, 0x61, 0x64, 0x65, 0x72, 0x73, 0x45, 0x6e, 0x74, 0x72, 0x79, - 0x12, 0x10, 0x0a, 0x03, 0x6b, 0x65, 0x79, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x03, 0x6b, - 0x65, 0x79, 0x12, 0x14, 0x0a, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, - 0x09, 0x52, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x3a, 0x02, 0x38, 0x01, 0x22, 0x69, 0x0a, 0x0b, - 0x41, 0x75, 0x74, 0x68, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x12, 0x12, 0x0a, 0x04, 0x68, - 0x6f, 0x73, 0x74, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x68, 0x6f, 0x73, 0x74, 0x12, - 0x1c, 0x0a, 0x09, 0x72, 0x65, 0x66, 0x65, 0x72, 0x65, 0x6e, 0x63, 0x65, 0x18, 0x02, 0x20, 0x01, - 0x28, 0x09, 0x52, 0x09, 0x72, 0x65, 0x66, 0x65, 0x72, 0x65, 0x6e, 0x63, 0x65, 0x12, 0x28, 0x0a, - 0x0f, 0x77, 0x77, 0x77, 0x61, 0x75, 0x74, 0x68, 0x65, 0x6e, 0x74, 0x69, 0x63, 0x61, 0x74, 0x65, - 0x18, 0x03, 0x20, 0x03, 0x28, 0x09, 0x52, 0x0f, 0x77, 0x77, 0x77, 0x61, 0x75, 0x74, 0x68, 0x65, - 0x6e, 0x74, 0x69, 0x63, 0x61, 0x74, 0x65, 0x22, 0xbc, 0x01, 0x0a, 0x0c, 0x41, 0x75, 0x74, 0x68, - 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12, 0x3f, 0x0a, 0x08, 0x61, 0x75, 0x74, 0x68, - 0x54, 0x79, 0x70, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0e, 0x32, 0x23, 0x2e, 0x63, 0x6f, 0x6e, - 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x64, 0x2e, 0x74, 0x79, 0x70, 0x65, 0x73, 0x2e, 0x74, 0x72, - 0x61, 0x6e, 0x73, 0x66, 0x65, 0x72, 0x2e, 0x41, 0x75, 0x74, 0x68, 0x54, 0x79, 0x70, 0x65, 0x52, - 0x08, 0x61, 0x75, 0x74, 0x68, 0x54, 0x79, 0x70, 0x65, 0x12, 0x16, 0x0a, 0x06, 0x73, 0x65, 0x63, - 0x72, 0x65, 0x74, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x06, 0x73, 0x65, 0x63, 0x72, 0x65, - 0x74, 0x12, 0x1a, 0x0a, 0x08, 0x75, 0x73, 0x65, 0x72, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x03, 0x20, - 0x01, 0x28, 0x09, 0x52, 0x08, 0x75, 0x73, 0x65, 0x72, 0x6e, 0x61, 0x6d, 0x65, 0x12, 0x37, 0x0a, - 0x09, 0x65, 0x78, 0x70, 0x69, 0x72, 0x65, 0x5f, 0x61, 0x74, 0x18, 0x04, 0x20, 0x01, 0x28, 0x0b, - 0x32, 0x1a, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, - 0x75, 0x66, 0x2e, 0x54, 0x69, 0x6d, 0x65, 0x73, 0x74, 0x61, 0x6d, 0x70, 0x52, 0x08, 0x65, 0x78, - 0x70, 0x69, 0x72, 0x65, 0x41, 0x74, 0x2a, 0x3e, 0x0a, 0x08, 0x41, 0x75, 0x74, 0x68, 0x54, 0x79, - 0x70, 0x65, 0x12, 0x08, 0x0a, 0x04, 0x4e, 0x4f, 0x4e, 0x45, 0x10, 0x00, 0x12, 0x0f, 0x0a, 0x0b, - 0x43, 0x52, 0x45, 0x44, 0x45, 0x4e, 0x54, 0x49, 0x41, 0x4c, 0x53, 0x10, 0x01, 0x12, 0x0b, 0x0a, - 0x07, 0x52, 0x45, 0x46, 0x52, 0x45, 0x53, 0x48, 0x10, 0x02, 0x12, 0x0a, 0x0a, 0x06, 0x48, 0x45, - 0x41, 0x44, 0x45, 0x52, 0x10, 0x03, 0x42, 0x38, 0x5a, 0x36, 0x67, 0x69, 0x74, 0x68, 0x75, 0x62, - 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x63, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x64, 0x2f, - 0x63, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x64, 0x2f, 0x76, 0x32, 0x2f, 0x61, 0x70, - 0x69, 0x2f, 0x74, 0x79, 0x70, 0x65, 0x73, 0x2f, 0x74, 0x72, 0x61, 0x6e, 0x73, 0x66, 0x65, 0x72, - 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33, + 0x12, 0x19, 0x0a, 0x08, 0x68, 0x6f, 0x73, 0x74, 0x5f, 0x64, 0x69, 0x72, 0x18, 0x03, 0x20, 0x01, + 0x28, 0x09, 0x52, 0x07, 0x68, 0x6f, 0x73, 0x74, 0x44, 0x69, 0x72, 0x1a, 0x3a, 0x0a, 0x0c, 0x48, + 0x65, 0x61, 0x64, 0x65, 0x72, 0x73, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x12, 0x10, 0x0a, 0x03, 0x6b, + 0x65, 0x79, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x03, 0x6b, 0x65, 0x79, 0x12, 0x14, 0x0a, + 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x05, 0x76, 0x61, + 0x6c, 0x75, 0x65, 0x3a, 0x02, 0x38, 0x01, 0x22, 0x69, 0x0a, 0x0b, 0x41, 0x75, 0x74, 0x68, 0x52, + 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x12, 0x12, 0x0a, 0x04, 0x68, 0x6f, 0x73, 0x74, 0x18, 0x01, + 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x68, 0x6f, 0x73, 0x74, 0x12, 0x1c, 0x0a, 0x09, 0x72, 0x65, + 0x66, 0x65, 0x72, 0x65, 0x6e, 0x63, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x09, 0x72, + 0x65, 0x66, 0x65, 0x72, 0x65, 0x6e, 0x63, 0x65, 0x12, 0x28, 0x0a, 0x0f, 0x77, 0x77, 0x77, 0x61, + 0x75, 0x74, 0x68, 0x65, 0x6e, 0x74, 0x69, 0x63, 0x61, 0x74, 0x65, 0x18, 0x03, 0x20, 0x03, 0x28, + 0x09, 0x52, 0x0f, 0x77, 0x77, 0x77, 0x61, 0x75, 0x74, 0x68, 0x65, 0x6e, 0x74, 0x69, 0x63, 0x61, + 0x74, 0x65, 0x22, 0xbc, 0x01, 0x0a, 0x0c, 0x41, 0x75, 0x74, 0x68, 0x52, 0x65, 0x73, 0x70, 0x6f, + 0x6e, 0x73, 0x65, 0x12, 0x3f, 0x0a, 0x08, 0x61, 0x75, 0x74, 0x68, 0x54, 0x79, 0x70, 0x65, 0x18, + 0x01, 0x20, 0x01, 0x28, 0x0e, 0x32, 0x23, 0x2e, 0x63, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, + 0x72, 0x64, 0x2e, 0x74, 0x79, 0x70, 0x65, 0x73, 0x2e, 0x74, 0x72, 0x61, 0x6e, 0x73, 0x66, 0x65, + 0x72, 0x2e, 0x41, 0x75, 0x74, 0x68, 0x54, 0x79, 0x70, 0x65, 0x52, 0x08, 0x61, 0x75, 0x74, 0x68, + 0x54, 0x79, 0x70, 0x65, 0x12, 0x16, 0x0a, 0x06, 0x73, 0x65, 0x63, 0x72, 0x65, 0x74, 0x18, 0x02, + 0x20, 0x01, 0x28, 0x09, 0x52, 0x06, 0x73, 0x65, 0x63, 0x72, 0x65, 0x74, 0x12, 0x1a, 0x0a, 0x08, + 0x75, 0x73, 0x65, 0x72, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x52, 0x08, + 0x75, 0x73, 0x65, 0x72, 0x6e, 0x61, 0x6d, 0x65, 0x12, 0x37, 0x0a, 0x09, 0x65, 0x78, 0x70, 0x69, + 0x72, 0x65, 0x5f, 0x61, 0x74, 0x18, 0x04, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1a, 0x2e, 0x67, 0x6f, + 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x54, 0x69, + 0x6d, 0x65, 0x73, 0x74, 0x61, 0x6d, 0x70, 0x52, 0x08, 0x65, 0x78, 0x70, 0x69, 0x72, 0x65, 0x41, + 0x74, 0x2a, 0x3e, 0x0a, 0x08, 0x41, 0x75, 0x74, 0x68, 0x54, 0x79, 0x70, 0x65, 0x12, 0x08, 0x0a, + 0x04, 0x4e, 0x4f, 0x4e, 0x45, 0x10, 0x00, 0x12, 0x0f, 0x0a, 0x0b, 0x43, 0x52, 0x45, 0x44, 0x45, + 0x4e, 0x54, 0x49, 0x41, 0x4c, 0x53, 0x10, 0x01, 0x12, 0x0b, 0x0a, 0x07, 0x52, 0x45, 0x46, 0x52, + 0x45, 0x53, 0x48, 0x10, 0x02, 0x12, 0x0a, 0x0a, 0x06, 0x48, 0x45, 0x41, 0x44, 0x45, 0x52, 0x10, + 0x03, 0x42, 0x38, 0x5a, 0x36, 0x67, 0x69, 0x74, 0x68, 0x75, 0x62, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, + 0x63, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x64, 0x2f, 0x63, 0x6f, 0x6e, 0x74, 0x61, + 0x69, 0x6e, 0x65, 0x72, 0x64, 0x2f, 0x76, 0x32, 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x74, 0x79, 0x70, + 0x65, 0x73, 0x2f, 0x74, 0x72, 0x61, 0x6e, 0x73, 0x66, 0x65, 0x72, 0x62, 0x06, 0x70, 0x72, 0x6f, + 0x74, 0x6f, 0x33, } var ( diff --git a/api/types/transfer/registry.proto b/api/types/transfer/registry.proto index f83fa1689..7e72c16d1 100644 --- a/api/types/transfer/registry.proto +++ b/api/types/transfer/registry.proto @@ -35,7 +35,7 @@ message RegistryResolver { // Headers map headers = 2; - // Allow custom hosts dir? + string host_dir = 3; // Force skip verify // Force HTTP // CA callback? Client TLS callback? diff --git a/cmd/ctr/commands/images/pull.go b/cmd/ctr/commands/images/pull.go index a21cddc8e..328c853e3 100644 --- a/cmd/ctr/commands/images/pull.go +++ b/cmd/ctr/commands/images/pull.go @@ -132,7 +132,10 @@ command. As part of this process, we do the following: sopts = append(sopts, image.WithAllMetadata) } - reg := registry.NewOCIRegistry(ref, nil, ch) + reg, err := registry.NewOCIRegistry(ctx, ref, registry.WithCredentials(ch), registry.WithHostDir(context.String("hosts-dir"))) + if err != nil { + return err + } is := image.NewStore(ref, sopts...) pf, done := ProgressHandler(ctx, os.Stdout) diff --git a/cmd/ctr/commands/images/push.go b/cmd/ctr/commands/images/push.go index 6e7d18376..987ab9d50 100644 --- a/cmd/ctr/commands/images/push.go +++ b/cmd/ctr/commands/images/push.go @@ -104,7 +104,10 @@ var pushCommand = &cli.Command{ if local == "" { local = ref } - reg := registry.NewOCIRegistry(ref, nil, ch) + reg, err := registry.NewOCIRegistry(ctx, ref, registry.WithCredentials(ch), registry.WithHostDir(context.String("hosts-dir"))) + if err != nil { + return err + } is := image.NewStore(local) pf, done := ProgressHandler(ctx, os.Stdout) diff --git a/core/transfer/registry/registry.go b/core/transfer/registry/registry.go index 7fdca72ee..415296f56 100644 --- a/core/transfer/registry/registry.go +++ b/core/transfer/registry/registry.go @@ -28,6 +28,7 @@ import ( transfertypes "github.com/containerd/containerd/v2/api/types/transfer" "github.com/containerd/containerd/v2/core/remotes" "github.com/containerd/containerd/v2/core/remotes/docker" + "github.com/containerd/containerd/v2/core/remotes/docker/config" "github.com/containerd/containerd/v2/core/streaming" "github.com/containerd/containerd/v2/core/transfer" "github.com/containerd/containerd/v2/core/transfer/plugins" @@ -42,37 +43,73 @@ func init() { plugins.Register(&transfertypes.OCIRegistry{}, &OCIRegistry{}) } +type registryOpts struct { + headers http.Header + creds CredentialHelper + hostDir string +} + +// Opt sets registry-related configurations. +type Opt func(o *registryOpts) error + +// WithHeaders configures HTTP request header fields sent by the resolver. +func WithHeaders(headers http.Header) Opt { + return func(o *registryOpts) error { + o.headers = headers + return nil + } +} + +// WithCredentials configures a helper that provides credentials for a host. +func WithCredentials(creds CredentialHelper) Opt { + return func(o *registryOpts) error { + o.creds = creds + return nil + } +} + +// WithHostDir specifies the host configuration directory. +func WithHostDir(hostDir string) Opt { + return func(o *registryOpts) error { + o.hostDir = hostDir + return nil + } +} + // NewOCIRegistry initializes with hosts, authorizer callback, and headers -func NewOCIRegistry(ref string, headers http.Header, creds CredentialHelper) *OCIRegistry { - // Create an authorizer - var aopts []docker.AuthorizerOpt - if creds != nil { +func NewOCIRegistry(ctx context.Context, ref string, opts ...Opt) (*OCIRegistry, error) { + var ropts registryOpts + for _, o := range opts { + if err := o(&ropts); err != nil { + return nil, err + } + } + hostOptions := config.HostOptions{} + if ropts.hostDir != "" { + hostOptions.HostDir = config.HostDirFromRoot(ropts.hostDir) + } + if ropts.creds != nil { // TODO: Support bearer - aopts = append(aopts, docker.WithAuthCreds(func(host string) (string, string, error) { - c, err := creds.GetCredentials(context.Background(), ref, host) + hostOptions.Credentials = func(host string) (string, string, error) { + c, err := ropts.creds.GetCredentials(context.Background(), ref, host) if err != nil { return "", "", err } return c.Username, c.Secret, nil - })) + } } - - ropts := []docker.RegistryOpt{ - docker.WithAuthorizer(docker.NewDockerAuthorizer(aopts...)), - } - - // TODO: Apply local configuration, maybe dynamically create resolver when requested resolver := docker.NewResolver(docker.ResolverOptions{ - Hosts: docker.ConfigureDefaultRegistries(ropts...), - Headers: headers, + Hosts: config.ConfigureHosts(ctx, hostOptions), + Headers: ropts.headers, }) return &OCIRegistry{ reference: ref, - headers: headers, - creds: creds, + headers: ropts.headers, + creds: ropts.creds, resolver: resolver, - } + hostDir: ropts.hostDir, + }, nil } // From stream @@ -96,6 +133,8 @@ type OCIRegistry struct { resolver remotes.Resolver + hostDir string + // This could be an interface which returns resolver? // Resolver could also be a plug-able interface, to call out to a program to fetch? } @@ -194,6 +233,7 @@ func (r *OCIRegistry) MarshalAny(ctx context.Context, sm streaming.StreamCreator }() res.AuthStream = sid } + res.HostDir = r.hostDir s := &transfertypes.OCIRegistry{ Reference: r.reference, Resolver: res, @@ -203,16 +243,16 @@ func (r *OCIRegistry) MarshalAny(ctx context.Context, sm streaming.StreamCreator } func (r *OCIRegistry) UnmarshalAny(ctx context.Context, sm streaming.StreamGetter, a typeurl.Any) error { - var ( - s transfertypes.OCIRegistry - ropts []docker.RegistryOpt - aopts []docker.AuthorizerOpt - ) + var s transfertypes.OCIRegistry if err := typeurl.UnmarshalTo(a, &s); err != nil { return err } + hostOptions := config.HostOptions{} if s.Resolver != nil { + if s.Resolver.HostDir != "" { + hostOptions.HostDir = config.HostDirFromRoot(s.Resolver.HostDir) + } if sid := s.Resolver.AuthStream; sid != "" { stream, err := sm.Get(ctx, sid) if err != nil { @@ -222,26 +262,24 @@ func (r *OCIRegistry) UnmarshalAny(ctx context.Context, sm streaming.StreamGette r.creds = &credCallback{ stream: stream, } - aopts = append(aopts, docker.WithAuthCreds(func(host string) (string, string, error) { + hostOptions.Credentials = func(host string) (string, string, error) { c, err := r.creds.GetCredentials(context.Background(), s.Reference, host) if err != nil { return "", "", err } return c.Username, c.Secret, nil - })) + } } r.headers = http.Header{} for k, v := range s.Resolver.Headers { r.headers.Add(k, v) } } - authorizer := docker.NewDockerAuthorizer(aopts...) - ropts = append(ropts, docker.WithAuthorizer(authorizer)) r.reference = s.Reference r.resolver = docker.NewResolver(docker.ResolverOptions{ - Hosts: docker.ConfigureDefaultRegistries(ropts...), + Hosts: config.ConfigureHosts(ctx, hostOptions), Headers: r.headers, })