Skip to content

Commit

Permalink
feat(eks): support Bottlerocket Nvidia AMIs (#28287)
Browse files Browse the repository at this point in the history
Adds support for `BOTTLEROCKET_ARM_64_NVIDIA` and `BOTTLEROCKET_x86_64_NVIDIA` AMI types.

Closes #28241.

----

*By submitting this pull request, I confirm that my contribution is made under the terms of the Apache-2.0 license*
  • Loading branch information
lpizzinidev committed Dec 8, 2023
1 parent 020bf18 commit 6aa1b1b
Show file tree
Hide file tree
Showing 3 changed files with 71 additions and 11 deletions.
11 changes: 11 additions & 0 deletions packages/aws-cdk-lib/aws-eks/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -558,6 +558,17 @@ For example, if the Amazon EKS cluster version is `1.17`, the Bottlerocket AMI v
Please note Bottlerocket does not allow to customize bootstrap options and `bootstrapOptions` properties is not supported when you create the `Bottlerocket` capacity.

To create a Bottlerocket managed nodegroup with Nvidia-based EC2 instance types use the `BOTTLEROCKET_X86_64_NVIDIA` or
`BOTTLEROCKET_ARM_64_NVIDIA` AMIs:

```ts
declare const cluster: eks.Cluster;
cluster.addNodegroupCapacity('BottlerocketNvidiaNG', {
amiType: eks.NodegroupAmiType.BOTTLEROCKET_X86_64_NVIDIA,
instanceTypes: [new ec2.InstanceType('g4dn.xlarge')],
});
```

For more details about Bottlerocket, see [Bottlerocket FAQs](https://aws.amazon.com/bottlerocket/faqs/) and [Bottlerocket Open Source Blog](https://aws.amazon.com/blogs/opensource/announcing-the-general-availability-of-bottlerocket-an-open-source-linux-distribution-purpose-built-to-run-containers/).

### Endpoint Access
Expand Down
29 changes: 21 additions & 8 deletions packages/aws-cdk-lib/aws-eks/lib/managed-nodegroup.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,9 +17,13 @@ export interface INodegroup extends IResource {
}

/**
* The AMI type for your node group. GPU instance types should use the `AL2_x86_64_GPU` AMI type, which uses the
* Amazon EKS-optimized Linux AMI with GPU support. Non-GPU instances should use the `AL2_x86_64` AMI type, which
* uses the Amazon EKS-optimized Linux AMI.
* The AMI type for your node group.
*
* GPU instance types should use the `AL2_x86_64_GPU` AMI type, which uses the
* Amazon EKS-optimized Linux AMI with GPU support or the `BOTTLEROCKET_ARM_64_NVIDIA` or `BOTTLEROCKET_X86_64_NVIDIA`
* AMI types, which uses the Amazon EKS-optimized Linux AMI with Nvidia-GPU support.
*
* Non-GPU instances should use the `AL2_x86_64` AMI type, which uses the Amazon EKS-optimized Linux AMI.
*/
export enum NodegroupAmiType {
/**
Expand All @@ -35,13 +39,21 @@ export enum NodegroupAmiType {
*/
AL2_ARM_64 = 'AL2_ARM_64',
/**
* Bottlerocket Linux(ARM-64)
* Bottlerocket Linux (ARM-64)
*/
BOTTLEROCKET_ARM_64 = 'BOTTLEROCKET_ARM_64',
/**
* Bottlerocket(x86-64)
* Bottlerocket (x86-64)
*/
BOTTLEROCKET_X86_64 = 'BOTTLEROCKET_x86_64',
/**
* Bottlerocket Linux with Nvidia-GPU support (ARM-64)
*/
BOTTLEROCKET_ARM_64_NVIDIA = 'BOTTLEROCKET_ARM_64_NVIDIA',
/**
* Bottlerocket with Nvidia-GPU support (x86-64)
*/
BOTTLEROCKET_X86_64_NVIDIA = 'BOTTLEROCKET_x86_64_NVIDIA',
/**
* Windows Core 2019 (x86-64)
*/
Expand Down Expand Up @@ -215,7 +227,7 @@ export interface NodegroupOptions {
/**
* The instance type to use for your node group. Currently, you can specify a single instance type for a node group.
* The default value for this parameter is `t3.medium`. If you choose a GPU instance type, be sure to specify the
* `AL2_x86_64_GPU` with the amiType parameter.
* `AL2_x86_64_GPU`, `BOTTLEROCKET_ARM_64_NVIDIA`, or `BOTTLEROCKET_x86_64_NVIDIA` with the amiType parameter.
*
* @default t3.medium
* @deprecated Use `instanceTypes` instead.
Expand Down Expand Up @@ -409,7 +421,7 @@ export class Nodegroup extends Resource implements INodegroup {

// if the user explicitly configured an ami type, make sure it's included in the possibleAmiTypes
if (props.amiType && !possibleAmiTypes.includes(props.amiType)) {
throw new Error(`The specified AMI does not match the instance types architecture, either specify one of ${possibleAmiTypes} or don't specify any`);
throw new Error(`The specified AMI does not match the instance types architecture, either specify one of ${possibleAmiTypes.join(', ')} or don't specify any`);
}

//if the user explicitly configured a Windows ami type, make sure the instanceType is allowed
Expand Down Expand Up @@ -550,7 +562,8 @@ const x8664AmiTypes: NodegroupAmiType[] = [NodegroupAmiType.AL2_X86_64, Nodegrou
const windowsAmiTypes: NodegroupAmiType[] = [NodegroupAmiType.WINDOWS_CORE_2019_X86_64,
NodegroupAmiType.WINDOWS_CORE_2022_X86_64, NodegroupAmiType.WINDOWS_FULL_2019_X86_64,
NodegroupAmiType.WINDOWS_FULL_2022_X86_64];
const gpuAmiTypes: NodegroupAmiType[] = [NodegroupAmiType.AL2_X86_64_GPU];
const gpuAmiTypes: NodegroupAmiType[] = [NodegroupAmiType.AL2_X86_64_GPU,
NodegroupAmiType.BOTTLEROCKET_X86_64_NVIDIA, NodegroupAmiType.BOTTLEROCKET_ARM_64_NVIDIA];

/**
* This function check if the instanceType is GPU instance.
Expand Down
42 changes: 39 additions & 3 deletions packages/aws-cdk-lib/aws-eks/test/nodegroup.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -558,7 +558,7 @@ describe('node group', () => {
new ec2.InstanceType('p3.large'),
new ec2.InstanceType('g3.large'),
],
})).toThrow(/The specified AMI does not match the instance types architecture, either specify one of AL2_x86_64_GPU or don't specify any/);
})).toThrow(/The specified AMI does not match the instance types architecture, either specify one of AL2_x86_64_GPU, BOTTLEROCKET_x86_64_NVIDIA, BOTTLEROCKET_ARM_64_NVIDIA or don't specify any/);
});

/**
Expand All @@ -580,7 +580,7 @@ describe('node group', () => {
new ec2.InstanceType('c5.large'),
new ec2.InstanceType('m5.large'),
],
})).toThrow(/The specified AMI does not match the instance types architecture, either specify one of AL2_x86_64,BOTTLEROCKET_x86_64,WINDOWS_CORE_2019_x86_64,WINDOWS_CORE_2022_x86_64,WINDOWS_FULL_2019_x86_64,WINDOWS_FULL_2022_x86_64 or don't specify any/);
})).toThrow(/The specified AMI does not match the instance types architecture, either specify one of AL2_x86_64, BOTTLEROCKET_x86_64, WINDOWS_CORE_2019_x86_64, WINDOWS_CORE_2022_x86_64, WINDOWS_FULL_2019_x86_64, WINDOWS_FULL_2022_x86_64 or don't specify any/);
});

test('throws when AmiType is Windows and forbidden instanceType is selected', () => {
Expand Down Expand Up @@ -619,7 +619,43 @@ describe('node group', () => {
new ec2.InstanceType('c5.large'),
new ec2.InstanceType('m5.large'),
],
})).toThrow(/The specified AMI does not match the instance types architecture, either specify one of AL2_x86_64,BOTTLEROCKET_x86_64,WINDOWS_CORE_2019_x86_64,WINDOWS_CORE_2022_x86_64,WINDOWS_FULL_2019_x86_64,WINDOWS_FULL_2022_x86_64 or don't specify any/);
})).toThrow(/The specified AMI does not match the instance types architecture, either specify one of AL2_x86_64, BOTTLEROCKET_x86_64, WINDOWS_CORE_2019_x86_64, WINDOWS_CORE_2022_x86_64, WINDOWS_FULL_2019_x86_64, WINDOWS_FULL_2022_x86_64 or don't specify any/);
});

test('throws when LaunchTemplate is undefined, amiType is BOTTLEROCKET_ARM_64_NVIDIA and instanceTypes are not GPU', () => {
// GIVEN
const { stack, vpc } = testFixture();
const cluster = new eks.Cluster(stack, 'Cluster', {
vpc,
defaultCapacity: 0,
version: CLUSTER_VERSION,
});
// THEN
expect(() => cluster.addNodegroupCapacity('ng', {
amiType: NodegroupAmiType.BOTTLEROCKET_ARM_64_NVIDIA,
instanceTypes: [
new ec2.InstanceType('c5.large'),
new ec2.InstanceType('m5.large'),
],
})).toThrow(/The specified AMI does not match the instance types architecture, either specify one of AL2_x86_64, BOTTLEROCKET_x86_64, WINDOWS_CORE_2019_x86_64, WINDOWS_CORE_2022_x86_64, WINDOWS_FULL_2019_x86_64, WINDOWS_FULL_2022_x86_64 or don't specify any/);
});

test('throws when LaunchTemplate is undefined, amiType is BOTTLEROCKET_X86_64_NVIDIA and instanceTypes are not GPU', () => {
// GIVEN
const { stack, vpc } = testFixture();
const cluster = new eks.Cluster(stack, 'Cluster', {
vpc,
defaultCapacity: 0,
version: CLUSTER_VERSION,
});
// THEN
expect(() => cluster.addNodegroupCapacity('ng', {
amiType: NodegroupAmiType.BOTTLEROCKET_X86_64_NVIDIA,
instanceTypes: [
new ec2.InstanceType('c5.large'),
new ec2.InstanceType('m5.large'),
],
})).toThrow(/The specified AMI does not match the instance types architecture, either specify one of AL2_x86_64, BOTTLEROCKET_x86_64, WINDOWS_CORE_2019_x86_64, WINDOWS_CORE_2022_x86_64, WINDOWS_FULL_2019_x86_64, WINDOWS_FULL_2022_x86_64 or don't specify any/);
});

/**
Expand Down

0 comments on commit 6aa1b1b

Please sign in to comment.