Skip to content

Commit 7018b4e

Browse files
committed
Add cluster registry config
Signed-off-by: melserngawy <[email protected]>
1 parent 2fe1c84 commit 7018b4e

File tree

6 files changed

+416
-59
lines changed

6 files changed

+416
-59
lines changed

config/crd/bases/controlplane.cluster.x-k8s.io_rosacontrolplanes.yaml

Lines changed: 71 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -82,6 +82,77 @@ spec:
8282
rule: self == oldSelf
8383
- message: billingAccount must be a valid AWS account ID
8484
rule: self.matches('^[0-9]{12}$')
85+
clusterRegistryConfig:
86+
description: ClusterRegistryConfig represents registry config used
87+
with the cluster.
88+
properties:
89+
additionalTrustedCa:
90+
additionalProperties:
91+
type: string
92+
description: |-
93+
AdditionalTrustedCa containing the registry hostname as the key, and the PEM-encoded certificate as the value,
94+
for each additional registry CA to trust.
95+
type: object
96+
allowedRegistriesForImport:
97+
description: |-
98+
AllowedRegistriesForImport limits the container image registries that normal users may import
99+
images from. Set this list to the registries that you trust to contain valid Docker
100+
images and that you want applications to be able to import from.
101+
items:
102+
description: RegistryLocation contains a location of the registry
103+
specified by the registry domain name.
104+
properties:
105+
domainName:
106+
description: |-
107+
domainName specifies a domain name for the registry. The domain name might include wildcards, like '*' or '??'.
108+
In case the registry use non-standard (80 or 443) port, the port should be included in the domain name as well.
109+
type: string
110+
insecure:
111+
default: false
112+
description: insecure indicates whether the registry is
113+
secure (https) or insecure (http), default is secured.
114+
type: boolean
115+
type: object
116+
type: array
117+
platformAllowlistID:
118+
description: PlatformAllowlistID contains a reference to whitelisted
119+
internal registries for the platform to work.
120+
type: string
121+
registrySources:
122+
description: |-
123+
RegistrySources contains configuration that determines how the container runtime
124+
should treat individual registries when accessing images. It does not contain configuration
125+
for the internal cluster registry.
126+
properties:
127+
allowedRegistries:
128+
description: |-
129+
AllowedRegistries: registries for which image pull and push actions are allowed.
130+
To specify all subdomains, add the asterisk (*) wildcard character as a prefix to the domain name.
131+
For example, *.example.com. You can specify an individual repository within a registry.
132+
For example: reg1.io/myrepo/myapp:latest. All other registries are blocked.
133+
items:
134+
type: string
135+
type: array
136+
blockedRegistries:
137+
description: |-
138+
BlockedRegistries: registries for which image pull and push actions are denied.
139+
To specify all subdomains, add the asterisk (*) wildcard character as a prefix to the domain name.
140+
For example, *.example.com. You can specify an individual repository within a registry.
141+
For example: reg1.io/myrepo/myapp:latest. All other registries are allowed.
142+
items:
143+
type: string
144+
type: array
145+
insecureRegistries:
146+
description: |-
147+
InsecureRegistries are registries which do not have a valid TLS certificate or only support HTTP connections.
148+
To specify all subdomains, add the asterisk (*) wildcard character as a prefix to the domain name.
149+
For example, *.example.com. You can specify an individual repository within a registry.
150+
For example: reg1.io/myrepo/myapp:latest.
151+
items:
152+
type: string
153+
type: array
154+
type: object
155+
type: object
85156
controlPlaneEndpoint:
86157
description: ControlPlaneEndpoint represents the endpoint used to
87158
communicate with the control plane.

controlplane/rosa/api/v1beta2/rosacontrolplane_types.go

Lines changed: 65 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -180,6 +180,71 @@ type RosaControlPlaneSpec struct { //nolint: maligned
180180
// ControlPlaneEndpoint represents the endpoint used to communicate with the control plane.
181181
// +optional
182182
ControlPlaneEndpoint clusterv1.APIEndpoint `json:"controlPlaneEndpoint"`
183+
184+
// ClusterRegistryConfig represents registry config used with the cluster.
185+
// +optional
186+
ClusterRegistryConfig *RegistryConfig `json:"clusterRegistryConfig,omitempty"`
187+
}
188+
189+
// RegistryConfig for ROSA-HCP cluster
190+
type RegistryConfig struct {
191+
// AdditionalTrustedCa containing the registry hostname as the key, and the PEM-encoded certificate as the value,
192+
// for each additional registry CA to trust.
193+
// +optional
194+
AdditionalTrustedCa map[string]string `json:"additionalTrustedCa,omitempty"`
195+
196+
// AllowedRegistriesForImport limits the container image registries that normal users may import
197+
// images from. Set this list to the registries that you trust to contain valid Docker
198+
// images and that you want applications to be able to import from.
199+
// +optional
200+
AllowedRegistriesForImport []RegistryLocation `json:"allowedRegistriesForImport,omitempty"`
201+
202+
// PlatformAllowlistID contains a reference to whitelisted internal registries for the platform to work.
203+
// +optional
204+
PlatformAllowlistID string `json:"platformAllowlistID,omitempty"`
205+
206+
// RegistrySources contains configuration that determines how the container runtime
207+
// should treat individual registries when accessing images. It does not contain configuration
208+
// for the internal cluster registry.
209+
// +optional
210+
RegistrySources *RegistrySources `json:"registrySources,omitempty"`
211+
}
212+
213+
// RegistryLocation contains a location of the registry specified by the registry domain name.
214+
type RegistryLocation struct {
215+
// domainName specifies a domain name for the registry. The domain name might include wildcards, like '*' or '??'.
216+
// In case the registry use non-standard (80 or 443) port, the port should be included in the domain name as well.
217+
// +optional
218+
DomainName string `json:"domainName,omitempty"`
219+
220+
// insecure indicates whether the registry is secure (https) or insecure (http), default is secured.
221+
// +kubebuilder:default=false
222+
// +optional
223+
Insecure bool `json:"insecure,omitempty"`
224+
}
225+
226+
// RegistrySources contains registries configuration.
227+
type RegistrySources struct {
228+
// AllowedRegistries: registries for which image pull and push actions are allowed.
229+
// To specify all subdomains, add the asterisk (*) wildcard character as a prefix to the domain name.
230+
// For example, *.example.com. You can specify an individual repository within a registry.
231+
// For example: reg1.io/myrepo/myapp:latest. All other registries are blocked.
232+
// +optional
233+
AllowedRegistries []string `json:"allowedRegistries,omitempty"`
234+
235+
// BlockedRegistries: registries for which image pull and push actions are denied.
236+
// To specify all subdomains, add the asterisk (*) wildcard character as a prefix to the domain name.
237+
// For example, *.example.com. You can specify an individual repository within a registry.
238+
// For example: reg1.io/myrepo/myapp:latest. All other registries are allowed.
239+
// +optional
240+
BlockedRegistries []string `json:"blockedRegistries,omitempty"`
241+
242+
// InsecureRegistries are registries which do not have a valid TLS certificate or only support HTTP connections.
243+
// To specify all subdomains, add the asterisk (*) wildcard character as a prefix to the domain name.
244+
// For example, *.example.com. You can specify an individual repository within a registry.
245+
// For example: reg1.io/myrepo/myapp:latest.
246+
// +optional
247+
InsecureRegistries []string `json:"insecureRegistries,omitempty"`
183248
}
184249

185250
// NetworkSpec for ROSA-HCP.

controlplane/rosa/api/v1beta2/zz_generated.deepcopy.go

Lines changed: 82 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

controlplane/rosa/controllers/rosacontrolplane_controller.go

Lines changed: 39 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,8 @@ import (
2828
"strings"
2929
"time"
3030

31+
stsv2 "github.com/aws/aws-sdk-go-v2/service/sts"
32+
sts "github.com/aws/aws-sdk-go/service/sts"
3133
"github.com/google/go-cmp/cmp"
3234
idputils "github.com/openshift-online/ocm-common/pkg/idp/utils"
3335
cmv1 "github.com/openshift-online/ocm-sdk-go/clustersmgmt/v1"
@@ -206,7 +208,7 @@ func (r *ROSAControlPlaneReconciler) reconcileNormal(ctx context.Context, rosaSc
206208
return ctrl.Result{}, fmt.Errorf("failed to create OCM client: %w", err)
207209
}
208210

209-
creator, err := rosaaws.CreatorForCallerIdentity(rosaScope.Identity)
211+
creator, err := rosaaws.CreatorForCallerIdentity(convertStsV2(rosaScope.Identity))
210212
if err != nil {
211213
return ctrl.Result{}, fmt.Errorf("failed to transform caller identity to creator: %w", err)
212214
}
@@ -334,7 +336,7 @@ func (r *ROSAControlPlaneReconciler) reconcileDelete(ctx context.Context, rosaSc
334336
return ctrl.Result{}, fmt.Errorf("failed to create OCM client: %w", err)
335337
}
336338

337-
creator, err := rosaaws.CreatorForCallerIdentity(rosaScope.Identity)
339+
creator, err := rosaaws.CreatorForCallerIdentity(convertStsV2(rosaScope.Identity))
338340
if err != nil {
339341
return ctrl.Result{}, fmt.Errorf("failed to transform caller identity to creator: %w", err)
340342
}
@@ -888,6 +890,32 @@ func buildOCMClusterSpec(controlPlaneSpec rosacontrolplanev1.RosaControlPlaneSpe
888890
}
889891
}
890892

893+
// Set the cluster registry config.
894+
if controlPlaneSpec.ClusterRegistryConfig != nil {
895+
if len(controlPlaneSpec.ClusterRegistryConfig.AdditionalTrustedCa) > 0 {
896+
ocmClusterSpec.AdditionalTrustedCa = controlPlaneSpec.ClusterRegistryConfig.AdditionalTrustedCa
897+
}
898+
899+
if len(controlPlaneSpec.ClusterRegistryConfig.AllowedRegistriesForImport) > 0 {
900+
registers := make([]string, 0)
901+
for id := range controlPlaneSpec.ClusterRegistryConfig.AllowedRegistriesForImport {
902+
registers = append(registers, controlPlaneSpec.ClusterRegistryConfig.AllowedRegistriesForImport[id].DomainName+":"+
903+
strconv.FormatBool(controlPlaneSpec.ClusterRegistryConfig.AllowedRegistriesForImport[id].Insecure))
904+
}
905+
ocmClusterSpec.AllowedRegistriesForImport = strings.Join(registers, ",")
906+
}
907+
908+
if controlPlaneSpec.ClusterRegistryConfig.RegistrySources != nil {
909+
ocmClusterSpec.BlockedRegistries = controlPlaneSpec.ClusterRegistryConfig.RegistrySources.BlockedRegistries
910+
ocmClusterSpec.AllowedRegistries = controlPlaneSpec.ClusterRegistryConfig.RegistrySources.AllowedRegistries
911+
ocmClusterSpec.InsecureRegistries = controlPlaneSpec.ClusterRegistryConfig.RegistrySources.InsecureRegistries
912+
}
913+
914+
if controlPlaneSpec.ClusterRegistryConfig.PlatformAllowlistID != "" {
915+
ocmClusterSpec.PlatformAllowlist = controlPlaneSpec.ClusterRegistryConfig.PlatformAllowlistID
916+
}
917+
}
918+
891919
return ocmClusterSpec, nil
892920
}
893921

@@ -996,3 +1024,12 @@ func buildAPIEndpoint(cluster *cmv1.Cluster) (*clusterv1.APIEndpoint, error) {
9961024
Port: int32(port), // #nosec G109
9971025
}, nil
9981026
}
1027+
1028+
// TODO: Remove this and update the aws-sdk lib to v2.
1029+
func convertStsV2(identity *sts.GetCallerIdentityOutput) *stsv2.GetCallerIdentityOutput {
1030+
return &stsv2.GetCallerIdentityOutput{
1031+
Account: identity.Account,
1032+
Arn: identity.Arn,
1033+
UserId: identity.UserId,
1034+
}
1035+
}

0 commit comments

Comments
 (0)