Skip to content

Commit

Permalink
Merge branch 'main' into niroam-ec2-instance-type-p5
Browse files Browse the repository at this point in the history
  • Loading branch information
mergify[bot] committed Nov 2, 2023
2 parents 5f1df97 + 23b8f8f commit 6b86647
Show file tree
Hide file tree
Showing 4 changed files with 243 additions and 14 deletions.
48 changes: 48 additions & 0 deletions packages/aws-cdk-lib/aws-ec2/lib/instance-types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -158,6 +158,26 @@ export enum InstanceClass {
*/
R6ID = 'r6id',

/**
* Memory optimized instances for high performance computing powered by Intel Xeon Scalable processors (code named Ice Lake), 6th generation
*/
MEMORY6_INTEL_HIGH_PERFORMANCE = 'memory6-intel-high-performance',

/**
* Memory optimized instances for high performance computing powered by Intel Xeon Scalable processors (code named Ice Lake), 6th generation
*/
R6IN = 'r6in',

/**
* Memory optimized instances with local NVME drive for high performance computing powered by Intel Xeon Scalable processors (code named Ice Lake), 6th generation
*/
MEMORY6_INTEL_NVME_DRIVE_HIGH_PERFORMANCE = 'memory6-intel-nvme-drive-high-performance',

/**
* Memory optimized instances with local NVME drive for high performance computing powered by Intel Xeon Scalable processors (code named Ice Lake), 6th generation
*/
R6IDN = 'r6idn',

/**
* Memory optimized instances for high performance computing, 5th generation
*/
Expand Down Expand Up @@ -910,6 +930,26 @@ export enum InstanceClass {
*/
M6ID = 'm6id',

/**
* Standard instances for high performance computing powered by Intel Xeon Scalable processors (code named Ice Lake), 6th generation.
*/
STANDARD6_INTEL_HIGH_PERFORMANCE = 'standard6-intel-high-performance',

/**
* Standard instances for high performance computing powered by Intel Xeon Scalable processors (code named Ice Lake), 6th generation.
*/
M6IN = 'm6in',

/**
* Standard instances with local NVME drive for high performance computing powered by Intel Xeon Scalable processors (code named Ice Lake), 6th generation.
*/
STANDARD6_INTEL_NVME_DRIVE_HIGH_PERFORMANCE = 'standard6-intel-nvme-drive-high-performance',

/**
* Standard instances with local NVME drive for high performance computing powered by Intel Xeon Scalable processors (code named Ice Lake), 6th generation.
*/
M6IDN = 'm6idn',

/**
* Standard instances based on 3rd Gen AMD EPYC processors, 6th generation.
*/
Expand Down Expand Up @@ -1229,6 +1269,10 @@ export class InstanceType {
[InstanceClass.R6I]: 'r6i',
[InstanceClass.MEMORY6_INTEL_NVME_DRIVE]: 'r6id',
[InstanceClass.R6ID]: 'r6id',
[InstanceClass.MEMORY6_INTEL_HIGH_PERFORMANCE]: 'r6in',
[InstanceClass.R6IN]: 'r6in',
[InstanceClass.MEMORY6_INTEL_NVME_DRIVE_HIGH_PERFORMANCE]: 'r6idn',
[InstanceClass.R6IDN]: 'r6idn',
[InstanceClass.MEMORY5_HIGH_PERFORMANCE]: 'r5n',
[InstanceClass.R5N]: 'r5n',
[InstanceClass.MEMORY5_NVME_DRIVE]: 'r5d',
Expand Down Expand Up @@ -1367,6 +1411,10 @@ export class InstanceType {
[InstanceClass.M6I]: 'm6i',
[InstanceClass.STANDARD6_INTEL_NVME_DRIVE]: 'm6id',
[InstanceClass.M6ID]: 'm6id',
[InstanceClass.STANDARD6_INTEL_HIGH_PERFORMANCE]: 'm6in',
[InstanceClass.M6IN]: 'm6in',
[InstanceClass.STANDARD6_INTEL_NVME_DRIVE_HIGH_PERFORMANCE]: 'm6idn',
[InstanceClass.M6IDN]: 'm6idn',
[InstanceClass.STANDARD6_AMD]: 'm6a',
[InstanceClass.M6A]: 'm6a',
[InstanceClass.STANDARD6_GRAVITON2_NVME_DRIVE]: 'm6gd',
Expand Down
10 changes: 5 additions & 5 deletions packages/aws-cdk-lib/aws-opensearchservice/lib/domain.ts
Original file line number Diff line number Diff line change
Expand Up @@ -1525,8 +1525,8 @@ export class Domain extends DomainBase implements IDomain, ec2.IConnectable {

// Validate against instance type restrictions, per
// https://docs.aws.amazon.com/opensearch-service/latest/developerguide/supported-instance-types.html
if (isSomeInstanceType('i3', 'r6gd') && ebsEnabled) {
throw new Error('I3 and R6GD instance types do not support EBS storage volumes.');
if (isSomeInstanceType('i3', 'r6gd', 'im4gn') && ebsEnabled) {
throw new Error('I3, R6GD, and IM4GN instance types do not support EBS storage volumes.');
}

if (isSomeInstanceType('m3', 'r3', 't2') && encryptionAtRestEnabled) {
Expand All @@ -1541,10 +1541,10 @@ export class Domain extends DomainBase implements IDomain, ec2.IConnectable {
throw new Error('T2 and T3 instance types do not support UltraWarm storage.');
}

// Only R3, I3 and r6gd support instance storage, per
// Only R3, I3, R6GD, and IM4GN support instance storage, per
// https://aws.amazon.com/opensearch-service/pricing/
if (!ebsEnabled && !isEveryDatanodeInstanceType('r3', 'i3', 'r6gd')) {
throw new Error('EBS volumes are required when using instance types other than r3, i3 or r6gd.');
if (!ebsEnabled && !isEveryDatanodeInstanceType('r3', 'i3', 'r6gd', 'im4gn')) {
throw new Error('EBS volumes are required when using instance types other than R3, I3, R6GD, or IM4GN.');
}

// Only for a valid ebs volume configuration, per
Expand Down
28 changes: 19 additions & 9 deletions packages/aws-cdk-lib/aws-opensearchservice/test/domain.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -1809,8 +1809,8 @@ each(testedOpenSearchVersions).describe('custom error responses', (engineVersion
})).toThrow(/Node-to-node encryption requires Elasticsearch version 6.0 or later or OpenSearch version 1.0 or later/);
});

test('error when i3 or r6g instance types are specified with EBS enabled', () => {
expect(() => new Domain(stack, 'Domain1', {
test('error when I3, R6GD, and IM4GN instance types are specified with EBS enabled', () => {
expect(() => new Domain(stack, 'Domain2', {
version: engineVersion,
capacity: {
dataNodeInstanceType: 'i3.2xlarge.search',
Expand All @@ -1819,8 +1819,8 @@ each(testedOpenSearchVersions).describe('custom error responses', (engineVersion
volumeSize: 100,
volumeType: EbsDeviceVolumeType.GENERAL_PURPOSE_SSD,
},
})).toThrow(/I3 and R6GD instance types do not support EBS storage volumes/);
expect(() => new Domain(stack, 'Domain2', {
})).toThrow(/I3, R6GD, and IM4GN instance types do not support EBS storage volumes./);
expect(() => new Domain(stack, 'Domain3', {
version: engineVersion,
capacity: {
dataNodeInstanceType: 'r6gd.large.search',
Expand All @@ -1829,7 +1829,17 @@ each(testedOpenSearchVersions).describe('custom error responses', (engineVersion
volumeSize: 100,
volumeType: EbsDeviceVolumeType.GENERAL_PURPOSE_SSD,
},
})).toThrow(/I3 and R6GD instance types do not support EBS storage volumes/);
})).toThrow(/I3, R6GD, and IM4GN instance types do not support EBS storage volumes./);
expect(() => new Domain(stack, 'Domain4', {
version: engineVersion,
capacity: {
dataNodeInstanceType: 'im4gn.2xlarge.search',
},
ebs: {
volumeSize: 100,
volumeType: EbsDeviceVolumeType.GENERAL_PURPOSE_SSD,
},
})).toThrow(/I3, R6GD, and IM4GN instance types do not support EBS storage volumes./);
});

test('error when m3, r3, or t2 instance types are specified with encryption at rest enabled', () => {
Expand Down Expand Up @@ -1872,7 +1882,7 @@ each(testedOpenSearchVersions).describe('custom error responses', (engineVersion
})).toThrow(/t2.micro.search instance type supports only Elasticsearch versions 1.5 and 2.3/);
});

test('error when any instance type other than R3, I3 and R6GD are specified without EBS enabled', () => {
test('error when any instance type other than R3, I3, R6GD, or IM4GN are specified without EBS enabled', () => {
expect(() => new Domain(stack, 'Domain1', {
version: engineVersion,
ebs: {
Expand All @@ -1881,16 +1891,16 @@ each(testedOpenSearchVersions).describe('custom error responses', (engineVersion
capacity: {
masterNodeInstanceType: 'm5.large.search',
},
})).toThrow(/EBS volumes are required when using instance types other than r3, i3 or r6gd/);
})).toThrow(/EBS volumes are required when using instance types other than R3, I3, R6GD, or IM4GN./);
expect(() => new Domain(stack, 'Domain2', {
version: engineVersion,
ebs: {
enabled: false,
},
capacity: {
dataNodeInstanceType: 'm5.large.search',
dataNodeInstanceType: 'r5.large.search',
},
})).toThrow(/EBS volumes are required when using instance types other than r3, i3 or r6gd/);
})).toThrow(/EBS volumes are required when using instance types other than R3, I3, R6GD, or IM4GN./);
});

test('can use compatible master instance types that does not have local storage when data node type is i3 or r6gd', () => {
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,171 @@
const mockGetPipelineState = jest.fn();
const mockPutApprovalResult = jest.fn();
const mockCodePipeline = {
getPipelineState: mockGetPipelineState,
putApprovalResult: mockPutApprovalResult,
};

jest.mock('@aws-sdk/client-codepipeline', () => {
return {
CodePipeline: jest.fn(() => mockCodePipeline),
};
});

jest.setTimeout(10_000);

import { handler } from '../../lib/private/approve-lambda/index';

describe('approve-lambda handler', () => {

beforeEach(() => {
jest.spyOn(global, 'setTimeout');
});

afterEach(() => {
jest.clearAllMocks();
});

test('automatic approval works', async () => {
// GIVEN
mockGetPipelineState.mockImplementation(() => {
return {
stageStates: [{
stageName: 'stage',
actionStates: [{
actionName: 'action',
latestExecution: {
lastStatusChange: 1446137358.328,
status: 'Succeeded',
token: 'token',
},
}],
}],
};
});

const event = {
PipelineName: 'pipeline',
StageName: 'stage',
ActionName: 'action',
};

// WHEN
await handler(event, {});

// THEN
expect(mockPutApprovalResult).toHaveBeenCalled();
});

test('does not approve if stageName not found', async () => {
// GIVEN
mockGetPipelineState.mockImplementation(async () => {
return {
stageStates: [{
stageName: 'unknown',
actionStates: [{
actionName: 'action',
latestExecution: {
lastStatusChange: 1446137358.328,
status: 'Succeeded',
token: 'token',
},
}],
}],
};
});

// expire deadline after first loop
jest.spyOn(Date, 'now')
.mockReturnValueOnce(0)
.mockReturnValueOnce(0)
.mockReturnValueOnce(10 * 60_000);

const event = {
PipelineName: 'pipeline',
StageName: 'stage',
ActionName: 'action',
};

// WHEN
await handler(event, {});

// THEN
expect(setTimeout).toHaveBeenCalled();
expect(mockPutApprovalResult).not.toHaveBeenCalled();
});

test('does not approve if actionName not found', async () => {
// GIVEN
mockGetPipelineState.mockImplementation(async () => {
return {
stageStates: [{
stageName: 'stage',
actionStates: [{
actionName: 'unknown',
latestExecution: {
lastStatusChange: 1446137358.328,
status: 'Succeeded',
token: 'token',
},
}],
}],
};
});

// expire deadline after first loop
jest.spyOn(Date, 'now')
.mockReturnValueOnce(0)
.mockReturnValueOnce(0)
.mockReturnValueOnce(10 * 60_000);

const event = {
PipelineName: 'pipeline',
StageName: 'stage',
ActionName: 'action',
};

// WHEN
await handler(event, {});

// THEN
expect(setTimeout).toHaveBeenCalled();
expect(mockPutApprovalResult).not.toHaveBeenCalled();
});

test('does not approve if token not present', async () => {
// GIVEN
mockGetPipelineState.mockImplementation(async () => {
return {
stageStates: [{
stageName: 'stage',
actionStates: [{
actionName: 'unknown',
latestExecution: {
lastStatusChange: 1446137358.328,
status: 'Succeeded',
},
}],
}],
};
});

// expire deadline after first loop
jest.spyOn(Date, 'now')
.mockReturnValueOnce(0)
.mockReturnValueOnce(0)
.mockReturnValueOnce(10 * 60_000);

const event = {
PipelineName: 'pipeline',
StageName: 'stage',
ActionName: 'action',
};

// WHEN
await handler(event, {});

// THEN
expect(setTimeout).toHaveBeenCalled();
expect(mockPutApprovalResult).not.toHaveBeenCalled();
});
});

0 comments on commit 6b86647

Please sign in to comment.