@composurecdk/ec2 0.6.0 → 0.8.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +121 -0
- package/dist/commonjs/index.d.ts +14 -0
- package/dist/commonjs/index.d.ts.map +1 -0
- package/dist/commonjs/index.js +22 -0
- package/dist/commonjs/index.js.map +1 -0
- package/dist/commonjs/instance-alarm-config.d.ts.map +1 -0
- package/dist/commonjs/instance-alarm-config.js +3 -0
- package/dist/commonjs/instance-alarm-config.js.map +1 -0
- package/dist/commonjs/instance-alarm-defaults.d.ts.map +1 -0
- package/dist/commonjs/instance-alarm-defaults.js +65 -0
- package/dist/commonjs/instance-alarm-defaults.js.map +1 -0
- package/dist/commonjs/instance-alarms.d.ts.map +1 -0
- package/dist/commonjs/instance-alarms.js +132 -0
- package/dist/commonjs/instance-alarms.js.map +1 -0
- package/dist/{instance-builder.d.ts → commonjs/instance-builder.d.ts} +44 -6
- package/dist/commonjs/instance-builder.d.ts.map +1 -0
- package/dist/commonjs/instance-builder.js +135 -0
- package/dist/commonjs/instance-builder.js.map +1 -0
- package/dist/commonjs/instance-defaults.d.ts.map +1 -0
- package/dist/commonjs/instance-defaults.js +62 -0
- package/dist/commonjs/instance-defaults.js.map +1 -0
- package/dist/commonjs/instance-volume-attachment-config.d.ts +34 -0
- package/dist/commonjs/instance-volume-attachment-config.d.ts.map +1 -0
- package/dist/commonjs/instance-volume-attachment-config.js +3 -0
- package/dist/commonjs/instance-volume-attachment-config.js.map +1 -0
- package/dist/commonjs/instance-volume-attachment-defaults.d.ts +14 -0
- package/dist/commonjs/instance-volume-attachment-defaults.d.ts.map +1 -0
- package/dist/commonjs/instance-volume-attachment-defaults.js +27 -0
- package/dist/commonjs/instance-volume-attachment-defaults.js.map +1 -0
- package/dist/commonjs/instance-volume-attachments.d.ts +59 -0
- package/dist/commonjs/instance-volume-attachments.d.ts.map +1 -0
- package/dist/commonjs/instance-volume-attachments.js +107 -0
- package/dist/commonjs/instance-volume-attachments.js.map +1 -0
- package/dist/commonjs/package.json +3 -0
- package/dist/commonjs/volume-alarm-config.d.ts +35 -0
- package/dist/commonjs/volume-alarm-config.d.ts.map +1 -0
- package/dist/commonjs/volume-alarm-config.js +3 -0
- package/dist/commonjs/volume-alarm-config.js.map +1 -0
- package/dist/commonjs/volume-alarm-defaults.d.ts +17 -0
- package/dist/commonjs/volume-alarm-defaults.d.ts.map +1 -0
- package/dist/commonjs/volume-alarm-defaults.js +30 -0
- package/dist/commonjs/volume-alarm-defaults.js.map +1 -0
- package/dist/commonjs/volume-alarms.d.ts +29 -0
- package/dist/commonjs/volume-alarms.d.ts.map +1 -0
- package/dist/commonjs/volume-alarms.js +92 -0
- package/dist/commonjs/volume-alarms.js.map +1 -0
- package/dist/commonjs/volume-builder.d.ts +171 -0
- package/dist/commonjs/volume-builder.d.ts.map +1 -0
- package/dist/commonjs/volume-builder.js +98 -0
- package/dist/commonjs/volume-builder.js.map +1 -0
- package/dist/commonjs/volume-defaults.d.ts +15 -0
- package/dist/commonjs/volume-defaults.d.ts.map +1 -0
- package/dist/commonjs/volume-defaults.js +50 -0
- package/dist/commonjs/volume-defaults.js.map +1 -0
- package/dist/{vpc-builder.d.ts → commonjs/vpc-builder.d.ts} +3 -2
- package/dist/commonjs/vpc-builder.d.ts.map +1 -0
- package/dist/commonjs/vpc-builder.js +82 -0
- package/dist/commonjs/vpc-builder.js.map +1 -0
- package/dist/commonjs/vpc-defaults.d.ts.map +1 -0
- package/dist/commonjs/vpc-defaults.js +58 -0
- package/dist/commonjs/vpc-defaults.js.map +1 -0
- package/dist/esm/index.d.ts +14 -0
- package/dist/esm/index.d.ts.map +1 -0
- package/dist/esm/index.js +10 -0
- package/dist/esm/index.js.map +1 -0
- package/dist/esm/instance-alarm-config.d.ts +62 -0
- package/dist/esm/instance-alarm-config.d.ts.map +1 -0
- package/dist/esm/instance-alarm-config.js.map +1 -0
- package/dist/esm/instance-alarm-defaults.d.ts +20 -0
- package/dist/esm/instance-alarm-defaults.d.ts.map +1 -0
- package/dist/esm/instance-alarm-defaults.js.map +1 -0
- package/dist/esm/instance-alarms.d.ts +28 -0
- package/dist/esm/instance-alarms.d.ts.map +1 -0
- package/dist/esm/instance-alarms.js.map +1 -0
- package/dist/esm/instance-builder.d.ts +223 -0
- package/dist/esm/instance-builder.d.ts.map +1 -0
- package/dist/{instance-builder.js → esm/instance-builder.js} +49 -4
- package/dist/esm/instance-builder.js.map +1 -0
- package/dist/esm/instance-defaults.d.ts +14 -0
- package/dist/esm/instance-defaults.d.ts.map +1 -0
- package/dist/esm/instance-defaults.js.map +1 -0
- package/dist/esm/instance-volume-attachment-config.d.ts +34 -0
- package/dist/esm/instance-volume-attachment-config.d.ts.map +1 -0
- package/dist/esm/instance-volume-attachment-config.js +2 -0
- package/dist/esm/instance-volume-attachment-config.js.map +1 -0
- package/dist/esm/instance-volume-attachment-defaults.d.ts +14 -0
- package/dist/esm/instance-volume-attachment-defaults.d.ts.map +1 -0
- package/dist/esm/instance-volume-attachment-defaults.js +24 -0
- package/dist/esm/instance-volume-attachment-defaults.js.map +1 -0
- package/dist/esm/instance-volume-attachments.d.ts +59 -0
- package/dist/esm/instance-volume-attachments.d.ts.map +1 -0
- package/dist/esm/instance-volume-attachments.js +104 -0
- package/dist/esm/instance-volume-attachments.js.map +1 -0
- package/dist/esm/package.json +3 -0
- package/dist/esm/volume-alarm-config.d.ts +35 -0
- package/dist/esm/volume-alarm-config.d.ts.map +1 -0
- package/dist/esm/volume-alarm-config.js +2 -0
- package/dist/esm/volume-alarm-config.js.map +1 -0
- package/dist/esm/volume-alarm-defaults.d.ts +17 -0
- package/dist/esm/volume-alarm-defaults.d.ts.map +1 -0
- package/dist/esm/volume-alarm-defaults.js +27 -0
- package/dist/esm/volume-alarm-defaults.js.map +1 -0
- package/dist/esm/volume-alarms.d.ts +29 -0
- package/dist/esm/volume-alarms.d.ts.map +1 -0
- package/dist/esm/volume-alarms.js +88 -0
- package/dist/esm/volume-alarms.js.map +1 -0
- package/dist/esm/volume-builder.d.ts +171 -0
- package/dist/esm/volume-builder.d.ts.map +1 -0
- package/dist/esm/volume-builder.js +95 -0
- package/dist/esm/volume-builder.js.map +1 -0
- package/dist/esm/volume-defaults.d.ts +15 -0
- package/dist/esm/volume-defaults.d.ts.map +1 -0
- package/dist/esm/volume-defaults.js +47 -0
- package/dist/esm/volume-defaults.js.map +1 -0
- package/dist/esm/vpc-builder.d.ts +110 -0
- package/dist/esm/vpc-builder.d.ts.map +1 -0
- package/dist/{vpc-builder.js → esm/vpc-builder.js} +2 -2
- package/dist/esm/vpc-builder.js.map +1 -0
- package/dist/esm/vpc-defaults.d.ts +15 -0
- package/dist/esm/vpc-defaults.d.ts.map +1 -0
- package/dist/esm/vpc-defaults.js.map +1 -0
- package/package.json +36 -17
- package/dist/index.d.ts +0 -7
- package/dist/index.d.ts.map +0 -1
- package/dist/index.js +0 -6
- package/dist/index.js.map +0 -1
- package/dist/instance-alarm-config.d.ts.map +0 -1
- package/dist/instance-alarm-config.js.map +0 -1
- package/dist/instance-alarm-defaults.d.ts.map +0 -1
- package/dist/instance-alarm-defaults.js.map +0 -1
- package/dist/instance-alarms.d.ts.map +0 -1
- package/dist/instance-alarms.js.map +0 -1
- package/dist/instance-builder.d.ts.map +0 -1
- package/dist/instance-builder.js.map +0 -1
- package/dist/instance-defaults.d.ts.map +0 -1
- package/dist/instance-defaults.js.map +0 -1
- package/dist/vpc-builder.d.ts.map +0 -1
- package/dist/vpc-builder.js.map +0 -1
- package/dist/vpc-defaults.d.ts.map +0 -1
- package/dist/vpc-defaults.js.map +0 -1
- /package/dist/{instance-alarm-config.d.ts → commonjs/instance-alarm-config.d.ts} +0 -0
- /package/dist/{instance-alarm-defaults.d.ts → commonjs/instance-alarm-defaults.d.ts} +0 -0
- /package/dist/{instance-alarms.d.ts → commonjs/instance-alarms.d.ts} +0 -0
- /package/dist/{instance-defaults.d.ts → commonjs/instance-defaults.d.ts} +0 -0
- /package/dist/{vpc-defaults.d.ts → commonjs/vpc-defaults.d.ts} +0 -0
- /package/dist/{instance-alarm-config.js → esm/instance-alarm-config.js} +0 -0
- /package/dist/{instance-alarm-defaults.js → esm/instance-alarm-defaults.js} +0 -0
- /package/dist/{instance-alarms.js → esm/instance-alarms.js} +0 -0
- /package/dist/{instance-defaults.js → esm/instance-defaults.js} +0 -0
- /package/dist/{vpc-defaults.js → esm/vpc-defaults.js} +0 -0
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"instance-builder.js","sourceRoot":"","sources":["../../src/instance-builder.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"instance-defaults.d.ts","sourceRoot":"","sources":["../../src/instance-defaults.ts"],"names":[],"mappings":"AAAA,OAAO,EAA0C,KAAK,aAAa,EAAE,MAAM,qBAAqB,CAAC;AAEjG;;;;;;;;;;GAUG;AACH,eAAO,MAAM,iBAAiB,EAAE,OAAO,CAAC,aAAa,CAiDpD,CAAC"}
|
|
@@ -0,0 +1,62 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.INSTANCE_DEFAULTS = void 0;
|
|
4
|
+
const aws_ec2_1 = require("aws-cdk-lib/aws-ec2");
|
|
5
|
+
/**
|
|
6
|
+
* Secure, AWS-recommended defaults applied to every EC2 instance built with
|
|
7
|
+
* {@link createInstanceBuilder}. Each property can be individually overridden
|
|
8
|
+
* via the builder's fluent API.
|
|
9
|
+
*
|
|
10
|
+
* Three required properties intentionally have no default — they are
|
|
11
|
+
* application-specific and must be supplied explicitly:
|
|
12
|
+
* - `vpc` (via the builder's `.vpc()` method)
|
|
13
|
+
* - `instanceType`
|
|
14
|
+
* - `machineImage`
|
|
15
|
+
*/
|
|
16
|
+
exports.INSTANCE_DEFAULTS = {
|
|
17
|
+
/**
|
|
18
|
+
* Require IMDSv2. IMDSv1 is vulnerable to SSRF-based credential exfiltration;
|
|
19
|
+
* IMDSv2 requires a session token and blocks the common attack pattern.
|
|
20
|
+
* @see https://docs.aws.amazon.com/wellarchitected/latest/security-pillar/sec_detect_investigate_events_app_service_logging.html
|
|
21
|
+
* @see https://docs.aws.amazon.com/AWSEC2/latest/UserGuide/configuring-instance-metadata-service.html
|
|
22
|
+
*/
|
|
23
|
+
requireImdsv2: true,
|
|
24
|
+
/**
|
|
25
|
+
* Enable detailed (1-minute) CloudWatch metrics. Without this, instance
|
|
26
|
+
* metrics are emitted at 5-minute granularity, which makes short-window
|
|
27
|
+
* alarm evaluation unreliable.
|
|
28
|
+
* @see https://docs.aws.amazon.com/AWSEC2/latest/UserGuide/using-cloudwatch-new.html
|
|
29
|
+
*/
|
|
30
|
+
detailedMonitoring: true,
|
|
31
|
+
/**
|
|
32
|
+
* Attach the AmazonSSMManagedInstanceCore managed policy so Session Manager
|
|
33
|
+
* can be used in place of SSH. Removes the need for key pairs, bastion
|
|
34
|
+
* hosts, or inbound SSH access.
|
|
35
|
+
* @see https://docs.aws.amazon.com/systems-manager/latest/userguide/session-manager.html
|
|
36
|
+
*/
|
|
37
|
+
ssmSessionPermissions: true,
|
|
38
|
+
/**
|
|
39
|
+
* EBS-optimized networking — dedicated bandwidth between the instance and
|
|
40
|
+
* its EBS volumes. Free and on-by-default for current-generation instance
|
|
41
|
+
* types; set explicitly for consistency.
|
|
42
|
+
* @see https://docs.aws.amazon.com/AWSEC2/latest/UserGuide/ebs-optimized.html
|
|
43
|
+
*/
|
|
44
|
+
ebsOptimized: true,
|
|
45
|
+
/**
|
|
46
|
+
* Encrypt the root EBS volume at rest using the account's default EBS KMS
|
|
47
|
+
* key. GP3 is the current-generation general-purpose volume type — cheaper
|
|
48
|
+
* and faster than GP2 at equivalent sizes. Users override this to change
|
|
49
|
+
* volume size, IOPS, throughput, or to add additional block devices.
|
|
50
|
+
* @see https://docs.aws.amazon.com/AWSEC2/latest/UserGuide/EBSEncryption.html
|
|
51
|
+
*/
|
|
52
|
+
blockDevices: [
|
|
53
|
+
{
|
|
54
|
+
deviceName: "/dev/xvda",
|
|
55
|
+
volume: aws_ec2_1.BlockDeviceVolume.ebs(8, {
|
|
56
|
+
encrypted: true,
|
|
57
|
+
volumeType: aws_ec2_1.EbsDeviceVolumeType.GP3,
|
|
58
|
+
}),
|
|
59
|
+
},
|
|
60
|
+
],
|
|
61
|
+
};
|
|
62
|
+
//# sourceMappingURL=instance-defaults.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"instance-defaults.js","sourceRoot":"","sources":["../../src/instance-defaults.ts"],"names":[],"mappings":";;;AAAA,iDAAiG;AAEjG;;;;;;;;;;GAUG;AACU,QAAA,iBAAiB,GAA2B;IACvD;;;;;OAKG;IACH,aAAa,EAAE,IAAI;IAEnB;;;;;OAKG;IACH,kBAAkB,EAAE,IAAI;IAExB;;;;;OAKG;IACH,qBAAqB,EAAE,IAAI;IAE3B;;;;;OAKG;IACH,YAAY,EAAE,IAAI;IAElB;;;;;;OAMG;IACH,YAAY,EAAE;QACZ;YACE,UAAU,EAAE,WAAW;YACvB,MAAM,EAAE,2BAAiB,CAAC,GAAG,CAAC,CAAC,EAAE;gBAC/B,SAAS,EAAE,IAAI;gBACf,UAAU,EAAE,6BAAmB,CAAC,GAAG;aACpC,CAAC;SACH;KACF;CACF,CAAC"}
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
import type { AlarmConfig } from "@composurecdk/cloudwatch";
|
|
2
|
+
/**
|
|
3
|
+
* Controls which recommended alarms are created for a per-attachment EBS
|
|
4
|
+
* volume on an EC2 instance.
|
|
5
|
+
*
|
|
6
|
+
* Default thresholds are sourced from the AWS-recommended CloudWatch
|
|
7
|
+
* alarm guide. Set the master switch or individual alarms to `false` to
|
|
8
|
+
* disable them, or provide an {@link AlarmConfig} to tune thresholds.
|
|
9
|
+
*
|
|
10
|
+
* @see https://docs.aws.amazon.com/AmazonCloudWatch/latest/monitoring/Best_Practice_Recommended_Alarms_AWS_Services.html#EBS
|
|
11
|
+
*/
|
|
12
|
+
export interface VolumeAttachmentAlarmConfig {
|
|
13
|
+
/**
|
|
14
|
+
* Master switch: set to `false` to disable all per-attachment alarms.
|
|
15
|
+
* @default true
|
|
16
|
+
*/
|
|
17
|
+
enabled?: boolean;
|
|
18
|
+
/**
|
|
19
|
+
* Alarm when the per-attachment EBS volume status check reports a
|
|
20
|
+
* stalled I/O condition — typically a host or storage-subsystem issue
|
|
21
|
+
* for that specific attachment.
|
|
22
|
+
*
|
|
23
|
+
* Metric: `AWS/EBS VolumeStalledIOCheck`, statistic Maximum,
|
|
24
|
+
* period 1 minute. Default threshold: >= 1 over 10 consecutive minutes.
|
|
25
|
+
*
|
|
26
|
+
* The metric is published only for Nitro-instance attachments. On
|
|
27
|
+
* non-Nitro instances the alarm sits at `INSUFFICIENT_DATA`, which the
|
|
28
|
+
* `treatMissingData: NOT_BREACHING` default makes harmless.
|
|
29
|
+
*
|
|
30
|
+
* @see https://docs.aws.amazon.com/AmazonCloudWatch/latest/monitoring/Best_Practice_Recommended_Alarms_AWS_Services.html#EBS
|
|
31
|
+
*/
|
|
32
|
+
volumeStalledIo?: AlarmConfig | false;
|
|
33
|
+
}
|
|
34
|
+
//# sourceMappingURL=instance-volume-attachment-config.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"instance-volume-attachment-config.d.ts","sourceRoot":"","sources":["../../src/instance-volume-attachment-config.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,0BAA0B,CAAC;AAE5D;;;;;;;;;GASG;AACH,MAAM,WAAW,2BAA2B;IAC1C;;;OAGG;IACH,OAAO,CAAC,EAAE,OAAO,CAAC;IAElB;;;;;;;;;;;;;OAaG;IACH,eAAe,CAAC,EAAE,WAAW,GAAG,KAAK,CAAC;CACvC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"instance-volume-attachment-config.js","sourceRoot":"","sources":["../../src/instance-volume-attachment-config.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
import type { AlarmConfigDefaults } from "@composurecdk/cloudwatch";
|
|
2
|
+
interface VolumeAttachmentAlarmDefaults {
|
|
3
|
+
enabled: true;
|
|
4
|
+
volumeStalledIo: AlarmConfigDefaults;
|
|
5
|
+
}
|
|
6
|
+
/**
|
|
7
|
+
* AWS-recommended default alarm configuration for per-attachment EBS
|
|
8
|
+
* volumes.
|
|
9
|
+
*
|
|
10
|
+
* @see https://docs.aws.amazon.com/AmazonCloudWatch/latest/monitoring/Best_Practice_Recommended_Alarms_AWS_Services.html#EBS
|
|
11
|
+
*/
|
|
12
|
+
export declare const VOLUME_ATTACHMENT_ALARM_DEFAULTS: VolumeAttachmentAlarmDefaults;
|
|
13
|
+
export {};
|
|
14
|
+
//# sourceMappingURL=instance-volume-attachment-defaults.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"instance-volume-attachment-defaults.d.ts","sourceRoot":"","sources":["../../src/instance-volume-attachment-defaults.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,0BAA0B,CAAC;AAEpE,UAAU,6BAA6B;IACrC,OAAO,EAAE,IAAI,CAAC;IACd,eAAe,EAAE,mBAAmB,CAAC;CACtC;AAED;;;;;GAKG;AACH,eAAO,MAAM,gCAAgC,EAAE,6BAgB9C,CAAC"}
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.VOLUME_ATTACHMENT_ALARM_DEFAULTS = void 0;
|
|
4
|
+
const aws_cloudwatch_1 = require("aws-cdk-lib/aws-cloudwatch");
|
|
5
|
+
/**
|
|
6
|
+
* AWS-recommended default alarm configuration for per-attachment EBS
|
|
7
|
+
* volumes.
|
|
8
|
+
*
|
|
9
|
+
* @see https://docs.aws.amazon.com/AmazonCloudWatch/latest/monitoring/Best_Practice_Recommended_Alarms_AWS_Services.html#EBS
|
|
10
|
+
*/
|
|
11
|
+
exports.VOLUME_ATTACHMENT_ALARM_DEFAULTS = {
|
|
12
|
+
enabled: true,
|
|
13
|
+
/**
|
|
14
|
+
* The single AWS-recommended EBS alarm. Complements the existing
|
|
15
|
+
* `attachedEbsStatusCheckFailed` on the instance: the EC2-side metric
|
|
16
|
+
* pages on instance-level reachability, this one on per-volume health.
|
|
17
|
+
* The 10-of-10 evaluation window matches AWS guidance — EBS
|
|
18
|
+
* infrastructure usually self-heals within a few minutes.
|
|
19
|
+
*/
|
|
20
|
+
volumeStalledIo: {
|
|
21
|
+
threshold: 1,
|
|
22
|
+
evaluationPeriods: 10,
|
|
23
|
+
datapointsToAlarm: 10,
|
|
24
|
+
treatMissingData: aws_cloudwatch_1.TreatMissingData.NOT_BREACHING,
|
|
25
|
+
},
|
|
26
|
+
};
|
|
27
|
+
//# sourceMappingURL=instance-volume-attachment-defaults.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"instance-volume-attachment-defaults.js","sourceRoot":"","sources":["../../src/instance-volume-attachment-defaults.ts"],"names":[],"mappings":";;;AAAA,+DAA8D;AAQ9D;;;;;GAKG;AACU,QAAA,gCAAgC,GAAkC;IAC7E,OAAO,EAAE,IAAI;IAEb;;;;;;OAMG;IACH,eAAe,EAAE;QACf,SAAS,EAAE,CAAC;QACZ,iBAAiB,EAAE,EAAE;QACrB,iBAAiB,EAAE,EAAE;QACrB,gBAAgB,EAAE,iCAAgB,CAAC,aAAa;KACjD;CACF,CAAC"}
|
|
@@ -0,0 +1,59 @@
|
|
|
1
|
+
import { type Alarm } from "aws-cdk-lib/aws-cloudwatch";
|
|
2
|
+
import { CfnVolumeAttachment, type Instance, type InstanceProps, type IVolume } from "aws-cdk-lib/aws-ec2";
|
|
3
|
+
import type { IConstruct } from "constructs";
|
|
4
|
+
import { type Resolvable } from "@composurecdk/core";
|
|
5
|
+
import type { VolumeBuilderResult } from "./volume-builder.js";
|
|
6
|
+
import type { VolumeAttachmentAlarmConfig } from "./instance-volume-attachment-config.js";
|
|
7
|
+
/**
|
|
8
|
+
* Reference to the volume to be attached. Either a sibling
|
|
9
|
+
* {@link VolumeBuilderResult} (the common composed-system case) or a
|
|
10
|
+
* concrete {@link IVolume} (for externally-managed volumes).
|
|
11
|
+
*/
|
|
12
|
+
export type AttachVolumeRef = Resolvable<VolumeBuilderResult> | Resolvable<IVolume>;
|
|
13
|
+
/**
|
|
14
|
+
* Configuration for a single `attachVolume` call.
|
|
15
|
+
*/
|
|
16
|
+
export interface AttachVolumeOptions {
|
|
17
|
+
/**
|
|
18
|
+
* Linux device name to attach the volume as (e.g. `/dev/sdf`).
|
|
19
|
+
*
|
|
20
|
+
* The Linux kernel may rename this to `xvdf` etc. on the instance —
|
|
21
|
+
* resolve mounts via UUID rather than the device path.
|
|
22
|
+
*
|
|
23
|
+
* @see https://docs.aws.amazon.com/AWSEC2/latest/UserGuide/device_naming.html
|
|
24
|
+
*/
|
|
25
|
+
device: string;
|
|
26
|
+
/**
|
|
27
|
+
* Configuration for the per-attachment recommended alarms.
|
|
28
|
+
*
|
|
29
|
+
* @default - alarms enabled with the defaults in
|
|
30
|
+
* {@link VOLUME_ATTACHMENT_ALARM_DEFAULTS}.
|
|
31
|
+
*/
|
|
32
|
+
recommendedAlarms?: VolumeAttachmentAlarmConfig | false;
|
|
33
|
+
}
|
|
34
|
+
/**
|
|
35
|
+
* Internal config captured by {@link IInstanceBuilder.attachVolume} and
|
|
36
|
+
* forwarded to {@link createVolumeAttachments} at build time.
|
|
37
|
+
*
|
|
38
|
+
* @internal
|
|
39
|
+
*/
|
|
40
|
+
export interface PendingVolumeAttachment {
|
|
41
|
+
key: string;
|
|
42
|
+
volumeRef: AttachVolumeRef;
|
|
43
|
+
options: AttachVolumeOptions;
|
|
44
|
+
}
|
|
45
|
+
/**
|
|
46
|
+
* Creates a {@link CfnVolumeAttachment} for each pending attachment and
|
|
47
|
+
* (when configured) the per-attachment recommended alarms. Synth-time AZ
|
|
48
|
+
* alignment is validated when both the volume's AZ and the instance's
|
|
49
|
+
* effective AZ are concrete strings.
|
|
50
|
+
*
|
|
51
|
+
* @returns The created `CfnVolumeAttachment`s keyed by attachment key,
|
|
52
|
+
* plus the per-attachment alarms keyed by `${attachmentKey}.${alarmKey}`
|
|
53
|
+
* so they can be flat-merged into the instance's `alarms` record.
|
|
54
|
+
*/
|
|
55
|
+
export declare function createVolumeAttachments(scope: IConstruct, id: string, instance: Instance, instanceProps: InstanceProps, attachments: PendingVolumeAttachment[], context?: Record<string, object>): {
|
|
56
|
+
attachments: Record<string, CfnVolumeAttachment>;
|
|
57
|
+
alarms: Record<string, Alarm>;
|
|
58
|
+
};
|
|
59
|
+
//# sourceMappingURL=instance-volume-attachments.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"instance-volume-attachments.d.ts","sourceRoot":"","sources":["../../src/instance-volume-attachments.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,KAAK,KAAK,EAAqC,MAAM,4BAA4B,CAAC;AAC3F,OAAO,EACL,mBAAmB,EACnB,KAAK,QAAQ,EACb,KAAK,aAAa,EAClB,KAAK,OAAO,EAEb,MAAM,qBAAqB,CAAC;AAC7B,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,YAAY,CAAC;AAC7C,OAAO,EAAW,KAAK,UAAU,EAAE,MAAM,oBAAoB,CAAC;AAE9D,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,qBAAqB,CAAC;AAC/D,OAAO,KAAK,EAAE,2BAA2B,EAAE,MAAM,wCAAwC,CAAC;AAM1F;;;;GAIG;AACH,MAAM,MAAM,eAAe,GAAG,UAAU,CAAC,mBAAmB,CAAC,GAAG,UAAU,CAAC,OAAO,CAAC,CAAC;AAEpF;;GAEG;AACH,MAAM,WAAW,mBAAmB;IAClC;;;;;;;OAOG;IACH,MAAM,EAAE,MAAM,CAAC;IAEf;;;;;OAKG;IACH,iBAAiB,CAAC,EAAE,2BAA2B,GAAG,KAAK,CAAC;CACzD;AAED;;;;;GAKG;AACH,MAAM,WAAW,uBAAuB;IACtC,GAAG,EAAE,MAAM,CAAC;IACZ,SAAS,EAAE,eAAe,CAAC;IAC3B,OAAO,EAAE,mBAAmB,CAAC;CAC9B;AAsFD;;;;;;;;;GASG;AACH,wBAAgB,uBAAuB,CACrC,KAAK,EAAE,UAAU,EACjB,EAAE,EAAE,MAAM,EACV,QAAQ,EAAE,QAAQ,EAClB,aAAa,EAAE,aAAa,EAC5B,WAAW,EAAE,uBAAuB,EAAE,EACtC,OAAO,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,GAC/B;IAAE,WAAW,EAAE,MAAM,CAAC,MAAM,EAAE,mBAAmB,CAAC,CAAC;IAAC,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,KAAK,CAAC,CAAA;CAAE,CAwCrF"}
|
|
@@ -0,0 +1,107 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.createVolumeAttachments = createVolumeAttachments;
|
|
4
|
+
const aws_cdk_lib_1 = require("aws-cdk-lib");
|
|
5
|
+
const aws_cloudwatch_1 = require("aws-cdk-lib/aws-cloudwatch");
|
|
6
|
+
const aws_ec2_1 = require("aws-cdk-lib/aws-ec2");
|
|
7
|
+
const core_1 = require("@composurecdk/core");
|
|
8
|
+
const cloudwatch_1 = require("@composurecdk/cloudwatch");
|
|
9
|
+
const instance_volume_attachment_defaults_js_1 = require("./instance-volume-attachment-defaults.js");
|
|
10
|
+
const STALLED_IO_PERIOD = aws_cdk_lib_1.Duration.minutes(1);
|
|
11
|
+
const STALLED_IO_PERIOD_LABEL = `${String(STALLED_IO_PERIOD.toMinutes())} minute`;
|
|
12
|
+
function resolveInstanceAz(instanceProps) {
|
|
13
|
+
if (instanceProps.availabilityZone && !aws_cdk_lib_1.Token.isUnresolved(instanceProps.availabilityZone)) {
|
|
14
|
+
return instanceProps.availabilityZone;
|
|
15
|
+
}
|
|
16
|
+
let selected;
|
|
17
|
+
try {
|
|
18
|
+
selected = instanceProps.vpc.selectSubnets(instanceProps.vpcSubnets);
|
|
19
|
+
}
|
|
20
|
+
catch {
|
|
21
|
+
// selectSubnets() throws for several unrelated reasons (no matching subnets,
|
|
22
|
+
// unresolved tokens, etc.). The validation is best-effort — if we can't
|
|
23
|
+
// resolve a concrete AZ, fall through and let CFN surface the real failure.
|
|
24
|
+
return undefined;
|
|
25
|
+
}
|
|
26
|
+
return selected.availabilityZones.find((az) => !aws_cdk_lib_1.Token.isUnresolved(az));
|
|
27
|
+
}
|
|
28
|
+
function unwrapVolume(resolved) {
|
|
29
|
+
if ("volumeId" in resolved) {
|
|
30
|
+
return resolved;
|
|
31
|
+
}
|
|
32
|
+
return resolved.volume;
|
|
33
|
+
}
|
|
34
|
+
function volumeAttachmentMetric(volume, instance, metricName, statistic, period) {
|
|
35
|
+
return new aws_cloudwatch_1.Metric({
|
|
36
|
+
namespace: "AWS/EBS",
|
|
37
|
+
metricName,
|
|
38
|
+
dimensionsMap: {
|
|
39
|
+
VolumeId: volume.volumeId,
|
|
40
|
+
InstanceId: instance.instanceId,
|
|
41
|
+
},
|
|
42
|
+
statistic,
|
|
43
|
+
period,
|
|
44
|
+
});
|
|
45
|
+
}
|
|
46
|
+
function resolveVolumeAttachmentAlarmDefinitions(attachmentKey, volume, instance, config) {
|
|
47
|
+
if (config === false)
|
|
48
|
+
return [];
|
|
49
|
+
const enabled = config?.enabled ?? instance_volume_attachment_defaults_js_1.VOLUME_ATTACHMENT_ALARM_DEFAULTS.enabled;
|
|
50
|
+
if (!enabled)
|
|
51
|
+
return [];
|
|
52
|
+
if (config?.volumeStalledIo === false)
|
|
53
|
+
return [];
|
|
54
|
+
const cfg = (0, cloudwatch_1.resolveAlarmConfig)(config?.volumeStalledIo, instance_volume_attachment_defaults_js_1.VOLUME_ATTACHMENT_ALARM_DEFAULTS.volumeStalledIo);
|
|
55
|
+
return [
|
|
56
|
+
{
|
|
57
|
+
key: `${attachmentKey}.volumeStalledIo`,
|
|
58
|
+
alarmName: cfg.alarmName,
|
|
59
|
+
metric: volumeAttachmentMetric(volume, instance, "VolumeStalledIOCheck", aws_cloudwatch_1.Stats.MAXIMUM, STALLED_IO_PERIOD),
|
|
60
|
+
threshold: cfg.threshold,
|
|
61
|
+
comparisonOperator: aws_cloudwatch_1.ComparisonOperator.GREATER_THAN_OR_EQUAL_TO_THRESHOLD,
|
|
62
|
+
evaluationPeriods: cfg.evaluationPeriods,
|
|
63
|
+
datapointsToAlarm: cfg.datapointsToAlarm,
|
|
64
|
+
treatMissingData: cfg.treatMissingData,
|
|
65
|
+
description: `EBS volume attachment "${attachmentKey}" is reporting a stalled I/O condition. ` +
|
|
66
|
+
`Threshold: >= ${String(cfg.threshold)} (max) over ${String(cfg.evaluationPeriods)} x ${STALLED_IO_PERIOD_LABEL}. ` +
|
|
67
|
+
`Note: VolumeStalledIOCheck is published only for Nitro-instance attachments.`,
|
|
68
|
+
},
|
|
69
|
+
];
|
|
70
|
+
}
|
|
71
|
+
/**
|
|
72
|
+
* Creates a {@link CfnVolumeAttachment} for each pending attachment and
|
|
73
|
+
* (when configured) the per-attachment recommended alarms. Synth-time AZ
|
|
74
|
+
* alignment is validated when both the volume's AZ and the instance's
|
|
75
|
+
* effective AZ are concrete strings.
|
|
76
|
+
*
|
|
77
|
+
* @returns The created `CfnVolumeAttachment`s keyed by attachment key,
|
|
78
|
+
* plus the per-attachment alarms keyed by `${attachmentKey}.${alarmKey}`
|
|
79
|
+
* so they can be flat-merged into the instance's `alarms` record.
|
|
80
|
+
*/
|
|
81
|
+
function createVolumeAttachments(scope, id, instance, instanceProps, attachments, context) {
|
|
82
|
+
const attachmentRecords = {};
|
|
83
|
+
const alarmDefinitions = [];
|
|
84
|
+
// Resolve the instance AZ once — it is the same for every attachment.
|
|
85
|
+
const instanceAz = attachments.length > 0 ? resolveInstanceAz(instanceProps) : undefined;
|
|
86
|
+
for (const pending of attachments) {
|
|
87
|
+
const resolved = (0, core_1.resolve)(pending.volumeRef, context);
|
|
88
|
+
const volume = unwrapVolume(resolved);
|
|
89
|
+
if (instanceAz !== undefined && !aws_cdk_lib_1.Token.isUnresolved(volume.availabilityZone)) {
|
|
90
|
+
if (volume.availabilityZone !== instanceAz) {
|
|
91
|
+
throw new Error(`attachVolume "${pending.key}": volume is in availability zone "${volume.availabilityZone}" ` +
|
|
92
|
+
`but the instance is in "${instanceAz}". ` +
|
|
93
|
+
`EBS volumes can only attach to instances in the same AZ.`);
|
|
94
|
+
}
|
|
95
|
+
}
|
|
96
|
+
const attachment = new aws_ec2_1.CfnVolumeAttachment(scope, `${id}${pending.key}Attachment`, {
|
|
97
|
+
device: pending.options.device,
|
|
98
|
+
instanceId: instance.instanceId,
|
|
99
|
+
volumeId: volume.volumeId,
|
|
100
|
+
});
|
|
101
|
+
attachmentRecords[pending.key] = attachment;
|
|
102
|
+
alarmDefinitions.push(...resolveVolumeAttachmentAlarmDefinitions(pending.key, volume, instance, pending.options.recommendedAlarms));
|
|
103
|
+
}
|
|
104
|
+
const alarms = alarmDefinitions.length > 0 ? (0, cloudwatch_1.createAlarms)(scope, id, alarmDefinitions) : {};
|
|
105
|
+
return { attachments: attachmentRecords, alarms };
|
|
106
|
+
}
|
|
107
|
+
//# sourceMappingURL=instance-volume-attachments.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"instance-volume-attachments.js","sourceRoot":"","sources":["../../src/instance-volume-attachments.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
import type { AlarmConfig } from "@composurecdk/cloudwatch";
|
|
2
|
+
/**
|
|
3
|
+
* Controls which recommended alarms are created for an EBS volume.
|
|
4
|
+
* All applicable alarms are enabled by default with AWS-recommended
|
|
5
|
+
* thresholds. Set individual alarms to `false` to disable them, or
|
|
6
|
+
* provide an {@link AlarmConfig} to tune thresholds.
|
|
7
|
+
*
|
|
8
|
+
* @see https://docs.aws.amazon.com/AmazonCloudWatch/latest/monitoring/Best_Practice_Recommended_Alarms_AWS_Services.html#EBS
|
|
9
|
+
*/
|
|
10
|
+
export interface VolumeAlarmConfig {
|
|
11
|
+
/**
|
|
12
|
+
* Master switch: set to `false` to disable all recommended alarms.
|
|
13
|
+
* Individual alarms can also be disabled via their own entry.
|
|
14
|
+
* @default true
|
|
15
|
+
*/
|
|
16
|
+
enabled?: boolean;
|
|
17
|
+
/**
|
|
18
|
+
* Alarm when a burstable volume's I/O credit balance falls low,
|
|
19
|
+
* indicating the volume is about to be throttled to baseline IOPS or
|
|
20
|
+
* throughput.
|
|
21
|
+
*
|
|
22
|
+
* Only created when the configured `volumeType` is one of the burstable
|
|
23
|
+
* types: `gp2` (IOPS credits), `st1` and `sc1` (throughput credits).
|
|
24
|
+
* For non-burstable types (`gp3`, `io1`, `io2`, `standard`) the metric
|
|
25
|
+
* is not emitted, so the alarm is skipped entirely.
|
|
26
|
+
*
|
|
27
|
+
* Metric: `AWS/EBS BurstBalance`, statistic Average, period 5 minutes.
|
|
28
|
+
* Default threshold: < 20% over 3 consecutive 5-minute windows.
|
|
29
|
+
*
|
|
30
|
+
* @see https://docs.aws.amazon.com/AmazonCloudWatch/latest/monitoring/Best_Practice_Recommended_Alarms_AWS_Services.html#EBS
|
|
31
|
+
* @see https://docs.aws.amazon.com/ebs/latest/userguide/general-purpose.html#gp2-volume-performance
|
|
32
|
+
*/
|
|
33
|
+
burstBalance?: AlarmConfig | false;
|
|
34
|
+
}
|
|
35
|
+
//# sourceMappingURL=volume-alarm-config.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"volume-alarm-config.d.ts","sourceRoot":"","sources":["../../src/volume-alarm-config.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,0BAA0B,CAAC;AAE5D;;;;;;;GAOG;AACH,MAAM,WAAW,iBAAiB;IAChC;;;;OAIG;IACH,OAAO,CAAC,EAAE,OAAO,CAAC;IAElB;;;;;;;;;;;;;;;OAeG;IACH,YAAY,CAAC,EAAE,WAAW,GAAG,KAAK,CAAC;CACpC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"volume-alarm-config.js","sourceRoot":"","sources":["../../src/volume-alarm-config.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import type { AlarmConfigDefaults } from "@composurecdk/cloudwatch";
|
|
2
|
+
interface VolumeAlarmDefaults {
|
|
3
|
+
enabled: true;
|
|
4
|
+
burstBalance: AlarmConfigDefaults;
|
|
5
|
+
}
|
|
6
|
+
/**
|
|
7
|
+
* AWS-recommended default alarm configuration for EBS volumes.
|
|
8
|
+
*
|
|
9
|
+
* Thresholds are sourced from the CloudWatch Best Practice Recommended
|
|
10
|
+
* Alarms guide. Thresholds may reasonably be tuned per-workload; defaults
|
|
11
|
+
* bias toward catching obvious issues without excessive noise.
|
|
12
|
+
*
|
|
13
|
+
* @see https://docs.aws.amazon.com/AmazonCloudWatch/latest/monitoring/Best_Practice_Recommended_Alarms_AWS_Services.html#EBS
|
|
14
|
+
*/
|
|
15
|
+
export declare const VOLUME_ALARM_DEFAULTS: VolumeAlarmDefaults;
|
|
16
|
+
export {};
|
|
17
|
+
//# sourceMappingURL=volume-alarm-defaults.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"volume-alarm-defaults.d.ts","sourceRoot":"","sources":["../../src/volume-alarm-defaults.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,0BAA0B,CAAC;AAEpE,UAAU,mBAAmB;IAC3B,OAAO,EAAE,IAAI,CAAC;IACd,YAAY,EAAE,mBAAmB,CAAC;CACnC;AAED;;;;;;;;GAQG;AACH,eAAO,MAAM,qBAAqB,EAAE,mBAgBnC,CAAC"}
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.VOLUME_ALARM_DEFAULTS = void 0;
|
|
4
|
+
const aws_cloudwatch_1 = require("aws-cdk-lib/aws-cloudwatch");
|
|
5
|
+
/**
|
|
6
|
+
* AWS-recommended default alarm configuration for EBS volumes.
|
|
7
|
+
*
|
|
8
|
+
* Thresholds are sourced from the CloudWatch Best Practice Recommended
|
|
9
|
+
* Alarms guide. Thresholds may reasonably be tuned per-workload; defaults
|
|
10
|
+
* bias toward catching obvious issues without excessive noise.
|
|
11
|
+
*
|
|
12
|
+
* @see https://docs.aws.amazon.com/AmazonCloudWatch/latest/monitoring/Best_Practice_Recommended_Alarms_AWS_Services.html#EBS
|
|
13
|
+
*/
|
|
14
|
+
exports.VOLUME_ALARM_DEFAULTS = {
|
|
15
|
+
enabled: true,
|
|
16
|
+
/**
|
|
17
|
+
* Burst credit balance is a percentage. Below 20% the volume is
|
|
18
|
+
* approaching throttling to baseline performance — early warning to
|
|
19
|
+
* upsize, switch to a non-burstable type (e.g. `gp3`), or investigate
|
|
20
|
+
* unexpectedly heavy I/O. The 3-of-3 evaluation at 5-minute granularity
|
|
21
|
+
* suppresses transient dips around backup windows.
|
|
22
|
+
*/
|
|
23
|
+
burstBalance: {
|
|
24
|
+
threshold: 20,
|
|
25
|
+
evaluationPeriods: 3,
|
|
26
|
+
datapointsToAlarm: 3,
|
|
27
|
+
treatMissingData: aws_cloudwatch_1.TreatMissingData.NOT_BREACHING,
|
|
28
|
+
},
|
|
29
|
+
};
|
|
30
|
+
//# sourceMappingURL=volume-alarm-defaults.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"volume-alarm-defaults.js","sourceRoot":"","sources":["../../src/volume-alarm-defaults.ts"],"names":[],"mappings":";;;AAAA,+DAA8D;AAQ9D;;;;;;;;GAQG;AACU,QAAA,qBAAqB,GAAwB;IACxD,OAAO,EAAE,IAAI;IAEb;;;;;;OAMG;IACH,YAAY,EAAE;QACZ,SAAS,EAAE,EAAE;QACb,iBAAiB,EAAE,CAAC;QACpB,iBAAiB,EAAE,CAAC;QACpB,gBAAgB,EAAE,iCAAgB,CAAC,aAAa;KACjD;CACF,CAAC"}
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
import { type Alarm } from "aws-cdk-lib/aws-cloudwatch";
|
|
2
|
+
import { EbsDeviceVolumeType, type Volume } from "aws-cdk-lib/aws-ec2";
|
|
3
|
+
import type { IConstruct } from "constructs";
|
|
4
|
+
import type { AlarmDefinition } from "@composurecdk/cloudwatch";
|
|
5
|
+
import { AlarmDefinitionBuilder } from "@composurecdk/cloudwatch";
|
|
6
|
+
import type { VolumeAlarmConfig } from "./volume-alarm-config.js";
|
|
7
|
+
/**
|
|
8
|
+
* Resolves the recommended alarm configuration into fully-resolved
|
|
9
|
+
* {@link AlarmDefinition}s, applying contextual logic for the
|
|
10
|
+
* burstable-only credit alarm.
|
|
11
|
+
*/
|
|
12
|
+
export declare function resolveVolumeAlarmDefinitions(volume: Volume, config: VolumeAlarmConfig | undefined, volumeType: EbsDeviceVolumeType | undefined): AlarmDefinition[];
|
|
13
|
+
/**
|
|
14
|
+
* Creates AWS-recommended CloudWatch alarms for an EBS volume,
|
|
15
|
+
* merging recommended definitions with any custom alarm builders.
|
|
16
|
+
*
|
|
17
|
+
* @param scope - CDK construct scope for creating alarm constructs.
|
|
18
|
+
* @param id - Base identifier for alarm construct ids.
|
|
19
|
+
* @param volume - The EBS volume to create alarms for.
|
|
20
|
+
* @param config - User-provided alarm configuration, or `false` to disable all.
|
|
21
|
+
* @param volumeType - Resolved volume type, used to gate the contextual
|
|
22
|
+
* burst-balance alarm.
|
|
23
|
+
* @param customAlarms - Custom alarm builders added via `addAlarm()`.
|
|
24
|
+
* @returns A record mapping alarm keys to their created Alarm constructs.
|
|
25
|
+
*
|
|
26
|
+
* @see https://docs.aws.amazon.com/AmazonCloudWatch/latest/monitoring/Best_Practice_Recommended_Alarms_AWS_Services.html#EBS
|
|
27
|
+
*/
|
|
28
|
+
export declare function createVolumeAlarms(scope: IConstruct, id: string, volume: Volume, config: VolumeAlarmConfig | false | undefined, volumeType: EbsDeviceVolumeType | undefined, customAlarms?: AlarmDefinitionBuilder<Volume>[]): Record<string, Alarm>;
|
|
29
|
+
//# sourceMappingURL=volume-alarms.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"volume-alarms.d.ts","sourceRoot":"","sources":["../../src/volume-alarms.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,KAAK,KAAK,EAAqC,MAAM,4BAA4B,CAAC;AAC3F,OAAO,EAAE,mBAAmB,EAAgB,KAAK,MAAM,EAAE,MAAM,qBAAqB,CAAC;AACrF,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,YAAY,CAAC;AAC7C,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,0BAA0B,CAAC;AAChE,OAAO,EAAE,sBAAsB,EAAoC,MAAM,0BAA0B,CAAC;AACpG,OAAO,KAAK,EAAE,iBAAiB,EAAE,MAAM,0BAA0B,CAAC;AA4ClE;;;;GAIG;AACH,wBAAgB,6BAA6B,CAC3C,MAAM,EAAE,MAAM,EACd,MAAM,EAAE,iBAAiB,GAAG,SAAS,EACrC,UAAU,EAAE,mBAAmB,GAAG,SAAS,GAC1C,eAAe,EAAE,CAqBnB;AAED;;;;;;;;;;;;;;GAcG;AACH,wBAAgB,kBAAkB,CAChC,KAAK,EAAE,UAAU,EACjB,EAAE,EAAE,MAAM,EACV,MAAM,EAAE,MAAM,EACd,MAAM,EAAE,iBAAiB,GAAG,KAAK,GAAG,SAAS,EAC7C,UAAU,EAAE,mBAAmB,GAAG,SAAS,EAC3C,YAAY,GAAE,sBAAsB,CAAC,MAAM,CAAC,EAAO,GAClD,MAAM,CAAC,MAAM,EAAE,KAAK,CAAC,CAUvB"}
|
|
@@ -0,0 +1,92 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.resolveVolumeAlarmDefinitions = resolveVolumeAlarmDefinitions;
|
|
4
|
+
exports.createVolumeAlarms = createVolumeAlarms;
|
|
5
|
+
const aws_cdk_lib_1 = require("aws-cdk-lib");
|
|
6
|
+
const aws_cloudwatch_1 = require("aws-cdk-lib/aws-cloudwatch");
|
|
7
|
+
const aws_ec2_1 = require("aws-cdk-lib/aws-ec2");
|
|
8
|
+
const cloudwatch_1 = require("@composurecdk/cloudwatch");
|
|
9
|
+
const volume_alarm_defaults_js_1 = require("./volume-alarm-defaults.js");
|
|
10
|
+
/**
|
|
11
|
+
* BurstBalance is published at 5-minute granularity for burstable volume
|
|
12
|
+
* types. A shorter period yields missing data rather than higher resolution.
|
|
13
|
+
*
|
|
14
|
+
* @see https://docs.aws.amazon.com/ebs/latest/userguide/using_cloudwatch_ebs.html
|
|
15
|
+
*/
|
|
16
|
+
const BURST_METRIC_PERIOD = aws_cdk_lib_1.Duration.minutes(5);
|
|
17
|
+
const BURST_METRIC_PERIOD_LABEL = `${String(BURST_METRIC_PERIOD.toMinutes())} minute`;
|
|
18
|
+
/**
|
|
19
|
+
* EBS volume types that publish a `BurstBalance` metric. `gp2` accrues IOPS
|
|
20
|
+
* credits; `st1` and `sc1` accrue throughput credits. Other types
|
|
21
|
+
* (`gp3`, `io1`, `io2`, `standard`) have no burst credit model.
|
|
22
|
+
*
|
|
23
|
+
* @see https://docs.aws.amazon.com/ebs/latest/userguide/using_cloudwatch_ebs.html
|
|
24
|
+
*/
|
|
25
|
+
const BURSTABLE_VOLUME_TYPES = new Set([
|
|
26
|
+
aws_ec2_1.EbsDeviceVolumeType.GP2,
|
|
27
|
+
aws_ec2_1.EbsDeviceVolumeType.ST1,
|
|
28
|
+
aws_ec2_1.EbsDeviceVolumeType.SC1,
|
|
29
|
+
]);
|
|
30
|
+
function isBurstableVolumeType(volumeType) {
|
|
31
|
+
return volumeType !== undefined && BURSTABLE_VOLUME_TYPES.has(volumeType);
|
|
32
|
+
}
|
|
33
|
+
function volumeMetric(volume, metricName, statistic, period) {
|
|
34
|
+
return new aws_cloudwatch_1.Metric({
|
|
35
|
+
namespace: "AWS/EBS",
|
|
36
|
+
metricName,
|
|
37
|
+
dimensionsMap: { VolumeId: volume.volumeId },
|
|
38
|
+
statistic,
|
|
39
|
+
period,
|
|
40
|
+
});
|
|
41
|
+
}
|
|
42
|
+
/**
|
|
43
|
+
* Resolves the recommended alarm configuration into fully-resolved
|
|
44
|
+
* {@link AlarmDefinition}s, applying contextual logic for the
|
|
45
|
+
* burstable-only credit alarm.
|
|
46
|
+
*/
|
|
47
|
+
function resolveVolumeAlarmDefinitions(volume, config, volumeType) {
|
|
48
|
+
if (config?.enabled === false)
|
|
49
|
+
return [];
|
|
50
|
+
const definitions = [];
|
|
51
|
+
if (config?.burstBalance !== false && isBurstableVolumeType(volumeType)) {
|
|
52
|
+
const cfg = (0, cloudwatch_1.resolveAlarmConfig)(config?.burstBalance, volume_alarm_defaults_js_1.VOLUME_ALARM_DEFAULTS.burstBalance);
|
|
53
|
+
definitions.push({
|
|
54
|
+
key: "burstBalance",
|
|
55
|
+
alarmName: cfg.alarmName,
|
|
56
|
+
metric: volumeMetric(volume, "BurstBalance", aws_cloudwatch_1.Stats.AVERAGE, BURST_METRIC_PERIOD),
|
|
57
|
+
threshold: cfg.threshold,
|
|
58
|
+
comparisonOperator: aws_cloudwatch_1.ComparisonOperator.LESS_THAN_THRESHOLD,
|
|
59
|
+
evaluationPeriods: cfg.evaluationPeriods,
|
|
60
|
+
datapointsToAlarm: cfg.datapointsToAlarm,
|
|
61
|
+
treatMissingData: cfg.treatMissingData,
|
|
62
|
+
description: `EBS burstable volume burst credit balance is low — baseline-IOPS throttling is imminent. Threshold: < ${String(cfg.threshold)}% (average) over ${String(cfg.evaluationPeriods)} x ${BURST_METRIC_PERIOD_LABEL}.`,
|
|
63
|
+
});
|
|
64
|
+
}
|
|
65
|
+
return definitions;
|
|
66
|
+
}
|
|
67
|
+
/**
|
|
68
|
+
* Creates AWS-recommended CloudWatch alarms for an EBS volume,
|
|
69
|
+
* merging recommended definitions with any custom alarm builders.
|
|
70
|
+
*
|
|
71
|
+
* @param scope - CDK construct scope for creating alarm constructs.
|
|
72
|
+
* @param id - Base identifier for alarm construct ids.
|
|
73
|
+
* @param volume - The EBS volume to create alarms for.
|
|
74
|
+
* @param config - User-provided alarm configuration, or `false` to disable all.
|
|
75
|
+
* @param volumeType - Resolved volume type, used to gate the contextual
|
|
76
|
+
* burst-balance alarm.
|
|
77
|
+
* @param customAlarms - Custom alarm builders added via `addAlarm()`.
|
|
78
|
+
* @returns A record mapping alarm keys to their created Alarm constructs.
|
|
79
|
+
*
|
|
80
|
+
* @see https://docs.aws.amazon.com/AmazonCloudWatch/latest/monitoring/Best_Practice_Recommended_Alarms_AWS_Services.html#EBS
|
|
81
|
+
*/
|
|
82
|
+
function createVolumeAlarms(scope, id, volume, config, volumeType, customAlarms = []) {
|
|
83
|
+
if (config === false)
|
|
84
|
+
return {};
|
|
85
|
+
const enabled = config?.enabled ?? volume_alarm_defaults_js_1.VOLUME_ALARM_DEFAULTS.enabled;
|
|
86
|
+
if (!enabled)
|
|
87
|
+
return {};
|
|
88
|
+
const recommended = resolveVolumeAlarmDefinitions(volume, config, volumeType);
|
|
89
|
+
const custom = customAlarms.map((b) => b.resolve(volume));
|
|
90
|
+
return (0, cloudwatch_1.createAlarms)(scope, id, [...recommended, ...custom]);
|
|
91
|
+
}
|
|
92
|
+
//# sourceMappingURL=volume-alarms.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"volume-alarms.js","sourceRoot":"","sources":["../../src/volume-alarms.ts"],"names":[],"mappings":";;AAuDA,sEAyBC;AAiBD,gDAiBC;AAlHD,6CAAuC;AACvC,+DAA2F;AAC3F,iDAAqF;AAGrF,yDAAoG;AAEpG,yEAAmE;AAEnE;;;;;GAKG;AACH,MAAM,mBAAmB,GAAG,sBAAQ,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC;AAChD,MAAM,yBAAyB,GAAG,GAAG,MAAM,CAAC,mBAAmB,CAAC,SAAS,EAAE,CAAC,SAAS,CAAC;AAEtF;;;;;;GAMG;AACH,MAAM,sBAAsB,GAAqC,IAAI,GAAG,CAAC;IACvE,6BAAmB,CAAC,GAAG;IACvB,6BAAmB,CAAC,GAAG;IACvB,6BAAmB,CAAC,GAAG;CACxB,CAAC,CAAC;AAEH,SAAS,qBAAqB,CAAC,UAA2C;IACxE,OAAO,UAAU,KAAK,SAAS,IAAI,sBAAsB,CAAC,GAAG,CAAC,UAAU,CAAC,CAAC;AAC5E,CAAC;AAED,SAAS,YAAY,CACnB,MAAe,EACf,UAAkB,EAClB,SAAiB,EACjB,MAAgB;IAEhB,OAAO,IAAI,uBAAM,CAAC;QAChB,SAAS,EAAE,SAAS;QACpB,UAAU;QACV,aAAa,EAAE,EAAE,QAAQ,EAAE,MAAM,CAAC,QAAQ,EAAE;QAC5C,SAAS;QACT,MAAM;KACP,CAAC,CAAC;AACL,CAAC;AAED;;;;GAIG;AACH,SAAgB,6BAA6B,CAC3C,MAAc,EACd,MAAqC,EACrC,UAA2C;IAE3C,IAAI,MAAM,EAAE,OAAO,KAAK,KAAK;QAAE,OAAO,EAAE,CAAC;IAEzC,MAAM,WAAW,GAAsB,EAAE,CAAC;IAE1C,IAAI,MAAM,EAAE,YAAY,KAAK,KAAK,IAAI,qBAAqB,CAAC,UAAU,CAAC,EAAE,CAAC;QACxE,MAAM,GAAG,GAAG,IAAA,+BAAkB,EAAC,MAAM,EAAE,YAAY,EAAE,gDAAqB,CAAC,YAAY,CAAC,CAAC;QACzF,WAAW,CAAC,IAAI,CAAC;YACf,GAAG,EAAE,cAAc;YACnB,SAAS,EAAE,GAAG,CAAC,SAAS;YACxB,MAAM,EAAE,YAAY,CAAC,MAAM,EAAE,cAAc,EAAE,sBAAK,CAAC,OAAO,EAAE,mBAAmB,CAAC;YAChF,SAAS,EAAE,GAAG,CAAC,SAAS;YACxB,kBAAkB,EAAE,mCAAkB,CAAC,mBAAmB;YAC1D,iBAAiB,EAAE,GAAG,CAAC,iBAAiB;YACxC,iBAAiB,EAAE,GAAG,CAAC,iBAAiB;YACxC,gBAAgB,EAAE,GAAG,CAAC,gBAAgB;YACtC,WAAW,EAAE,yGAAyG,MAAM,CAAC,GAAG,CAAC,SAAS,CAAC,oBAAoB,MAAM,CAAC,GAAG,CAAC,iBAAiB,CAAC,MAAM,yBAAyB,GAAG;SAC/N,CAAC,CAAC;IACL,CAAC;IAED,OAAO,WAAW,CAAC;AACrB,CAAC;AAED;;;;;;;;;;;;;;GAcG;AACH,SAAgB,kBAAkB,CAChC,KAAiB,EACjB,EAAU,EACV,MAAc,EACd,MAA6C,EAC7C,UAA2C,EAC3C,eAAiD,EAAE;IAEnD,IAAI,MAAM,KAAK,KAAK;QAAE,OAAO,EAAE,CAAC;IAEhC,MAAM,OAAO,GAAG,MAAM,EAAE,OAAO,IAAI,gDAAqB,CAAC,OAAO,CAAC;IACjE,IAAI,CAAC,OAAO;QAAE,OAAO,EAAE,CAAC;IAExB,MAAM,WAAW,GAAG,6BAA6B,CAAC,MAAM,EAAE,MAAM,EAAE,UAAU,CAAC,CAAC;IAC9E,MAAM,MAAM,GAAG,YAAY,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,OAAO,CAAC,MAAM,CAAC,CAAC,CAAC;IAE1D,OAAO,IAAA,yBAAY,EAAC,KAAK,EAAE,EAAE,EAAE,CAAC,GAAG,WAAW,EAAE,GAAG,MAAM,CAAC,CAAC,CAAC;AAC9D,CAAC"}
|