AWSCDK::EC2

516 types

Amazon EC2 Construct Library

The aws-cdk-lib/aws-ec2 package contains primitives for setting up networking and instances.

require 'aws-cdk-lib'

VPC

Most projects need a Virtual Private Cloud to provide security by means of network partitioning. This is achieved by creating an instance of Vpc:

vpc = AWSCDK::EC2::VPC.new(self, "VPC")

All default constructs require EC2 instances to be launched inside a VPC, so you should generally start by defining a VPC whenever you need to launch instances for your project.

Subnet Types

A VPC consists of one or more subnets that instances can be placed into. CDK distinguishes three different subnet types:

A default VPC configuration will create public and private subnets. However, if natGateways:0 and subnet_configuration is undefined, default VPC configuration will create public and isolated subnets. See Advanced Subnet Configuration below for information on how to change the default subnet configuration.

Constructs using the VPC will "launch instances" (or more accurately, create Elastic Network Interfaces) into one or more of the subnets. They all accept a property called subnet_selection (sometimes called vpc_subnets) to allow you to select in what subnet to place the ENIs, usually defaulting to private subnets if the property is omitted.

If you would like to save on the cost of NAT gateways, you can use isolated subnets instead of private subnets (as described in Advanced Subnet Configuration). If you need private instances to have internet connectivity, another option is to reduce the number of NAT gateways created by setting the nat_gateways property to a lower value (the default is one NAT gateway per availability zone). Be aware that this may have availability implications for your application.

Read more about subnets.

Control over availability zones

By default, a VPC will spread over at most 3 Availability Zones available to it. To change the number of Availability Zones that the VPC will spread over, specify the max_azs property when defining it.

The number of Availability Zones that are available depends on the region and account of the Stack containing the VPC. If the region and account are specified on the Stack, the CLI will look up the existing Availability Zones and get an accurate count. The result of this operation will be written to a file called cdk.context.json. You must commit this file to source control so that the lookup values are available in non-privileged environments such as CI build steps, and to ensure your template builds are repeatable.

If region and account are not specified, the stack could be deployed anywhere and it will have to make a safe choice, limiting itself to 2 Availability Zones.

Therefore, to get the VPC to spread over 3 or more availability zones, you must specify the environment where the stack will be deployed.

You can gain full control over the availability zones selection strategy by overriding the Stack's get availabilityZones() method:

// This example is only available in TypeScript

class MyStack extends Stack {

  constructor(scope: Construct, id: string, props?: StackProps) {
    super(scope, id, props);

    // ...
  }

  get availabilityZones(): string[] {
    return ['us-west-2a', 'us-west-2b'];
  }

}

Note that overriding the get availabilityZones() method will override the default behavior for all constructs defined within the Stack.

Choosing subnets for resources

When creating resources that create Elastic Network Interfaces (such as databases or instances), there is an option to choose which subnets to place them in. For example, a VPC endpoint by default is placed into a subnet in every availability zone, but you can override which subnets to use. The property is typically called one of subnets, vpc_subnets or subnet_selection.

The example below will place the endpoint into two AZs (us-east-1a and us-east-1c), in Isolated subnets:

vpc = nil # AWSCDK::EC2::VPC


AWSCDK::EC2::InterfaceVPCEndpoint.new(self, "VPC Endpoint", {
    vpc: vpc,
    service: AWSCDK::EC2::InterfaceVPCEndpointService.new("com.amazonaws.vpce.us-east-1.vpce-svc-uuddlrlrbastrtsvc", 443),
    subnets: {
        subnet_type: AWSCDK::EC2::SubnetType::PRIVATE_ISOLATED,
        availability_zones: ["us-east-1a", "us-east-1c"],
    },
})

You can also specify specific subnet objects for granular control:

vpc = nil # AWSCDK::EC2::VPC
subnet1 = nil # AWSCDK::EC2::Subnet
subnet2 = nil # AWSCDK::EC2::Subnet


AWSCDK::EC2::InterfaceVPCEndpoint.new(self, "VPC Endpoint", {
    vpc: vpc,
    service: AWSCDK::EC2::InterfaceVPCEndpointService.new("com.amazonaws.vpce.us-east-1.vpce-svc-uuddlrlrbastrtsvc", 443),
    subnets: {
        subnets: [subnet1, subnet2],
    },
})

Which subnets are selected is evaluated as follows:

Using NAT instances

By default, the Vpc construct will create NAT gateways for you, which are managed by AWS. If you would prefer to use your own managed NAT instances instead, specify a different value for the nat_gateway_provider property, as follows:

The construct will automatically selects the latest version of Amazon Linux 2023. If you prefer to use a custom AMI, use machineImage: MachineImage.genericLinux({ ... }) and configure the right AMI ID for the regions you want to deploy to.

Warning The NAT instances created using this method will be unmonitored. They are not part of an Auto Scaling Group, and if they become unavailable or are terminated for any reason, will not be restarted or replaced.

By default, the NAT instances will route all traffic. To control what traffic gets routed, pass a custom value for default_allowed_traffic and access the NatInstanceProvider.connections member after having passed the NAT provider to the VPC:

instance_type = nil # AWSCDK::EC2::InstanceType


provider = AWSCDK::EC2::NatProvider.instance_v2({
    instance_type: instance_type,
    default_allowed_traffic: AWSCDK::EC2::NatTrafficDirection::OUTBOUND_ONLY,
})
AWSCDK::EC2::VPC.new(self, "TheVPC", {
    nat_gateway_provider: provider,
})
provider.connections.allow_from(AWSCDK::EC2::Peer.ipv4("1.2.3.4/8"), AWSCDK::EC2::Port.HTTP)

You can also customize the characteristics of your NAT instances, including their security group, as well as their initialization scripts:

bucket = nil # AWSCDK::S3::Bucket


user_data = AWSCDK::EC2::UserData.for_linux
user_data.add_commands(*AWSCDK::EC2::NatInstanceProviderV2.DEFAULT_USER_DATA_COMMANDS, "echo \"hello world!\" > hello.txt", "aws s3 cp hello.txt s3://#{bucket.bucket_name}")

provider = AWSCDK::EC2::NatProvider.instance_v2({
    instance_type: AWSCDK::EC2::InstanceType.new("t3.small"),
    credit_specification: AWSCDK::EC2::CpuCredits::UNLIMITED,
    default_allowed_traffic: AWSCDK::EC2::NatTrafficDirection::NONE,
})

vpc = AWSCDK::EC2::VPC.new(self, "TheVPC", {
    nat_gateway_provider: provider,
    nat_gateways: 2,
})

security_group = AWSCDK::EC2::SecurityGroup.new(self, "SecurityGroup", {vpc: vpc})
security_group.add_egress_rule(AWSCDK::EC2::Peer.any_ipv4, AWSCDK::EC2::Port.tcp(443))
provider.gateway_instances.each do |gateway|
  bucket.grants.write(gateway)
  gateway.add_security_group(security_group)
end
# Configure the `natGatewayProvider` when defining a Vpc
nat_gateway_provider = AWSCDK::EC2::NatProvider.instance({
    instance_type: AWSCDK::EC2::InstanceType.new("t3.small"),
})

vpc = AWSCDK::EC2::VPC.new(self, "MyVpc", {
    nat_gateway_provider: nat_gateway_provider,

    # The 'natGateways' parameter now controls the number of NAT instances
    nat_gateways: 2,
})

The V1 NatProvider.instance construct will use the AWS official NAT instance AMI, which has already reached EOL on Dec 31, 2023. For more information, see the following blog post: Amazon Linux AMI end of life.

instance_type = nil # AWSCDK::EC2::InstanceType


provider = AWSCDK::EC2::NatProvider.instance({
    instance_type: instance_type,
    default_allowed_traffic: AWSCDK::EC2::NatTrafficDirection::OUTBOUND_ONLY,
})
AWSCDK::EC2::VPC.new(self, "TheVPC", {
    nat_gateway_provider: provider,
})
provider.connections.allow_from(AWSCDK::EC2::Peer.ipv4("1.2.3.4/8"), AWSCDK::EC2::Port.HTTP)

Associate Public IP Address to NAT Instance

You can choose to associate public IP address to a NAT instance V2 by specifying associate_public_ip_address like the following:

nat_gateway_provider = AWSCDK::EC2::NatProvider.instance_v2({
    instance_type: AWSCDK::EC2::InstanceType.new("t3.small"),
    associate_public_ip_address: true,
})

In certain scenarios where the public subnet has set map_public_ip_on_launch to false, NAT instances does not get public IP addresses assigned which would result in non-working NAT instance as NAT instance requires a public IP address to enable outbound internet connectivity. Users can specify associate_public_ip_address to true to solve this problem.

Ip Address Management

The VPC spans a supernet IP range, which contains the non-overlapping IPs of its contained subnets. Possible sources for this IP range are:

By default the Vpc will allocate the 10.0.0.0/16 address range which will be exhaustively spread across all subnets in the subnet configuration. This behavior can be changed by passing an object that implements IIpAddresses to the ip_address property of a Vpc. See the subsequent sections for the options.

Be aware that if you don't explicitly reserve subnet groups in subnet_configuration, the address space will be fully allocated! If you predict you may need to add more subnet groups later, add them early on and set reserved: true (see the "Advanced Subnet Configuration" section for more information).

Specifying a CIDR directly

Use IpAddresses.cidr to define a Cidr range for your Vpc directly in code:

require 'aws-cdk-lib'


AWSCDK::EC2::VPC.new(self, "TheVPC", {
    ip_addresses: AWSCDK::EC2::IPAddresses.cidr("10.0.1.0/20"),
})

Space will be allocated to subnets in the following order:

The argument to IpAddresses.cidr may not be a token, and concrete Cidr values are generated in the synthesized CloudFormation template.

Allocating an IP range from AWS IPAM

Amazon VPC IP Address Manager (IPAM) manages a large IP space, from which chunks can be allocated for use in the Vpc. For information on Amazon VPC IP Address Manager please see the official documentation. An example of allocating from AWS IPAM looks like this:

require 'aws-cdk-lib'

pool = nil # AWSCDK::EC2::CfnIPAMPool


AWSCDK::EC2::VPC.new(self, "TheVPC", {
    ip_addresses: AWSCDK::EC2::IPAddresses.aws_ipam_allocation({
        ipv4_ipam_pool_id: pool.ref,
        ipv4_netmask_length: 18,
        default_subnet_ipv4_netmask_length: 24,
    }),
})

IpAddresses.awsIpamAllocation requires the following:

With this method of IP address management, no attempt is made to guess at subnet group sizes or to exhaustively allocate the IP range. All subnet groups must have an explicit cidr_mask set as part of their subnet configuration, or default_subnet_ipv4_netmask_length must be set for a default size. If not, synthesis will fail and you must provide one or the other.

Dual Stack configuration

To allocate both IPv4 and IPv6 addresses in your VPC, you can configure your VPC to have a dual stack protocol.

AWSCDK::EC2::VPC.new(self, "DualStackVpc", {
    ip_protocol: AWSCDK::EC2::IPProtocol::DUAL_STACK,
})

By default, a dual stack VPC will create an Amazon provided IPv6 /56 CIDR block associated to the VPC. It will then assign /64 portions of the block to each subnet. For each subnet, auto-assigning an IPv6 address will be enabled, and auto-asigning a public IPv4 address will be disabled. An egress only internet gateway will be created for PRIVATE_WITH_EGRESS subnets, and IPv6 routes will be added for IGWs and EIGWs.

Disabling the auto-assigning of a public IPv4 address by default can avoid the cost of public IPv4 addresses starting 2/1/2024. For use cases that need an IPv4 address, the map_public_ip_on_launch property in subnet_configuration can be set to auto-assign the IPv4 address. Note that private IPv4 address allocation will not be changed.

See Advanced Subnet Configuration for all IPv6 specific properties.

Reserving availability zones

There are situations where the IP space for availability zones will need to be reserved. This is useful in situations where availability zones would need to be added after the vpc is originally deployed, without causing IP renumbering for availability zones subnets. The IP space for reserving n availability zones can be done by setting the reserved_azs to n in vpc props, as shown below:

vpc = AWSCDK::EC2::VPC.new(self, "TheVPC", {
    cidr: "10.0.0.0/21",
    max_azs: 3,
    reserved_azs: 1,
})

In the example above, the subnets for reserved availability zones is not actually provisioned but its IP space is still reserved. If, in the future, new availability zones needs to be provisioned, then we would decrement the value of reserved_azs and increment the max_azs or availability_zones accordingly. This action would not cause the IP address of subnets to get renumbered, but rather the IP space that was previously reserved will be used for the new availability zones subnets.

Advanced Subnet Configuration

If the default VPC configuration (public and private subnets spanning the size of the VPC) don't suffice for you, you can configure what subnets to create by specifying the subnet_configuration property. It allows you to configure the number and size of all subnets. Specifying an advanced subnet configuration could look like this:

vpc = AWSCDK::EC2::VPC.new(self, "TheVPC", {
    # 'IpAddresses' configures the IP range and size of the entire VPC.
    # The IP space will be divided based on configuration for the subnets.
    ip_addresses: AWSCDK::EC2::IPAddresses.cidr("10.0.0.0/21"),

    # 'maxAzs' configures the maximum number of availability zones to use.
    # If you want to specify the exact availability zones you want the VPC
    # to use, use `availabilityZones` instead.
    max_azs: 3,

    # 'subnetConfiguration' specifies the "subnet groups" to create.
    # Every subnet group will have a subnet for each AZ, so this
    # configuration will create `3 groups × 3 AZs = 9` subnets.
    subnet_configuration: [
        {
            # 'subnetType' controls Internet access, as described above.
            subnet_type: AWSCDK::EC2::SubnetType::PUBLIC,

            # 'name' is used to name this particular subnet group. You will have to
            # use the name for subnet selection if you have more than one subnet
            # group of the same type.
            name: "Ingress",

            # 'cidrMask' specifies the IP addresses in the range of individual
            # subnets in the group. Each of the subnets in this group will contain
            # `2^(32 address bits - 24 subnet bits) - 2 reserved addresses = 254`
            # usable IP addresses.
            # If 'cidrMask' is left out the available address space is evenly
            # divided across the remaining subnet groups.
            cidr_mask: 24,
        },
        {
            cidr_mask: 24,
            name: "Application",
            subnet_type: AWSCDK::EC2::SubnetType::PRIVATE_WITH_EGRESS,
        },
        {
            cidr_mask: 28,
            name: "Database",
            subnet_type: AWSCDK::EC2::SubnetType::PRIVATE_ISOLATED,

            # 'reserved' can be used to reserve IP address space. No resources will
            # be created for this subnet, but the IP range will be kept available for
            # future creation of this subnet, or even for future subdivision.
            reserved: true,
        },
    ],
})

The example above is one possible configuration, but the user can use the constructs above to implement many other network configurations.

The Vpc from the above configuration in a Region with three availability zones will be the following:

Subnet Name Type IP Block AZ Features
IngressSubnet1 PUBLIC 10.0.0.0/24 #1 NAT Gateway
IngressSubnet2 PUBLIC 10.0.1.0/24 #2 NAT Gateway
IngressSubnet3 PUBLIC 10.0.2.0/24 #3 NAT Gateway
ApplicationSubnet1 PRIVATE 10.0.3.0/24 #1 Route to NAT in IngressSubnet1
ApplicationSubnet2 PRIVATE 10.0.4.0/24 #2 Route to NAT in IngressSubnet2
ApplicationSubnet3 PRIVATE 10.0.5.0/24 #3 Route to NAT in IngressSubnet3
DatabaseSubnet1 ISOLATED 10.0.6.0/28 #1 Only routes within the VPC
DatabaseSubnet2 ISOLATED 10.0.6.16/28 #2 Only routes within the VPC
DatabaseSubnet3 ISOLATED 10.0.6.32/28 #3 Only routes within the VPC

Dual Stack Configurations

Here is a break down of IPv4 and IPv6 specific subnet_configuration properties in a dual stack VPC:

vpc = AWSCDK::EC2::VPC.new(self, "TheVPC", {
    ip_protocol: AWSCDK::EC2::IPProtocol::DUAL_STACK,

    subnet_configuration: [
        {
            # general properties
            name: "Public",
            subnet_type: AWSCDK::EC2::SubnetType::PUBLIC,
            reserved: false,

            # IPv4 specific properties
            map_public_ip_on_launch: true,
            cidr_mask: 24,

            # new IPv6 specific property
            ipv6_assign_address_on_creation: true,
        },
    ],
})

The property map_public_ip_on_launch controls if a public IPv4 address will be assigned. This defaults to false for dual stack VPCs to avoid inadvertant costs of having the public address. However, a public IP must be enabled (or otherwise configured with BYOIP or IPAM) in order for services that rely on the address to function.

The ipv6_assign_address_on_creation property controls the same behavior for the IPv6 address. It defaults to true.

Using IPv6 specific properties in an IPv4 only VPC will result in errors.

Accessing the Internet Gateway

If you need access to the internet gateway, you can get its ID like so:

vpc = nil # AWSCDK::EC2::VPC


igw_id = vpc.internet_gateway_id

For a VPC with only ISOLATED subnets, this value will be undefined.

This is only supported for VPCs created in the stack - currently you're unable to get the ID for imported VPCs. To do that you'd have to specifically look up the Internet Gateway by name, which would require knowing the name beforehand.

This can be useful for configuring routing using a combination of gateways: for more information see Routing below.

Disabling the creation of the default internet gateway

If you need to control the creation of the internet gateway explicitly, you can disable the creation of the default one using the create_internet_gateway property:

vpc = AWSCDK::EC2::VPC.new(self, "VPC", {
    create_internet_gateway: false,
    subnet_configuration: [
        {
            subnet_type: AWSCDK::EC2::SubnetType::PUBLIC,
            name: "Public",
        },
    ],
})

Routing

It's possible to add routes to any subnets using the add_route() method. If for example you want an isolated subnet to have a static route via the default Internet Gateway created for the public subnet - perhaps for routing a VPN connection - you can do so like this:

vpc = AWSCDK::EC2::VPC.new(self, "VPC", {
    subnet_configuration: [
        {
            subnet_type: AWSCDK::EC2::SubnetType::PUBLIC,
            name: "Public",
        },
        {
            subnet_type: AWSCDK::EC2::SubnetType::PRIVATE_ISOLATED,
            name: "Isolated",
        },
    ],
})

(vpc.isolated_subnets[0]).add_route("StaticRoute", {
    router_id: vpc.internet_gateway_id,
    router_type: AWSCDK::EC2::RouterType::GATEWAY,
    destination_cidr_block: "8.8.8.8/32",
})

Note that we cast to Subnet here because the list of subnets only returns an ISubnet.

Reserving subnet IP space

There are situations where the IP space for a subnet or number of subnets will need to be reserved. This is useful in situations where subnets would need to be added after the vpc is originally deployed, without causing IP renumbering for existing subnets. The IP space for a subnet may be reserved by setting the reserved subnetConfiguration property to true, as shown below:

vpc = AWSCDK::EC2::VPC.new(self, "TheVPC", {
    nat_gateways: 1,
    subnet_configuration: [
        {
            cidr_mask: 26,
            name: "Public",
            subnet_type: AWSCDK::EC2::SubnetType::PUBLIC,
        },
        {
            cidr_mask: 26,
            name: "Application1",
            subnet_type: AWSCDK::EC2::SubnetType::PRIVATE_WITH_EGRESS,
        },
        {
            cidr_mask: 26,
            name: "Application2",
            subnet_type: AWSCDK::EC2::SubnetType::PRIVATE_WITH_EGRESS,
            reserved: true,
        },
        {
            cidr_mask: 27,
            name: "Database",
            subnet_type: AWSCDK::EC2::SubnetType::PRIVATE_ISOLATED,
        },
    ],
})

In the example above, the subnet for Application2 is not actually provisioned but its IP space is still reserved. If in the future this subnet needs to be provisioned, then the reserved: true property should be removed. Reserving parts of the IP space prevents the other subnets from getting renumbered.

Sharing VPCs between stacks

If you are creating multiple Stacks inside the same CDK application, you can reuse a VPC defined in one Stack in another by simply passing the VPC instance around:

#
# Stack1 creates the VPC
#
class Stack1 < AWSCDK::Stack
  attr_reader :vpc

  def initialize(scope, id, props = nil)
    super(scope, id, props)

    @vpc = AWSCDK::EC2::VPC.new(self, "VPC")
  end
end

#
# Stack2 consumes the VPC
#
class Stack2 < AWSCDK::Stack
  def initialize(scope, id, props)
    super(scope, id, props)

    # Pass the VPC to a construct that needs it
    ConstructThatTakesAVpc.new(self, "Construct", {
        vpc: props[:vpc],
    })
  end
end

stack1 = Stack1.new(app, "Stack1")
stack2 = Stack2.new(app, "Stack2", {
    vpc: stack1.vpc,
})

Note: If you encounter an error like "Delete canceled. Cannot delete export ..." when using a cross-stack reference to a VPC, it's likely due to CloudFormation export/import constraints. In such cases, it's safer to use Vpc.fromLookup() in the consuming stack instead of directly referencing the VPC object, more details is provided in Importing an existing VPC. This avoids creating CloudFormation exports and gives more flexibility, especially when stacks need to be deleted or updated independently.

Importing an existing VPC

If your VPC is created outside your CDK app, you can use Vpc.fromLookup(). The CDK CLI will search for the specified VPC in the stack's region and account, and import the subnet configuration. Looking up can be done by VPC ID, but more flexibly by searching for a specific tag on the VPC.

Subnet types will be determined from the aws-cdk:subnet-type tag on the subnet if it exists, or the presence of a route to an Internet Gateway otherwise. Subnet names will be determined from the aws-cdk:subnet-name tag on the subnet if it exists, or will mirror the subnet type otherwise (i.e. a public subnet will have the name "Public").

The result of the Vpc.fromLookup() operation will be written to a file called cdk.context.json. You must commit this file to source control so that the lookup values are available in non-privileged environments such as CI build steps, and to ensure your template builds are repeatable.

Here's how Vpc.fromLookup() can be used:

vpc = AWSCDK::EC2::VPC.from_lookup(stack, "VPC", {
    # This imports the default VPC but you can also
    # specify a 'vpcName' or 'tags'.
    is_default: true,
})

Vpc.fromLookup is the recommended way to import VPCs. If for whatever reason you do not want to use the context mechanism to look up a VPC at synthesis time, you can also use Vpc.fromVpcAttributes. This has the following limitations:

Using Vpc.fromVpcAttributes() looks like this:

vpc = AWSCDK::EC2::VPC.from_vpc_attributes(self, "VPC", {
    vpc_id: "vpc-1234",
    availability_zones: ["us-east-1a", "us-east-1b"],

    # Either pass literals for all IDs
    public_subnet_ids: ["s-12345", "s-67890"],

    # OR: import a list of known length
    private_subnet_ids: AWSCDK::Fn.import_list_value("PrivateSubnetIds", 2),

    # OR: split an imported string to a list of known length
    isolated_subnet_ids: AWSCDK::Fn.split(",", AWSCDK::SSM::StringParameter.value_for_string_parameter(self, "MyParameter"), 2),
})

For each subnet group the import function accepts optional parameters for subnet names, route table ids and IPv4 CIDR blocks. When supplied, the length of these lists are required to match the length of the list of subnet ids, allowing the lists to be zipped together to form ISubnet instances.

Public subnet group example (for private or isolated subnet groups, use the properties with the respective prefix):

vpc = AWSCDK::EC2::VPC.from_vpc_attributes(self, "VPC", {
    vpc_id: "vpc-1234",
    availability_zones: ["us-east-1a", "us-east-1b", "us-east-1c"],
    public_subnet_ids: ["s-12345", "s-34567", "s-56789"],
    public_subnet_names: ["Subnet A", "Subnet B", "Subnet C"],
    public_subnet_route_table_ids: ["rt-12345", "rt-34567", "rt-56789"],
    public_subnet_ipv4_cidr_blocks: ["10.0.0.0/24", "10.0.1.0/24", "10.0.2.0/24"],
})

The above example will create an IVpc instance with three public subnets:

| Subnet id | Availability zone | Subnet name | Route table id | IPv4 CIDR | | --------- | ----------------- | ----------- | -------------- | ----------- | | s-12345 | us-east-1a | Subnet A | rt-12345 | 10.0.0.0/24 | | s-34567 | us-east-1b | Subnet B | rt-34567 | 10.0.1.0/24 | | s-56789 | us-east-1c | Subnet B | rt-56789 | 10.0.2.0/24 |

Restricting access to the VPC default security group

AWS Security best practices recommend that the VPC default security group should not allow inbound and outbound traffic. When the @aws-cdk/aws-ec2:restrictDefaultSecurityGroup feature flag is set to true (default for new projects) this will be enabled by default. If you do not have this feature flag set you can either set the feature flag or you can set the restrict_default_security_group property to true.

AWSCDK::EC2::VPC.new(self, "VPC", {
    restrict_default_security_group: true,
})

If you set this property to true and then later remove it or set it to false the default ingress/egress will be restored on the default security group.

Allowing Connections

In AWS, all network traffic in and out of Elastic Network Interfaces (ENIs) is controlled by Security Groups. You can think of Security Groups as a firewall with a set of rules. By default, Security Groups allow no incoming (ingress) traffic and all outgoing (egress) traffic. You can add ingress rules to them to allow incoming traffic streams. To exert fine-grained control over egress traffic, set allowAllOutbound: false on the SecurityGroup, after which you can add egress traffic rules.

You can manipulate Security Groups directly:

my_security_group = AWSCDK::EC2::SecurityGroup.new(self, "SecurityGroup", {
    vpc: vpc,
    description: "Allow ssh access to ec2 instances",
    allow_all_outbound: true,
})
my_security_group.add_ingress_rule(AWSCDK::EC2::Peer.any_ipv4, AWSCDK::EC2::Port.tcp(22), "allow ssh access from the world")

All constructs that create ENIs on your behalf (typically constructs that create EC2 instances or other VPC-connected resources) will all have security groups automatically assigned. Those constructs have an attribute called connections, which is an object that makes it convenient to update the security groups. If you want to allow connections between two constructs that have security groups, you have to add an Egress rule to one Security Group, and an Ingress rule to the other. The connections object will automatically take care of this for you:

load_balancer = nil # AWSCDK::ElasticLoadBalancingv2::ApplicationLoadBalancer
app_fleet = nil # AWSCDK::Autoscaling::AutoScalingGroup
db_fleet = nil # AWSCDK::Autoscaling::AutoScalingGroup


# Allow connections from anywhere
load_balancer.connections.allow_from_any_ipv4(AWSCDK::EC2::Port.HTTPS, "Allow inbound HTTPS")

# The same, but an explicit IP address
load_balancer.connections.allow_from(AWSCDK::EC2::Peer.ipv4("1.2.3.4/32"), AWSCDK::EC2::Port.HTTPS, "Allow inbound HTTPS")

# Allow connection between AutoScalingGroups
app_fleet.connections.allow_to(db_fleet, AWSCDK::EC2::Port.HTTPS, "App can call database")

Connection Peers

There are various classes that implement the connection peer part:

app_fleet = nil # AWSCDK::Autoscaling::AutoScalingGroup
db_fleet = nil # AWSCDK::Autoscaling::AutoScalingGroup


# Simple connection peers
peer = AWSCDK::EC2::Peer.ipv4("10.0.0.0/16")
peer = AWSCDK::EC2::Peer.any_ipv4
peer = AWSCDK::EC2::Peer.ipv6("::0/0")
peer = AWSCDK::EC2::Peer.any_ipv6
app_fleet.connections.allow_to(peer, AWSCDK::EC2::Port.HTTPS, "Allow outbound HTTPS")

Any object that has a security group can itself be used as a connection peer:

fleet1 = nil # AWSCDK::Autoscaling::AutoScalingGroup
fleet2 = nil # AWSCDK::Autoscaling::AutoScalingGroup
app_fleet = nil # AWSCDK::Autoscaling::AutoScalingGroup


# These automatically create appropriate ingress and egress rules in both security groups
fleet1.connections.allow_to(fleet2, AWSCDK::EC2::Port.HTTP, "Allow between fleets")

app_fleet.connections.allow_from_any_ipv4(AWSCDK::EC2::Port.HTTP, "Allow from load balancer")

A managed prefix list is also a connection peer:

app_fleet = nil # AWSCDK::Autoscaling::AutoScalingGroup


prefix_list = AWSCDK::EC2::PrefixList.new(self, "PrefixList", {max_entries: 10})
app_fleet.connections.allow_from(prefix_list, AWSCDK::EC2::Port.HTTPS)

Rule Configuration Interfaces

The IPeer interface provides type-safe methods for generating security group rule configurations. The to_ingress_rule_config() and to_egress_rule_config() methods return strongly-typed interfaces instead of any, enabling better IDE autocompletion and compile-time type checking:

Port Ranges

The connections that are allowed are specified by port ranges. A number of classes provide the connection specifier:

AWSCDK::EC2::Port.tcp(80)
AWSCDK::EC2::Port.HTTPS
AWSCDK::EC2::Port.tcp_range(60000, 65535)
AWSCDK::EC2::Port.all_tcp
AWSCDK::EC2::Port.all_icmp
AWSCDK::EC2::Port.all_icmp_v6
AWSCDK::EC2::Port.all_traffic

NOTE: Not all protocols have corresponding helper methods. In the absence of a helper method, you can instantiate Port yourself with your own settings. You are also welcome to contribute new helper methods.

Default Ports

Some Constructs have default ports associated with them. For example, the listener of a load balancer does (it's the public port), or instances of an RDS database (it's the port the database is accepting connections on).

If the object you're calling the peering method on has a default port associated with it, you can call allow_default_port_from() and omit the port specifier. If the argument has an associated default port, call allow_default_port_to().

For example:

listener = nil # AWSCDK::ElasticLoadBalancingv2::ApplicationListener
app_fleet = nil # AWSCDK::Autoscaling::AutoScalingGroup
rds_database = nil # AWSCDK::RDS::DatabaseCluster


# Port implicit in listener
listener.connections.allow_default_port_from_any_ipv4("Allow public")

# Port implicit in peer
app_fleet.connections.allow_default_port_to(rds_database, "Fleet can access database")

Security group rules

By default, security group wills be added inline to the security group in the output cloud formation template, if applicable. This includes any static rules by ip address and port range. This optimization helps to minimize the size of the template.

In some environments this is not desirable, for example if your security group access is controlled via tags. You can disable inline rules per security group or globally via the context key @aws-cdk/aws-ec2.securityGroupDisableInlineRules.

my_security_group_without_inline_rules = AWSCDK::EC2::SecurityGroup.new(self, "SecurityGroup", {
    vpc: vpc,
    description: "Allow ssh access to ec2 instances",
    allow_all_outbound: true,
    disable_inline_rules: true,
})
# This will add the rule as an external cloud formation construct
my_security_group_without_inline_rules.add_ingress_rule(AWSCDK::EC2::Peer.any_ipv4, AWSCDK::EC2::Port.SSH, "allow ssh access from the world")

Importing an existing security group

If you know the ID and the configuration of the security group to import, you can use SecurityGroup.fromSecurityGroupId:

sg = AWSCDK::EC2::SecurityGroup.from_security_group_id(self, "SecurityGroupImport", "sg-1234", {
    allow_all_outbound: true,
})

Alternatively, use lookup methods to import security groups if you do not know the ID or the configuration details. Method SecurityGroup.fromLookupByName looks up a security group if the security group ID is unknown.

sg = AWSCDK::EC2::SecurityGroup.from_lookup_by_name(self, "SecurityGroupLookup", "security-group-name", vpc)

If the security group ID is known and configuration details are unknown, use method SecurityGroup.fromLookupById instead. This method will lookup property allow_all_outbound from the current configuration of the security group.

sg = AWSCDK::EC2::SecurityGroup.from_lookup_by_id(self, "SecurityGroupLookup", "sg-1234")

The result of SecurityGroup.fromLookupByName and SecurityGroup.fromLookupById operations will be written to a file called cdk.context.json. You must commit this file to source control so that the lookup values are available in non-privileged environments such as CI build steps, and to ensure your template builds are repeatable.

Cross Stack Connections

If you are attempting to add a connection from a peer in one stack to a peer in a different stack, sometimes it is necessary to ensure that you are making the connection in a specific stack in order to avoid a cyclic reference. If there are no other dependencies between stacks then it will not matter in which stack you make the connection, but if there are existing dependencies (i.e. stack1 already depends on stack2), then it is important to make the connection in the dependent stack (i.e. stack1).

Whenever you make a connections function call, the ingress and egress security group rules will be added to the stack that the calling object exists in. So if you are doing something like peer1.connections.allowFrom(peer2), then the security group rules (both ingress and egress) will be created in peer1's Stack.

As an example, if we wanted to allow a connection from a security group in one stack (egress) to a security group in a different stack (ingress), we would make the connection like:

If Stack1 depends on Stack2

# Stack 1
stack1 = nil # AWSCDK::Stack
stack2 = nil # AWSCDK::Stack


sg1 = AWSCDK::EC2::SecurityGroup.new(stack1, "SG1", {
    allow_all_outbound: false,
    vpc: vpc,
})

# Stack 2
sg2 = AWSCDK::EC2::SecurityGroup.new(stack2, "SG2", {
    allow_all_outbound: false,
    vpc: vpc,
})

# `connections.allowTo` on `sg1` since we want the
# rules to be created in Stack1
sg1.connections.allow_to(sg2, AWSCDK::EC2::Port.tcp(3333))

In this case both the Ingress Rule for sg2 and the Egress Rule for sg1 will both be created in Stack 1 which avoids the cyclic reference.

If Stack2 depends on Stack1

# Stack 1
stack1 = nil # AWSCDK::Stack
stack2 = nil # AWSCDK::Stack


sg1 = AWSCDK::EC2::SecurityGroup.new(stack1, "SG1", {
    allow_all_outbound: false,
    vpc: vpc,
})

# Stack 2
sg2 = AWSCDK::EC2::SecurityGroup.new(stack2, "SG2", {
    allow_all_outbound: false,
    vpc: vpc,
})

# `connections.allowFrom` on `sg2` since we want the
# rules to be created in Stack2
sg2.connections.allow_from(sg1, AWSCDK::EC2::Port.tcp(3333))

In this case both the Ingress Rule for sg2 and the Egress Rule for sg1 will both be created in Stack 2 which avoids the cyclic reference.

Machine Images (AMIs)

AMIs control the OS that gets launched when you start your EC2 instance. The EC2 library contains constructs to select the AMI you want to use.

Depending on the type of AMI, you select it a different way. Here are some examples of images you might want to use:

# Pick the right Amazon Linux edition. All arguments shown are optional
# and will default to these values when omitted.
amzn_linux = AWSCDK::EC2::MachineImage.latest_amazon_linux({
    generation: AWSCDK::EC2::AmazonLinuxGeneration::AMAZON_LINUX,
    edition: AWSCDK::EC2::AmazonLinuxEdition::STANDARD,
    virtualization: AWSCDK::EC2::AmazonLinuxVirt::HVM,
    storage: AWSCDK::EC2::AmazonLinuxStorage::GENERAL_PURPOSE,
    cpu_type: AWSCDK::EC2::AmazonLinuxCpuType::X86_64,
})

# Pick a Windows edition to use
windows = AWSCDK::EC2::MachineImage.latest_windows(AWSCDK::EC2::WindowsVersion::WINDOWS_SERVER_2019_ENGLISH_FULL_BASE)

# Read AMI id from SSM parameter store
ssm = AWSCDK::EC2::MachineImage.from_ssm_parameter("/my/ami", {os: AWSCDK::EC2::OperatingSystemType::LINUX})

# Look up the most recent image matching a set of AMI filters.
# In this case, look up the NAT instance AMI, by using a wildcard
# in the 'name' field:
nat_ami = AWSCDK::EC2::MachineImage.lookup({
    name: "amzn-ami-vpc-nat-*",
    owners: ["amazon"],
})

# For other custom (Linux) images, instantiate a `GenericLinuxImage` with
# a map giving the AMI to in for each region:
linux = AWSCDK::EC2::MachineImage.generic_linux({
    "us-east-1" => "ami-97785bed",
    "eu-west-1" => "ami-12345678",
})

# For other custom (Windows) images, instantiate a `GenericWindowsImage` with
# a map giving the AMI to in for each region:
generic_windows = AWSCDK::EC2::MachineImage.generic_windows({
    "us-east-1" => "ami-97785bed",
    "eu-west-1" => "ami-12345678",
})

NOTE: The AMIs selected by MachineImage.lookup() will be cached in cdk.context.json, so that your AutoScalingGroup instances aren't replaced while you are making unrelated changes to your CDK app.

To query for the latest AMI again, remove the relevant cache entry from cdk.context.json, or use the cdk context command. For more information, see Runtime Context in the CDK developer guide.

To customize the cache key, use the additional_cache_key parameter. This allows you to have multiple lookups with the same parameters cache their values separately. This can be useful if you want to scope the context variable to a construct (ie, using additionalCacheKey: this.node.path), so that if the value in the cache needs to be updated, it does not need to be updated for all constructs at the same time.

MachineImage.genericLinux(), MachineImage.genericWindows() will use CfnMapping in an agnostic stack.

Special VPC configurations

VPN connections to a VPC

Create your VPC with VPN connections by specifying the vpn_connections props (keys are construct ids):

require 'aws-cdk-lib'


vpc = AWSCDK::EC2::VPC.new(self, "MyVpc", {
    vpn_connections: {
        dynamic: {
             # Dynamic routing (BGP)
            ip: "1.2.3.4",
            tunnel_options: [
                {
                    pre_shared_key_secret: AWSCDK::SecretValue.unsafe_plain_text("secretkey1234"),
                },
                {
                    pre_shared_key_secret: AWSCDK::SecretValue.unsafe_plain_text("secretkey5678"),
                },
            ],
        },
        static: {
             # Static routing
            ip: "4.5.6.7",
            static_routes: [
                "192.168.10.0/24",
                "192.168.20.0/24",
            ],
        },
    },
})

To create a VPC that can accept VPN connections, set vpn_gateway to true:

vpc = AWSCDK::EC2::VPC.new(self, "MyVpc", {
    vpn_gateway: true,
})

VPN connections can then be added:

vpc.add_vpn_connection("Dynamic", {
    ip: "1.2.3.4",
})

By default, routes will be propagated on the route tables associated with the private subnets. If no private subnets exist, isolated subnets are used. If no isolated subnets exist, public subnets are used. Use the Vpc property vpn_route_propagation to customize this behavior.

VPN connections expose metrics (cloudwatch.Metric) across all tunnels in the account/region and per connection:

# Across all tunnels in the account/region
all_data_out = AWSCDK::EC2::VpnConnection.metric_all_tunnel_data_out

# For a specific vpn connection
vpn_connection = vpc.add_vpn_connection("Dynamic", {
    ip: "1.2.3.4",
})
state = vpn_connection.metric_tunnel_state

VPC endpoints

A VPC endpoint enables you to privately connect your VPC to supported AWS services and VPC endpoint services powered by PrivateLink without requiring an internet gateway, NAT device, VPN connection, or AWS Direct Connect connection. Instances in your VPC do not require public IP addresses to communicate with resources in the service. Traffic between your VPC and the other service does not leave the Amazon network.

Endpoints are virtual devices. They are horizontally scaled, redundant, and highly available VPC components that allow communication between instances in your VPC and services without imposing availability risks or bandwidth constraints on your network traffic.

# Add gateway endpoints when creating the VPC
vpc = AWSCDK::EC2::VPC.new(self, "MyVpc", {
    gateway_endpoints: {
        S3: {
            service: AWSCDK::EC2::GatewayVPCEndpointAWSService.S3,
        },
    },
})

# Alternatively gateway endpoints can be added on the VPC
dynamo_db_endpoint = vpc.add_gateway_endpoint("DynamoDbEndpoint", {
    service: AWSCDK::EC2::GatewayVPCEndpointAWSService.DYNAMODB,
})

# This allows to customize the endpoint policy
dynamo_db_endpoint.add_to_policy(
AWSCDK::IAM::PolicyStatement.new({
     # Restrict to listing and describing tables
    principals: [AWSCDK::IAM::AnyPrincipal.new],
    actions: ["dynamodb:DescribeTable", "dynamodb:ListTables"],
    resources: ["*"],
}))

# Add an interface endpoint
vpc.add_interface_endpoint("EcrDockerEndpoint", {
    service: AWSCDK::EC2::InterfaceVPCEndpointAWSService.ECR_DOCKER,
})

By default, CDK will place a VPC endpoint in one subnet per AZ. If you wish to override the AZs CDK places the VPC endpoint in, use the subnets parameter as follows:

vpc = nil # AWSCDK::EC2::VPC


AWSCDK::EC2::InterfaceVPCEndpoint.new(self, "VPC Endpoint", {
    vpc: vpc,
    service: AWSCDK::EC2::InterfaceVPCEndpointService.new("com.amazonaws.vpce.us-east-1.vpce-svc-uuddlrlrbastrtsvc", 443),
    # Choose which availability zones to place the VPC endpoint in, based on
    # available AZs
    subnets: {
        availability_zones: ["us-east-1a", "us-east-1c"],
    },
})

Per the AWS documentation, not all VPC endpoint services are available in all AZs. If you specify the parameter lookup_supported_azs, CDK attempts to discover which AZs an endpoint service is available in, and will ensure the VPC endpoint is not placed in a subnet that doesn't match those AZs. These AZs will be stored in cdk.context.json.

vpc = nil # AWSCDK::EC2::VPC


AWSCDK::EC2::InterfaceVPCEndpoint.new(self, "VPC Endpoint", {
    vpc: vpc,
    service: AWSCDK::EC2::InterfaceVPCEndpointService.new("com.amazonaws.vpce.us-east-1.vpce-svc-uuddlrlrbastrtsvc", 443),
    # Choose which availability zones to place the VPC endpoint in, based on
    # available AZs
    lookup_supported_azs: true,
})

Pre-defined AWS services are defined in the InterfaceVpcEndpointAwsService class, and can be used to create VPC endpoints without having to configure name, ports, etc. For example, a Keyspaces endpoint can be created for use in your VPC:

vpc = nil # AWSCDK::EC2::VPC


AWSCDK::EC2::InterfaceVPCEndpoint.new(self, "VPC Endpoint", {
    vpc: vpc,
    service: AWSCDK::EC2::InterfaceVPCEndpointAWSService.KEYSPACES,
})

For cross-region VPC endpoints, specify the service_region parameter:

vpc = nil # AWSCDK::EC2::VPC


AWSCDK::EC2::InterfaceVPCEndpoint.new(self, "CrossRegionEndpoint", {
    vpc: vpc,
    service: AWSCDK::EC2::InterfaceVPCEndpointService.new("com.amazonaws.vpce.us-east-1.vpce-svc-123456", 443),
    service_region: "us-east-1",
})

Security groups for interface VPC endpoints

By default, interface VPC endpoints create a new security group and all traffic to the endpoint from within the VPC will be automatically allowed.

Use the connections object to allow other traffic to flow to the endpoint:

my_endpoint = nil # AWSCDK::EC2::InterfaceVPCEndpoint


my_endpoint.connections.allow_default_port_from_any_ipv4

Alternatively, existing security groups can be used by specifying the security_groups prop.

IPv6 and Dualstack support

As IPv4 addresses are running out, many AWS services are adding support for IPv6 or Dualstack (IPv4 and IPv6 support) for their VPC Endpoints.

IPv6 and Dualstack address types can be configured by using:

vpc.add_interface_endpoint("ExampleEndpoint", {
    service: AWSCDK::EC2::InterfaceVPCEndpointAWSService.ECR,
    ip_address_type: AWSCDK::EC2::VPCEndpointIPAddressType::IPV6,
    dns_record_ip_type: AWSCDK::EC2::VPCEndpointDNSRecordIPType::IPV6,
})

The possible values for ip_address_type are:

VPC endpoint services

A VPC endpoint service enables you to expose a Network Load Balancer(s) as a provider service to consumers, who connect to your service over a VPC endpoint. You can restrict access to your service via allowed principals (anything that extends ArnPrincipal), and require that new connections be manually accepted. You can also enable Contributor Insight rules.

network_load_balancer1 = nil # AWSCDK::ElasticLoadBalancingv2::NetworkLoadBalancer
network_load_balancer2 = nil # AWSCDK::ElasticLoadBalancingv2::NetworkLoadBalancer


AWSCDK::EC2::VPCEndpointService.new(self, "EndpointService", {
    vpc_endpoint_service_load_balancers: [network_load_balancer1, network_load_balancer2],
    acceptance_required: true,
    allowed_principals: [AWSCDK::IAM::ARNPrincipal.new("arn:aws:iam::123456789012:root")],
    contributor_insights: true,
})

You can also include a service principal in the allowed_principals property by specifying it as a parameter to the ArnPrincipal constructor. The resulting VPC endpoint will have an allowlisted principal of type Service, instead of Arn for that item in the list.

network_load_balancer = nil # AWSCDK::ElasticLoadBalancingv2::NetworkLoadBalancer


AWSCDK::EC2::VPCEndpointService.new(self, "EndpointService", {
    vpc_endpoint_service_load_balancers: [network_load_balancer],
    allowed_principals: [AWSCDK::IAM::ARNPrincipal.new("ec2.amazonaws.com")],
})

You can specify which IP address types (IPv4, IPv6, or both) are supported for your VPC endpoint service:

network_load_balancer = nil # AWSCDK::ElasticLoadBalancingv2::NetworkLoadBalancer


AWSCDK::EC2::VPCEndpointService.new(self, "EndpointService", {
    vpc_endpoint_service_load_balancers: [network_load_balancer],
    # Support both IPv4 and IPv6 connections to the endpoint service
    supported_ip_address_types: [
        AWSCDK::EC2::IPAddressType::IPV4,
        AWSCDK::EC2::IPAddressType::IPV6,
    ],
})

You can restrict access to your endpoint service to specific AWS regions:

network_load_balancer = nil # AWSCDK::ElasticLoadBalancingv2::NetworkLoadBalancer


AWSCDK::EC2::VPCEndpointService.new(self, "EndpointService", {
    vpc_endpoint_service_load_balancers: [network_load_balancer],
    # Allow service consumers from these regions only
    allowed_regions: ["us-east-1", "eu-west-1"],
})

Endpoint services support private DNS, which makes it easier for clients to connect to your service by automatically setting up DNS in their VPC. You can enable private DNS on an endpoint service like so:

require 'aws-cdk-lib'
zone = nil # AWSCDK::Route53::PublicHostedZone
vpces = nil # AWSCDK::EC2::VPCEndpointService


AWSCDK::Route53::VPCEndpointServiceDomainName.new(self, "EndpointDomain", {
    endpoint_service: vpces,
    domain_name: "my-stuff.aws-cdk.dev",
    public_hosted_zone: zone,
})

Note: The domain name must be owned (registered through Route53) by the account the endpoint service is in, or delegated to the account. The VpcEndpointServiceDomainName will handle the AWS side of domain verification, the process for which can be found here

Client VPN endpoint

AWS Client VPN is a managed client-based VPN service that enables you to securely access your AWS resources and resources in your on-premises network. With Client VPN, you can access your resources from any location using an OpenVPN-based VPN client.

Use the add_client_vpn_endpoint() method to add a client VPN endpoint to a VPC:

vpc.add_client_vpn_endpoint("Endpoint", {
    cidr: "10.100.0.0/16",
    server_certificate_arn: "arn:aws:acm:us-east-1:123456789012:certificate/server-certificate-id",
    # Mutual authentication
    client_certificate_arn: "arn:aws:acm:us-east-1:123456789012:certificate/client-certificate-id",
    # User-based authentication
    user_based_authentication: AWSCDK::EC2::ClientVpnUserBasedAuthentication.federated(saml_provider),
})

The endpoint must use at least one authentication method:

If user-based authentication is used, the self-service portal URL is made available via a CloudFormation output.

By default, a new security group is created, and logging is enabled. Moreover, a rule to authorize all users to the VPC CIDR is created.

To customize authorization rules, set the authorize_all_users_to_vpc_cidr prop to false and use add_authorization_rule():

endpoint = vpc.add_client_vpn_endpoint("Endpoint", {
    cidr: "10.100.0.0/16",
    server_certificate_arn: "arn:aws:acm:us-east-1:123456789012:certificate/server-certificate-id",
    user_based_authentication: AWSCDK::EC2::ClientVpnUserBasedAuthentication.federated(saml_provider),
    authorize_all_users_to_vpc_cidr: false,
})

endpoint.add_authorization_rule("Rule", {
    cidr: "10.0.10.0/32",
    group_id: "group-id",
})

Use add_route() to configure network routes:

endpoint = vpc.add_client_vpn_endpoint("Endpoint", {
    cidr: "10.100.0.0/16",
    server_certificate_arn: "arn:aws:acm:us-east-1:123456789012:certificate/server-certificate-id",
    user_based_authentication: AWSCDK::EC2::ClientVpnUserBasedAuthentication.federated(saml_provider),
})

# Client-to-client access
endpoint.add_route("Route", {
    cidr: "10.100.0.0/16",
    target: AWSCDK::EC2::ClientVpnRouteTarget.local,
})

Use the connections object of the endpoint to allow traffic to other security groups.

To enable client route enforcement, configure the clientRouteEnforcementOptions.enforced prop to true:

endpoint = vpc.add_client_vpn_endpoint("Endpoint", {
    cidr: "10.100.0.0/16",
    server_certificate_arn: "arn:aws:acm:us-east-1:123456789012:certificate/server-certificate-id",
    client_certificate_arn: "arn:aws:acm:us-east-1:123456789012:certificate/client-certificate-id",
    client_route_enforcement_options: {
        enforced: true,
    },
})

To control whether clients are automatically disconnected when the maximum session duration is reached, use the disconnect_on_session_timeout prop. By default (true), clients are disconnected and must manually reconnect. Set to false to allow automatic reconnection attempts:

endpoint = vpc.add_client_vpn_endpoint("Endpoint", {
    cidr: "10.100.0.0/16",
    server_certificate_arn: "arn:aws:acm:us-east-1:123456789012:certificate/server-certificate-id",
    client_certificate_arn: "arn:aws:acm:us-east-1:123456789012:certificate/client-certificate-id",
    disconnect_on_session_timeout: false,
})

Detail information about maximum VPN session duration timeout can be found in the AWS documentation.

Instances

You can use the Instance class to start up a single EC2 instance. For production setups, we recommend you use an AutoScalingGroup from the aws-autoscaling module instead, as AutoScalingGroups will take care of restarting your instance if it ever fails.

vpc = nil # AWSCDK::EC2::VPC
instance_type = nil # AWSCDK::EC2::InstanceType


# Amazon Linux 2
AWSCDK::EC2::Instance.new(self, "Instance2", {
    vpc: vpc,
    instance_type: instance_type,
    machine_image: AWSCDK::EC2::MachineImage.latest_amazon_linux2,
})

# Amazon Linux 2 with kernel 5.x
AWSCDK::EC2::Instance.new(self, "Instance3", {
    vpc: vpc,
    instance_type: instance_type,
    machine_image: AWSCDK::EC2::MachineImage.latest_amazon_linux2({
        kernel: AWSCDK::EC2::AmazonLinux2Kernel.KERNEL_5_10,
    }),
})

# Amazon Linux 2023
AWSCDK::EC2::Instance.new(self, "Instance4", {
    vpc: vpc,
    instance_type: instance_type,
    machine_image: AWSCDK::EC2::MachineImage.latest_amazon_linux2023,
})

# Graviton 3 Processor
AWSCDK::EC2::Instance.new(self, "Instance5", {
    vpc: vpc,
    instance_type: AWSCDK::EC2::InstanceType.of(AWSCDK::EC2::InstanceClass::C7G, AWSCDK::EC2::InstanceSize::LARGE),
    machine_image: AWSCDK::EC2::MachineImage.latest_amazon_linux2023({
        cpu_type: AWSCDK::EC2::AmazonLinuxCpuType::ARM_64,
    }),
})

Latest Amazon Linux Images

Rather than specifying a specific AMI ID to use, it is possible to specify a SSM Parameter that contains the AMI ID. AWS publishes a set of public parameters that contain the latest Amazon Linux AMIs. To make it easier to query a particular image parameter, the CDK provides a couple of constructs AmazonLinux2ImageSsmParameter, AmazonLinux2022ImageSsmParameter, & AmazonLinux2023SsmParameter. For example to use the latest al2023 image:

vpc = nil # AWSCDK::EC2::VPC


AWSCDK::EC2::Instance.new(self, "LatestAl2023", {
    vpc: vpc,
    instance_type: AWSCDK::EC2::InstanceType.of(AWSCDK::EC2::InstanceClass::C7G, AWSCDK::EC2::InstanceSize::LARGE),
    machine_image: AWSCDK::EC2::MachineImage.latest_amazon_linux2023,
})

Warning Since this retrieves the value from an SSM parameter at deployment time, the value will be resolved each time the stack is deployed. This means that if the parameter contains a different value on your next deployment, the instance will be replaced.

It is also possible to perform the lookup once at synthesis time and then cache the value in CDK context. This way the value will not change on future deployments unless you manually refresh the context.

vpc = nil # AWSCDK::EC2::VPC


AWSCDK::EC2::Instance.new(self, "LatestAl2023", {
    vpc: vpc,
    instance_type: AWSCDK::EC2::InstanceType.of(AWSCDK::EC2::InstanceClass::C7G, AWSCDK::EC2::InstanceSize::LARGE),
    machine_image: AWSCDK::EC2::MachineImage.latest_amazon_linux2023({
        cached_in_context: true,
    }),
})

# or
AWSCDK::EC2::Instance.new(self, "LatestAl2023", {
    vpc: vpc,
    instance_type: AWSCDK::EC2::InstanceType.of(AWSCDK::EC2::InstanceClass::C7G, AWSCDK::EC2::InstanceSize::LARGE),
    # context cache is turned on by default
    machine_image: AWSCDK::EC2::AmazonLinux2023ImageSSMParameter.new,
})

# or
AWSCDK::EC2::Instance.new(self, "LatestAl2023", {
    vpc: vpc,
    instance_type: AWSCDK::EC2::InstanceType.of(AWSCDK::EC2::InstanceClass::C7G, AWSCDK::EC2::InstanceSize::LARGE),
    machine_image: AWSCDK::EC2::MachineImage.latest_amazon_linux2023({
        cached_in_context: true,
        # creates a distinct context variable for this image, instead of resolving to the same
        # value anywhere this lookup is done in your app
        additional_cache_key: @node.path,
    }),
})

# or
AWSCDK::EC2::Instance.new(self, "LatestAl2023", {
    vpc: vpc,
    instance_type: AWSCDK::EC2::InstanceType.of(AWSCDK::EC2::InstanceClass::C7G, AWSCDK::EC2::InstanceSize::LARGE),
    # context cache is turned on by default
    machine_image: AWSCDK::EC2::AmazonLinux2023ImageSSMParameter.new({
        # creates a distinct context variable for this image, instead of resolving to the same
        # value anywhere this lookup is done in your app
        additional_cache_key: @node.path,
    }),
})

Kernel Versions

Each Amazon Linux AMI uses a specific kernel version. Most Amazon Linux generations come with an AMI using the "default" kernel and then 1 or more AMIs using a specific kernel version, which may or may not be different from the default kernel version.

For example, Amazon Linux 2 has two different AMIs available from the SSM parameters.

If a new Amazon Linux generation AMI is published with a new kernel version, then a new SSM parameter will be created with the new version (e.g. /aws/service/ami-amazon-linux-latest/amzn2-ami-kernel-5.15-hvm-x86_64-ebs), but the "default" AMI may or may not be updated.

If you would like to make sure you always have the latest kernel version, then either specify the specific latest kernel version or opt-in to using the CDK latest kernel version.

vpc = nil # AWSCDK::EC2::VPC


AWSCDK::EC2::Instance.new(self, "LatestAl2023", {
    vpc: vpc,
    instance_type: AWSCDK::EC2::InstanceType.of(AWSCDK::EC2::InstanceClass::C7G, AWSCDK::EC2::InstanceSize::LARGE),
    # context cache is turned on by default
    machine_image: AWSCDK::EC2::AmazonLinux2023ImageSSMParameter.new({
        kernel: AWSCDK::EC2::AmazonLinux2023Kernel.KERNEL_6_1,
    }),
})

CDK managed latest

vpc = nil # AWSCDK::EC2::VPC


AWSCDK::EC2::Instance.new(self, "LatestAl2023", {
    vpc: vpc,
    instance_type: AWSCDK::EC2::InstanceType.of(AWSCDK::EC2::InstanceClass::C7G, AWSCDK::EC2::InstanceSize::LARGE),
    # context cache is turned on by default
    machine_image: AWSCDK::EC2::AmazonLinux2023ImageSSMParameter.new({
        kernel: AWSCDK::EC2::AmazonLinux2023Kernel.CDK_LATEST,
    }),
})

# or

AWSCDK::EC2::Instance.new(self, "LatestAl2023", {
    vpc: vpc,
    instance_type: AWSCDK::EC2::InstanceType.of(AWSCDK::EC2::InstanceClass::C7G, AWSCDK::EC2::InstanceSize::LARGE),
    machine_image: AWSCDK::EC2::MachineImage.latest_amazon_linux2023,
})

When using the CDK managed latest version, when a new kernel version is made available the LATEST will be updated to point to the new kernel version. You then would be required to update the newest CDK version for it to take effect.

Configuring Instances using CloudFormation Init (cfn-init)

CloudFormation Init allows you to configure your instances by writing files to them, installing software packages, starting services and running arbitrary commands. By default, if any of the instance setup commands throw an error; the deployment will fail and roll back to the previously known good state. The following documentation also applies to AutoScalingGroups.

For the full set of capabilities of this system, see the documentation for AWS::CloudFormation::Init. Here is an example of applying some configuration to an instance:

vpc = nil # AWSCDK::EC2::VPC
instance_type = nil # AWSCDK::EC2::InstanceType
machine_image = nil # AWSCDK::EC2::IMachineImage


AWSCDK::EC2::Instance.new(self, "Instance", {
    vpc: vpc,
    instance_type: instance_type,
    machine_image: machine_image,

    # Showing the most complex setup, if you have simpler requirements
    # you can use `CloudFormationInit.fromElements()`.
    init: AWSCDK::EC2::CloudFormationInit.from_config_sets({
        config_sets: {
            # Applies the configs below in this order
            default: ["yumPreinstall", "config"],
        },
        configs: {
            yum_preinstall: AWSCDK::EC2::InitConfig.new([
                AWSCDK::EC2::InitPackage.yum("git"),
            ]),
            config: AWSCDK::EC2::InitConfig.new([
                AWSCDK::EC2::InitFile.from_object("/etc/stack.json", {
                    stack_id: AWSCDK::Stack.of(self).stack_id,
                    stack_name: AWSCDK::Stack.of(self).stack_name,
                    region: AWSCDK::Stack.of(self).region,
                }),
                AWSCDK::EC2::InitGroup.from_name("my-group"),
                AWSCDK::EC2::InitUser.from_name("my-user"),
                AWSCDK::EC2::InitPackage.rpm("http://mirrors.ukfast.co.uk/sites/dl.fedoraproject.org/pub/epel/8/Everything/x86_64/Packages/r/rubygem-git-1.5.0-2.el8.noarch.rpm"),
            ]),
        },
    }),
    init_options: {
        # Optional, which configsets to activate (['default'] by default)
        config_sets: ["default"],

        # Optional, how long the installation is expected to take (5 minutes by default)
        timeout: AWSCDK::Duration.minutes(30),

        # Optional, whether to include the --url argument when running cfn-init and cfn-signal commands (false by default)
        include_url: true,

        # Optional, whether to include the --role argument when running cfn-init and cfn-signal commands (false by default)
        include_role: true,
    },
})

InitCommand can not be used to start long-running processes. At deploy time, cfn-init will always wait for the process to exit before continuing, causing the CloudFormation deployment to fail because the signal hasn't been received within the expected timeout.

Instead, you should install a service configuration file onto your machine InitFile, and then use InitService to start it.

If your Linux OS is using SystemD (like Amazon Linux 2 or higher), the CDK has helpers to create a long-running service using CFN Init. You can create a SystemD-compatible config file using InitService.systemdConfigFile(), and start it immediately. The following examples shows how to start a trivial Python 3 web server:

vpc = nil # AWSCDK::EC2::VPC
instance_type = nil # AWSCDK::EC2::InstanceType


AWSCDK::EC2::Instance.new(self, "Instance", {
    vpc: vpc,
    instance_type: instance_type,
    machine_image: AWSCDK::EC2::MachineImage.latest_amazon_linux2023,

    init: AWSCDK::EC2::CloudFormationInit.from_elements(AWSCDK::EC2::InitService.systemd_config_file("simpleserver", {
        command: "/usr/bin/python3 -m http.server 8080",
        cwd: "/var/www/html",
    }), AWSCDK::EC2::InitService.enable("simpleserver", {
        service_manager: AWSCDK::EC2::ServiceManager::SYSTEMD,
    }), AWSCDK::EC2::InitFile.from_string("/var/www/html/index.html", "Hello! It's working!")),
})

You can have services restarted after the init process has made changes to the system. To do that, instantiate an InitServiceRestartHandle and pass it to the config elements that need to trigger the restart and the service itself. For example, the following config writes a config file for nginx, extracts an archive to the root directory, and then restarts nginx so that it picks up the new config and files:

my_bucket = nil # AWSCDK::S3::Bucket


handle = AWSCDK::EC2::InitServiceRestartHandle.new

AWSCDK::EC2::CloudFormationInit.from_elements(AWSCDK::EC2::InitFile.from_string("/etc/nginx/nginx.conf", "...", {service_restart_handles: [handle]}), AWSCDK::EC2::InitSource.from_s3_object("/var/www/html", my_bucket, "html.zip", {service_restart_handles: [handle]}), AWSCDK::EC2::InitService.enable("nginx", {
    service_restart_handle: handle,
}))

You can use the environment_variables or environment_files parameters to specify environment variables for your services:

AWSCDK::EC2::InitConfig.new([
    AWSCDK::EC2::InitFile.from_string("/myvars.env", "VAR_FROM_FILE=\"VAR_FROM_FILE\""),
    AWSCDK::EC2::InitService.systemd_config_file("myapp", {
        command: "/usr/bin/python3 -m http.server 8080",
        cwd: "/var/www/html",
        environment_variables: {
            MY_VAR: "MY_VAR",
        },
        environment_files: ["/myvars.env"],
    }),
])

Bastion Hosts

A bastion host functions as an instance used to access servers and resources in a VPC without open up the complete VPC on a network level. You can use bastion hosts using a standard SSH connection targeting port 22 on the host. As an alternative, you can connect the SSH connection feature of AWS Systems Manager Session Manager, which does not need an opened security group. (https://aws.amazon.com/about-aws/whats-new/2019/07/session-manager-launches-tunneling-support-for-ssh-and-scp/)

A default bastion host for use via SSM can be configured like:

host = AWSCDK::EC2::BastionHostLinux.new(self, "BastionHost", {vpc: vpc})

If you want to connect from the internet using SSH, you need to place the host into a public subnet. You can then configure allowed source hosts.

host = AWSCDK::EC2::BastionHostLinux.new(self, "BastionHost", {
    vpc: vpc,
    subnet_selection: {subnet_type: AWSCDK::EC2::SubnetType::PUBLIC},
})
host.allow_ssh_access_from(AWSCDK::EC2::Peer.ipv4("1.2.3.4/32"))

As there are no SSH public keys deployed on this machine, you need to use EC2 Instance Connect with the command aws ec2-instance-connect send-ssh-public-key to provide your SSH public key.

EBS volume for the bastion host can be encrypted like:

host = AWSCDK::EC2::BastionHostLinux.new(self, "BastionHost", {
    vpc: vpc,
    block_devices: [
        {
            device_name: "/dev/sdh",
            volume: AWSCDK::EC2::BlockDeviceVolume.ebs(10, {
                encrypted: true,
            }),
        },
    ],
})

It's recommended to set the @aws-cdk/aws-ec2:bastionHostUseAmazonLinux2023ByDefault feature flag to true to use Amazon Linux 2023 as the bastion host AMI. Without this flag set, the bastion host will default to Amazon Linux 2, which will be unsupported in June 2025.

{
  "context": {
    "@aws-cdk/aws-ec2:bastionHostUseAmazonLinux2023ByDefault": true
  }
}

Placement Group

Specify placement_group to enable the placement group support:

instance_type = nil # AWSCDK::EC2::InstanceType


pg = AWSCDK::EC2::PlacementGroup.new(self, "test-pg", {
    strategy: AWSCDK::EC2::PlacementGroupStrategy::SPREAD,
})

AWSCDK::EC2::Instance.new(self, "Instance", {
    vpc: vpc,
    instance_type: instance_type,
    machine_image: AWSCDK::EC2::MachineImage.latest_amazon_linux2023,
    placement_group: pg,
})

Block Devices

To add EBS block device mappings, specify the block_devices property. The following example sets the EBS-backed root device (/dev/sda1) size to 50 GiB, and adds another EBS-backed device mapped to /dev/sdm that is 100 GiB in size:

vpc = nil # AWSCDK::EC2::VPC
instance_type = nil # AWSCDK::EC2::InstanceType
machine_image = nil # AWSCDK::EC2::IMachineImage


AWSCDK::EC2::Instance.new(self, "Instance", {
    vpc: vpc,
    instance_type: instance_type,
    machine_image: machine_image,

    # ...

    block_devices: [
        {
            device_name: "/dev/sda1",
            volume: AWSCDK::EC2::BlockDeviceVolume.ebs(50),
        },
        {
            device_name: "/dev/sdm",
            volume: AWSCDK::EC2::BlockDeviceVolume.ebs(100),
        },
    ],
})

It is also possible to encrypt the block devices. In this example we will create an customer managed key encrypted EBS-backed root device:

require 'aws-cdk-lib'

vpc = nil # AWSCDK::EC2::VPC
instance_type = nil # AWSCDK::EC2::InstanceType
machine_image = nil # AWSCDK::EC2::IMachineImage


kms_key = AWSCDK::KMS::Key.new(self, "KmsKey")

AWSCDK::EC2::Instance.new(self, "Instance", {
    vpc: vpc,
    instance_type: instance_type,
    machine_image: machine_image,

    # ...

    block_devices: [
        {
            device_name: "/dev/sda1",
            volume: AWSCDK::EC2::BlockDeviceVolume.ebs(50, {
                encrypted: true,
                kms_key: kms_key,
            }),
        },
    ],
})

To specify the throughput value for gp3 volumes, use the throughput property:

vpc = nil # AWSCDK::EC2::VPC
instance_type = nil # AWSCDK::EC2::InstanceType
machine_image = nil # AWSCDK::EC2::IMachineImage


AWSCDK::EC2::Instance.new(self, "Instance", {
    vpc: vpc,
    instance_type: instance_type,
    machine_image: machine_image,

    # ...

    block_devices: [
        {
            device_name: "/dev/sda1",
            volume: AWSCDK::EC2::BlockDeviceVolume.ebs(100, {
                volume_type: AWSCDK::EC2::EbsDeviceVolumeType::GP3,
                throughput: 250,
            }),
        },
    ],
})

EBS Optimized Instances

An Amazon EBS–optimized instance uses an optimized configuration stack and provides additional, dedicated capacity for Amazon EBS I/O. This optimization provides the best performance for your EBS volumes by minimizing contention between Amazon EBS I/O and other traffic from your instance.

Depending on the instance type, this features is enabled by default while others require explicit activation. Please refer to the documentation for details.

vpc = nil # AWSCDK::EC2::VPC
instance_type = nil # AWSCDK::EC2::InstanceType
machine_image = nil # AWSCDK::EC2::IMachineImage


AWSCDK::EC2::Instance.new(self, "Instance", {
    vpc: vpc,
    instance_type: instance_type,
    machine_image: machine_image,
    ebs_optimized: true,
    block_devices: [
        {
            device_name: "/dev/xvda",
            volume: AWSCDK::EC2::BlockDeviceVolume.ebs(8),
        },
    ],
})

Volumes

Whereas a BlockDeviceVolume is an EBS volume that is created and destroyed as part of the creation and destruction of a specific instance. A Volume is for when you want an EBS volume separate from any particular instance. A Volume is an EBS block device that can be attached to, or detached from, any instance at any time. Some types of Volumes can also be attached to multiple instances at the same time to allow you to have shared storage between those instances.

A notable restriction is that a Volume can only be attached to instances in the same availability zone as the Volume itself.

The following demonstrates how to create a 500 GiB encrypted Volume in the us-west-2a availability zone, and give a role the ability to attach that Volume to a specific instance:

instance = nil # AWSCDK::EC2::Instance
role = nil # AWSCDK::IAM::Role


volume = AWSCDK::EC2::Volume.new(self, "Volume", {
    availability_zone: "us-west-2a",
    size: AWSCDK::Size.gibibytes(500),
    encrypted: true,
})

volume.grant_attach_volume(role, [instance])

Instances Attaching Volumes to Themselves

If you need to grant an instance the ability to attach/detach an EBS volume to/from itself, then using grant_attach_volume and grant_detach_volume as outlined above will lead to an unresolvable circular reference between the instance role and the instance. In this case, use grant_attach_volume_by_resource_tag and grant_detach_volume_by_resource_tag as follows:

instance = nil # AWSCDK::EC2::Instance
volume = nil # AWSCDK::EC2::Volume


attach_grant = volume.grant_attach_volume_by_resource_tag(instance.grant_principal, [instance])
detach_grant = volume.grant_detach_volume_by_resource_tag(instance.grant_principal, [instance])

Attaching Volumes

The Amazon EC2 documentation for Linux Instances and Windows Instances contains information on how to attach and detach your Volumes to/from instances, and how to format them for use.

The following is a sample skeleton of EC2 UserData that can be used to attach a Volume to the Linux instance that it is running on:

instance = nil # AWSCDK::EC2::Instance
volume = nil # AWSCDK::EC2::Volume


volume.grant_attach_volume_by_resource_tag(instance.grant_principal, [instance])
target_device = "/dev/xvdz"
instance.user_data.add_commands("TOKEN=$(curl -SsfX PUT \"http://169.254.169.254/latest/api/token\" -H \"X-aws-ec2-metadata-token-ttl-seconds: 21600\")", "INSTANCE_ID=$(curl -SsfH \"X-aws-ec2-metadata-token: $TOKEN\" http://169.254.169.254/latest/meta-data/instance-id)", "aws --region #{AWSCDK::Stack.of(self).region} ec2 attach-volume --volume-id #{volume.volume_id} --instance-id $INSTANCE_ID --device #{target_device}", "while ! test -e #{target_device}; do sleep 1; done")

Tagging Volumes

You can configure tag propagation on volume creation.

vpc = nil # AWSCDK::EC2::VPC
instance_type = nil # AWSCDK::EC2::InstanceType
machine_image = nil # AWSCDK::EC2::IMachineImage


AWSCDK::EC2::Instance.new(self, "Instance", {
    vpc: vpc,
    machine_image: machine_image,
    instance_type: instance_type,
    propagate_tags_to_volume_on_creation: true,
})

Throughput on GP3 Volumes

You can specify the throughput of a GP3 volume from 125 (default) to 2000.

AWSCDK::EC2::Volume.new(self, "Volume", {
    availability_zone: "us-east-1a",
    size: AWSCDK::Size.gibibytes(125),
    volume_type: AWSCDK::EC2::EbsDeviceVolumeType::GP3,
    throughput: 125,
})

Volume initialization rate

When creating an EBS volume from a snapshot, you can specify the volume initialization rate at which the snapshot blocks are downloaded from Amazon S3 to the volume. Specifying a volume initialization rate ensures that the volume is initialized at a predictable and consistent rate after creation.

AWSCDK::EC2::Volume.new(self, "Volume", {
    availability_zone: "us-east-1a",
    size: AWSCDK::Size.gibibytes(500),
    snapshot_id: "snap-1234567890abcdef0",
    volume_initialization_rate: AWSCDK::Size.mebibytes(250),
})

The volume_initialization_rate must be:

Configuring Instance Metadata Service (IMDS)

Comprehensive Metadata Options

You can configure EC2 Instance Metadata Service options using individual properties. This provides comprehensive control over all metadata service settings:

vpc = nil # AWSCDK::EC2::VPC
instance_type = nil # AWSCDK::EC2::InstanceType
machine_image = nil # AWSCDK::EC2::IMachineImage


# Example 1: Enforce IMDSv2 with comprehensive options
AWSCDK::EC2::Instance.new(self, "Instance", {
    vpc: vpc,
    instance_type: instance_type,
    machine_image: machine_image,
    http_endpoint: true,
    http_protocol_ipv6: false,
    http_put_response_hop_limit: 2,
    http_tokens: AWSCDK::EC2::HttpTokens::REQUIRED,
    instance_metadata_tags: true,
})

# Example 2: Enforce IMDSv2 with minimal configuration
AWSCDK::EC2::Instance.new(self, "SecureInstance", {
    vpc: vpc,
    instance_type: instance_type,
    machine_image: machine_image,
    http_tokens: AWSCDK::EC2::HttpTokens::REQUIRED,
})

Simple IMDSv2 Enforcement

For simple IMDSv2 enforcement without additional configuration, you can use the require_imdsv2 property:

vpc = nil # AWSCDK::EC2::VPC
instance_type = nil # AWSCDK::EC2::InstanceType
machine_image = nil # AWSCDK::EC2::IMachineImage


AWSCDK::EC2::Instance.new(self, "Instance", {
    vpc: vpc,
    instance_type: instance_type,
    machine_image: machine_image,

    # Simple IMDSv2 enforcement
    require_imdsv2: true,
})

Applying to Multiple Instances

You can also use the either the InstanceRequireImdsv2Aspect for EC2 instances or the LaunchTemplateRequireImdsv2Aspect for EC2 launch templates to apply the operation to multiple instances or launch templates, respectively.

The following example demonstrates how to use the InstanceRequireImdsv2Aspect to require IMDSv2 for all EC2 instances in a stack:

aspect = AWSCDK::EC2::InstanceRequireImdsv2Aspect.new
AWSCDK::Aspects.of(self).add(aspect)

Associating a Public IP Address with an Instance

All subnets have an attribute that determines whether instances launched into that subnet are assigned a public IPv4 address. This attribute is set to true by default for default public subnets. Thus, an EC2 instance launched into a default public subnet will be assigned a public IPv4 address. Nondefault public subnets have this attribute set to false by default and any EC2 instance launched into a nondefault public subnet will not be assigned a public IPv4 address automatically. To automatically assign a public IPv4 address to an instance launched into a nondefault public subnet, you can set the associate_public_ip_address property on the Instance construct to true. Alternatively, to not automatically assign a public IPv4 address to an instance launched into a default public subnet, you can set associate_public_ip_address to false. Including this property, removing this property, or updating the value of this property on an existing instance will result in replacement of the instance.

vpc = AWSCDK::EC2::VPC.new(self, "VPC", {
    cidr: "10.0.0.0/16",
    nat_gateways: 0,
    max_azs: 3,
    subnet_configuration: [
        {
            name: "public-subnet-1",
            subnet_type: AWSCDK::EC2::SubnetType::PUBLIC,
            cidr_mask: 24,
        },
    ],
})

instance = AWSCDK::EC2::Instance.new(self, "Instance", {
    vpc: vpc,
    vpc_subnets: {subnet_group_name: "public-subnet-1"},
    instance_type: AWSCDK::EC2::InstanceType.of(AWSCDK::EC2::InstanceClass::T3, AWSCDK::EC2::InstanceSize::NANO),
    machine_image: AWSCDK::EC2::AmazonLinuxImage.new({generation: AWSCDK::EC2::AmazonLinuxGeneration::AMAZON_LINUX_2}),
    detailed_monitoring: true,
    associate_public_ip_address: true,
})

Specifying a key pair

To allow SSH access to an EC2 instance by default, a Key Pair must be specified. Key pairs can be provided with the key_pair property to instances and launch templates. You can create a key pair for an instance like this:

vpc = nil # AWSCDK::EC2::VPC
instance_type = nil # AWSCDK::EC2::InstanceType


key_pair = AWSCDK::EC2::KeyPair.new(self, "KeyPair", {
    type: AWSCDK::EC2::KeyPairType::ED25519,
    format: AWSCDK::EC2::KeyPairFormat::PEM,
})
instance = AWSCDK::EC2::Instance.new(self, "Instance", {
    vpc: vpc,
    instance_type: instance_type,
    machine_image: AWSCDK::EC2::MachineImage.latest_amazon_linux2023,
    key_pair: key_pair,
})

When a new EC2 Key Pair is created (without imported material), the private key material is automatically stored in Systems Manager Parameter Store. This can be retrieved from the key pair construct:

key_pair = AWSCDK::EC2::KeyPair.new(self, "KeyPair")
private_key = key_pair.private_key

If you already have an SSH key that you wish to use in EC2, that can be provided when constructing the KeyPair. If public key material is provided, the key pair is considered "imported" and there will not be any data automatically stored in Systems Manager Parameter Store and the type property cannot be specified for the key pair.

key_pair = AWSCDK::EC2::KeyPair.new(self, "KeyPair", {
    public_key_material: "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIB7jpNzG+YG0s+xIGWbxrxIZiiozHOEuzIJacvASP0mq",
})

Using an existing EC2 Key Pair

If you already have an EC2 Key Pair created outside of the CDK, you can import that key to your CDK stack.

You can import it purely by name:

key_pair = AWSCDK::EC2::KeyPair.from_key_pair_name(self, "KeyPair", "the-keypair-name")

Or by specifying additional attributes:

key_pair = AWSCDK::EC2::KeyPair.from_key_pair_attributes(self, "KeyPair", {
    key_pair_name: "the-keypair-name",
    type: AWSCDK::EC2::KeyPairType::RSA,
})

Using IPv6 IPs

Instances can be given IPv6 IPs by launching them into a subnet of a dual stack VPC.

vpc = AWSCDK::EC2::VPC.new(self, "Ip6VpcDualStack", {
    ip_protocol: AWSCDK::EC2::IPProtocol::DUAL_STACK,
    subnet_configuration: [
        {
            name: "Public",
            subnet_type: AWSCDK::EC2::SubnetType::PUBLIC,
            map_public_ip_on_launch: true,
        },
        {
            name: "Private",
            subnet_type: AWSCDK::EC2::SubnetType::PRIVATE_ISOLATED,
        },
    ],
})

instance = AWSCDK::EC2::Instance.new(self, "MyInstance", {
    instance_type: AWSCDK::EC2::InstanceType.of(AWSCDK::EC2::InstanceClass::T2, AWSCDK::EC2::InstanceSize::MICRO),
    machine_image: AWSCDK::EC2::MachineImage.latest_amazon_linux2,
    vpc: vpc,
    vpc_subnets: {subnet_type: AWSCDK::EC2::SubnetType::PUBLIC},
    allow_all_ipv6_outbound: true,
})

instance.connections.allow_from(AWSCDK::EC2::Peer.any_ipv6, AWSCDK::EC2::Port.all_icmp_v6, "allow ICMPv6")

Note to set map_public_ip_on_launch to true in the subnet_configuration.

Additionally, IPv6 support varies by instance type. Most instance types have IPv6 support with exception of m1-m3, c1, g2, and t1.micro. A full list can be found here: https://docs.aws.amazon.com/AWSEC2/latest/UserGuide/using-eni.html#AvailableIpPerENI.

Specifying the IPv6 Address

If you want to specify the number of IPv6 addresses to assign to the instance, you can use the ipv6_addresse_count property:

# dual stack VPC
vpc = nil # AWSCDK::EC2::VPC


instance = AWSCDK::EC2::Instance.new(self, "MyInstance", {
    instance_type: AWSCDK::EC2::InstanceType.of(AWSCDK::EC2::InstanceClass::M5, AWSCDK::EC2::InstanceSize::LARGE),
    machine_image: AWSCDK::EC2::MachineImage.latest_amazon_linux2,
    vpc: vpc,
    vpc_subnets: {subnet_type: AWSCDK::EC2::SubnetType::PUBLIC},
    # Assign 2 IPv6 addresses to the instance
    ipv6_address_count: 2,
})

Credit configuration modes for burstable instances

You can set the credit configuration mode for burstable instances (T2, T3, T3a and T4g instance types):

vpc = nil # AWSCDK::EC2::VPC


instance = AWSCDK::EC2::Instance.new(self, "Instance", {
    instance_type: AWSCDK::EC2::InstanceType.of(AWSCDK::EC2::InstanceClass::T3, AWSCDK::EC2::InstanceSize::MICRO),
    machine_image: AWSCDK::EC2::MachineImage.latest_amazon_linux2,
    vpc: vpc,
    credit_specification: AWSCDK::EC2::CpuCredits::STANDARD,
})

It is also possible to set the credit configuration mode for NAT instances.

nat_instance_provider = AWSCDK::EC2::NatProvider.instance({
    instance_type: AWSCDK::EC2::InstanceType.of(AWSCDK::EC2::InstanceClass::T4G, AWSCDK::EC2::InstanceSize::LARGE),
    machine_image: AWSCDK::EC2::AmazonLinuxImage.new,
    credit_specification: AWSCDK::EC2::CpuCredits::UNLIMITED,
})
AWSCDK::EC2::VPC.new(self, "VPC", {
    nat_gateway_provider: nat_instance_provider,
})

Note: CpuCredits.UNLIMITED mode is not supported for T3 instances that are launched on a Dedicated Host.

Shutdown behavior

You can specify the behavior of the instance when you initiate shutdown from the instance (using the operating system command for system shutdown).

vpc = nil # AWSCDK::EC2::VPC


AWSCDK::EC2::Instance.new(self, "Instance", {
    vpc: vpc,
    instance_type: AWSCDK::EC2::InstanceType.of(AWSCDK::EC2::InstanceClass::T3, AWSCDK::EC2::InstanceSize::NANO),
    machine_image: AWSCDK::EC2::AmazonLinuxImage.new({generation: AWSCDK::EC2::AmazonLinuxGeneration::AMAZON_LINUX_2}),
    instance_initiated_shutdown_behavior: AWSCDK::EC2::InstanceInitiatedShutdownBehavior::TERMINATE,
})

Enabling Nitro Enclaves

You can enable AWS Nitro Enclaves for your EC2 instances by setting the enclave_enabled property to true. Nitro Enclaves is a feature of AWS Nitro System that enables creating isolated and highly constrained CPU environments known as enclaves.

vpc = nil # AWSCDK::EC2::VPC


instance = AWSCDK::EC2::Instance.new(self, "Instance", {
    instance_type: AWSCDK::EC2::InstanceType.of(AWSCDK::EC2::InstanceClass::M5, AWSCDK::EC2::InstanceSize::XLARGE),
    machine_image: AWSCDK::EC2::AmazonLinuxImage.new,
    vpc: vpc,
    enclave_enabled: true,
})

NOTE: You must use an instance type and operating system that support Nitro Enclaves. For more information, see Requirements.

Enabling Termination Protection

You can enable Termination Protection for your EC2 instances by setting the disable_api_termination property to true. Termination Protection controls whether the instance can be terminated using the AWS Management Console, AWS Command Line Interface (AWS CLI), or API.

vpc = nil # AWSCDK::EC2::VPC


instance = AWSCDK::EC2::Instance.new(self, "Instance", {
    instance_type: AWSCDK::EC2::InstanceType.of(AWSCDK::EC2::InstanceClass::M5, AWSCDK::EC2::InstanceSize::XLARGE),
    machine_image: AWSCDK::EC2::AmazonLinuxImage.new,
    vpc: vpc,
    disable_api_termination: true,
})

Enabling Instance Hibernation

You can enable Instance Hibernation for your EC2 instances by setting the hibernation_enabled property to true. Instance Hibernation saves the instance's in-memory (RAM) state when an instance is stopped, and restores that state when the instance is started.

vpc = nil # AWSCDK::EC2::VPC


instance = AWSCDK::EC2::Instance.new(self, "Instance", {
    instance_type: AWSCDK::EC2::InstanceType.of(AWSCDK::EC2::InstanceClass::M5, AWSCDK::EC2::InstanceSize::XLARGE),
    machine_image: AWSCDK::EC2::AmazonLinuxImage.new,
    vpc: vpc,
    hibernation_enabled: true,
    block_devices: [
        {
            device_name: "/dev/xvda",
            volume: AWSCDK::EC2::BlockDeviceVolume.ebs(30, {
                volume_type: AWSCDK::EC2::EbsDeviceVolumeType::GP3,
                encrypted: true,
                delete_on_termination: true,
            }),
        },
    ],
})

NOTE: You must use an instance and a volume that meet the requirements for hibernation. For more information, see Prerequisites for Amazon EC2 instance hibernation.

VPC Flow Logs

VPC Flow Logs is a feature that enables you to capture information about the IP traffic going to and from network interfaces in your VPC. Flow log data can be published to Amazon CloudWatch Logs and Amazon S3. After you've created a flow log, you can retrieve and view its data in the chosen destination. (https://docs.aws.amazon.com/vpc/latest/userguide/flow-logs.html).

By default, a flow log will be created with CloudWatch Logs as the destination.

You can create a flow log like this:

vpc = nil # AWSCDK::EC2::VPC


AWSCDK::EC2::FlowLog.new(self, "FlowLog", {
    resource_type: AWSCDK::EC2::FlowLogResourceType.from_vpc(vpc),
})

Or you can add a Flow Log to a VPC by using the addFlowLog method like this:

vpc = AWSCDK::EC2::VPC.new(self, "Vpc")

vpc.add_flow_log("FlowLog")

You can also add multiple flow logs with different destinations.

vpc = AWSCDK::EC2::VPC.new(self, "Vpc")

vpc.add_flow_log("FlowLogS3", {
    destination: AWSCDK::EC2::FlowLogDestination.to_s3,
})

# Only reject traffic and interval every minute.
vpc.add_flow_log("FlowLogCloudWatch", {
    traffic_type: AWSCDK::EC2::FlowLogTrafficType::REJECT,
    max_aggregation_interval: AWSCDK::EC2::FlowLogMaxAggregationInterval::ONE_MINUTE,
})

To create a Transit Gateway flow log, you can use the from_transit_gateway_id method:

tgw = nil # AWSCDK::EC2::CfnTransitGateway


AWSCDK::EC2::FlowLog.new(self, "TransitGatewayFlowLog", {
    resource_type: AWSCDK::EC2::FlowLogResourceType.from_transit_gateway_id(tgw.ref),
})

To create a Transit Gateway Attachment flow log, you can use the from_transit_gateway_attachment_id method:

tgw_attachment = nil # AWSCDK::EC2::CfnTransitGatewayAttachment


AWSCDK::EC2::FlowLog.new(self, "TransitGatewayAttachmentFlowLog", {
    resource_type: AWSCDK::EC2::FlowLogResourceType.from_transit_gateway_attachment_id(tgw_attachment.ref),
})

For flow logs targeting TransitGateway and TransitGatewayAttachment, specifying the traffic_type is not possible.

Custom Formatting

You can also custom format flow logs.

vpc = AWSCDK::EC2::VPC.new(self, "Vpc")

vpc.add_flow_log("FlowLog", {
    log_format: [
        AWSCDK::EC2::LogFormat.DST_PORT,
        AWSCDK::EC2::LogFormat.SRC_PORT,
    ],
})

# If you just want to add a field to the default field
vpc.add_flow_log("FlowLog", {
    log_format: [
        AWSCDK::EC2::LogFormat.VERSION,
        AWSCDK::EC2::LogFormat.ALL_DEFAULT_FIELDS,
    ],
})

# If AWS CDK does not support the new fields
vpc.add_flow_log("FlowLog", {
    log_format: [
        AWSCDK::EC2::LogFormat.SRC_PORT,
        AWSCDK::EC2::LogFormat.custom("${new-field}"),
    ],
})

By default, the CDK will create the necessary resources for the destination. For the CloudWatch Logs destination it will create a CloudWatch Logs Log Group as well as the IAM role with the necessary permissions to publish to the log group. In the case of an S3 destination, it will create the S3 bucket.

If you want to customize any of the destination resources you can provide your own as part of the destination.

CloudWatch Logs

vpc = nil # AWSCDK::EC2::VPC


log_group = AWSCDK::Logs::LogGroup.new(self, "MyCustomLogGroup")

role = AWSCDK::IAM::Role.new(self, "MyCustomRole", {
    assumed_by: AWSCDK::IAM::ServicePrincipal.new("vpc-flow-logs.amazonaws.com"),
})

AWSCDK::EC2::FlowLog.new(self, "FlowLog", {
    resource_type: AWSCDK::EC2::FlowLogResourceType.from_vpc(vpc),
    destination: AWSCDK::EC2::FlowLogDestination.to_cloud_watch_logs(log_group, role),
})

S3

vpc = nil # AWSCDK::EC2::VPC


bucket = AWSCDK::S3::Bucket.new(self, "MyCustomBucket")

AWSCDK::EC2::FlowLog.new(self, "FlowLog", {
    resource_type: AWSCDK::EC2::FlowLogResourceType.from_vpc(vpc),
    destination: AWSCDK::EC2::FlowLogDestination.to_s3(bucket),
})

AWSCDK::EC2::FlowLog.new(self, "FlowLogWithKeyPrefix", {
    resource_type: AWSCDK::EC2::FlowLogResourceType.from_vpc(vpc),
    destination: AWSCDK::EC2::FlowLogDestination.to_s3(bucket, "prefix/"),
})

Amazon Data Firehose

require 'aws-cdk-lib'

vpc = nil # AWSCDK::EC2::VPC
delivery_stream = nil # AWSCDK::KinesisFirehose::IDeliveryStream


vpc.add_flow_log("FlowLogsFirehose", {
    destination: AWSCDK::EC2::FlowLogDestination.to_firehose(delivery_stream),
})

When the S3 destination is configured, AWS will automatically create an S3 bucket policy that allows the service to write logs to the bucket. This makes it impossible to later update that bucket policy. To have CDK create the bucket policy so that future updates can be made, the @aws-cdk/aws-s3:createDefaultLoggingPolicy feature flag can be used. This can be set in the cdk.json file.

{
  "context": {
    "@aws-cdk/aws-s3:createDefaultLoggingPolicy": true
  }
}

User Data

User data enables you to run a script when your instances start up. In order to configure these scripts you can add commands directly to the script or you can use the UserData's convenience functions to aid in the creation of your script.

A user data could be configured to run a script found in an asset through the following:

require 'aws-cdk-lib'

instance = nil # AWSCDK::EC2::Instance


asset = AWSCDK::S3Assets::Asset.new(self, "Asset", {
    path: "./configure.sh",
})

local_path = instance.user_data.add_s3_download_command({
    bucket: asset.bucket,
    bucket_key: asset.s3_object_key,
    region: "us-east-1",
})
instance.user_data.add_execute_file_command({
    file_path: local_path,
    arguments: "--verbose -y",
})
asset.grant_read(instance.role)

Persisting user data

By default, EC2 UserData is run once on only the first time that an instance is started. It is possible to make the user data script run on every start of the instance.

When creating a Windows UserData you can use the persist option to set whether or not to add <persist>true</persist> to the user data script. it can be used as follows:

windows_user_data = AWSCDK::EC2::UserData.for_windows({persist: true})

For a Linux instance, this can be accomplished by using a Multipart user data to configure cloud-config as detailed in: https://aws.amazon.com/premiumsupport/knowledge-center/execute-user-data-ec2/

Multipart user data

In addition, to above the MultipartUserData can be used to change instance startup behavior. Multipart user data are composed from separate parts forming archive. The most common parts are scripts executed during instance set-up. However, there are other kinds, too.

The advantage of multipart archive is in flexibility when it's needed to add additional parts or to use specialized parts to fine tune instance startup. Some services (like AWS Batch) support only MultipartUserData.

The parts can be executed at different moment of instance start-up and can serve a different purpose. This is controlled by content_type property. For common scripts, text/x-shellscript; charset="utf-8" can be used as content type.

In order to create archive the MultipartUserData has to be instantiated. Than, user can add parts to multipart archive using add_part. The MultipartBody contains methods supporting creation of body parts.

If the very custom part is required, it can be created using MultipartUserData.fromRawBody, in this case full control over content type, transfer encoding, and body properties is given to the user.

Below is an example for creating multipart user data with single body part responsible for installing awscli and configuring maximum size of storage used by Docker containers:

boot_hook_conf = AWSCDK::EC2::UserData.for_linux
boot_hook_conf.add_commands("cloud-init-per once docker_options echo 'OPTIONS=\"${OPTIONS} --storage-opt dm.basesize=40G\"' >> /etc/sysconfig/docker")

setup_commands = AWSCDK::EC2::UserData.for_linux
setup_commands.add_commands("sudo yum install awscli && echo Packages installed らと > /var/tmp/setup")

multipart_user_data = AWSCDK::EC2::MultipartUserData.new
# The docker has to be configured at early stage, so content type is overridden to boothook
multipart_user_data.add_part(AWSCDK::EC2::MultipartBody.from_user_data(boot_hook_conf, "text/cloud-boothook; charset=\"us-ascii\""))
# Execute the rest of setup
multipart_user_data.add_part(AWSCDK::EC2::MultipartBody.from_user_data(setup_commands))

AWSCDK::EC2::LaunchTemplate.new(self, "", {
    user_data: multipart_user_data,
    block_devices: [],
})

For more information see Specifying Multiple User Data Blocks Using a MIME Multi Part Archive

Using add*Command on MultipartUserData

To use the add*Command methods, that are inherited from the UserData interface, on MultipartUserData you must add a part to the MultipartUserData and designate it as the receiver for these methods. This is accomplished by using the add_user_data_part() method on MultipartUserData with the make_default argument set to true:

multipart_user_data = AWSCDK::EC2::MultipartUserData.new
commands_user_data = AWSCDK::EC2::UserData.for_linux
multipart_user_data.add_user_data_part(commands_user_data, AWSCDK::EC2::MultipartBody.SHELL_SCRIPT, true)

# Adding commands to the multipartUserData adds them to commandsUserData, and vice-versa.
multipart_user_data.add_commands("touch /root/multi.txt")
commands_user_data.add_commands("touch /root/userdata.txt")

When used on an EC2 instance, the above multipart_user_data will create both multi.txt and userdata.txt in /root.

Importing existing subnet

To import an existing Subnet, call Subnet.fromSubnetAttributes() or Subnet.fromSubnetId(). Only if you supply the subnet's Availability Zone and Route Table Ids when calling Subnet.fromSubnetAttributes() will you be able to use the CDK features that use these values (such as selecting one subnet per AZ).

Importing an existing subnet looks like this:

# Supply all properties
subnet1 = AWSCDK::EC2::Subnet.from_subnet_attributes(self, "SubnetFromAttributes", {
    subnet_id: "s-1234",
    availability_zone: "pub-az-4465",
    route_table_id: "rt-145",
})

# Supply only subnet id
subnet2 = AWSCDK::EC2::Subnet.from_subnet_id(self, "SubnetFromId", "s-1234")

Launch Templates

A Launch Template is a standardized template that contains the configuration information to launch an instance. They can be used when launching instances on their own, through Amazon EC2 Auto Scaling, EC2 Fleet, and Spot Fleet. Launch templates enable you to store launch parameters so that you do not have to specify them every time you launch an instance. For information on Launch Templates please see the official documentation.

The following demonstrates how to create a launch template with an Amazon Machine Image, security group, and an instance profile.

vpc = nil # AWSCDK::EC2::VPC


role = AWSCDK::IAM::Role.new(self, "Role", {
    assumed_by: AWSCDK::IAM::ServicePrincipal.new("ec2.amazonaws.com"),
})
instance_profile = AWSCDK::IAM::InstanceProfile.new(self, "InstanceProfile", {
    role: role,
})

template = AWSCDK::EC2::LaunchTemplate.new(self, "LaunchTemplate", {
    launch_template_name: "MyTemplateV1",
    version_description: "This is my v1 template",
    machine_image: AWSCDK::EC2::MachineImage.latest_amazon_linux2023,
    security_group: AWSCDK::EC2::SecurityGroup.new(self, "LaunchTemplateSG", {
        vpc: vpc,
    }),
    instance_profile: instance_profile,
})

And the following demonstrates how to enable metadata options support.

AWSCDK::EC2::LaunchTemplate.new(self, "LaunchTemplate", {
    http_endpoint: true,
    http_protocol_ipv6: true,
    http_put_response_hop_limit: 1,
    http_tokens: AWSCDK::EC2::LaunchTemplateHttpTokens::REQUIRED,
    instance_metadata_tags: true,
})

And the following demonstrates how to add one or more security groups to launch template.

vpc = nil # AWSCDK::EC2::VPC


sg1 = AWSCDK::EC2::SecurityGroup.new(self, "sg1", {
    vpc: vpc,
})
sg2 = AWSCDK::EC2::SecurityGroup.new(self, "sg2", {
    vpc: vpc,
})

launch_template = AWSCDK::EC2::LaunchTemplate.new(self, "LaunchTemplate", {
    machine_image: AWSCDK::EC2::MachineImage.latest_amazon_linux2023,
    security_group: sg1,
})

launch_template.add_security_group(sg2)

To use AWS Systems Manager parameters instead of AMI IDs in launch templates and resolve the AMI IDs at instance launch time:

launch_template = AWSCDK::EC2::LaunchTemplate.new(self, "LaunchTemplate", {
    machine_image: AWSCDK::EC2::MachineImage.resolve_ssm_parameter_at_launch("parameterName"),
})

Placement Group

Specify placement_group to enable the placement group support:

instance_type = nil # AWSCDK::EC2::InstanceType


pg = AWSCDK::EC2::PlacementGroup.new(self, "test-pg", {
    strategy: AWSCDK::EC2::PlacementGroupStrategy::SPREAD,
})

AWSCDK::EC2::LaunchTemplate.new(self, "LaunchTemplate", {
    instance_type: instance_type,
    machine_image: AWSCDK::EC2::MachineImage.latest_amazon_linux2023,
    placement_group: pg,
})

Please note this feature does not support Launch Configurations.

Detailed Monitoring

The following demonstrates how to enable Detailed Monitoring for an EC2 instance. Keep in mind that Detailed Monitoring results in additional charges.

vpc = nil # AWSCDK::EC2::VPC
instance_type = nil # AWSCDK::EC2::InstanceType


AWSCDK::EC2::Instance.new(self, "Instance1", {
    vpc: vpc,
    instance_type: instance_type,
    machine_image: AWSCDK::EC2::MachineImage.latest_amazon_linux2023,
    detailed_monitoring: true,
})

Connecting to your instances using SSM Session Manager

SSM Session Manager makes it possible to connect to your instances from the AWS Console, without preparing SSH keys.

To do so, you need to:

If these conditions are met, you can connect to the instance from the EC2 Console. Example:

vpc = nil # AWSCDK::EC2::VPC
instance_type = nil # AWSCDK::EC2::InstanceType


AWSCDK::EC2::Instance.new(self, "Instance1", {
    vpc: vpc,
    instance_type: instance_type,

    # Amazon Linux 2023 comes with SSM Agent by default
    machine_image: AWSCDK::EC2::MachineImage.latest_amazon_linux2023,

    # Turn on SSM
    ssm_session_permissions: true,
})

Managed Prefix Lists

Create and manage customer-managed prefix lists. If you don't specify anything in this construct, it will manage IPv4 addresses.

You can also create an empty Prefix List with only the maximum number of entries specified, as shown in the following code. If nothing is specified, maxEntries=1.

AWSCDK::EC2::PrefixList.new(self, "EmptyPrefixList", {
    max_entries: 100,
})

max_entries can also be omitted as follows. In this case maxEntries: 2, will be set.

AWSCDK::EC2::PrefixList.new(self, "PrefixList", {
    entries: [
        {cidr: "10.0.0.1/32"},
        {cidr: "10.0.0.2/32", description: "sample1"},
    ],
})

To import AWS-managed prefix list, you can use PrefixList.fromLookup().

AWSCDK::EC2::PrefixList.from_lookup(self, "PrefixListFromName", {
    prefix_list_name: "com.amazonaws.global.cloudfront.origin-facing",
})

For more information see Work with customer-managed prefix lists.

IAM instance profile

Use instance_profile to apply specific IAM Instance Profile. Cannot be used with role

instance_type = nil # AWSCDK::EC2::InstanceType
vpc = nil # AWSCDK::EC2::VPC


role = AWSCDK::IAM::Role.new(self, "Role", {
    assumed_by: AWSCDK::IAM::ServicePrincipal.new("ec2.amazonaws.com"),
})
instance_profile = AWSCDK::IAM::InstanceProfile.new(self, "InstanceProfile", {
    role: role,
})

AWSCDK::EC2::Instance.new(self, "Instance", {
    vpc: vpc,
    instance_type: instance_type,
    machine_image: AWSCDK::EC2::MachineImage.latest_amazon_linux2023,
    instance_profile: instance_profile,
})

API Reference

Classes 195

AclCIDREither an IPv4 or an IPv6 CIDR. AclTrafficThe traffic that is configured using a Network ACL entry. AmazonLinux2022ImageSSMParameterA SSM Parameter that contains the AMI ID for Amazon Linux 2023. AmazonLinux2022KernelAmazon Linux 2022 kernel versions. AmazonLinux2023ImageSSMParameterA SSM Parameter that contains the AMI ID for Amazon Linux 2023. AmazonLinux2023KernelAmazon Linux 2023 kernel versions. AmazonLinux2ImageSSMParameterA SSM Parameter that contains the AMI ID for Amazon Linux 2. AmazonLinux2KernelAmazon Linux 2 kernel versions. AmazonLinuxImageSelects the latest version of Amazon Linux. AmazonLinuxImageSSMParameterBase BastionHostLinuxThis creates a linux bastion host you can use to connect to other instances or services in BlockDeviceVolumeDescribes a block device mapping for an EC2 instance or Auto Scaling group. CfnCapacityManagerDataExportCreates a new data export configuration for EC2 Capacity Manager. CfnCapacityReservationCreates a new Capacity Reservation with the specified attributes. CfnCapacityReservationFleetCreates a new Capacity Reservation Fleet with the specified attributes. CfnCarrierGatewayCreates a carrier gateway. CfnClientVpnAuthorizationRuleSpecifies an ingress authorization rule to add to a Client VPN endpoint. CfnClientVpnEndpointSpecifies a Client VPN endpoint. CfnClientVpnRouteSpecifies a network route to add to a Client VPN endpoint. CfnClientVpnTargetNetworkAssociationSpecifies a target network to associate with a Client VPN endpoint. CfnCustomerGatewaySpecifies a customer gateway. CfnDHCPOptionsSpecifies a set of DHCP options for your VPC. CfnEC2FleetSpecifies the configuration information to launch a fleet--or group--of instances. CfnEgressOnlyInternetGateway[IPv6 only] Specifies an egress-only internet gateway for your VPC. CfnEIPSpecifies an Elastic IP (EIP) address and can, optionally, associate it with an Amazon EC2 CfnEIPAssociationAssociates an Elastic IP address with an instance or a network interface. CfnEnclaveCertificateIAMRoleAssociationAssociates an AWS Identity and Access Management (IAM) role with an Certificate Manager (A CfnFlowLogSpecifies a VPC flow log that captures IP traffic for a specified network interface, subne CfnGatewayRouteTableAssociationAssociates a virtual private gateway or internet gateway with a route table. CfnHostAllocates a fully dedicated physical server for launching EC2 instances. CfnInstanceSpecifies an EC2 instance. CfnInstanceConnectEndpointCreates an EC2 Instance Connect Endpoint. CfnInternetGatewayAllocates an internet gateway for use with a VPC. CfnIPAMIPAM is a VPC feature that you can use to automate your IP address management workflows in CfnIPAMAllocationIn IPAM, an allocation is a CIDR assignment from an IPAM pool to another IPAM pool or to a CfnIPAMPoolIn IPAM, a pool is a collection of contiguous IP addresses CIDRs. CfnIPAMPoolCIDRA CIDR provisioned to an IPAM pool. CfnIPAMPrefixListResolverResource Type definition for AWS::EC2::IPAMPrefixListResolver. CfnIPAMPrefixListResolverTargetResource Type definition for AWS::EC2::IPAMPrefixListResolverTarget. CfnIPAMResourceDiscoveryA resource discovery is an IPAM component that enables IPAM to manage and monitor resource CfnIPAMResourceDiscoveryAssociationAn IPAM resource discovery association. CfnIPAMScopeIn IPAM, a scope is the highest-level container within IPAM. CfnIPPoolRouteTableAssociationA route server association is the connection established between a route server and a VPC. CfnKeyPairSpecifies a key pair for use with an Amazon Elastic Compute Cloud instance as follows:. CfnLaunchTemplateSpecifies the properties for creating a launch template. CfnLocalGatewayRouteCreates a static route for the specified local gateway route table. You must specify one o CfnLocalGatewayRouteTableDescribes a local gateway route table. CfnLocalGatewayRouteTableVirtualInterfaceGroupAssociationDescribes an association between a local gateway route table and a virtual interface group CfnLocalGatewayRouteTableVPCAssociationAssociates the specified VPC with the specified local gateway route table. CfnLocalGatewayVirtualInterfaceDescribes a local gateway virtual interface. CfnLocalGatewayVirtualInterfaceGroupDescribes a local gateway virtual interface group. CfnNatGatewaySpecifies a network address translation (NAT) gateway in the specified subnet. CfnNetworkAclSpecifies a network ACL for your VPC. CfnNetworkAclEntrySpecifies an entry, known as a rule, in a network ACL with a rule number you specify. CfnNetworkInsightsAccessScopeDescribes a Network Access Scope. CfnNetworkInsightsAccessScopeAnalysisDescribes a Network Access Scope analysis. CfnNetworkInsightsAnalysisSpecifies a network insights analysis. CfnNetworkInsightsPathSpecifies a path to analyze for reachability. CfnNetworkInterfaceDescribes a network interface in an Amazon EC2 instance for AWS CloudFormation . CfnNetworkInterfaceAttachmentAttaches an elastic network interface (ENI) to an Amazon EC2 instance. CfnNetworkInterfacePermissionSpecifies a permission for the network interface, For example, you can grant an AWS -autho CfnNetworkPerformanceMetricSubscriptionDescribes Infrastructure Performance subscriptions. CfnPlacementGroupSpecifies a placement group in which to launch instances. CfnPrefixListSpecifies a managed prefix list. CfnRouteSpecifies a route in a route table. For more information, see [Routes](https://docs.aws.am CfnRouteServerSpecifies a route server to manage dynamic routing in a VPC. CfnRouteServerAssociationSpecifies the association between a route server and a VPC. CfnRouteServerEndpointCreates a new endpoint for a route server in a specified subnet. CfnRouteServerPeerSpecifies a BGP peer configuration for a route server endpoint. CfnRouteServerPropagationSpecifies route propagation from a route server to a route table. CfnRouteTableSpecifies a route table for the specified VPC. CfnSecurityGroupSpecifies a security group. CfnSecurityGroupEgressAdds the specified outbound (egress) rule to a security group. CfnSecurityGroupIngressAdds an inbound (ingress) rule to a security group. CfnSecurityGroupVPCAssociationA security group association with a VPC. CfnSnapshotBlockPublicAccessSpecifies the state of the *block public access for snapshots* setting for the Region. CfnSpotFleetSpecifies a Spot Fleet request. CfnSqlHaStandbyDetectedInstanceResource Type definition for AWS::EC2::SqlHaStandbyDetectedInstance. CfnSubnetSpecifies a subnet for the specified VPC. CfnSubnetCIDRBlockAssociates a CIDR block with your subnet. CfnSubnetNetworkAclAssociationAssociates a subnet with a network ACL. For more information, see [ReplaceNetworkAclAssoci CfnSubnetRouteTableAssociationAssociates a subnet with a route table. CfnTrafficMirrorFilterSpecifies a Traffic Mirror filter. CfnTrafficMirrorFilterRuleCreates a Traffic Mirror filter rule. CfnTrafficMirrorSessionCreates a Traffic Mirror session. CfnTrafficMirrorTargetSpecifies a target for your Traffic Mirror session. CfnTransitGatewaySpecifies a transit gateway. CfnTransitGatewayAttachmentAttaches a VPC to a transit gateway. CfnTransitGatewayConnectCreates a Connect attachment from a specified transit gateway attachment. CfnTransitGatewayConnectPeerDescribes a transit gateway Connect peer. CfnTransitGatewayMeteringPolicyDescribes a transit gateway metering policy. CfnTransitGatewayMeteringPolicyEntryCreates an entry in a transit gateway metering policy to define traffic measurement rules. CfnTransitGatewayMulticastDomainCreates a multicast domain using the specified transit gateway. CfnTransitGatewayMulticastDomainAssociationAssociates the specified subnets and transit gateway attachments with the specified transi CfnTransitGatewayMulticastGroupMemberRegisters members (network interfaces) with the transit gateway multicast group. CfnTransitGatewayMulticastGroupSourceRegisters sources (network interfaces) with the specified transit gateway multicast domain CfnTransitGatewayPeeringAttachmentRequests a transit gateway peering attachment between the specified transit gateway (reque CfnTransitGatewayRouteSpecifies a static route for a transit gateway route table. CfnTransitGatewayRouteTableSpecifies a route table for a transit gateway. CfnTransitGatewayRouteTableAssociationAssociates the specified attachment with the specified transit gateway route table. CfnTransitGatewayRouteTablePropagationEnables the specified attachment to propagate routes to the specified propagation route ta CfnTransitGatewayVPCAttachmentSpecifies a VPC attachment. CfnVerifiedAccessEndpointAn AWS Verified Access endpoint specifies the application that AWS Verified Access provide CfnVerifiedAccessGroupAn AWS Verified Access group is a collection of AWS Verified Access endpoints who's associ CfnVerifiedAccessInstanceAn AWS Verified Access instance is a regional entity that evaluates application requests a CfnVerifiedAccessTrustProviderA trust provider is a third-party entity that creates, maintains, and manages identity inf CfnVolumeSpecifies an Amazon Elastic Block Store (Amazon EBS) volume. CfnVolumeAttachmentAttaches an Amazon EBS volume to a running instance and exposes it to the instance with th CfnVPCSpecifies a virtual private cloud (VPC). CfnVPCBlockPublicAccessExclusionCreate a VPC Block Public Access (BPA) exclusion. CfnVPCBlockPublicAccessOptionsVPC Block Public Access (BPA) enables you to block resources in VPCs and subnets that you CfnVPCCIDRBlockAssociates a CIDR block with your VPC. CfnVPCDHCPOptionsAssociationAssociates a set of DHCP options with a VPC, or associates no DHCP options with the VPC. CfnVPCEncryptionControlDescribes the configuration and state of VPC encryption controls. CfnVPCEndpointSpecifies a VPC endpoint. CfnVPCEndpointConnectionNotificationSpecifies a connection notification for a VPC endpoint or VPC endpoint service. CfnVPCEndpointServiceCreates a VPC endpoint service configuration to which service consumers ( AWS accounts, us CfnVPCEndpointServicePermissionsGrant or revoke permissions for service consumers (users, IAM roles, and AWS accounts) to CfnVPCGatewayAttachmentAttaches an internet gateway, or a virtual private gateway to a VPC, enabling connectivity CfnVPCPeeringConnectionRequests a VPC peering connection between two VPCs: a requester VPC that you own and an ac CfnVPNConcentratorDescribes a VPN concentrator. CfnVPNConnectionSpecifies a VPN connection between a virtual private gateway and a VPN customer gateway or CfnVPNConnectionRouteSpecifies a static route for a VPN connection between an existing virtual private gateway CfnVPNGatewaySpecifies a virtual private gateway. CfnVPNGatewayRoutePropagationEnables a virtual private gateway (VGW) to propagate routes to the specified route table o ClientVpnAuthorizationRuleA client VPN authorization rule. ClientVpnEndpointA client VPN connection. ClientVpnRouteA client VPN route. ClientVpnRouteTargetTarget for a client VPN route. ClientVpnUserBasedAuthenticationUser-based authentication for a client VPN endpoint. CloudFormationInitA CloudFormation-init configuration. ConnectionsManage the allowed network connections for constructs with Security Groups. FlowLogA VPC flow log. FlowLogDestinationThe destination type for the flow log. FlowLogResourceTypeThe type of resource to create the flow log for. GatewayVPCEndpointA gateway VPC endpoint. GatewayVPCEndpointAWSServiceAn AWS service for a gateway VPC endpoint. GenericLinuxImageConstruct a Linux machine image from an AMI map. GenericSSMParameterImageSelect the image based on a given SSM parameter at deployment time of the CloudFormation S GenericWindowsImageConstruct a Windows machine image from an AMI map. InitCommandCommand to execute on the instance. InitCommandWaitDurationRepresents a duration to wait after a command has finished, in case of a reboot (Windows o InitConfigA collection of configuration elements. InitElementBase class for all CloudFormation Init elements. InitFileCreate files on the EC2 instance. InitGroupCreate Linux/UNIX groups and assign group IDs. InitPackageA package to be installed during cfn-init time. InitServiceA services that be enabled, disabled or restarted when the instance is launched. InitServiceRestartHandleAn object that represents reasons to restart an InitService. InitSourceExtract an archive into a directory. InitUserCreate Linux/UNIX users and to assign user IDs. InstanceThis represents a single EC2 instance. InstanceRequireImdsv2AspectAspect that applies IMDS configuration on EC2 Instance constructs. InstanceTypeInstance type for EC2 instances. InterfaceVPCEndpointA interface VPC endpoint. InterfaceVPCEndpointAWSServiceAn AWS service for an interface VPC endpoint. InterfaceVPCEndpointServiceA custom-hosted service for an interface VPC endpoint. IPAddressesAn abstract Provider of IpAddresses. Ipv6AddressesAn abstract Provider of Ipv6Addresses. KeyPairAn EC2 Key Pair. LaunchTemplateThis represents an EC2 LaunchTemplate. LaunchTemplateRequireImdsv2AspectAspect that applies IMDS configuration on EC2 Launch Template constructs. LaunchTemplateSpecialVersionsA class that provides convenient access to special version tokens for LaunchTemplate versi LogFormatThe following table describes all of the available fields for a flow log record. LookupMachineImageA machine image whose AMI ID will be searched using DescribeImages. MachineImageFactory functions for standard Amazon Machine Image objects. MultipartBodyThe base class for all classes which can be used as `MultipartUserData`. MultipartUserDataMime multipart user data. NatGatewayProviderProvider for NAT Gateways. NatInstanceImageMachine image representing the latest NAT instance image. NatInstanceProviderNAT provider which uses NAT Instances. NatInstanceProviderV2Modern NAT provider which uses NAT Instances. NatProviderNAT providers. NetworkAclDefine a new custom network ACL. NetworkAclEntryDefine an entry in a Network ACL table. PeerPeer object factories (to be used in Security Group management). PlacementGroupDefines a placement group. PortInterface for classes that provide the connection-specification parts of a security group PrefixListA managed prefix list. PrivateSubnetRepresents a private VPC subnet resource. PublicSubnetRepresents a public VPC subnet resource. ResolveSSMParameterAtLaunchImageSelect the image based on a given SSM parameter at instance launch time. SecurityGroupCreates an Amazon EC2 security group within a VPC. SubnetRepresents a new VPC subnet resource. SubnetFilterContains logic which chooses a set of subnets from a larger list, in conjunction with Subn SubnetNetworkAclAssociation UserDataInstance User Data. VolumeCreates a new EBS Volume in AWS EC2. VPCDefine an AWS Virtual Private Cloud. VPCEndpoint VPCEndpointServiceA VPC endpoint service. VpnConnectionDefine a VPN Connection. VpnConnectionBaseBase class for Vpn connections. VpnGatewayThe VPN Gateway that shall be added to the VPC. WindowsImageSelect the latest version of the indicated Windows version.

Interfaces 267

AclCIDRConfigAcl Configuration for CIDR. AclIcmpProperties to create Icmp. AclPortRangeProperties to create PortRange. AclTrafficConfigAcl Configuration for traffic. AddRouteOptionsOptions for adding a new route to a subnet. AllocateCIDRRequestRequest for subnets CIDR to be allocated for a Vpc. AllocatedSubnetCIDR Allocated Subnet. AllocateIpv6CIDRRequestRequest for subnet IPv6 CIDRs to be allocated for a VPC. AllocateVPCIpv6CIDRRequestRequest for allocation of the VPC IPv6 CIDR. AmazonLinux2022ImageSSMParameterPropsProperties specific to al2022 images. AmazonLinux2023ImageSSMParameterPropsProperties specific to al2023 images. AmazonLinux2ImageSSMParameterPropsProperties specific to amzn2 images. AmazonLinuxImagePropsAmazon Linux image properties. AmazonLinuxImageSSMParameterBaseOptionsBase options for amazon linux ssm parameters. AmazonLinuxImageSSMParameterBasePropsBase properties for an Amazon Linux SSM Parameter. AmazonLinuxImageSSMParameterCommonOptionsCommon options across all generations. ApplyCloudFormationInitOptionsOptions for applying CloudFormation init to an instance or instance group. AttachInitOptionsOptions for attaching a CloudFormationInit to a resource. AWSIpamPropsConfiguration for AwsIpam. BastionHostLinuxPropsProperties of the bastion host. BlockDeviceBlock device. CfnCapacityManagerDataExportPropsProperties for defining a `CfnCapacityManagerDataExport`. CfnCapacityReservationFleetPropsProperties for defining a `CfnCapacityReservationFleet`. CfnCapacityReservationPropsProperties for defining a `CfnCapacityReservation`. CfnCarrierGatewayPropsProperties for defining a `CfnCarrierGateway`. CfnClientVpnAuthorizationRulePropsProperties for defining a `CfnClientVpnAuthorizationRule`. CfnClientVpnEndpointPropsProperties for defining a `CfnClientVpnEndpoint`. CfnClientVpnRoutePropsProperties for defining a `CfnClientVpnRoute`. CfnClientVpnTargetNetworkAssociationPropsProperties for defining a `CfnClientVpnTargetNetworkAssociation`. CfnCustomerGatewayPropsProperties for defining a `CfnCustomerGateway`. CfnDHCPOptionsPropsProperties for defining a `CfnDHCPOptions`. CfnEC2FleetPropsProperties for defining a `CfnEC2Fleet`. CfnEgressOnlyInternetGatewayPropsProperties for defining a `CfnEgressOnlyInternetGateway`. CfnEIPAssociationPropsProperties for defining a `CfnEIPAssociation`. CfnEIPPropsProperties for defining a `CfnEIP`. CfnEnclaveCertificateIAMRoleAssociationPropsProperties for defining a `CfnEnclaveCertificateIamRoleAssociation`. CfnFlowLogPropsProperties for defining a `CfnFlowLog`. CfnGatewayRouteTableAssociationPropsProperties for defining a `CfnGatewayRouteTableAssociation`. CfnHostPropsProperties for defining a `CfnHost`. CfnInstanceConnectEndpointPropsProperties for defining a `CfnInstanceConnectEndpoint`. CfnInstancePropsProperties for defining a `CfnInstance`. CfnInternetGatewayPropsProperties for defining a `CfnInternetGateway`. CfnIPAMAllocationPropsProperties for defining a `CfnIPAMAllocation`. CfnIPAMPoolCIDRPropsProperties for defining a `CfnIPAMPoolCidr`. CfnIPAMPoolPropsProperties for defining a `CfnIPAMPool`. CfnIPAMPrefixListResolverPropsProperties for defining a `CfnIPAMPrefixListResolver`. CfnIPAMPrefixListResolverTargetPropsProperties for defining a `CfnIPAMPrefixListResolverTarget`. CfnIPAMPropsProperties for defining a `CfnIPAM`. CfnIPAMResourceDiscoveryAssociationPropsProperties for defining a `CfnIPAMResourceDiscoveryAssociation`. CfnIPAMResourceDiscoveryPropsProperties for defining a `CfnIPAMResourceDiscovery`. CfnIPAMScopePropsProperties for defining a `CfnIPAMScope`. CfnIPPoolRouteTableAssociationPropsProperties for defining a `CfnIpPoolRouteTableAssociation`. CfnKeyPairPropsProperties for defining a `CfnKeyPair`. CfnLaunchTemplatePropsProperties for defining a `CfnLaunchTemplate`. CfnLocalGatewayRoutePropsProperties for defining a `CfnLocalGatewayRoute`. CfnLocalGatewayRouteTablePropsProperties for defining a `CfnLocalGatewayRouteTable`. CfnLocalGatewayRouteTableVirtualInterfaceGroupAssociationPropsProperties for defining a `CfnLocalGatewayRouteTableVirtualInterfaceGroupAssociation`. CfnLocalGatewayRouteTableVPCAssociationPropsProperties for defining a `CfnLocalGatewayRouteTableVPCAssociation`. CfnLocalGatewayVirtualInterfaceGroupPropsProperties for defining a `CfnLocalGatewayVirtualInterfaceGroup`. CfnLocalGatewayVirtualInterfacePropsProperties for defining a `CfnLocalGatewayVirtualInterface`. CfnNatGatewayPropsProperties for defining a `CfnNatGateway`. CfnNetworkAclEntryPropsProperties for defining a `CfnNetworkAclEntry`. CfnNetworkAclPropsProperties for defining a `CfnNetworkAcl`. CfnNetworkInsightsAccessScopeAnalysisPropsProperties for defining a `CfnNetworkInsightsAccessScopeAnalysis`. CfnNetworkInsightsAccessScopePropsProperties for defining a `CfnNetworkInsightsAccessScope`. CfnNetworkInsightsAnalysisPropsProperties for defining a `CfnNetworkInsightsAnalysis`. CfnNetworkInsightsPathPropsProperties for defining a `CfnNetworkInsightsPath`. CfnNetworkInterfaceAttachmentPropsProperties for defining a `CfnNetworkInterfaceAttachment`. CfnNetworkInterfacePermissionPropsProperties for defining a `CfnNetworkInterfacePermission`. CfnNetworkInterfacePropsProperties for defining a `CfnNetworkInterface`. CfnNetworkPerformanceMetricSubscriptionPropsProperties for defining a `CfnNetworkPerformanceMetricSubscription`. CfnPlacementGroupPropsProperties for defining a `CfnPlacementGroup`. CfnPrefixListPropsProperties for defining a `CfnPrefixList`. CfnRoutePropsProperties for defining a `CfnRoute`. CfnRouteServerAssociationPropsProperties for defining a `CfnRouteServerAssociation`. CfnRouteServerEndpointPropsProperties for defining a `CfnRouteServerEndpoint`. CfnRouteServerPeerPropsProperties for defining a `CfnRouteServerPeer`. CfnRouteServerPropagationPropsProperties for defining a `CfnRouteServerPropagation`. CfnRouteServerPropsProperties for defining a `CfnRouteServer`. CfnRouteTablePropsProperties for defining a `CfnRouteTable`. CfnSecurityGroupEgressPropsProperties for defining a `CfnSecurityGroupEgress`. CfnSecurityGroupIngressPropsProperties for defining a `CfnSecurityGroupIngress`. CfnSecurityGroupPropsProperties for defining a `CfnSecurityGroup`. CfnSecurityGroupVPCAssociationPropsProperties for defining a `CfnSecurityGroupVpcAssociation`. CfnSnapshotBlockPublicAccessPropsProperties for defining a `CfnSnapshotBlockPublicAccess`. CfnSpotFleetPropsProperties for defining a `CfnSpotFleet`. CfnSqlHaStandbyDetectedInstancePropsProperties for defining a `CfnSqlHaStandbyDetectedInstance`. CfnSubnetCIDRBlockPropsProperties for defining a `CfnSubnetCidrBlock`. CfnSubnetNetworkAclAssociationPropsProperties for defining a `CfnSubnetNetworkAclAssociation`. CfnSubnetPropsProperties for defining a `CfnSubnet`. CfnSubnetRouteTableAssociationPropsProperties for defining a `CfnSubnetRouteTableAssociation`. CfnTrafficMirrorFilterPropsProperties for defining a `CfnTrafficMirrorFilter`. CfnTrafficMirrorFilterRulePropsProperties for defining a `CfnTrafficMirrorFilterRule`. CfnTrafficMirrorSessionPropsProperties for defining a `CfnTrafficMirrorSession`. CfnTrafficMirrorTargetPropsProperties for defining a `CfnTrafficMirrorTarget`. CfnTransitGatewayAttachmentPropsProperties for defining a `CfnTransitGatewayAttachment`. CfnTransitGatewayConnectPeerPropsProperties for defining a `CfnTransitGatewayConnectPeer`. CfnTransitGatewayConnectPropsProperties for defining a `CfnTransitGatewayConnect`. CfnTransitGatewayMeteringPolicyEntryPropsProperties for defining a `CfnTransitGatewayMeteringPolicyEntry`. CfnTransitGatewayMeteringPolicyPropsProperties for defining a `CfnTransitGatewayMeteringPolicy`. CfnTransitGatewayMulticastDomainAssociationPropsProperties for defining a `CfnTransitGatewayMulticastDomainAssociation`. CfnTransitGatewayMulticastDomainPropsProperties for defining a `CfnTransitGatewayMulticastDomain`. CfnTransitGatewayMulticastGroupMemberPropsProperties for defining a `CfnTransitGatewayMulticastGroupMember`. CfnTransitGatewayMulticastGroupSourcePropsProperties for defining a `CfnTransitGatewayMulticastGroupSource`. CfnTransitGatewayPeeringAttachmentPropsProperties for defining a `CfnTransitGatewayPeeringAttachment`. CfnTransitGatewayPropsProperties for defining a `CfnTransitGateway`. CfnTransitGatewayRoutePropsProperties for defining a `CfnTransitGatewayRoute`. CfnTransitGatewayRouteTableAssociationPropsProperties for defining a `CfnTransitGatewayRouteTableAssociation`. CfnTransitGatewayRouteTablePropagationPropsProperties for defining a `CfnTransitGatewayRouteTablePropagation`. CfnTransitGatewayRouteTablePropsProperties for defining a `CfnTransitGatewayRouteTable`. CfnTransitGatewayVPCAttachmentPropsProperties for defining a `CfnTransitGatewayVpcAttachment`. CfnVerifiedAccessEndpointPropsProperties for defining a `CfnVerifiedAccessEndpoint`. CfnVerifiedAccessGroupPropsProperties for defining a `CfnVerifiedAccessGroup`. CfnVerifiedAccessInstancePropsProperties for defining a `CfnVerifiedAccessInstance`. CfnVerifiedAccessTrustProviderPropsProperties for defining a `CfnVerifiedAccessTrustProvider`. CfnVolumeAttachmentPropsProperties for defining a `CfnVolumeAttachment`. CfnVolumePropsProperties for defining a `CfnVolume`. CfnVPCBlockPublicAccessExclusionPropsProperties for defining a `CfnVPCBlockPublicAccessExclusion`. CfnVPCBlockPublicAccessOptionsPropsProperties for defining a `CfnVPCBlockPublicAccessOptions`. CfnVPCCIDRBlockPropsProperties for defining a `CfnVPCCidrBlock`. CfnVPCDHCPOptionsAssociationPropsProperties for defining a `CfnVPCDHCPOptionsAssociation`. CfnVPCEncryptionControlPropsProperties for defining a `CfnVPCEncryptionControl`. CfnVPCEndpointConnectionNotificationPropsProperties for defining a `CfnVPCEndpointConnectionNotification`. CfnVPCEndpointPropsProperties for defining a `CfnVPCEndpoint`. CfnVPCEndpointServicePermissionsPropsProperties for defining a `CfnVPCEndpointServicePermissions`. CfnVPCEndpointServicePropsProperties for defining a `CfnVPCEndpointService`. CfnVPCGatewayAttachmentPropsProperties for defining a `CfnVPCGatewayAttachment`. CfnVPCPeeringConnectionPropsProperties for defining a `CfnVPCPeeringConnection`. CfnVPCPropsProperties for defining a `CfnVPC`. CfnVPNConcentratorPropsProperties for defining a `CfnVPNConcentrator`. CfnVPNConnectionPropsProperties for defining a `CfnVPNConnection`. CfnVPNConnectionRoutePropsProperties for defining a `CfnVPNConnectionRoute`. CfnVPNGatewayPropsProperties for defining a `CfnVPNGateway`. CfnVPNGatewayRoutePropagationPropsProperties for defining a `CfnVPNGatewayRoutePropagation`. ClientRouteEnforcementOptionsOptions for Client Route Enforcement. ClientVpnAuthorizationRuleOptionsOptions for a ClientVpnAuthorizationRule. ClientVpnAuthorizationRulePropsProperties for a ClientVpnAuthorizationRule. ClientVpnEndpointAttributesAttributes when importing an existing client VPN endpoint. ClientVpnEndpointOptionsOptions for a client VPN endpoint. ClientVpnEndpointPropsProperties for a client VPN endpoint. ClientVpnRouteOptionsOptions for a ClientVpnRoute. ClientVpnRoutePropsProperties for a ClientVpnRoute. CommonNetworkAclEntryOptionsBasic NetworkACL entry props. ConfigSetPropsOptions for CloudFormationInit.withConfigSets. ConfigureNatOptionsOptions passed by the VPC when NAT needs to be configured. ConnectionRule ConnectionsPropsProperties to intialize a new Connections object. CreateIpv6CIDRBlocksRequestRequest for IPv6 CIDR block to be split up. DestinationOptionsOptions for writing logs to a destination. EbsDeviceOptionsBlock device options for an EBS volume. EbsDeviceOptionsBaseBase block device options for an EBS volume. EbsDevicePropsProperties of an EBS block device. EbsDeviceSnapshotOptionsBlock device options for an EBS volume created from a snapshot. EgressRuleConfigConfiguration for an egress security group rule. EnableVpnGatewayOptionsOptions for the Vpc.enableVpnGateway() method. ExecuteFileOptionsOptions when executing a file. FlowLogDestinationConfigFlow Log Destination configuration. FlowLogOptionsOptions to add a flow log to a VPC. FlowLogPropsProperties of a VPC Flow Log. GatewayConfigPair represents a gateway created by NAT Provider. GatewayVPCEndpointOptionsOptions to add a gateway endpoint to a VPC. GatewayVPCEndpointPropsConstruction properties for a GatewayVpcEndpoint. GenericLinuxImagePropsConfiguration options for GenericLinuxImage. GenericWindowsImagePropsConfiguration options for GenericWindowsImage. IClientVpnConnectionHandlerA connection handler for client VPN endpoints. IClientVpnEndpointA client VPN endpoint. IConnectableAn object that has a Connections object. IFlowLogA FlowLog. IGatewayVPCEndpointA gateway VPC endpoint. IGatewayVPCEndpointServiceA service for a gateway VPC endpoint. IInstance IInterfaceVPCEndpointAn interface VPC endpoint. IInterfaceVPCEndpointServiceA service for an interface VPC endpoint. IIPAddressesImplementations for ip address management. IIpv6AddressesImplementations for IPv6 address management. IKeyPairAn EC2 Key Pair. ILaunchTemplateInterface for LaunchTemplate-like objects. IMachineImageInterface for classes that can select an appropriate machine image to use. INetworkAclA NetworkAcl. INetworkAclEntryA NetworkAclEntry. IngressRuleConfigConfiguration for an ingress security group rule. InitCommandOptionsOptions for InitCommand. InitFileAssetOptionsAdditional options for creating an InitFile from an asset. InitFileOptionsOptions for InitFile. InitServiceOptionsOptions for an InitService. InitSourceAssetOptionsAdditional options for an InitSource that builds an asset from local files. InitSourceOptionsAdditional options for an InitSource. InitUserOptionsOptional parameters used when creating a user. InstancePropsProperties of an EC2 Instance. InstanceRequireImdsv2AspectPropsProperties for `InstanceRequireImdsv2Aspect`. InstanceRequirementsConfigThe attributes for the instance types for a mixed instances policy. InterfaceVPCEndpointAttributesConstruction properties for an ImportedInterfaceVpcEndpoint. InterfaceVPCEndpointAWSServicePropsOptional properties for the InterfaceVpcEndpointAwsService class. InterfaceVPCEndpointOptionsOptions to add an interface endpoint to a VPC. InterfaceVPCEndpointPropsConstruction properties for an InterfaceVpcEndpoint. IPeerInterface for classes that provide the peer-specification parts of a security group rule. IPlacementGroupDetermines where your instances are placed on the underlying hardware according to the spe IPrefixListA prefix list. IPrivateSubnet IPublicSubnet IRouteTableAn abstract route table. ISecurityGroupInterface for security group-like objects. ISubnet ISubnetNetworkAclAssociationA SubnetNetworkAclAssociation. IVolumeAn EBS Volume in AWS EC2. IVPC IVPCEndpointA VPC endpoint. IVPCEndpointServiceA VPC endpoint service. IVPCEndpointServiceLoadBalancerA load balancer that can host a VPC Endpoint Service. IVpnConnection IVpnGatewayThe virtual private gateway interface. KeyPairAttributesAttributes of a Key Pair. KeyPairPropsThe properties of a Key Pair. LaunchTemplateAttributesAttributes for an imported LaunchTemplate. LaunchTemplatePropsProperties of a LaunchTemplate. LaunchTemplateRequireImdsv2AspectPropsProperties for `LaunchTemplateRequireImdsv2Aspect`. LaunchTemplateSpotOptionsInterface for the Spot market instance options provided in a LaunchTemplate. LinuxUserDataOptionsOptions when constructing UserData for Linux. LocationPackageOptionsOptions for InitPackage.rpm/InitPackage.msi. LookupMachineImagePropsProperties for looking up an image. MachineImageConfigConfiguration for a machine image. MultipartBodyOptionsOptions when creating `MultipartBody`. MultipartUserDataOptionsOptions for creating `MultipartUserData`. NamedPackageOptionsOptions for InitPackage.yum/apt/rubyGem/python. NatGatewayPropsProperties for a NAT gateway. NatInstancePropsProperties for a NAT instance. NetworkAclEntryPropsProperties to create NetworkAclEntry. NetworkAclPropsProperties to create NetworkAcl. PlacementGroupPropsProps for a PlacementGroup. PortPropsProperties to create a port range. PrefixListLookupOptionsProperties for looking up an existing managed prefix list. PrefixListOptionsOptions to add a prefix list. PrefixListPropsProperties for creating a prefix list. PrivateSubnetAttributes PrivateSubnetProps PublicSubnetAttributes PublicSubnetProps RequestedSubnetSubnet requested for allocation. RuleConfigCommon configuration properties shared by ingress and egress security group rules. RuleScopeThe scope and id in which a given SecurityGroup rule should be defined. S3DestinationOptionsOptions for writing logs to a S3 destination. S3DownloadOptionsOptions when downloading files from S3. SecurityGroupImportOptionsAdditional options for imported security groups. SecurityGroupProps SelectedSubnetsResult of selecting a subset of subnets from a VPC. SSMParameterImageOptionsProperties for GenericSsmParameterImage. SubnetAttributes SubnetConfigurationSpecify configuration parameters for a single subnet group in a VPC. SubnetIpamOptionsCIDR Allocated Subnets. SubnetNetworkAclAssociationPropsProperties to create a SubnetNetworkAclAssociation. SubnetPropsSpecify configuration parameters for a VPC subnet. SubnetSelectionCustomize subnets that are selected for placement of ENIs. SystemdConfigFileOptionsOptions for creating a SystemD configuration file. VolumeAttributesAttributes required to import an existing EBS Volume into the Stack. VolumePropsProperties of an EBS Volume. VPCAttributesProperties that reference an external Vpc. VPCEndpointServicePropsConstruction properties for a VpcEndpointService. VPCIpamOptionsCIDR Allocated Vpc. VPCLookupOptionsProperties for looking up an existing VPC. VPCPropsConfiguration for Vpc. VpnConnectionAttributesAttributes of an imported VpnConnection. VpnConnectionOptions VpnConnectionProps VpnGatewayPropsThe VpnGateway Properties. VpnTunnelOption WindowsImagePropsConfiguration options for WindowsImage. WindowsUserDataOptionsOptions when constructing UserData for Windows.

Enums 54

AcceleratorManufacturerSupported hardware accelerator manufacturers. AcceleratorNameSpecific hardware accelerator models supported by EC2. AcceleratorTypeHardware accelerator categories available for EC2 instances. ActionWhat action to apply to traffic matching the ACL. AddressFamilyThe IP address type. AmazonLinuxCpuTypeCPU type. AmazonLinuxEditionAmazon Linux edition. AmazonLinuxGenerationWhat generation of Amazon Linux to use. AmazonLinuxKernelAmazon Linux Kernel. AmazonLinuxStorageAvailable storage options for Amazon Linux images Only applies to Amazon Linux & Amazon Li AmazonLinuxVirtVirtualization type for Amazon Linux. BareMetalBare metal support requirements for EC2 instances. BurstablePerformanceBurstable CPU performance requirements for EC2 instances. ClientVpnSessionTimeoutMaximum VPN session duration time. CpuCreditsProvides the options for specifying the CPU credit type for burstable EC2 instance types ( CpuManufacturerCPU manufacturers supported by EC2 instances. DefaultInstanceTenancyThe default tenancy of instances launched into the VPC. EbsDeviceVolumeTypeSupported EBS volume types for blockDevices. FlowLogDestinationTypeThe available destination types for Flow Logs. FlowLogFileFormatThe file format for flow logs written to an S3 bucket destination. FlowLogMaxAggregationIntervalThe maximum interval of time during which a flow of packets is captured and aggregated int FlowLogTrafficTypeThe type of VPC traffic to log. HttpTokensThe state of token usage for your instance metadata requests. InstanceArchitectureIdentifies an instance's CPU architecture. InstanceClassWhat class and generation of instance to use. InstanceGenerationInstance generation categories for EC2. InstanceInitiatedShutdownBehaviorProvides the options for specifying the instance initiated shutdown behavior. InstanceSizeWhat size of instance to use. IPAddressTypeIP address types supported for VPC endpoint service. IPProtocolThe types of IP addresses provisioned in the VPC. KeyPairFormatThe format of the Key Pair. KeyPairTypeThe type of the key pair. LaunchTemplateHttpTokensThe state of token usage for your instance metadata requests. LocalStorageLocal storage support requirements for EC2 instances. LocalStorageTypeTypes of local storage available for EC2 instances. NatTrafficDirectionDirection of traffic to allow all by default. OperatingSystemTypeThe OS type of a particular image. PlacementGroupSpreadLevelDetermines how this placement group spreads instances. PlacementGroupStrategyWhich strategy to use when launching instances. ProtocolProtocol for use in Connection Rules. RouterTypeType of router used in route. ServiceManagerThe service manager that will be used by InitServices. SpotInstanceInterruptionProvides the options for the types of interruption for spot instances. SpotRequestTypeThe Spot Instance request type. SubnetTypeThe type of Subnet. TrafficDirectionDirection of traffic the AclEntry applies to. TransportProtocolTransport protocol for client VPN. VPCEndpointDNSRecordIPTypeEnums for all Dns Record IP Address types. VPCEndpointIPAddressTypeIP address type for the endpoint. VPCEndpointPrivateDNSOnlyForInboundResolverEndpointIndicates whether to enable private DNS only for inbound endpoints. VPCEndpointTypeThe type of VPC endpoint. VpnConnectionTypeThe VPN connection type. VpnPortPort for client VPN. WindowsVersionThe Windows version to use for the WindowsImage.