Skip to content

Commit 4004d1f

Browse files
authored
Support importing certificates into ACM (#40)
Description of changes: Adds support for [importing certificates](https://docs.aws.amazon.com/acm/latest/APIReference/API_ImportCertificate.html) into ACM. When `Spec.Certificate` is set, the controller attempts to import a certificate into ACM, otherwise it requests a certificate. It is an error to set fields used to request a certificate when importing a certificate and vice versa. The two fields required for importing a certificate (`Certificate` and `PrivateKey`) are both secret references. While the certificate portion may not be private information, it’s common to store TLS certificates as secrets in Kubernetes. The ACK runtime currently only supports resolving `Opaque` secrets and not TLS certificates, so users wanting to import existing TLS secrets into ACM will have to migrate them first. The `late_initialize_post_read_one` hook is used to allow late initialization of optional fields, otherwise the controller will keep retrying `DescribeCertificate` for setting fields that will never be returned from the API. `GoCodeSetSDKForStruct` in code-generator does not support resolving secret references for custom `[]byte` fields, so a wrapper type `importCertificateInput` has been introduced as a workaround. Issue #, if available: aws-controllers-k8s/community#2043 By submitting this pull request, I confirm that my contribution is made under the terms of the Apache 2.0 license.
1 parent 102a54f commit 4004d1f

26 files changed

+900
-53
lines changed
Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,13 @@
11
ack_generate_info:
2-
build_date: "2024-10-10T03:56:31Z"
2+
build_date: "2024-11-06T19:23:27Z"
33
build_hash: 36c2d234498c2bc4f60773ab8df632af4067f43b
4-
go_version: go1.23.2
4+
go_version: go1.22.4
55
version: v0.39.1
6-
api_directory_checksum: e337526dd1438ddb861e06bd92b5f640ba9ed537
6+
api_directory_checksum: b055cc57ac2cc8b07e374803c280b65d1a72f3bf
77
api_version: v1alpha1
88
aws_sdk_go_version: v1.49.0
99
generator_config_info:
10-
file_checksum: 910047b7946c5968bbc58b6334099deb005e95cc
10+
file_checksum: df0b4d7fe83a679c01131dc4af1844b5ff8105b3
1111
original_file_name: generator.yaml
1212
last_modification:
1313
reason: API generation

apis/v1alpha1/certificate.go

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

apis/v1alpha1/generator.yaml

Lines changed: 36 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -35,24 +35,55 @@ resources:
3535
code: input.SetValidationMethod("DNS")
3636
sdk_read_one_pre_set_output:
3737
template_path: hooks/certificate/sdk_read_one_pre_set_output.go.tpl
38+
sdk_file_end:
39+
template_path: hooks/certificate/sdk_file_end.go.tpl
40+
late_initialize_post_read_one:
41+
template_path: hooks/certificate/late_initialize_post_read_one.go.tpl
3842
exceptions:
3943
terminal_codes:
4044
- InvalidParameter
4145
- InvalidDomainValidationOptionsException
4246
- InvalidTagException
4347
- TagPolicyException
4448
- TooManyTagsException
49+
- InvalidArnException
4550
reconcile:
4651
requeue_on_success_seconds: 60
4752
fields:
48-
DomainValidationOptions:
53+
DomainName:
54+
is_primary_key: false
55+
is_required: false
56+
Certificate:
57+
type: "bytes"
58+
is_secret: true
59+
is_immutable: true
60+
compare:
61+
is_ignored: true
62+
PrivateKey:
63+
type: "bytes"
64+
is_secret: true
65+
is_immutable: true
66+
compare:
67+
is_ignored: true
68+
CertificateArn:
69+
type: string
70+
is_immutable: true
71+
CertificateChain:
72+
type: "bytes"
73+
is_immutable: true
74+
is_secret: true
75+
compare:
76+
is_ignored: true
77+
CertificateAuthorityARN:
78+
references:
79+
service_name: acmpca
80+
resource: CertificateAuthority
81+
path: Status.ACKResourceMetadata.ARN
82+
is_immutable: true
83+
KeyAlgorithm:
4984
late_initialize: {}
5085
Options:
5186
late_initialize: {}
52-
SubjectAlternativeNames:
53-
late_initialize: {}
54-
KeyAlgorithm:
55-
late_initialize: {}
5687
# NOTE(jaypipes): The Create operation (RequestCertificate) has a
5788
# response with only a single field (certificateArn). All of the status
5889
# fields for the certificate are in the ReadOne operation

apis/v1alpha1/zz_generated.deepcopy.go

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

cmd/controller/main.go

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

config/crd/bases/acm.services.k8s.aws_certificates.yaml

Lines changed: 82 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,31 @@ spec:
3939
spec:
4040
description: CertificateSpec defines the desired state of Certificate.
4141
properties:
42+
certificate:
43+
description: |-
44+
The Certificate to import into AWS Certificate Manager (ACM) to use with services that are integrated with ACM.
45+
This field is only valid when importing an existing certificate into ACM.
46+
properties:
47+
key:
48+
description: Key is the key within the secret
49+
type: string
50+
name:
51+
description: name is unique within a namespace to reference a
52+
secret resource.
53+
type: string
54+
namespace:
55+
description: namespace defines the space within which the secret
56+
name must be unique.
57+
type: string
58+
required:
59+
- key
60+
type: object
61+
x-kubernetes-map-type: atomic
62+
certificateARN:
63+
description: |-
64+
The Amazon Resource Name (ARN) of an imported certificate to replace. This field is only valid when importing
65+
an existing certificate into ACM.
66+
type: string
4267
certificateAuthorityARN:
4368
description: |-
4469
The Amazon Resource Name (ARN) of the private certificate authority (CA)
@@ -50,6 +75,43 @@ spec:
5075
5176
arn:aws:acm-pca:region:account:certificate-authority/12345678-1234-1234-1234-123456789012
5277
type: string
78+
certificateAuthorityRef:
79+
description: "AWSResourceReferenceWrapper provides a wrapper around
80+
*AWSResourceReference\ntype to provide more user friendly syntax
81+
for references using 'from' field\nEx:\nAPIIDRef:\n\n\tfrom:\n\t
82+
\ name: my-api"
83+
properties:
84+
from:
85+
description: |-
86+
AWSResourceReference provides all the values necessary to reference another
87+
k8s resource for finding the identifier(Id/ARN/Name)
88+
properties:
89+
name:
90+
type: string
91+
namespace:
92+
type: string
93+
type: object
94+
type: object
95+
certificateChain:
96+
description: |-
97+
SecretKeyReference combines a k8s corev1.SecretReference with a
98+
specific key within the referred-to Secret
99+
properties:
100+
key:
101+
description: Key is the key within the secret
102+
type: string
103+
name:
104+
description: name is unique within a namespace to reference a
105+
secret resource.
106+
type: string
107+
namespace:
108+
description: namespace defines the space within which the secret
109+
name must be unique.
110+
type: string
111+
required:
112+
- key
113+
type: object
114+
x-kubernetes-map-type: atomic
53115
domainName:
54116
description: |-
55117
Fully qualified domain name (FQDN), such as www.example.com, that you want
@@ -104,6 +166,26 @@ spec:
104166
certificateTransparencyLoggingPreference:
105167
type: string
106168
type: object
169+
privateKey:
170+
description: |-
171+
The private key that matches the public key in the certificate. This field is only valid when importing
172+
an existing certificate into ACM.
173+
properties:
174+
key:
175+
description: Key is the key within the secret
176+
type: string
177+
name:
178+
description: name is unique within a namespace to reference a
179+
secret resource.
180+
type: string
181+
namespace:
182+
description: namespace defines the space within which the secret
183+
name must be unique.
184+
type: string
185+
required:
186+
- key
187+
type: object
188+
x-kubernetes-map-type: atomic
107189
subjectAlternativeNames:
108190
description: |-
109191
Additional FQDNs to be included in the Subject Alternative Name extension
@@ -143,8 +225,6 @@ spec:
143225
type: string
144226
type: object
145227
type: array
146-
required:
147-
- domainName
148228
type: object
149229
status:
150230
description: CertificateStatus defines the observed state of Certificate

config/rbac/cluster-role-controller.yaml

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -42,6 +42,14 @@ rules:
4242
- get
4343
- patch
4444
- update
45+
- apiGroups:
46+
- acmpca.services.k8s.aws
47+
resources:
48+
- certificateauthorities
49+
- certificateauthorities/status
50+
verbs:
51+
- get
52+
- list
4553
- apiGroups:
4654
- services.k8s.aws
4755
resources:

documentation.yaml

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
resources:
2+
Certificate:
3+
fields:
4+
Certificate:
5+
prepend: |
6+
The Certificate to import into AWS Certificate Manager (ACM) to use with services that are integrated with ACM.
7+
This field is only valid when importing an existing certificate into ACM.
8+
PrivateKey:
9+
prepend: |
10+
The private key that matches the public key in the certificate. This field is only valid when importing
11+
an existing certificate into ACM.
12+
CertificateARN:
13+
prepend: |
14+
The Amazon Resource Name (ARN) of an imported certificate to replace. This field is only valid when importing
15+
an existing certificate into ACM.

generator.yaml

Lines changed: 36 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -35,24 +35,55 @@ resources:
3535
code: input.SetValidationMethod("DNS")
3636
sdk_read_one_pre_set_output:
3737
template_path: hooks/certificate/sdk_read_one_pre_set_output.go.tpl
38+
sdk_file_end:
39+
template_path: hooks/certificate/sdk_file_end.go.tpl
40+
late_initialize_post_read_one:
41+
template_path: hooks/certificate/late_initialize_post_read_one.go.tpl
3842
exceptions:
3943
terminal_codes:
4044
- InvalidParameter
4145
- InvalidDomainValidationOptionsException
4246
- InvalidTagException
4347
- TagPolicyException
4448
- TooManyTagsException
49+
- InvalidArnException
4550
reconcile:
4651
requeue_on_success_seconds: 60
4752
fields:
48-
DomainValidationOptions:
53+
DomainName:
54+
is_primary_key: false
55+
is_required: false
56+
Certificate:
57+
type: "bytes"
58+
is_secret: true
59+
is_immutable: true
60+
compare:
61+
is_ignored: true
62+
PrivateKey:
63+
type: "bytes"
64+
is_secret: true
65+
is_immutable: true
66+
compare:
67+
is_ignored: true
68+
CertificateArn:
69+
type: string
70+
is_immutable: true
71+
CertificateChain:
72+
type: "bytes"
73+
is_immutable: true
74+
is_secret: true
75+
compare:
76+
is_ignored: true
77+
CertificateAuthorityARN:
78+
references:
79+
service_name: acmpca
80+
resource: CertificateAuthority
81+
path: Status.ACKResourceMetadata.ARN
82+
is_immutable: true
83+
KeyAlgorithm:
4984
late_initialize: {}
5085
Options:
5186
late_initialize: {}
52-
SubjectAlternativeNames:
53-
late_initialize: {}
54-
KeyAlgorithm:
55-
late_initialize: {}
5687
# NOTE(jaypipes): The Create operation (RequestCertificate) has a
5788
# response with only a single field (certificateArn). All of the status
5889
# fields for the certificate are in the ReadOne operation

go.mod

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,8 +5,9 @@ go 1.22.0
55
toolchain go1.22.5
66

77
require (
8+
github.com/aws-controllers-k8s/acmpca-controller v0.0.17
89
github.com/aws-controllers-k8s/runtime v0.39.0
9-
github.com/aws/aws-sdk-go v1.49.0
10+
github.com/aws/aws-sdk-go v1.49.6
1011
github.com/go-logr/logr v1.4.2
1112
github.com/spf13/pflag v1.0.5
1213
k8s.io/api v0.31.0

0 commit comments

Comments
 (0)