Skip to content
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

Add support for AMIs based on AmazonLinux2023 #7684

Merged
merged 11 commits into from
Apr 4, 2024
Merged
33 changes: 31 additions & 2 deletions integration/tests/custom_ami/custom_ami_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,7 @@ func TestOverrideBootstrap(t *testing.T) {

var (
customAMIAL2 string
customAMIAL2023 string
customAMIBottlerocket string
)

Expand All @@ -47,15 +48,23 @@ var _ = BeforeSuite(func() {

// retrieve AL2 AMI
input := &awsssm.GetParameterInput{
Name: aws.String("/aws/service/eks/optimized-ami/1.22/amazon-linux-2/recommended/image_id"),
Name: aws.String(fmt.Sprintf("/aws/service/eks/optimized-ami/%s/amazon-linux-2/recommended/image_id", params.Version)),
}
output, err := ssm.GetParameter(context.Background(), input)
Expect(err).NotTo(HaveOccurred())
customAMIAL2 = *output.Parameter.Value

// retrieve AL2023 AMI
input = &awsssm.GetParameterInput{
Name: aws.String(fmt.Sprintf("/aws/service/eks/optimized-ami/%s/amazon-linux-2023/x86_64/standard/recommended/image_id", params.Version)),
}
output, err = ssm.GetParameter(context.Background(), input)
Expect(err).NotTo(HaveOccurred())
customAMIAL2023 = *output.Parameter.Value

// retrieve Bottlerocket AMI
input = &awsssm.GetParameterInput{
Name: aws.String("/aws/service/bottlerocket/aws-k8s-1.25/x86_64/latest/image_id"),
Name: aws.String(fmt.Sprintf("/aws/service/bottlerocket/aws-k8s-%s/x86_64/latest/image_id", params.Version)),
}
output, err = ssm.GetParameter(context.Background(), input)
Expect(err).NotTo(HaveOccurred())
Expand All @@ -75,6 +84,26 @@ var _ = BeforeSuite(func() {
var _ = Describe("(Integration) [Test Custom AMI]", func() {
params.LogStacksEventsOnFailure()

Context("al2023 managed and un-managed nodegroups", func() {
It("can create working nodegroups which can join the cluster", func() {
By(fmt.Sprintf("using the following EKS optimised AMI: %s", customAMIAL2023))
content, err := os.ReadFile(filepath.Join("testdata/al2023.yaml"))
Expect(err).NotTo(HaveOccurred())
content = bytes.ReplaceAll(content, []byte("<generated>"), []byte(params.ClusterName))
content = bytes.ReplaceAll(content, []byte("<generated-region>"), []byte(params.Region))
content = bytes.ReplaceAll(content, []byte("<generated-ami>"), []byte(customAMIAL2023))
cmd := params.EksctlCreateCmd.
WithArgs(
"nodegroup",
"--config-file", "-",
"--verbose", "4",
).
WithoutArg("--region", params.Region).
WithStdin(bytes.NewReader(content))
Expect(cmd).To(RunSuccessfully())
})
})

Context("override bootstrap command for managed and un-managed nodegroups", func() {

It("can create a working nodegroup which can join the cluster", func() {
Expand Down
19 changes: 19 additions & 0 deletions integration/tests/custom_ami/testdata/al2023.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
apiVersion: eksctl.io/v1alpha5
kind: ClusterConfig

# name is generated
metadata:
name: <generated>
region: <generated-region>

nodeGroups:
- name: unm-al2023
ami: <generated-ami>
amiFamily: AmazonLinux2023
desiredCapacity: 1

managedNodeGroups:
- name: mng-al2023
ami: <generated-ami>
amiFamily: AmazonLinux2023
desiredCapacity: 1
27 changes: 27 additions & 0 deletions integration/tests/managed/managed_nodegroup_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -70,6 +70,7 @@ var _ = Describe("(Integration) Create Managed Nodegroups", func() {

const (
updateConfigNodegroup = "ng-update-config"
al2023Nodegroup = "ng-al2023"
bottlerocketNodegroup = "ng-bottlerocket"
bottlerocketGPUNodegroup = "ng-bottlerocket-gpu"
ubuntuNodegroup = "ng-ubuntu"
Expand Down Expand Up @@ -302,6 +303,32 @@ var _ = Describe("(Integration) Create Managed Nodegroups", func() {
checkNg(bottlerocketGPUNodegroup)
})

It("supports AmazonLinux2023 nodegroups", func() {
clusterConfig := makeClusterConfig()
clusterConfig.ManagedNodeGroups = []*api.ManagedNodeGroup{
{
NodeGroupBase: &api.NodeGroupBase{
Name: al2023Nodegroup,
AMIFamily: "AmazonLinux2023",
},
},
}

By("creating it")
Expect(params.EksctlCreateCmd.
WithArgs(
"nodegroup",
"--config-file", "-",
"--verbose", "4",
).
WithoutArg("--region", params.Region).
WithStdin(clusterutils.Reader(clusterConfig))).
To(RunSuccessfully())

By("ensuring it is healthy")
checkNg(al2023Nodegroup)
})

It("supports bottlerocket and ubuntu nodegroups with additional volumes", func() {
clusterConfig := makeClusterConfig()
clusterConfig.ManagedNodeGroups = []*api.ManagedNodeGroup{
Expand Down
6 changes: 5 additions & 1 deletion pkg/ami/auto_resolver.go
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,10 @@ const (
// MakeImageSearchPatterns creates a map of image search patterns by image OS family and class
func MakeImageSearchPatterns(version string) map[string]map[int]string {
return map[string]map[int]string{
api.NodeImageFamilyAmazonLinux2023: {
ImageClassGeneral: fmt.Sprintf("amazon-eks-node-al2023-x86_64-standard-%s-v*", version),
a-hilaly marked this conversation as resolved.
Show resolved Hide resolved
ImageClassARM: fmt.Sprintf("amazon-eks-node-al2023-arm64-standard-%s-v*", version),
},
api.NodeImageFamilyAmazonLinux2: {
ImageClassGeneral: fmt.Sprintf("amazon-eks-node-%s-v*", version),
ImageClassGPU: fmt.Sprintf("amazon-eks-gpu-node-%s-*", version),
Expand Down Expand Up @@ -59,7 +63,7 @@ func OwnerAccountID(imageFamily, region string) (string, error) {
switch imageFamily {
case api.NodeImageFamilyUbuntu2204, api.NodeImageFamilyUbuntu2004, api.NodeImageFamilyUbuntu1804:
return ownerIDUbuntuFamily, nil
case api.NodeImageFamilyAmazonLinux2:
case api.NodeImageFamilyAmazonLinux2023, api.NodeImageFamilyAmazonLinux2:
return api.EKSResourceAccountID(region), nil
default:
if api.IsWindowsImage(imageFamily) {
Expand Down
7 changes: 7 additions & 0 deletions pkg/ami/ssm_resolver.go
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,9 @@ func MakeSSMParameterName(version, instanceType, imageFamily string) (string, er
const fieldName = "image_id"

switch imageFamily {
case api.NodeImageFamilyAmazonLinux2023:
return fmt.Sprintf("/aws/service/eks/optimized-ami/%s/%s/%s/standard/recommended/%s",
version, utils.ToKebabCase(imageFamily), instanceEC2ArchName(instanceType), fieldName), nil
TiberiuGC marked this conversation as resolved.
Show resolved Hide resolved
case api.NodeImageFamilyAmazonLinux2:
return fmt.Sprintf("/aws/service/eks/optimized-ami/%s/%s/recommended/%s", version, imageType(imageFamily, instanceType, version), fieldName), nil
case api.NodeImageFamilyWindowsServer2019CoreContainer,
Expand Down Expand Up @@ -83,6 +86,10 @@ func MakeSSMParameterName(version, instanceType, imageFamily string) (string, er
// MakeManagedSSMParameterName creates an SSM parameter name for a managed nodegroup
func MakeManagedSSMParameterName(version string, amiType ekstypes.AMITypes) (string, error) {
switch amiType {
case ekstypes.AMITypesAl2023X8664Standard:
return fmt.Sprintf("/aws/service/eks/optimized-ami/%s/%s/x86_64/standard/recommended/release_version", version, utils.ToKebabCase(api.NodeImageFamilyAmazonLinux2023)), nil
case ekstypes.AMITypesAl2023Arm64Standard:
a-hilaly marked this conversation as resolved.
Show resolved Hide resolved
return fmt.Sprintf("/aws/service/eks/optimized-ami/%s/%s/arm64/standard/recommended/release_version", version, utils.ToKebabCase(api.NodeImageFamilyAmazonLinux2023)), nil
case ekstypes.AMITypesAl2X8664:
imageType := utils.ToKebabCase(api.NodeImageFamilyAmazonLinux2)
return fmt.Sprintf("/aws/service/eks/optimized-ami/%s/%s/recommended/release_version", version, imageType), nil
Expand Down
10 changes: 6 additions & 4 deletions pkg/apis/eksctl.io/v1alpha5/assets/schema.json
Original file line number Diff line number Diff line change
Expand Up @@ -1256,11 +1256,12 @@
},
"amiFamily": {
"type": "string",
"description": "Valid variants are: `\"AmazonLinux2\"` (default), `\"Ubuntu2204\"`, `\"Ubuntu2004\"`, `\"Ubuntu1804\"`, `\"Bottlerocket\"`, `\"WindowsServer2019CoreContainer\"`, `\"WindowsServer2019FullContainer\"`, `\"WindowsServer2022CoreContainer\"`, `\"WindowsServer2022FullContainer\"`.",
"x-intellij-html-description": "Valid variants are: <code>&quot;AmazonLinux2&quot;</code> (default), <code>&quot;Ubuntu2204&quot;</code>, <code>&quot;Ubuntu2004&quot;</code>, <code>&quot;Ubuntu1804&quot;</code>, <code>&quot;Bottlerocket&quot;</code>, <code>&quot;WindowsServer2019CoreContainer&quot;</code>, <code>&quot;WindowsServer2019FullContainer&quot;</code>, <code>&quot;WindowsServer2022CoreContainer&quot;</code>, <code>&quot;WindowsServer2022FullContainer&quot;</code>.",
"description": "Valid variants are: `\"AmazonLinux2\"` (default), `\"AmazonLinux2023\"`, `\"Ubuntu2204\"`, `\"Ubuntu2004\"`, `\"Ubuntu1804\"`, `\"Bottlerocket\"`, `\"WindowsServer2019CoreContainer\"`, `\"WindowsServer2019FullContainer\"`, `\"WindowsServer2022CoreContainer\"`, `\"WindowsServer2022FullContainer\"`.",
"x-intellij-html-description": "Valid variants are: <code>&quot;AmazonLinux2&quot;</code> (default), <code>&quot;AmazonLinux2023&quot;</code>, <code>&quot;Ubuntu2204&quot;</code>, <code>&quot;Ubuntu2004&quot;</code>, <code>&quot;Ubuntu1804&quot;</code>, <code>&quot;Bottlerocket&quot;</code>, <code>&quot;WindowsServer2019CoreContainer&quot;</code>, <code>&quot;WindowsServer2019FullContainer&quot;</code>, <code>&quot;WindowsServer2022CoreContainer&quot;</code>, <code>&quot;WindowsServer2022FullContainer&quot;</code>.",
"default": "AmazonLinux2",
"enum": [
"AmazonLinux2",
"AmazonLinux2023",
"Ubuntu2204",
"Ubuntu2004",
"Ubuntu1804",
Expand Down Expand Up @@ -1589,11 +1590,12 @@
},
"amiFamily": {
"type": "string",
"description": "Valid variants are: `\"AmazonLinux2\"` (default), `\"Ubuntu2204\"`, `\"Ubuntu2004\"`, `\"Ubuntu1804\"`, `\"Bottlerocket\"`, `\"WindowsServer2019CoreContainer\"`, `\"WindowsServer2019FullContainer\"`, `\"WindowsServer2022CoreContainer\"`, `\"WindowsServer2022FullContainer\"`.",
"x-intellij-html-description": "Valid variants are: <code>&quot;AmazonLinux2&quot;</code> (default), <code>&quot;Ubuntu2204&quot;</code>, <code>&quot;Ubuntu2004&quot;</code>, <code>&quot;Ubuntu1804&quot;</code>, <code>&quot;Bottlerocket&quot;</code>, <code>&quot;WindowsServer2019CoreContainer&quot;</code>, <code>&quot;WindowsServer2019FullContainer&quot;</code>, <code>&quot;WindowsServer2022CoreContainer&quot;</code>, <code>&quot;WindowsServer2022FullContainer&quot;</code>.",
"description": "Valid variants are: `\"AmazonLinux2\"` (default), `\"AmazonLinux2023\"`, `\"Ubuntu2204\"`, `\"Ubuntu2004\"`, `\"Ubuntu1804\"`, `\"Bottlerocket\"`, `\"WindowsServer2019CoreContainer\"`, `\"WindowsServer2019FullContainer\"`, `\"WindowsServer2022CoreContainer\"`, `\"WindowsServer2022FullContainer\"`.",
"x-intellij-html-description": "Valid variants are: <code>&quot;AmazonLinux2&quot;</code> (default), <code>&quot;AmazonLinux2023&quot;</code>, <code>&quot;Ubuntu2204&quot;</code>, <code>&quot;Ubuntu2004&quot;</code>, <code>&quot;Ubuntu1804&quot;</code>, <code>&quot;Bottlerocket&quot;</code>, <code>&quot;WindowsServer2019CoreContainer&quot;</code>, <code>&quot;WindowsServer2019FullContainer&quot;</code>, <code>&quot;WindowsServer2022CoreContainer&quot;</code>, <code>&quot;WindowsServer2022FullContainer&quot;</code>.",
"default": "AmazonLinux2",
"enum": [
"AmazonLinux2",
"AmazonLinux2023",
"Ubuntu2204",
"Ubuntu2004",
"Ubuntu1804",
Expand Down
22 changes: 14 additions & 8 deletions pkg/apis/eksctl.io/v1alpha5/defaults.go
Original file line number Diff line number Diff line change
Expand Up @@ -249,17 +249,23 @@ func setContainerRuntimeDefault(ng *NodeGroup, clusterVersion string) {
return
}

// since clusterVersion is standardised beforehand, we can safely ignore the error
isDockershimDeprecated, _ := utils.IsMinVersion(DockershimDeprecationVersion, clusterVersion)
if ng.AMIFamily == NodeImageFamilyAmazonLinux2023 {
ng.ContainerRuntime = aws.String(ContainerRuntimeContainerD)
return
}

if isDockershimDeprecated {
// since clusterVersion is standardised beforehand, we can safely ignore the error
if isDockershimDeprecated, _ := utils.IsMinVersion(DockershimDeprecationVersion, clusterVersion); isDockershimDeprecated {
ng.ContainerRuntime = aws.String(ContainerRuntimeContainerD)
} else {
ng.ContainerRuntime = aws.String(ContainerRuntimeDockerD)
if IsWindowsImage(ng.AMIFamily) {
ng.ContainerRuntime = aws.String(ContainerRuntimeDockerForWindows)
}
return
}

if IsWindowsImage(ng.AMIFamily) {
ng.ContainerRuntime = aws.String(ContainerRuntimeDockerForWindows)
return
}

ng.ContainerRuntime = aws.String(ContainerRuntimeDockerD)
}

func setIAMDefaults(iamConfig *NodeGroupIAM) {
Expand Down
11 changes: 11 additions & 0 deletions pkg/apis/eksctl.io/v1alpha5/defaults_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -282,6 +282,17 @@ var _ = Describe("ClusterConfig validation", func() {
Expect(*testNodeGroup.ContainerRuntime).To(Equal(ContainerRuntimeDockerForWindows))
})
})
When("ami family is AmazonLinux2023", func() {
It("defaults to containerd as a container runtime", func() {
testNodeGroup := NodeGroup{
NodeGroupBase: &NodeGroupBase{
AMIFamily: NodeImageFamilyAmazonLinux2023,
},
}
SetNodeGroupDefaults(&testNodeGroup, &ClusterMeta{Version: Version1_23}, false)
Expect(*testNodeGroup.ContainerRuntime).To(Equal(ContainerRuntimeContainerD))
})
})
})

Context("Kubernetes version 1.24 or greater", func() {
Expand Down
36 changes: 36 additions & 0 deletions pkg/apis/eksctl.io/v1alpha5/gpu_validation_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,24 @@ var _ = Describe("GPU instance support", func() {
mng.InstanceSelector = &api.InstanceSelector{}
assertValidationError(e, api.ValidateManagedNodeGroup(0, mng))
},
Entry("AL2023 INF", gpuInstanceEntry{
amiFamily: api.NodeImageFamilyAmazonLinux2023,
gpuInstanceType: "inf1.xlarge",
expectUnsupportedErr: true,
instanceTypeName: "Inferentia",
}),
Entry("AL2023 TRN", gpuInstanceEntry{
amiFamily: api.NodeImageFamilyAmazonLinux2023,
gpuInstanceType: "trn1.2xlarge",
expectUnsupportedErr: true,
instanceTypeName: "Trainium",
}),
Entry("AL2023 NVIDIA", gpuInstanceEntry{
amiFamily: api.NodeImageFamilyAmazonLinux2023,
gpuInstanceType: "g4dn.xlarge",
expectUnsupportedErr: true,
instanceTypeName: "GPU",
}),
Entry("AL2", gpuInstanceEntry{
gpuInstanceType: "asdf",
amiFamily: api.NodeImageFamilyAmazonLinux2,
Expand Down Expand Up @@ -72,6 +90,24 @@ var _ = Describe("GPU instance support", func() {
assertValidationError(e, api.ValidateNodeGroup(0, ng, api.NewClusterConfig()))

},
Entry("AL2023 INF", gpuInstanceEntry{
amiFamily: api.NodeImageFamilyAmazonLinux2023,
gpuInstanceType: "inf1.xlarge",
expectUnsupportedErr: true,
instanceTypeName: "Inferentia",
}),
Entry("AL2023 TRN", gpuInstanceEntry{
amiFamily: api.NodeImageFamilyAmazonLinux2023,
gpuInstanceType: "trn1.2xlarge",
expectUnsupportedErr: true,
instanceTypeName: "Trainium",
}),
Entry("AL2023 NVIDIA", gpuInstanceEntry{
amiFamily: api.NodeImageFamilyAmazonLinux2023,
gpuInstanceType: "g4dn.xlarge",
expectUnsupportedErr: true,
instanceTypeName: "GPU",
}),
Entry("AL2", gpuInstanceEntry{
gpuInstanceType: "g4dn.xlarge",
amiFamily: api.NodeImageFamilyAmazonLinux2,
Expand Down
18 changes: 10 additions & 8 deletions pkg/apis/eksctl.io/v1alpha5/types.go
Original file line number Diff line number Diff line change
Expand Up @@ -222,12 +222,13 @@ const (
// All valid values of supported families should go in this block
const (
// DefaultNodeImageFamily (default)
DefaultNodeImageFamily = NodeImageFamilyAmazonLinux2
NodeImageFamilyAmazonLinux2 = "AmazonLinux2"
NodeImageFamilyUbuntu2204 = "Ubuntu2204"
NodeImageFamilyUbuntu2004 = "Ubuntu2004"
NodeImageFamilyUbuntu1804 = "Ubuntu1804"
NodeImageFamilyBottlerocket = "Bottlerocket"
DefaultNodeImageFamily = NodeImageFamilyAmazonLinux2
NodeImageFamilyAmazonLinux2023 = "AmazonLinux2023"
NodeImageFamilyAmazonLinux2 = "AmazonLinux2"
NodeImageFamilyUbuntu2204 = "Ubuntu2204"
NodeImageFamilyUbuntu2004 = "Ubuntu2004"
NodeImageFamilyUbuntu1804 = "Ubuntu1804"
NodeImageFamilyBottlerocket = "Bottlerocket"

NodeImageFamilyWindowsServer2019CoreContainer = "WindowsServer2019CoreContainer"
NodeImageFamilyWindowsServer2019FullContainer = "WindowsServer2019FullContainer"
Expand Down Expand Up @@ -603,9 +604,10 @@ func SupportedNodeVolumeTypes() []string {
}
}

// supportedAMIFamilies are the AMI families supported by EKS
func supportedAMIFamilies() []string {
// SupportedAMIFamilies are the AMI families supported by EKS
func SupportedAMIFamilies() []string {
return []string{
NodeImageFamilyAmazonLinux2023,
NodeImageFamilyAmazonLinux2,
NodeImageFamilyUbuntu2204,
NodeImageFamilyUbuntu2004,
Expand Down
Loading